diff options
-rw-r--r-- | NEWS | 6 | ||||
-rw-r--r-- | driver.c | 27 | ||||
-rw-r--r-- | fetchmail.c | 6 | ||||
-rw-r--r-- | fetchmail.man | 4 | ||||
-rw-r--r-- | imap.c | 18 | ||||
-rw-r--r-- | options.c | 6 | ||||
-rw-r--r-- | pop2.c | 5 | ||||
-rw-r--r-- | pop3.c | 14 |
8 files changed, 66 insertions, 20 deletions
@@ -4,6 +4,9 @@ fetchmail-1.9 (): features -- +* The first message from a query now includes the number of new messages + when this can be determined (that is not under POP2). + * POP3 UID support really works now. I make rude noises at the POP3 mavens who forced us to this with RFC1725, but thank Al Longyear <longyear@sii.com> for fixing and verifying my slightly buggy implementation. @@ -44,6 +47,9 @@ bugs -- * Find "nnn octets" anywhere on a POP3 server's RETR response line. +* Fixed various bugs in --check. It now reports PS_SUCCESS only if + there is new mail waiting. + fetchmail-1.8 (Fri Oct 11 15:08:10 EDT 1996): features -- @@ -536,7 +536,7 @@ struct method *proto; /* protocol method table */ char buf [POPBUFSIZE+1], host[HOSTLEN+1]; int socket; void (*sigsave)(); - int num, count, deletions = 0; + int num, count, new, deletions = 0; srvname = queryctl->servername; alarmed = 0; @@ -610,8 +610,8 @@ struct method *proto; /* protocol method table */ if (alarmed || ok != 0) goto cleanUp; - /* compute count, and get UID list if possible */ - if ((protocol->getrange)(socket, queryctl, &count) != 0 || alarmed) + /* compute number of messages and number of new messages waiting */ + if ((protocol->getrange)(socket, queryctl, &count, &new) != 0 || alarmed) goto cleanUp; /* show user how many messages we downloaded */ @@ -622,14 +622,25 @@ struct method *proto; /* protocol method table */ queryctl->localname, queryctl->servername); else + { + fprintf(stderr, "%d message%s", count, count > 1 ? "s" : ""); + if (new != -1) + fprintf(stderr, " (%d new)", new); fprintf(stderr, - "%d message%s from %s for %s@%s.\n", - count, count > 1 ? "s" : "", + " from %s for %s@%s.\n", queryctl->remotename, queryctl->localname, queryctl->servername); + } - if ((count > 0) && (!check_only)) + if (check_only) + { + if (new == -1 || queryctl->fetchall) + new = count; + ok = ((new > 0) ? PS_SUCCESS : PS_NOMAIL); + goto closeUp; + } + else if (count > 0) { if (queryctl->mda[0] == '\0') if ((mboxfd = Socket(queryctl->smtphost, SMTP_PORT)) < 0 @@ -750,10 +761,6 @@ struct method *proto; /* protocol method table */ close(socket); goto closeUp; } - else if (check_only) { - ok = ((count > 0) ? PS_SUCCESS : PS_NOMAIL); - goto closeUp; - } else { ok = gen_transact(socket, protocol->exit_cmd); if (ok == 0) diff --git a/fetchmail.c b/fetchmail.c index 0bdae28c..5c1023e7 100644 --- a/fetchmail.c +++ b/fetchmail.c @@ -400,7 +400,8 @@ char **argv; if (hostp->active && !(implicitmode && hostp->skip)) { popstatus = query_host(hostp); - update_uid_lists(hostp); + if (!check_only) + update_uid_lists(hostp); } } @@ -422,7 +423,8 @@ void termhook(int sig) if (sig != 0) fprintf(stderr, "terminated with signal %d\n", sig); - write_saved_lists(hostlist, idfile); + if (!check_only) + write_saved_lists(hostlist, idfile); unlink(lockfile); exit(popstatus); diff --git a/fetchmail.man b/fetchmail.man index f60574e7..03a72a69 100644 --- a/fetchmail.man +++ b/fetchmail.man @@ -84,7 +84,9 @@ before retrieving new messages. .B \-c, --check Return a status code to indicate whether there is mail waiting, without actually fetching or deleting mail (see EXIT CODES below). -(This option doesn't play well with queries to multiple sites.) +This option doesn't play well with queries to multiple sites, and +is ignored in daemon mode. It's also prone to false positives if +you leave read but undeleted mail in your server mailbox. .TP .B \-f pathname, --fetchmailrc pathname Specify a non-default name for the @@ -12,7 +12,7 @@ #include "socket.h" #include "fetchmail.h" -static int count, seen; +static int count, seen, recent, unseen; int imap_ok (socket, argbuf) /* parse command response */ @@ -35,6 +35,10 @@ int socket; /* interpret untagged status responses */ if (strstr(buf, "EXISTS")) count = atoi(buf+2); + if (strstr(buf, "RECENT")) + recent = atoi(buf+2); + if (strstr(buf, "UNSEEN")) + unseen = atoi(buf+2); if (strstr(buf, "FLAGS")) seen = (strstr(buf, "Seen") != (char *)NULL); } while @@ -79,15 +83,16 @@ char *buf; queryctl->remotename, queryctl->password)); } -static imap_getrange(socket, queryctl, countp) +static imap_getrange(socket, queryctl, countp, newp) /* get range of messages to be fetched */ int socket; struct hostrec *queryctl; -int *countp; +int *countp, *newp; { int ok; /* find out how many messages are waiting */ + recent = unseen = 0; ok = gen_transact(socket, "SELECT %s", queryctl->mailbox[0] ? queryctl->mailbox : "INBOX"); @@ -96,6 +101,13 @@ int *countp; *countp = count; + if (unseen) /* optional response, but better if we see it */ + *newp = unseen; + else if (recent) /* mandatory */ + *newp = recent; + else + *newp = -1; /* should never happen, RECENT is mandatory */ + return(0); } @@ -228,6 +228,12 @@ struct hostrec *queryctl; /* option record to be initialized */ } } + if (check_only && poll_interval) + { + fputs("The --check and --daemon options aren't compatible.\n", stderr); + return(-1); + } + if (errflag || ocount > 1) { /* squawk if syntax errors were detected */ fputs("usage: fetchmail [options] [server ...]\n", stderr); @@ -63,11 +63,11 @@ char *buf; queryctl->remotename, queryctl->password)); } -static pop2_getrange(socket, queryctl, countp) +static pop2_getrange(socket, queryctl, countp, newp) /* get range of messages to be fetched */ int socket; struct hostrec *queryctl; -int *countp; +int *countp, *newp; { /* * We should have picked up a count of messages in the user's @@ -88,6 +88,7 @@ int *countp; } *countp = pound_arg; + *newp = -1; return(0); } @@ -115,11 +115,11 @@ char *greeting; return(0); } -static pop3_getrange(socket, queryctl, countp) +static pop3_getrange(socket, queryctl, countp, newp) /* get range of messages to be fetched */ int socket; struct hostrec *queryctl; -int *countp; +int *countp, *newp; { int ok; char buf [POPBUFSIZE+1]; @@ -137,8 +137,11 @@ int *countp; /* * Newer, RFC-1725-conformant POP servers may not have the LAST command. + * We work as hard as possible to hide this ugliness, but it makes + * counting new messages intrinsically quadratic in the worst case. */ last = 0; + *newp = -1; if (*countp > 0 && !queryctl->fetchall) { char id [IDLEN+1]; @@ -149,12 +152,15 @@ int *countp; { if (sscanf(buf, "%d", &last) == 0) return(PS_ERROR); + *newp = (*countp - last); } else { int num; + struct idlist *idp; /* grab the mailbox's UID list */ + *newp = 0; gen_send(socket, "UIDL"); if ((ok = pop3_ok(socket, buf)) == 0) { while (SockGets(socket, buf, sizeof(buf)) >= 0) { @@ -164,7 +170,11 @@ int *countp; break; } if (sscanf(buf, "%d %s", &num, id) == 2) + { save_uid(&queryctl->newsaved, num, id); + if (!uid_in_list(&queryctl->oldsaved, id)) + (*newp)++; + } } } } |