aboutsummaryrefslogtreecommitdiffstats
path: root/driver.c
diff options
context:
space:
mode:
Diffstat (limited to 'driver.c')
-rw-r--r--driver.c134
1 files changed, 86 insertions, 48 deletions
diff --git a/driver.c b/driver.c
index d1ef6d48..2e123934 100644
--- a/driver.c
+++ b/driver.c
@@ -73,7 +73,6 @@
extern char *strstr(); /* needed on sysV68 R3V7.1. */
#endif /* strstr */
-int fetchlimit; /* how often to tear down the server connection */
int batchcount; /* count of messages sent in current batch */
flag peek_capable; /* can we peek for better error recovery? */
int pass; /* how many times have we re-polled? */
@@ -1354,10 +1353,11 @@ static void send_size_warnings(struct query *ctl)
#undef OVERHD
}
-int do_protocol(ctl, proto)
+static int do_session(ctl, proto, maxfetch)
/* retrieve messages from server using given protocol method table */
struct query *ctl; /* parsed options with merged-in defaults */
const struct method *proto; /* protocol method table */
+const int maxfetch; /* maximum number of messages to fetch */
{
int ok, js;
#ifdef HAVE_VOLATILE
@@ -1372,47 +1372,6 @@ const struct method *proto; /* protocol method table */
protocol = proto;
ctl->server.base_protocol = protocol;
-#ifndef KERBEROS_V4
- if (ctl->server.preauthenticate == A_KERBEROS_V4)
- {
- report(stderr, _("Kerberos V4 support not linked.\n"));
- return(PS_ERROR);
- }
-#endif /* KERBEROS_V4 */
-
-#ifndef KERBEROS_V5
- if (ctl->server.preauthenticate == A_KERBEROS_V5)
- {
- report(stderr, _("Kerberos V5 support not linked.\n"));
- return(PS_ERROR);
- }
-#endif /* KERBEROS_V5 */
-
- /* lacking methods, there are some options that may fail */
- if (!proto->is_old)
- {
- /* check for unsupported options */
- if (ctl->flush) {
- report(stderr,
- _("Option --flush is not supported with %s\n"),
- proto->name);
- return(PS_SYNTAX);
- }
- else if (ctl->fetchall) {
- report(stderr,
- _("Option --all is not supported with %s\n"),
- proto->name);
- return(PS_SYNTAX);
- }
- }
- if (!proto->getsizes && NUM_SPECIFIED(ctl->limit))
- {
- report(stderr,
- _("Option --limit is not supported with %s\n"),
- proto->name);
- return(PS_SYNTAX);
- }
-
pass = 0;
tagnum = 0;
tag[0] = '\0'; /* nuke any tag hanging out from previous query */
@@ -2067,12 +2026,12 @@ const struct method *proto; /* protocol method table */
report_complete(stdout, _(" not flushed\n"));
/* perhaps this as many as we're ready to handle */
- if (NUM_NONZERO(ctl->fetchlimit)
- && ctl->fetchlimit <= fetches)
+ if (maxfetch && maxfetch <= fetches && fetches < count)
{
- report(stdout, _("fetchlimit reached; %d messages left on server\n"),
- count - fetches);
- goto no_error;
+ report(stdout, _("fetchlimit %d reached; %d messages left on server\n"),
+ maxfetch, count - fetches);
+ ok = PS_MAXFETCH;
+ goto cleanUp;
}
}
@@ -2145,6 +2104,7 @@ const struct method *proto; /* protocol method table */
report(stderr, _("undefined error\n"));
break;
}
+ /* no report on PS_MAXFETCH or PS_UNDEFINED */
if (ok==PS_SOCKET || ok==PS_AUTHFAIL || ok==PS_SYNTAX
|| ok==PS_IOERR || ok==PS_ERROR || ok==PS_PROTOCOL
|| ok==PS_LOCKBUSY || ok==PS_SMTP || ok==PS_DNS)
@@ -2163,6 +2123,84 @@ closeUp:
return(ok);
}
+int do_protocol(ctl, proto)
+/* retrieve messages from server using given protocol method table */
+struct query *ctl; /* parsed options with merged-in defaults */
+const struct method *proto; /* protocol method table */
+{
+ int ok;
+
+#ifndef KERBEROS_V4
+ if (ctl->server.preauthenticate == A_KERBEROS_V4)
+ {
+ report(stderr, _("Kerberos V4 support not linked.\n"));
+ return(PS_ERROR);
+ }
+#endif /* KERBEROS_V4 */
+
+#ifndef KERBEROS_V5
+ if (ctl->server.preauthenticate == A_KERBEROS_V5)
+ {
+ report(stderr, _("Kerberos V5 support not linked.\n"));
+ return(PS_ERROR);
+ }
+#endif /* KERBEROS_V5 */
+
+ /* lacking methods, there are some options that may fail */
+ if (!proto->is_old)
+ {
+ /* check for unsupported options */
+ if (ctl->flush) {
+ report(stderr,
+ _("Option --flush is not supported with %s\n"),
+ proto->name);
+ return(PS_SYNTAX);
+ }
+ else if (ctl->fetchall) {
+ report(stderr,
+ _("Option --all is not supported with %s\n"),
+ proto->name);
+ return(PS_SYNTAX);
+ }
+ }
+ if (!proto->getsizes && NUM_SPECIFIED(ctl->limit))
+ {
+ report(stderr,
+ _("Option --limit is not supported with %s\n"),
+ proto->name);
+ return(PS_SYNTAX);
+ }
+
+ /*
+ * If no expunge limit or we do expunges within the driver,
+ * then just do one session, passing in any fetchlimit.
+ */
+ if (proto->retry || !NUM_SPECIFIED(ctl->expunge))
+ return(do_session(ctl, proto, NUM_VALUE_OUT(ctl->fetchlimit)));
+ /*
+ * There's an expunge limit, and it isn't handled in the driver itself.
+ * OK; do multiple sessions, each fetching a limited # of messages.
+ * Stop if the total count of retrieved messages exceeds ctl->fetchlimit
+ * (if it was nonzero).
+ */
+ else
+ {
+ int totalcount = 0;
+ int expunge = NUM_VALUE_OUT(ctl->expunge);
+ int fetchlimit = NUM_VALUE_OUT(ctl->fetchlimit);
+
+ do {
+ ok = do_session(ctl, proto, expunge);
+ totalcount += expunge;
+ if (NUM_SPECIFIED(ctl->fetchlimit) && totalcount >= fetchlimit)
+ break;
+ } while
+ (ok == PS_MAXFETCH);
+
+ return(ok);
+ }
+}
+
#if defined(HAVE_STDARG_H)
void gen_send(int sock, const char *fmt, ... )
#else