aboutsummaryrefslogtreecommitdiffstats
path: root/imap.c
diff options
context:
space:
mode:
Diffstat (limited to 'imap.c')
-rw-r--r--imap.c26
1 files changed, 24 insertions, 2 deletions
diff --git a/imap.c b/imap.c
index 0481587a..df787da6 100644
--- a/imap.c
+++ b/imap.c
@@ -62,6 +62,13 @@ extern char *strstr(); /* needed on sysV68 R3V7.1. */
#define IMAP4 0 /* IMAP4 rev 0, RFC1730 */
#define IMAP4rev1 1 /* IMAP4 rev 1, RFC2060 */
+static int imap_phase;
+#define PHASE_GETAUTH 0
+#define PHASE_GETRANGE 1
+#define PHASE_GETSIZES 2
+#define PHASE_FETCH 3
+#define PHASE_LOGOUT 4
+
static int count, seen, recent, unseen, deletions, imap_version, preauth;
static int expunged, expunge_period;
static char capabilities[MSGBUFSIZE+1];
@@ -144,7 +151,12 @@ int imap_ok(int sock, char *argbuf)
else if (strncmp(cp, "BAD", 3) == 0)
return(PS_ERROR);
else if (strncmp(cp, "NO", 2) == 0)
- return(PS_ERROR);
+ {
+ if (imap_phase == PHASE_GETAUTH)
+ return(PS_AUTHFAIL); /* RFC2060, 6.2.2 */
+ else
+ return(PS_ERROR);
+ }
else
return(PS_PROTOCOL);
}
@@ -196,7 +208,7 @@ static int do_otp(int sock, struct query *ctl)
};
if (rval)
- return PS_AUTHFAIL;
+ return(PS_AUTHFAIL);
to64frombits(buffer, response, strlen(response));
@@ -851,6 +863,8 @@ int imap_getauth(int sock, struct query *ctl, char *greeting)
{
int ok = 0;
+ imap_phase = PHASE_GETAUTH;
+
/* probe to see if we're running IMAP4 and can use RFC822.PEEK */
capabilities[0] = '\0';
if ((ok = gen_transact(sock, "CAPABILITY")) == PS_SUCCESS)
@@ -1028,6 +1042,8 @@ static int imap_getrange(int sock,
{
int ok;
+ imap_phase = PHASE_GETRANGE;
+
/* find out how many messages are waiting */
*bytes = recent = unseen = -1;
@@ -1093,6 +1109,8 @@ static int imap_getsizes(int sock, int count, int *sizes)
{
char buf [MSGBUFSIZE+1];
+ imap_phase = PHASE_GETSIZES;
+
/*
* Some servers (as in, PMDF5.1-9.1 under OpenVMS 6.1)
* won't accept 1:1 as valid set syntax. Some implementors
@@ -1114,6 +1132,8 @@ static int imap_getsizes(int sock, int count, int *sizes)
sizes[num - 1] = size;
}
+ imap_phase = PHASE_FETCH;
+
return(PS_SUCCESS);
}
@@ -1311,6 +1331,8 @@ static int imap_delete(int sock, struct query *ctl, int number)
static int imap_logout(int sock, struct query *ctl)
/* send logout command */
{
+ imap_phase = PHASE_LOGOUT;
+
/* if any un-expunged deletions remain, ship an expunge now */
if (deletions)
internal_expunge(sock);