From a437f594608cd307ca2c25871b79966de54cc93f Mon Sep 17 00:00:00 2001 From: Amar Tumballi Date: Sat, 21 Aug 2010 01:54:30 +0000 Subject: gf_system: fork/exec instead of system * most of the glusterd 'system()' are replaced with 'gf_system()' Signed-off-by: Amar Tumballi Signed-off-by: Anand V. Avati BUG: 1292 () URL: http://bugs.gluster.com/cgi-bin/bugzilla3/show_bug.cgi?id=1292 --- libglusterfs/src/common-utils.c | 56 ++++++++++++++++++++++++++++++ libglusterfs/src/common-utils.h | 2 ++ xlators/mgmt/glusterd/src/glusterd-op-sm.c | 14 ++++---- xlators/mgmt/glusterd/src/glusterd-utils.c | 2 +- 4 files changed, 66 insertions(+), 8 deletions(-) diff --git a/libglusterfs/src/common-utils.c b/libglusterfs/src/common-utils.c index 3b904f522..eef865ec5 100644 --- a/libglusterfs/src/common-utils.c +++ b/libglusterfs/src/common-utils.c @@ -36,6 +36,7 @@ #include #include #include +#include #include #include #include @@ -1466,3 +1467,58 @@ get_checksum_for_file (int fd, uint32_t *checksum) return ret; } + + +/* One should pass the command here with command with full path, + otherwise, execv will fail */ +int +gf_system (const char *command) +{ + int ret = -1; + pid_t pid = 0; + int status = 0; + int idx = 0; + char *dupcmd = NULL; + char *arg = NULL; + char *tmp = NULL; + char *argv[100] = { NULL, }; + + dupcmd = gf_strdup (command); + if (!dupcmd) + goto out; + + pid = fork (); + if (pid < 0) { + /* failure */ + goto out; + } + if (pid == 0) { + /* Child process */ + /* Step 0: Prepare the argv */ + arg = strtok_r (dupcmd, " ", &tmp); + while (arg) { + argv[idx] = arg; + arg = strtok_r (NULL, " ", &tmp); + idx++; + } + /* Step 1: Close all 'fd' */ + for (idx = 3; idx < 65536; idx++) { + close (idx); + } + /* Step 2: execv (); */ + ret = execvp (argv[0], argv); + + /* Code will not come here at all */ + gf_log ("", GF_LOG_ERROR, "execv of (%s) failed", command); + } + if (pid > 0) { + /* Current, ie, parent process */ + pid = waitpid (pid, &status, 0); + ret = status; + } +out: + if (dupcmd) + GF_FREE (dupcmd); + + return ret; +} diff --git a/libglusterfs/src/common-utils.h b/libglusterfs/src/common-utils.h index ab230993a..93d62f6cb 100644 --- a/libglusterfs/src/common-utils.h +++ b/libglusterfs/src/common-utils.h @@ -328,5 +328,7 @@ int gf_unlockfd (int fd); int get_checksum_for_file (int fd, uint32_t *checksum); int log_base2 (unsigned long x); +int gf_system (const char *command); + #endif /* _COMMON_UTILS_H */ diff --git a/xlators/mgmt/glusterd/src/glusterd-op-sm.c b/xlators/mgmt/glusterd/src/glusterd-op-sm.c index d24a4f159..b243e7895 100644 --- a/xlators/mgmt/glusterd/src/glusterd-op-sm.c +++ b/xlators/mgmt/glusterd/src/glusterd-op-sm.c @@ -294,7 +294,7 @@ glusterd_volume_create_generate_volfiles (glusterd_volinfo_t *volinfo) " -c %s -r 1 %s -p %d --num-replica %d", GFS_PREFIX, volinfo->volname, path, bricks, volinfo->port, volinfo->sub_count); - ret = system (cmd_str); + ret = gf_system (cmd_str); gf_log ("", 1, "%s", cmd_str); break; } @@ -306,7 +306,7 @@ glusterd_volume_create_generate_volfiles (glusterd_volinfo_t *volinfo) " -c %s -r 0 %s -p %d --num-stripe %d", GFS_PREFIX, volinfo->volname, path, bricks, volinfo->port, volinfo->sub_count); - ret = system (cmd_str); + ret = gf_system (cmd_str); gf_log ("", 1, "%s", cmd_str); break; } @@ -318,7 +318,7 @@ glusterd_volume_create_generate_volfiles (glusterd_volinfo_t *volinfo) " -n %s -c %s %s -p %d", GFS_PREFIX, volinfo->volname, path, bricks, volinfo->port); - ret = system (cmd_str); + ret = gf_system (cmd_str); gf_log ("", 1, "%s", cmd_str); break; } @@ -1013,7 +1013,7 @@ rb_spawn_dst_brick (glusterd_volinfo_t *volinfo, priv->workdir, volinfo->volname, RB_DSTBRICK_PIDFILE); - ret = system (cmd_str); + ret = gf_system (cmd_str); if (ret) { gf_log ("", GF_LOG_DEBUG, "Could not start glusterfs"); @@ -1048,7 +1048,7 @@ rb_spawn_glusterfs_client (glusterd_volinfo_t *volinfo, priv->workdir, volinfo->volname, RB_CLIENT_MOUNTPOINT); - ret = system (cmd_str); + ret = gf_system (cmd_str); if (ret) { gf_log ("", GF_LOG_DEBUG, "Could not start glusterfs"); @@ -1255,11 +1255,11 @@ rb_destroy_maintainence_client (glusterd_volinfo_t *volinfo, goto out; } - snprintf (cmd_str, 8192, "umount -f %s/vols/%s/%s", + snprintf (cmd_str, 8192, "/bin/umount -f %s/vols/%s/%s", priv->workdir, volinfo->volname, RB_CLIENT_MOUNTPOINT); - ret = system (cmd_str); + ret = gf_system (cmd_str); if (ret) { gf_log ("", GF_LOG_DEBUG, "umount failed on maintainence client"); diff --git a/xlators/mgmt/glusterd/src/glusterd-utils.c b/xlators/mgmt/glusterd/src/glusterd-utils.c index 424c35f2f..35dfa3dfb 100644 --- a/xlators/mgmt/glusterd/src/glusterd-utils.c +++ b/xlators/mgmt/glusterd/src/glusterd-utils.c @@ -771,7 +771,7 @@ glusterd_volume_start_glusterfs (glusterd_volinfo_t *volinfo, "-s localhost --volfile-id %s -p %s --brick-name %s " "--brick-port %d", GFS_PREFIX, port, volfile, pidfile, brickinfo->path, port); - ret = system (cmd_str); + ret = gf_system (cmd_str); if (ret == 0) { //pmap_registry_bind (THIS, port, brickinfo->path); -- cgit