fetchmail-friends
[Top] [All Lists]

Re: [fetchmail]fetchmail 5.8.14 FETCH response handling

2001-08-01 11:59:34
On Wed, 1 Aug 2001, Eric S. Raymond wrote:

fetchmail: about to deliver with: /usr/bin/procmail -d alt
#
fetchmail: IMAP< )
fetchmail: IMAP< A0995 OK FETCH completed.
fetchmail: IMAP> A0996 FETCH 496 BODY[TEXT]
fetchmail: IMAP< * 496 FETCH (BODY[TEXT] {0}
 (0 body octets)  not flushed
fetchmail: IMAP> A0997 FETCH 497 RFC822.HEADER
beginning to look for response...
fetchmail: IMAP< )
buffer: )
fetchmail: IMAP< A0996 OK FETCH completed.
buffer: A0996 OK FETCH completed.
+++returning PS_ERROR, NO found

Am I blind or am I not seeing the actual "NO"?

That's cuz the test is broken, the patch below fixes things.  sscanf()
reports _only_ the number of conversions.  if there's trailing regular
text ("%s %s %s foo") in the format string, there is absolutely no way to
tell whether or not the "foo" part got matched.  it would be interesting
to see a sscanf-like function that returned the number of characters
matched (counting format string characters, of course, not real
characters).

Now *you* figure out how to detect BAD and NO reliably.  If you make
imap_fetch_headers() return PS_TRANSIENT, the right thing should happen.
Send me back a patch including the above and I'll take it.

==========================================
diff -dur fetchmail-5.8.15/driver.c fetchmail-5.8.15-pl1/driver.c
--- fetchmail-5.8.15/driver.c   Mon Jun 25 13:59:18 2001
+++ fetchmail-5.8.15-pl1/driver.c       Wed Aug  1 11:38:14 2001
@@ -428,7 +428,14 @@

            /* request a message */
            err = 
(ctl->server.base_protocol->fetch_headers)(mailserver_socket,ctl,num, &len);
-           if (err != 0)
+           if (err == PS_TRANSIENT)    /* server is probably Exchange */
+           {
+               report_build(stdout,
+                            _("couldn't fetch headers, msg %d (%d octets)"),
+                            num, msgsizes[num-1]);
+               continue;
+           }
+           else if (err != 0)
                return(err);

            /* -1 means we didn't see a size in the response */
diff -dur fetchmail-5.8.15/fetchmail.c fetchmail-5.8.15-pl1/fetchmail.c
--- fetchmail-5.8.15/fetchmail.c        Mon Jul 23 02:39:43 2001
+++ fetchmail-5.8.15-pl1/fetchmail.c    Wed Aug  1 01:38:53 2001
@@ -128,6 +128,14 @@
 #define timestamp rfc822timestamp
 #endif

+char *skip_token(char *ptr)
+{
+    while(isspace(*ptr)) ptr++;
+    while(!isspace(*ptr) && !iscntrl(*ptr)) ptr++;
+    while(isspace(*ptr)) ptr++;
+    return(ptr);
+}
+
 int main(int argc, char **argv)
 {
     int bkgd = FALSE;
diff -dur fetchmail-5.8.15/fetchmail.h fetchmail-5.8.15-pl1/fetchmail.h
--- fetchmail-5.8.15/fetchmail.h        Sun Jun 24 12:08:14 2001
+++ fetchmail-5.8.15-pl1/fetchmail.h    Wed Aug  1 01:30:51 2001
@@ -405,6 +405,8 @@
 void report_at_line ();
 #endif

+char *skip_token(char *);
+
 /* driver.c -- main driver loop */
 void set_timeout(int);
 int do_protocol(struct query *, const struct method *);
diff -dur fetchmail-5.8.15/imap.c fetchmail-5.8.15-pl1/imap.c
--- fetchmail-5.8.15/imap.c     Mon Jul 30 20:12:39 2001
+++ fetchmail-5.8.15-pl1/imap.c Wed Aug  1 01:45:11 2001
@@ -675,15 +675,17 @@
     for (;;)
     {
        int     ok;
+       char    *ptr;

        if ((ok = gen_recv(sock, buf, sizeof(buf))))
            return(ok);
-       if (sscanf(buf+2, "%d FETCH (%*s {%d}", &num, lenp) == 2)
+       ptr = skip_token(buf);  /* either "* " or "AXXXX " */
+       if (sscanf(ptr, "%d FETCH (%*s {%d}", &num, lenp) == 2)
            break;
-       else if (sscanf(buf+2, "%d NO", &num) == 1)
-           return(PS_ERROR);
-       else if (sscanf(buf+2, "%d BAD", &num) == 1)
-           return(PS_ERROR);
+       else if (!strncmp(ptr, "NO", 2))
+           return(PS_TRANSIENT);
+       else if (!strncmp(ptr, "BAD", 3))
+           return(PS_TRANSIENT);
     }

     if (num != number)
==========================================

also the end-of-message checking may be broken...  it over-reads a
message (with the following patch):

That fscking broken pile of shite that Microsoft calls a mailserver is
notorious for returning bogus message sizes.  The driver loop plays
various games to try to cope, but given the way IMAP is delimited it's
hard to compensate.  It wouldn't surprise me a bit if Exchange had
found another clever way to give fetchmail indigestion.

okay, i can easily see that being the case, but that doesn't explain why
5.8.14 retrieved message 1210 fine.  i'll look into it.  responding "NO"
to a FETCH RFC822.HEADERS, though, is easily the most retarded thing i've
ever seen.

along the same lines, everything would break if another client was
simultaneously reading and deleting messages from a mailbox fetchmail was
trying to read from, right?


justin



<Prev in Thread] Current Thread [Next in Thread>