@@ -57,7 +57,7 @@ SOURCES=$(wildcard *.c)
OBJS=$(subst .c,.o,$(SOURCES))
TESTS=$(patsubst %.c,%,$(wildcard test/*.c))
-SHOBJS=pseudo_tables.o pseudo_util.o
+SHOBJS=pseudo_tables.o pseudo_util.o strtol.o
DBOBJS=pseudo_db.o
WRAPOBJS=pseudo_wrappers.o
@@ -100,15 +100,15 @@ $(BIN) $(LIB):
pseudo: $(PSEUDO)
-$(PSEUDO): pseudo.o $(SHOBJS) $(DBOBJS) pseudo_client.o pseudo_server.o pseudo_ipc.o | $(BIN)
+$(PSEUDO): pseudo.o $(SHOBJS) $(DBOBJS) pseudo_client.o pseudo_client_scanf.o pseudo_server.o pseudo_ipc.o | $(BIN)
$(CC) $(CFLAGS) $(CFLAGS_PSEUDO) -o $(PSEUDO) \
- pseudo.o pseudo_server.o pseudo_client.o pseudo_ipc.o \
+ pseudo.o pseudo_server.o pseudo_client.o pseudo_client_scanf.o pseudo_ipc.o \
$(DBOBJS) $(SHOBJS) $(LDFLAGS) $(DB_LDFLAGS) $(CLIENT_LDFLAGS)
pseudolog: $(PSEUDOLOG)
-$(PSEUDOLOG): pseudolog.o $(SHOBJS) $(DBOBJS) pseudo_client.o pseudo_ipc.o | $(BIN)
- $(CC) $(CFLAGS) $(CFLAGS_PSEUDO) -o $(PSEUDOLOG) pseudolog.o pseudo_client.o pseudo_ipc.o \
+$(PSEUDOLOG): pseudolog.o $(SHOBJS) $(DBOBJS) pseudo_client.o pseudo_client_scanf.o pseudo_ipc.o | $(BIN)
+ $(CC) $(CFLAGS) $(CFLAGS_PSEUDO) -o $(PSEUDOLOG) pseudolog.o pseudo_client.o pseudo_client_scanf.o pseudo_ipc.o \
$(DBOBJS) $(SHOBJS) $(LDFLAGS) $(DB_LDFLAGS) $(CLIENT_LDFLAGS)
pseudodb: $(PSEUDODB)
@@ -119,9 +119,9 @@ $(PSEUDODB): pseudodb.o $(SHOBJS) $(DBOBJS) pseudo_ipc.o | $(BIN)
libpseudo: $(LIBPSEUDO)
-$(LIBPSEUDO): $(WRAPOBJS) pseudo_client.o pseudo_ipc.o $(SHOBJS) | $(LIB)
+$(LIBPSEUDO): $(WRAPOBJS) pseudo_client.o pseudo_client_scanf.o pseudo_ipc.o $(SHOBJS) | $(LIB)
$(CC) $(CFLAGS) $(CFLAGS_PSEUDO) -shared -o $(LIBPSEUDO) \
- pseudo_client.o pseudo_ipc.o \
+ pseudo_client.o pseudo_client_scanf.o pseudo_ipc.o \
$(WRAPOBJS) $(SHOBJS) $(LDFLAGS) $(CLIENT_LDFLAGS)
# *everything* now relies on stuff that's generated in the
@@ -135,6 +135,8 @@ pseudo_client.o pseudo_server.o pseudo_ipc.o: pseudo_ipc.h
pseudo_client.o: pseudo_client.h
+pseudo_client_scanf.o: pseudo_client.h
+
pseudo_server.o: pseudo_server.h
tables: enums/*.in maketables templatefile.py $(TABLES)
@@ -55,7 +55,7 @@
errno = ENOSYS;
return -1;
#endif
- tmpfile_fd = atoi(oldpath + 14);
+ tmpfile_fd = pseudo_atoi_wrapper(oldpath + 14);
// call actual link
rc = real_linkat(AT_FDCWD, oldpath, AT_FDCWD, newpath, AT_SYMLINK_FOLLOW);
} else
@@ -212,7 +212,7 @@ main(int argc, char *argv[]) {
opt_S = 1;
break;
case 't': /* timeout */
- pseudo_server_timeout = strtol(optarg, &s, 10);
+ pseudo_server_timeout = pseudo_strtol_wrapper(optarg, &s, 10);
if (*s && !isspace(*s)) {
pseudo_diag("Timeout must be an integer value.\n");
usage(EXIT_FAILURE);
@@ -85,6 +85,10 @@ extern int pseudo_etc_file(const char *filename, char *realname, int flags, cons
extern void pseudo_stat32_from64(struct stat *, const struct stat64 *);
extern void pseudo_stat64_from32(struct stat64 *, const struct stat *);
+extern long pseudo_strtol_wrapper(const char *, char **, int);
+extern long long pseudo_strtoll_wrapper(const char *, char **, int);
+extern int pseudo_atoi_wrapper(const char *);
+
extern char *pseudo_version;
#ifndef PSEUDO_BINDIR
@@ -614,7 +614,7 @@ pseudo_init_client(void) {
* at all.
*/
if (*env) {
- pseudo_nosymlinkexp = strtol(env, &endptr, 10);
+ pseudo_nosymlinkexp = pseudo_strtol_wrapper(env, &endptr, 10);
if (*endptr)
pseudo_nosymlinkexp = 1;
} else {
@@ -624,20 +624,9 @@ pseudo_init_client(void) {
pseudo_nosymlinkexp = 0;
}
free(env);
- env = pseudo_get_value("PSEUDO_UIDS");
- if (env)
- sscanf(env, "%d,%d,%d,%d",
- &pseudo_ruid, &pseudo_euid,
- &pseudo_suid, &pseudo_fuid);
- free(env);
-
- env = pseudo_get_value("PSEUDO_GIDS");
- if (env)
- sscanf(env, "%d,%d,%d,%d",
- &pseudo_rgid, &pseudo_egid,
- &pseudo_sgid, &pseudo_fuid);
- free(env);
+ readenv_uids();
+ readenv_gids();
env = pseudo_get_value("PSEUDO_CHROOT");
if (env) {
pseudo_chroot = strdup(env);
@@ -1030,7 +1019,7 @@ client_spawn_server(void) {
pseudo_pidfile = pseudo_localstatedir_path(PSEUDO_PIDFILE);
fp = fopen(pseudo_pidfile, "r");
if (fp) {
- if (fscanf(fp, "%d", &server_pid) != 1) {
+ if (read_pidfile(fp, &server_pid) != 1) {
pseudo_debug(PDBGF_CLIENT, "Opened server PID file, but didn't get a pid.\n");
}
fclose(fp);
@@ -1295,7 +1284,7 @@ pseudo_client_setup(void) {
fp = fopen(pseudo_pidfile, "r");
free(pseudo_pidfile);
if (fp) {
- if (fscanf(fp, "%d", &server_pid) != 1) {
+ if (read_pidfile(fp, &server_pid) != 1) {
pseudo_debug(PDBGF_CLIENT, "Opened server PID file, but didn't get a pid.\n");
}
fclose(fp);
@@ -74,6 +74,10 @@ extern int pseudo_nosymlinkexp;
extern int pseudo_umask;
+extern void readenv_uids(void);
+extern void readenv_gids(void);
+extern int read_pidfile(FILE *, int *);
+
/* Root can read and write files, and enter directories which have no
* read, write, or execute permissions. (But can't execute files without
* execute permissions!)
new file mode 100644
@@ -0,0 +1,39 @@
+#include <stdio.h>
+#include "pseudo.h"
+#include "pseudo_ipc.h"
+#include "pseudo_client.h"
+
+/*
+ * glibc 2.38 would include __isoc23_strtol and similar symbols if _GNU_SOURCE
+ * is used. We have to set that for other definitions so delcare this wrapper
+ * in a context where we don't have that set.
+ *
+ * We need to wrap strtol, strtoll, atoi, fscanf and sscanf.
+ */
+
+void readenv_uids(void)
+{
+ char *env;
+ env = pseudo_get_value("PSEUDO_UIDS");
+ if (env)
+ sscanf(env, "%d,%d,%d,%d",
+ &pseudo_ruid, &pseudo_euid,
+ &pseudo_suid, &pseudo_fuid);
+ free(env);
+}
+
+void readenv_gids(void)
+{
+ char *env;
+ env = pseudo_get_value("PSEUDO_GIDS");
+ if (env)
+ sscanf(env, "%d,%d,%d,%d",
+ &pseudo_rgid, &pseudo_egid,
+ &pseudo_sgid, &pseudo_fuid);
+ free(env);
+}
+
+int read_pidfile(FILE *fp, int *server_pid)
+{
+ return fscanf(fp, "%d", server_pid);
+}
@@ -229,7 +229,7 @@ pseudo_init_util(void) {
env = pseudo_get_value("PSEUDO_DEBUG");
if (env) {
int i;
- int level = atoi(env);
+ int level = pseudo_atoi_wrapper(env);
if (level > 0) {
for (i = 0; i < level; ++i) {
pseudo_debug_verbose();
@@ -452,7 +452,7 @@ plog_trait(int opt, char *string) {
case PSQF_GID:
case PSQF_INODE:
case PSQF_UID:
- new_trait->data.ivalue = strtoll(string, &endptr, 0);
+ new_trait->data.ivalue = pseudo_strtoll_wrapper(string, &endptr, 0);
if (*endptr) {
pseudo_diag("Unexpected garbage after number (%llu): '%s'\n",
new_trait->data.ivalue, endptr);
@@ -462,7 +462,7 @@ plog_trait(int opt, char *string) {
break;
case PSQF_MODE:
case PSQF_PERM:
- new_trait->data.ivalue = strtoll(string, &endptr, 8);
+ new_trait->data.ivalue = pseudo_strtoll_wrapper(string, &endptr, 8);
if (!*endptr) {
break;
}
new file mode 100644
@@ -0,0 +1,26 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include "pseudo.h"
+
+/*
+ * glibc 2.38 would include __isoc23_strtol and similar symbols if _GNU_SOURCE
+ * is used. We have to set that for other definitions so delcare this wrapper
+ * in a context where we don't have that set.
+ *
+ * We need to wrap strtol, strtoll, atoi, fscanf and sscanf.
+ */
+
+int pseudo_atoi_wrapper(const char *nptr)
+{
+ return atoi(nptr);
+}
+
+long pseudo_strtol_wrapper(const char *nptr, char **endptr, int base)
+{
+ return strtol(nptr, endptr, base);
+}
+
+long long pseudo_strtoll_wrapper(const char *nptr, char **endptr, int base)
+{
+ return strtoll(nptr, endptr, base);
+}
glibc 2.38 would include __isoc23_strtol and similar symbols. This is trggerd by _GNU_SOURCE but we have to set that for other definitions. Therefore add seperate wrapper functions so we can control the contexts correctly and avoid that include when using the problematic functions (strtol, strtoll, atoi, fscanf and sscanf). Signed-off-by: Richard Purdie <richard.purdie@linuxfoundation.org> --- Makefile.in | 16 +++++++++------- ports/unix/guts/linkat.c | 2 +- pseudo.c | 2 +- pseudo.h | 4 ++++ pseudo_client.c | 21 +++++---------------- pseudo_client.h | 4 ++++ pseudo_client_scanf.c | 39 +++++++++++++++++++++++++++++++++++++++ pseudo_util.c | 2 +- pseudolog.c | 4 ++-- strtol.c | 26 ++++++++++++++++++++++++++ 10 files changed, 92 insertions(+), 28 deletions(-) create mode 100644 pseudo_client_scanf.c create mode 100644 strtol.c