]> Pileus Git - ~andy/fetchmail/blobdiff - pop2.c
Note Earl's regression fix for SSL_CTX_clear_options() on older OpenSSL.
[~andy/fetchmail] / pop2.c
diff --git a/pop2.c b/pop2.c
index e1804660a3a18e4db4ed21b140cda52b706613dc..03d58a18f92334be44b0c57bd5774e1cf6893d18 100644 (file)
--- a/pop2.c
+++ b/pop2.c
@@ -1,34 +1,36 @@
 /*
- * pop2.c -- POP@ protocol methods
+ * pop2.c -- POP2 protocol methods
  *
- * Copyright 1996 by Eric S. Raymond
- * All rights reserved.
+ * Copyright 1997 by Eric S. Raymond
  * For license terms, see the file COPYING in this directory.
  */
 
-#include  <config.h>
+#include  "config.h"
+
+#ifdef POP2_ENABLE
 #include  <stdio.h>
 #if defined(STDC_HEADERS)
 #include <stdlib.h>
 #endif
-#include  "socket.h"
+#ifdef HAVE_STRING_H
+#include <string.h>
+#endif
 #include  "fetchmail.h"
+#include  "socket.h"
+#include  "i18n.h"
 
 static int pound_arg, equal_arg;
 
-int pop2_ok (socket, argbuf)
+static int pop2_ok (int sock, char *argbuf)
 /* parse POP2 command response */
-int socket;
-char *argbuf;
 {
     int ok;
     char buf [POPBUFSIZE+1];
 
     pound_arg = equal_arg = -1;
-    if (SockGets(socket, buf, sizeof(buf)) >= 0) {
-       if (outlevel == O_VERBOSE)
-           fprintf(stderr,"%s\n",buf);
 
+    if ((ok = gen_recv(sock, buf, sizeof(buf))) == 0)
+    {
        if (buf[0] == '+')
            ok = 0;
        else if (buf[0] == '#')
@@ -49,104 +51,135 @@ char *argbuf;
        if (argbuf != NULL)
            strcpy(argbuf,buf);
     }
-    else 
-       ok = PS_SOCKET;
 
     return(ok);
 }
 
-int pop2_getauth(socket, ctl, buf)
+static int pop2_getauth(int sock, struct query *ctl, char *buf)
 /* apply for connection authorization */
-int socket;
-struct query *ctl;
-char *buf;
 {
-    return(gen_transact(socket,
+    int status;
+
+    (void)buf;
+
+    if (ctl->sslproto && !strcasecmp(ctl->sslproto, "tls1") && !ctl->use_ssl)
+    {
+       report(stderr, GT_("POP2 does not support STLS. Giving up.\n"));
+       return PS_SOCKET;
+    }
+
+    if (ctl->server.authenticate != A_ANY && ctl->server.authenticate != A_PASSWORD)
+    {
+       report(stderr, GT_("POP2 only supports password authentication. Giving up.\n"));
+       return PS_AUTHFAIL;
+    }
+
+    strlcpy(shroud, ctl->password, sizeof(shroud));
+    status = gen_transact(sock,
                  "HELO %s %s",
-                 ctl->remotename, ctl->password));
+                 ctl->remotename, ctl->password);
+    memset(shroud, 0x55, sizeof(shroud));
+    shroud[0] = '\0';
+    return status;
 }
 
-static int pop2_getrange(socket, ctl, countp, newp)
+static int pop2_getrange(int sock, struct query *ctl, const char *folder, 
+                        int *countp, int *newp, int *bytes)
 /* get range of messages to be fetched */
-int socket;
-struct query *ctl;
-int *countp, *newp;
 {
-    /*
-     * We should have picked up a count of messages in the user's
-     * default inbox from the pop2_getauth() response.
-     */
-    if (pound_arg == -1)
-       return(PS_ERROR);
+    (void)ctl;
 
     /* maybe the user wanted a non-default folder */
-    if (ctl->mailbox[0])
+    if (folder)
     {
-       int     ok = gen_transact(socket, "FOLD %s", ctl->mailbox);
+       int     ok = gen_transact(sock, "FOLD %s", folder);
 
        if (ok != 0)
            return(ok);
        if (pound_arg == -1)
            return(PS_ERROR);
     }
+    else
+       /*
+        * We should have picked up a count of messages in the user's
+        * default inbox from the pop2_getauth() response. 
+        *
+        * Note: this logic only works because there is no way to select
+        * both the unnamed folder and named folders within a single
+        * fetchmail run.  If that assumption ever becomes invalid, the
+        * pop2_getauth code will have to stash the pound response away
+        * explicitly in case it gets stepped on.
+        */
+       if (pound_arg == -1)
+           return(PS_ERROR);
 
     *countp = pound_arg;
-    *newp = -1;
+    *bytes = *newp = -1;
 
     return(0);
 }
 
-static int pop2_fetch(socket, number, lenp)
+static int pop2_fetch(int sock, struct query *ctl, int number, int *lenp)
 /* request nth message */
-int socket;
-int number;
-int *lenp; 
 {
     int        ok;
 
+    (void)ctl;
     *lenp = 0;
-    ok = gen_transact(socket, "READ %d", number);
+    ok = gen_transact(sock, "READ %d", number);
     if (ok)
        return(0);
     *lenp = equal_arg;
 
-    gen_send(socket, "RETR");
+    gen_send(sock, "RETR");
 
     return(ok);
 }
 
-static int pop2_trail(socket, ctl, number)
+static int pop2_trail(int sock, struct query *ctl, const char *tag)
 /* send acknowledgement for message data */
-int socket;
-struct query *ctl;
-int number;
 {
-    return(gen_transact(socket, ctl->keep ? "ACKS" : "ACKD"));
+    (void)ctl;
+    (void)tag;
+    return(gen_transact(sock, ctl->keep ? "ACKS" : "ACKD"));
+}
+
+static int pop2_logout(int sock, struct query *ctl)
+/* send logout command */
+{
+    (void)ctl;
+    return(gen_transact(sock, "QUIT"));
 }
 
-const static struct method pop2 =
+static const struct method pop2 =
 {
     "POP2",                            /* Post Office Protocol v2 */
-    109,                               /* standard POP2 port */
-    0,                                 /* this is not a tagged protocol */
-    0,                                 /* does not use message delimiter */
+    "pop2",                            /* standard POP2 port */
+    "pop2",                            /* ssl POP2 port - not */
+    FALSE,                             /* this is not a tagged protocol */
+    FALSE,                             /* does not use message delimiter */
     pop2_ok,                           /* parse command response */
     pop2_getauth,                      /* get authorization */
     pop2_getrange,                     /* query range of messages */
     NULL,                              /* no way to get sizes */
+    NULL,                              /* no way to get sizes of subsets */
     NULL,                              /* messages are always new */
     pop2_fetch,                                /* request given message */
+    NULL,                              /* no way to fetch body alone */
     pop2_trail,                                /* eat message trailer */
     NULL,                              /* no POP2 delete method */
-    NULL,                              /* no POP2 expunge command */
-    "QUIT",                            /* the POP2 exit command */
+    NULL,                              /* how to mark a message as seen */
+    NULL,                              /* how to end mailbox processing */
+    pop2_logout,                       /* log out, we're done */
+    FALSE                              /* no, we can't re-poll */
 };
 
-int doPOP2 (ctl)
+int doPOP2 (struct query *ctl)
 /* retrieve messages using POP2 */
-struct query *ctl;
 {
+    peek_capable = FALSE;
     return(do_protocol(ctl, &pop2));
 }
+#endif /* POP2_ENABLE */
 
 /* pop2.c ends here */