]> Pileus Git - ~andy/fetchmail/blobdiff - fetchmail.c
Needs this to work with Ultrix lex.
[~andy/fetchmail] / fetchmail.c
index 3700b0e8a8e080b41a511f68e8bf5224fba14d0e..68e8e4dc826cbe11b64b8d489887fec722d8c02e 100644 (file)
 static int load_params(int, char **, int);
 static void dump_params (struct query *);
 static int query_host(struct query *);
-static char *visbuf(const char *);
 
 /* controls the detail level of status/progress messages written to stderr */
 int outlevel;          /* see the O_.* constants above */
 
 /* daemon mode control */
-bool nodetach;         /* if TRUE, don't detach daemon process */
-bool quitmode;         /* if --quit was set */
-bool check_only;       /* if --probe was set */
+flag nodetach;         /* if TRUE, don't detach daemon process */
+flag quitmode;         /* if --quit was set */
+flag check_only;       /* if --probe was set */
 char *cmd_logfile;     /* if --logfile was set */
 int cmd_daemon;        /* if --daemon was set */
 
 /* miscellaneous global controls */
 char *idfile;          /* UID list file */
-bool versioninfo;      /* emit only version info */
+flag versioninfo;      /* emit only version info */
 char *user;            /* the name of the invoking user */
 char *fetchmailhost;   /* the name of the host running fetchmail */
 char *program_name;    /* the name to prefix error messages with */
 
 static char *lockfile;         /* name of lockfile */
 static int querystatus;                /* status of query */
+static int successes;          /* count number of successful polls */
 static int lastsig;            /* last signal received */
 
 static void termhook();                /* forward declaration of exit hook */
@@ -135,8 +135,12 @@ int main (int argc, char **argv)
            printf("\n");
        else
            printf(" and %s\n", rcfile);
+       if (poll_interval)
+           printf("Poll interval is %d seconds\n", poll_interval);
        if (outlevel == O_VERBOSE)
            printf("Lockfile at %s\n", tmpbuf);
+       if (logfile)
+           printf("Logfile is %s\n", logfile);
        for (ctl = querylist; ctl; ctl = ctl->next) {
            if (ctl->active && !(implicitmode && ctl->server.skip))
                dump_params(ctl);
@@ -390,6 +394,10 @@ int main (int argc, char **argv)
 #endif /* HAVE_GETHOSTBYNAME */
 
                querystatus = query_host(ctl);
+
+               if (querystatus == PS_SUCCESS)
+                   successes++;
+
                if (!check_only)
                    update_str_lists(ctl);
 #ifdef linux
@@ -479,10 +487,11 @@ int main (int argc, char **argv)
        (poll_interval);
 
     if (outlevel == O_VERBOSE)
-       fprintf(stderr,"fetchmail: normal termination, status %d\n",querystatus);
+       fprintf(stderr,"fetchmail: normal termination, status %d\n",
+               successes ? PS_SUCCESS : querystatus);
 
     termhook(0);
-    exit(querystatus);
+    exit(successes ? PS_SUCCESS : querystatus);
 }
 
 static int load_params(int argc, char **argv, int optind)
@@ -579,16 +588,6 @@ static int load_params(int argc, char **argv, int optind)
            }
 #endif /* !HAVE_GETHOSTBYNAME || !HAVE_RES_SEARCH */
 
-           /* compute server leaders for queries */
-           for (mp = querylist; mp && mp != ctl; mp = mp->next)
-               if (strcmp(mp->server.names->id, ctl->server.names->id) == 0)
-               {
-                   ctl->server.lead_server = mp->server.lead_server;
-                   goto no_new_server;
-               }
-           ctl->server.lead_server = &(ctl->server);
-       no_new_server:;
-
            /* this code enables flags to be turned off */
 #define DEFAULT(flag, dflt)    if (flag == FLAG_TRUE)\
                                        flag = TRUE;\
@@ -597,12 +596,13 @@ static int load_params(int argc, char **argv, int optind)
                                else\
                                        flag = (dflt)
            DEFAULT(ctl->keep, FALSE);
-           DEFAULT(ctl->flush, FALSE);
            DEFAULT(ctl->fetchall, FALSE);
