Fixed wait_process() to handle cases where waitpid() fails or
[rsync/rsync.git] / main.c
diff --git a/main.c b/main.c
index 5741ef9..da9946b 100644 (file)
--- a/main.c
+++ b/main.c
@@ -46,11 +46,8 @@ extern int keep_dirlinks;
 extern int preserve_hard_links;
 extern int protocol_version;
 extern int recurse;
-extern int fuzzy_basis;
 extern int relative_paths;
 extern int rsync_port;
-extern int inplace;
-extern int make_backups;
 extern int whole_file;
 extern int read_batch;
 extern int write_batch;
@@ -60,8 +57,6 @@ extern int filesfrom_fd;
 extern pid_t cleanup_child_pid;
 extern struct stats stats;
 extern char *filesfrom_host;
-extern char *partial_dir;
-extern char *basis_dir[];
 extern char *rsync_path;
 extern char *shell_cmd;
 extern char *batch_name;
@@ -86,12 +81,12 @@ static void show_malloc_stats(void);
 /****************************************************************************
 wait for a process to exit, calling io_flush while waiting
 ****************************************************************************/
-void wait_process(pid_t pid, int *status)
+static void wait_process(pid_t pid, int *code_ptr)
 {
        pid_t waited_pid;
-       int cnt;
+       int cnt, status;
 
-       while ((waited_pid = waitpid(pid, status, WNOHANG)) == 0) {
+       while ((waited_pid = waitpid(pid, &status, WNOHANG)) == 0) {
                msleep(20);
                io_flush(FULL_FLUSH);
        }
@@ -102,7 +97,8 @@ void wait_process(pid_t pid, int *status)
                 */
                for (cnt = 0;  cnt < MAXCHILDPROCS; cnt++) {
                        if (pid == pid_stat_table[cnt].pid) {
-                               *status = pid_stat_table[cnt].status;
+                               waited_pid = pid;
+                               status = pid_stat_table[cnt].status;
                                pid_stat_table[cnt].pid = 0;
                                break;
                        }
@@ -112,9 +108,18 @@ void wait_process(pid_t pid, int *status)
        /* TODO: If the child exited on a signal, then log an
         * appropriate error message.  Perhaps we should also accept a
         * message describing the purpose of the child.  Also indicate
-        * this to the caller so that thhey know something went
-        * wrong.  */
-       *status = WEXITSTATUS(*status);
+        * this to the caller so that they know something went wrong. */
+       if (waited_pid < 0)
+               *code_ptr = RERR_WAITCHILD;
+       else if (!WIFEXITED(status)) {
+               if (WCOREDUMP(status))
+                       *code_ptr = RERR_CRASHED;
+               else if (WIFSIGNALED(status))
+                       *code_ptr = RERR_TERMINATED;
+               else
+                       *code_ptr = RERR_WAITCHILD;
+       } else
+               *code_ptr = WEXITSTATUS(status);
 }
 
 /* This function gets called from all 3 processes.  We want the client side
@@ -465,7 +470,6 @@ static void read_final_goodbye(int f_in, int f_out)
 
 static void do_server_sender(int f_in, int f_out, int argc,char *argv[])
 {
-       int i;
        struct file_list *flist;
        char *dir = argv[0];
 
@@ -494,14 +498,6 @@ static void do_server_sender(int f_in, int f_out, int argc,char *argv[])
        argc--;
        argv++;
 
-       if (strcmp(dir,".")) {
-               int l = strlen(dir);
-               if (strcmp(dir,"/") == 0)
-                       l = 0;
-               for (i = 0; i < argc; i++)
-                       argv[i] += l+1;
-       }
-
        if (argc == 0 && (recurse || list_only)) {
                argc = 1;
                argv--;
@@ -679,14 +675,8 @@ static void do_server_recv(int f_in, int f_out, int argc,char *argv[])
        }
        the_file_list = flist;
 
-       if (argc > 0) {
-               if (strcmp(dir,".")) {
-                       argv[0] += strlen(dir);
-                       if (argv[0][0] == '/')
-                               argv[0]++;
-               }
+       if (argc > 0)
                local_name = get_local_name(flist,argv[0]);
-       }
 
        status = do_recv(f_in,f_out,flist,local_name);
        exit_cleanup(status);