Print strerror when a system error occurs; add a new function rsyserr
authorMartin Pool <mbp@samba.org>
Thu, 26 Oct 2000 07:24:18 +0000 (07:24 +0000)
committerMartin Pool <mbp@samba.org>
Thu, 26 Oct 2000 07:24:18 +0000 (07:24 +0000)
to do this.  This is not used in every case yet -- I've just changed a
few cases that were causing trouble.  Please convert others as you see them.

authenticate.c
backup.c
clientserver.c
exclude.c
log.c
rsync.h

index 30bc53d..842a59e 100644 (file)
@@ -85,7 +85,7 @@ static int get_secret(int module, char *user, char *secret, int len)
        if (fd == -1) return 0;
 
        if (do_stat(fname, &st) == -1) {
-               rprintf(FERROR,"stat(%s) : %s\n", fname, strerror(errno));
+               rsyserr(FERROR, errno, "stat(%s)", fname);
                ok = 0;
        } else if (lp_strict_modes(module)) {
                if ((st.st_mode & 06) != 0) {
@@ -150,7 +150,7 @@ static char *getpassf(char *filename)
        }
        
        if (do_stat(filename, &st) == -1) {
-               rprintf(FERROR,"stat(%s) : %s\n", filename, strerror(errno));
+               rsyserr(FERROR, errno, "stat(%s)", filename);
                ok = 0;
        } else if ((st.st_mode & 06) != 0) {
                rprintf(FERROR,"password file must not be other-accessible\n");
index 8c1d767..6604f0b 100644 (file)
--- a/backup.c
+++ b/backup.c
@@ -43,7 +43,7 @@ static int make_simple_backup(char *fname)
        if (do_rename(fname,fnamebak) != 0) {
                /* cygwin (at least version b19) reports EINVAL */
                if (errno != ENOENT && errno != EINVAL) {
-                       rprintf(FERROR,"rename %s %s : %s\n",fname,fnamebak,strerror(errno));
+                       rsyserr(FERROR, errno, "rename %s to backup %s", fname, fnamebak);
                        return 0;
                }
        } else if (verbose > 1) {
index 0164d07..914d642 100644 (file)
@@ -1,5 +1,6 @@
-/* 
-   Copyright (C) Andrew Tridgell 1998
+/* -*- c-file-style: "linux"; -*-
+   
+   Copyright (C) 1998-2000 by Andrew Tridgell
    
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
@@ -210,20 +211,20 @@ static int rsync_module(int fd, int i)
 
        if (use_chroot) {
                if (chroot(lp_path(i))) {
-                       rprintf(FERROR,"chroot %s failed\n", lp_path(i));
+                       rsyserr(FERROR, errno, "chroot %s failed", lp_path(i));
                        io_printf(fd,"@ERROR: chroot failed\n");
                        return -1;
                }
 
                if (!push_dir("/", 0)) {
-                       rprintf(FERROR,"chdir %s failed\n", lp_path(i));
+                        rsyserr(FERROR, errno, "chdir %s failed\n", lp_path(i));
                        io_printf(fd,"@ERROR: chdir failed\n");
                        return -1;
                }
 
        } else {
                if (!push_dir(lp_path(i), 0)) {
-                       rprintf(FERROR,"chdir %s failed\n", lp_path(i));
+                       rsyserr(FERROR, errno, "chdir %s failed\n", lp_path(i));
                        io_printf(fd,"@ERROR: chdir failed\n");
                        return -1;
                }
@@ -232,13 +233,13 @@ static int rsync_module(int fd, int i)
 
        if (am_root) {
                if (setgid(gid)) {
-                       rprintf(FERROR,"setgid %d failed\n", gid);
+                       rsyserr(FERROR, errno, "setgid %d failed", gid);
                        io_printf(fd,"@ERROR: setgid failed\n");
                        return -1;
                }
 
                if (setuid(uid)) {
-                       rprintf(FERROR,"setuid %d failed\n", uid);
+                       rsyserr(FERROR, errno, "setuid %d failed", uid);
                        io_printf(fd,"@ERROR: setuid failed\n");
                        return -1;
                }
@@ -461,7 +462,7 @@ int daemon_main(void)
                if ((fd = do_open(lp_pid_file(), O_WRONLY|O_CREAT|O_TRUNC,
                                        0666 & ~orig_umask)) == -1) {
                    cleanup_set_pid(0);
-                   rprintf(FLOG,"failed to create pid file %s\n", pid_file);
+                   rsyserr(FLOG, errno, "failed to create pid file %s", pid_file);
                    exit_cleanup(RERR_FILEIO);
                }
                slprintf(pidbuf, sizeof(pidbuf), "%d\n", pid);
index 3b70b4e..cbf6105 100644 (file)
--- a/exclude.c
+++ b/exclude.c
@@ -220,7 +220,10 @@ struct exclude_struct **make_exclude_list(char *fname,
        char line[MAXPATHLEN];
        if (!f) {
                if (fatal) {
-                       rprintf(FERROR,"%s : %s\n",fname,strerror(errno));
+                       rsyserr(FERROR, errno,
+                                "failed to open %s file %s",
+                                include ? "include" : "exclude",
+                                fname);
                        exit_cleanup(RERR_FILEIO);
                }
                return list;
diff --git a/log.c b/log.c
index c19ebe8..8928a38 100644 (file)
--- a/log.c
+++ b/log.c
@@ -1,5 +1,6 @@
-/* 
-   Copyright (C) Andrew Tridgell 1998
+/* -*- c-file-style: "linux"; -*-
+   
+   Copyright (C) 1998-2000 by Andrew Tridgell
    
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
@@ -171,8 +172,9 @@ void rwrite(enum logcode code, char *buf, int len)
 }
                
 
-/* this is the rsync debugging function. Call it with FINFO, FERROR or FLOG */
- void rprintf(enum logcode code, const char *format, ...)
+/* This is the rsync debugging function. Call it with FINFO, FERROR or
+ * FLOG. */
+void rprintf(enum logcode code, const char *format, ...)
 {
        va_list ap;  
        char buf[1024];
@@ -187,6 +189,45 @@ void rwrite(enum logcode code, char *buf, int len)
        rwrite(code, buf, len);
 }
 
+
+/* This is like rprintf, but it also tries to print some
+ * representation of the error code.  Normally errcode = errno.
+ *
+ * Unlike rprintf, this always adds a newline and there should not be
+ * one in the format string.
+ *
+ * Note that since strerror might involve dynamically loading a
+ * message catalog we need to call it once before chroot-ing. */
+void rsyserr(enum logcode code, int errcode, const char *format, ...)
+{
+       va_list ap;  
+       char buf[1024];
+       int len, sys_len;
+        char *sysmsg;
+
+       va_start(ap, format);
+       len = vslprintf(buf, sizeof(buf), format, ap);
+       va_end(ap);
+
+       if (len > sizeof(buf)-1) exit_cleanup(RERR_MESSAGEIO);
+
+        sysmsg = strerror(errcode);
+        sys_len = strlen(sysmsg);
+        if (len + 3 + sys_len > sizeof(buf) - 1)
+                exit_cleanup(RERR_MESSAGEIO);
+
+        strcpy(buf + len, ": ");
+        len += 2;
+        strcpy(buf + len, sysmsg);
+        len += sys_len;
+        strcpy(buf + len, "\n");
+        len++;
+
+       rwrite(code, buf, len);
+}
+
+
+
 void rflush(enum logcode code)
 {
        FILE *f = NULL;
diff --git a/rsync.h b/rsync.h
index 5f61caa..12dc2c8 100644 (file)
--- a/rsync.h
+++ b/rsync.h
@@ -1,5 +1,5 @@
 /* 
-   Copyright (C) Andrew Tridgell 1996
+   Copyright (C) by Andrew Tridgell 1996, 2000
    Copyright (C) Paul Mackerras 1996
    
    This program is free software; you can redistribute it and/or modify
@@ -63,7 +63,7 @@
 
 #define MPLEX_BASE 7
 
-enum logcode {FNONE=0, FERROR=1, FINFO=2, FLOG=3};
+enum logcode {FNONE=0, FERROR=1, FINFO=2, FLOG=3 };
 
 #include "errcode.h"
 
@@ -496,6 +496,14 @@ extern int errno;
 #endif
 ;
 
+/* This is just like rprintf, but it also tries to print some
+ * representation of the error code.  Normally errcode = errno. */
+void rsyserr(enum logcode, int, const char *, ...)
+#ifdef __GNUC__
+     __attribute__ ((format (printf, 3, 4)))
+#endif
+     ;
+
 #ifdef REPLACE_INET_NTOA
 #define inet_ntoa rep_inet_ntoa
 #endif