aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPeter Seebach <peter.seebach@windriver.com>2016-05-18 14:55:05 -0500
committerPeter Seebach <peter.seebach@windriver.com>2016-05-18 14:55:05 -0500
commit99eefa567400e894ec1f623ea1628700f1642b5c (patch)
treec4fe04d19b82b5e90e9f20d0bc43a5d9a3f2d856
parent2fec219b1da13e1e9f6bee24b26b3a9f7e728902 (diff)
downloadpseudo-99eefa567400e894ec1f623ea1628700f1642b5c.tar.gz
pseudo-99eefa567400e894ec1f623ea1628700f1642b5c.tar.bz2
pseudo-99eefa567400e894ec1f623ea1628700f1642b5c.zip
better handling of missing real_foo functions
So a recent change to ld.so behavior revealed that pseudo was not always correctly detecting that a function hadn't been found by the RTLD_NEXT search. This only happened for functions which genuinely didn't exist and wouldn't get called (like mknod on Linux, which is actually always done as an inline function that calls __xmknod), but when the diagnostics started showing up, it broke things. Fix it so the diagnostics would have shown up when things were originally broken, also fix the resulting diagnostics. Signed-off-by: Peter Seebach <peter.seebach@windriver.com>
-rw-r--r--ChangeLog.txt13
-rw-r--r--ports/linux/guts/mknod.c13
-rw-r--r--ports/linux/guts/mknodat.c13
-rw-r--r--ports/linux/pseudo_wrappers.c11
-rw-r--r--ports/linux/wrapfuncs.in2
-rw-r--r--ports/unix/subports12
-rw-r--r--ports/unix/syncfs/guts/syncfs.c (renamed from ports/unix/guts/syncfs.c)0
-rw-r--r--ports/unix/syncfs/wrapfuncs.in2
-rw-r--r--ports/unix/wrapfuncs.in1
-rw-r--r--pseudo_wrappers.c7
10 files changed, 70 insertions, 4 deletions
diff --git a/ChangeLog.txt b/ChangeLog.txt
index 442c575..7c1c253 100644
--- a/ChangeLog.txt
+++ b/ChangeLog.txt
@@ -1,3 +1,16 @@
+2016-05-18:
+ * (seebs) move syncfs to a subport so it can be enabled only on
+ systems which have it.
+ * (seebs) make pseudo_foo() wrappers for mknod/mknodat, similar to
+ the ones for stat/fstat, because Linux doesn't actually have mknod
+ (or stat) in glibc.
+ * Post diagnostic for missing real_foo() functions even when dlerror
+ doesn't give a specific error.
+ * All of this because ld.so started giving dlerror results for
+ missing functions with RTLD_NEXT. It turns out we were failing to
+ notice some missing functions. None of them actually mattered, but
+ it's worth fixing.
+
2016-05-12:
* (seebs) merge kergoth's fix to respect $(LDFLAGS) from environment.
* (seebs) call this 1.8.0
diff --git a/ports/linux/guts/mknod.c b/ports/linux/guts/mknod.c
new file mode 100644
index 0000000..eb90e66
--- /dev/null
+++ b/ports/linux/guts/mknod.c
@@ -0,0 +1,13 @@
+/*
+ * Copyright (c) 2016 Wind River Systems; see
+ * guts/COPYRIGHT for information.
+ *
+ * int mknod(const char *path, mode_t mode, dev_t dev)
+ * int rc = -1;
+ */
+
+ rc = wrap___xmknod(_MKNOD_VER, path, mode, &dev);
+
+/* return rc;
+ * }
+ */
diff --git a/ports/linux/guts/mknodat.c b/ports/linux/guts/mknodat.c
new file mode 100644
index 0000000..4956a6a
--- /dev/null
+++ b/ports/linux/guts/mknodat.c
@@ -0,0 +1,13 @@
+/*
+ * Copyright (c) 2016 Wind River Systems; see
+ * guts/COPYRIGHT for information.
+ *
+ * int mknodat(int dirfd, const char *path, mode_t mode, dev_t dev)
+ * int rc = -1;
+ */
+
+ rc = wrap___xmknodat(_MKNOD_VER, dirfd, path, mode, &dev);
+
+/* return rc;
+ * }
+ */
diff --git a/ports/linux/pseudo_wrappers.c b/ports/linux/pseudo_wrappers.c
index 26b29b0..0e9a41f 100644
--- a/ports/linux/pseudo_wrappers.c
+++ b/ports/linux/pseudo_wrappers.c
@@ -31,3 +31,14 @@ int
pseudo_fstat64(int fd, struct stat64 *buf) {
return real___fxstat64(_STAT_VER, fd, buf);
}
+
+/* similar thing happens with mknod */
+int
+pseudo_mknod(const char *path, mode_t mode, dev_t dev) {
+ return real___xmknod(_MKNOD_VER, path, mode, &dev);
+}
+
+int
+pseudo_mknodat(int dirfd, const char *path, mode_t mode, dev_t dev) {
+ return real___xmknodat(_MKNOD_VER, dirfd, path, mode, &dev);
+}
diff --git a/ports/linux/wrapfuncs.in b/ports/linux/wrapfuncs.in
index 3b8955a..c45e01a 100644
--- a/ports/linux/wrapfuncs.in
+++ b/ports/linux/wrapfuncs.in
@@ -7,6 +7,8 @@ int lchown(const char *path, uid_t owner, gid_t group); /* flags=AT_SYMLINK_NOFO
int __fxstatat(int ver, int dirfd, const char *path, struct stat *buf, int flags);
int openat(int dirfd, const char *path, int flags, ...{mode_t mode});
int __openat_2(int dirfd, const char *path, int flags);
+int mknod(const char *path, mode_t mode, dev_t dev); /* real_func=pseudo_mknod */
+int mknodat(int dirfd, const char *path, mode_t mode, dev_t dev); /* real_func=pseudo_mknodat */
int __xmknod(int ver, const char *path, mode_t mode, dev_t *dev); /* flags=AT_SYMLINK_NOFOLLOW */
int __xmknodat(int ver, int dirfd, const char *path, mode_t mode, dev_t *dev); /* flags=AT_SYMLINK_NOFOLLOW */
int fcntl(int fd, int cmd, ...{struct flock *lock});
diff --git a/ports/unix/subports b/ports/unix/subports
new file mode 100644
index 0000000..e41b036
--- /dev/null
+++ b/ports/unix/subports
@@ -0,0 +1,12 @@
+#!/bin/sh
+cat > dummy.c <<EOF
+#include <unistd.h>
+int main(void) {
+ syncfs(0);
+ return 0;
+}
+EOF
+if ${CC} -o dummy dummy.c > /dev/null 2>&1; then
+ echo "unix/syncfs"
+fi
+rm -f dummy.c dummy
diff --git a/ports/unix/guts/syncfs.c b/ports/unix/syncfs/guts/syncfs.c
index 2c9a685..2c9a685 100644
--- a/ports/unix/guts/syncfs.c
+++ b/ports/unix/syncfs/guts/syncfs.c
diff --git a/ports/unix/syncfs/wrapfuncs.in b/ports/unix/syncfs/wrapfuncs.in
new file mode 100644
index 0000000..7b36542
--- /dev/null
+++ b/ports/unix/syncfs/wrapfuncs.in
@@ -0,0 +1,2 @@
+# Added around 2011 to glibc
+int syncfs(int fd); /* async_skip=0 */
diff --git a/ports/unix/wrapfuncs.in b/ports/unix/wrapfuncs.in
index 1245593..2addb27 100644
--- a/ports/unix/wrapfuncs.in
+++ b/ports/unix/wrapfuncs.in
@@ -64,7 +64,6 @@ FILE *popen(const char *command, const char *mode); /* hand_wrapped=1 */
int fsync(int fd); /* async_skip=0 */
int fdatasync(int fd); /* async_skip=0 */
void sync(void); /* async_skip= */
-int syncfs(int fd); /* async_skip=0 */
int sync_file_range(int fd, off64_t offset, off64_t nbytes, unsigned int flags); /* async_skip=0 */
int msync(void *addr, size_t length, int flags); /* async_skip=0 */
mode_t umask(mode_t mask);
diff --git a/pseudo_wrappers.c b/pseudo_wrappers.c
index d1b0fca..615ac9a 100644
--- a/pseudo_wrappers.c
+++ b/pseudo_wrappers.c
@@ -138,7 +138,6 @@ pseudo_init_one_wrapper(pseudo_function *func) {
if (f) {
*func->real = f;
} else {
- e = dlerror();
#ifdef PSEUDO_NO_REAL_AT_FUNCTIONS
char *s = func->name;
s += strlen(s) - 2;
@@ -146,11 +145,13 @@ pseudo_init_one_wrapper(pseudo_function *func) {
if (!strcmp(s, "at")) {
return;
}
-#else
+#endif
+ e = dlerror();
if (e != NULL) {
pseudo_diag("No real function for %s: %s\n", func->name, e);
+ } else {
+ pseudo_diag("No real function for %s, but dlerror NULL.\n", func->name);
}
-#endif
}
}