Patch to add support for Dynamic Relay Authorization Control For more information about DRAC, see: http://mail.cc.umanitoba.ca/drac/index.html Installation ------------ 1. Apply this patch in the toplevel directory using the following command: # patch -b -p0 < contrib/drac_auth.patch 2. Cleanup any previous builds: # make distclean 3a. If you DO NOT have 'smake' and 'autoconf' installed on your system, goto step 3b. Perform the following to reconfigure your build: # rm aclocal.m4 configure # sh SMakefile # ./configure ... --with-drac= NOTE: you can find your original configure command in config.status Proceed to step 4. 3b. Edit imap/Makefile and modify the following three variables: DEFS = ... -DDRAC_AUTH LIBS = ... -ldrac LDFLAGS = ... -L 4. Build and install the software: # make # make install 5. If dracd is not running on the same system as Cyrus (localhost), use the 'drachost' option in cyrus.conf(5) to specify the hostname of the dracd server. 6. Installation is complete! Operation --------- The behavior of DRAC is controlled by the value of the 'dracinterval' option in imapd.conf(5). If 'dracinterval' is 0 (zero), DRAC is disabled. Otherwise, DRAC is enabled and has the following behavior: pop3d: Whenever a client opens a user's INBOX, drac_auth() is called. imapd: Once a client is logged in (via LOGIN or AUTHENTICATE), drac_send() will be once called every 'dracinterval' minutes. *** acconfig.h.orig Wed Feb 7 16:46:56 2001 --- acconfig.h Tue Mar 6 12:27:16 2001 *************** *** 78,83 **** --- 78,86 ---- /* the TCP control package */ #undef HAVE_LIBWRAP + /* the Dynamic Relay Authorization Control package */ + #undef DRAC_AUTH + /* do we have OpenSSL? */ #undef HAVE_SSL *** configure.in.orig Mon Feb 19 12:54:42 2001 --- configure.in Tue Mar 6 12:27:16 2001 *************** *** 714,719 **** --- 714,734 ---- SNMP_SUBDIRS="" AC_SUBST(SNMP_SUBDIRS) + + + dnl + dnl Test for DRAC + dnl + AC_ARG_WITH(drac, [ --with-drac=DIR use DRAC library in [no] ], + if test -d "$withval"; then + LDFLAGS="$LDFLAGS -L${withval}" + AC_CHECK_LIB(drac, dracauth, + AC_DEFINE(DRAC_AUTH) + LIBS="${LIBS} -ldrac") + fi) + + + CMU_SOCKETS CMU_LIBWRAP CMU_UCDSNMP *** imap/imapd.c.orig Fri Feb 16 13:55:10 2001 --- imap/imapd.c Tue Mar 6 15:48:05 2001 *************** *** 89,94 **** --- 89,98 ---- #ifdef HAVE_SSL #include "tls.h" + #ifdef DRAC_AUTH + static int drac_interval; /* dracd "ping" interval; 0 = disabled */ + #endif /* DRAC_AUTH */ + /* our tls connection, if any */ static SSL *tls_conn = NULL; #endif /* HAVE_SSL */ *************** *** 486,491 **** --- 490,510 ---- TLS negotiation immediately */ if (imaps == 1) cmd_starttls(NULL, 1); + #ifdef DRAC_AUTH + drac_interval = config_getint("dracinterval", 5); + if (drac_interval < 0) drac_interval = 0; + + if (drac_interval) { + char *err; + + if (dracconn(config_getstring("drachost", "localhost"), &err) != 0) { + /* disable DRAC */ + drac_interval = 0; + syslog(LOG_NOTICE, "dracconn: %s (DISABLED)", err); + } + } + #endif /* DRAC_AUTH */ + snmp_increment(TOTAL_CONNECTIONS, 1); snmp_increment(ACTIVE_CONNECTIONS, 1); *************** *** 561,566 **** --- 580,590 ---- prot_flush(imapd_out); /* one less active connection */ snmp_increment(ACTIVE_CONNECTIONS, -1); + + #ifdef DRAC_AUTH + if (drac_interval) (void) dracdisc((char **)NULL); + #endif /* DRAC_AUTH */ + exit(code); } *************** *** 581,586 **** --- 605,632 ---- } + #ifdef DRAC_AUTH + /* + * Ping dracd every 'drac_interval' minutes + * to let it know that we are still connected + */ + struct prot_waitevent *drac_ping(struct protstream *s, + struct prot_waitevent *ev, void *rock) + { + char *err; + + if (dracsend(imapd_remoteaddr.sin_addr.s_addr, &err) != 0) { + /* disable DRAC */ + prot_removewaitevent(s, ev); + syslog(LOG_NOTICE, "dracsend: %s (DISABLED)", err); + return NULL; + } + + ev->mark = time(NULL) + (drac_interval * 60); + return ev; + } + #endif /* DRAC_AUTH */ + /* * Top-level command loop parsing */ *************** *** 1429,1434 **** --- 1475,1485 ---- if (!reply) reply = "User logged in"; + #ifdef DRAC_AUTH + if (drac_interval) + prot_addwaitevent(imapd_in, 0 /* ping now */, drac_ping, NULL); + #endif /* DRAC_AUTH */ + /* Create telemetry log */ sprintf(buf, "%s%s%s/%lu", config_dir, FNAME_LOGDIR, imapd_userid, (unsigned long) getpid()); *************** *** 1585,1590 **** --- 1636,1646 ---- prot_setsasl(imapd_in, imapd_saslconn); prot_setsasl(imapd_out, imapd_saslconn); + + #ifdef DRAC_AUTH + if (drac_interval) + prot_addwaitevent(imapd_in, 0 /* ping now */, drac_ping, NULL); + #endif /* DRAC_AUTH */ /* Create telemetry log */ sprintf(buf, "%s%s%s/%lu", config_dir, FNAME_LOGDIR, imapd_userid, *** imap/pop3d.c.orig Fri Feb 16 13:55:10 2001 --- imap/pop3d.c Tue Mar 6 15:48:03 2001 *************** *** 98,104 **** extern int errno; ! #ifdef HAVE_SSL static SSL *tls_conn; --- 98,106 ---- extern int errno; ! #ifdef DRAC_AUTH ! static int drac_enabled; ! #endif /* DRAC_AUTH */ #ifdef HAVE_SSL static SSL *tls_conn; *************** *** 276,281 **** --- 278,287 ---- TLS negotiation immediatly */ if (pop3s == 1) cmd_starttls(1); + #ifdef DRAC_AUTH + drac_enabled = (config_getint("dracinterval", 5) > 0); + #endif /* DRAC_AUTH */ + prot_printf(popd_out, "+OK %s Cyrus POP3 %s server ready\r\n", config_servername, CYRUS_VERSION); cmdloop(); *************** *** 1110,1115 **** --- 1116,1134 ---- } popd_mailbox = &mboxstruct; proc_register("pop3d", popd_clienthost, popd_userid, popd_mailbox->name); + + #ifdef DRAC_AUTH + if (drac_enabled) { + char *err; + + if (dracauth(config_getstring("drachost", "localhost"), + popd_remoteaddr.sin_addr.s_addr, &err) != 0) { + /* disable DRAC */ + drac_enabled = 0; + syslog(LOG_NOTICE, "dracauth: %s (DISABLED)", err); + } + } + #endif /* DRAC_AUTH */ /* Create telemetry log */ sprintf(buf, "%s%s%s/%lu", config_dir, FNAME_LOGDIR, popd_userid, *** lib/prot.c.orig Thu Dec 21 15:29:46 2000 --- lib/prot.c Tue Mar 6 20:24:42 2001 *************** *** 340,346 **** fd_set rfds; int haveinput; time_t read_timeout; ! struct prot_waitevent *event; assert(!s->write); --- 340,346 ---- fd_set rfds; int haveinput; time_t read_timeout; ! struct prot_waitevent *event, *next; assert(!s->write); *************** *** 376,383 **** do { sleepfor = read_timeout - now; /* execute each callback that has timed out */ ! for (event = s->waitevent; event != NULL; event = event->next) { if (now >= event->mark) { event = (*event->proc)(s, event, event->rock); } --- 376,384 ---- do { sleepfor = read_timeout - now; /* execute each callback that has timed out */ ! for (event = s->waitevent; event; event = next) { + next = event->next; if (now >= event->mark) { event = (*event->proc)(s, event, event->rock); } *** man/imapd.conf.5.orig Mon Feb 19 14:39:37 2001 --- man/imapd.conf.5 Tue Mar 6 15:55:09 2001 *************** *** 217,222 **** --- 217,228 ---- file overrides the SASL configuration file. .IP "\fBlmtpsocket:\fR /var/imap/socket/lmtp" 5 Unix domain socket that lmtpd listens on. + .IP "\fBdracinterval:\fR 5" 5 + If nonzero, enables the use of DRAC (Dynamic Relay Authorization Control) + by the pop3d and imapd daemons. Also sets the interval (in minutes) between + re-authorization requests made by imapd. + .IP "\fBdrachost:\fR localhost" 5 + Hostname of the dracd server. .SH SEE ALSO .PP \fBimapd(8)\fR, \fBpop3d(8)\fR, \fBlmtpd(8)\fR, \fBtimsieved(8)\fR,