+           DEFAULT(ctl->flush, FALSE);
            DEFAULT(ctl->rewrite, TRUE);
            DEFAULT(ctl->stripcr, (ctl->mda != (char *)NULL)); 
            DEFAULT(ctl->forcecr, FALSE);
            DEFAULT(ctl->pass8bits, FALSE);
+           DEFAULT(ctl->dropstatus, FALSE);
            DEFAULT(ctl->server.dns, TRUE);
            DEFAULT(ctl->server.uidl, FALSE);
 #undef DEFAULT
@@ -663,11 +663,26 @@ void termhook(int sig)
 {
     struct query       *ctl;
 
+    /* 
+     * Craig Metz, the RFC1938 one-time-password guy, points out:
+     * "Remember that most kernels don't zero pages before handing them to the
+     * next process and many kernels share pages between user and kernel space.
+     * You'd be very surprised what you can find from a short program to do a
+     * malloc() and then dump the contents of the pages you got. By zeroing
+     * the secrets at end of run (earlier if you can), you make sure the next
+     * guy can't get the password/pass phrase."
+     *
+     * Right you are, Craig!
+     */
+    for (ctl = querylist; ctl; ctl = ctl->next)
+       if (ctl->password)
+           memset(ctl->password, '\0', strlen(ctl->password));
+
     /*
      * Sending SMTP QUIT on signal is theoretically nice, but led to a 
      * subtle bug.  If fetchmail was terminated by signal while it was 
      * shipping message text, it would hang forever waiting for a
-     * command acknowledge.  In theory we could disable the QUIT
+     * command acknowledge.  In theory we could enable the QUIT
      * only outside of the message send.  In practice, we don't
      * care.  All mailservers hang up on a dropped TCP/IP connection
      * anyway.
@@ -684,7 +699,7 @@ void termhook(int sig)
     if (!check_only)
        write_saved_lists(querylist, idfile);
 
-    exit(querystatus);
+    exit(successes ? PS_SUCCESS : querystatus);
 }
 
 /*
@@ -769,10 +784,9 @@ void dump_params (struct query *ctl)
     printf("Options for retrieving from %s@%s:\n",
           ctl->remotename, visbuf(ctl->server.names->id));
 
-    if (logfile)
-       printf("  Logfile is %s\n", logfile);
-    if (poll_interval)
-       printf("  Poll interval is %d seconds\n", poll_interval);
+    if (ctl->server.via)
+       printf("  Mail will be retrieved via %s\n", ctl->server.via);
+
     if (ctl->server.interval)
        printf("  Poll of this server will occur every %d intervals.\n",
               ctl->server.interval);
@@ -865,6 +879,9 @@ void dump_params (struct query *ctl)
     printf("  Interpretation of Content-Transfer-Encoding is %sabled (pass8bits %s).\n",
           ctl->pass8bits ? "dis" : "en",
           ctl->pass8bits ? "on" : "off");
+    printf("  Nonempty Status lines will be %s (dropstatus %s)\n",
+          ctl->dropstatus ? "discarded" : "kept",
+          ctl->dropstatus ? "on" : "off");
     if (ctl->limit > 0)
        printf("  Message size limit is %d bytes (--limit %d).\n", 
               ctl->limit, ctl->limit);
@@ -954,44 +971,4 @@ void dump_params (struct query *ctl)
        }
 }
 
-static char *visbuf(const char *buf)
-/* visibilize a given string */
-{
-    static char vbuf[BUFSIZ];
-    char *tp = vbuf;
-
-    while (*buf)
-    {
-       if (isprint(*buf) || *buf == ' ')
-           *tp++ = *buf++;
-       else if (*buf == '\n')
-       {
-           *tp++ = '\\'; *tp++ = 'n';
-           buf++;
-       }
-       else if (*buf == '\r')
-       {
-           *tp++ = '\\'; *tp++ = 'r';
-           buf++;
-       }
-       else if (*buf == '\b')
-       {
-           *tp++ = '\\'; *tp++ = 'b';
-           buf++;
-       }
-       else if (*buf < ' ')
-       {
-           *tp++ = '\\'; *tp++ = '^'; *tp++ = '@' + *buf;
-           buf++;
-       }
-       else
-       {
-           (void) sprintf(tp, "\\0x%02x", *buf++);
-           tp += strlen(tp);
-       }
-    }
-    *tp++ = '\0';
-    return(vbuf);
-}
-
 /* fetchmail.c ends here */