Hi!

I'm using the UW IMAP imapd in my network on a GNU/Linux host, along
with Kerberos authentication, and plaintext passwords using PAM and
the pam_krb5 module.

The pam_krb5 module saves the user's decoded ticket in /tmp upon a
call to pam_setcred. However, imapd deliberately doesn't clean up
these tickets when the user logs out, which leaves /tmp on the mail
server filled up with users' tickets. To remedy this, I patched imapd
and ipop3d to fix this, and so I thought I'd send you a patch in case
you want it. The problem is that I don't really know much about the
portability issues in the UW IMAP suite, so the patch isn't really
complete because of that. I would fix it, but I don't know exactly
how.

Fredrik Tolf

--- ./src/c-client/env.h~	2001-11-20 22:56:35.000000000 +0100
+++ ./src/c-client/env.h	2004-04-18 15:11:48.000000000 +0200
@@ -30,6 +30,7 @@ long server_input_wait (long seconds);
 void server_init (char *server,char *service,char *sasl,
 		  void *clkint,void *kodint,void *hupint,void *trmint);
 long server_login (char *user,char *pass,char *authuser,int argc,char *argv[]);
+void server_logout (void);
 long authserver_login (char *user,char *authuser,int argc,char *argv[]);
 long anonymous_login (int argc,char *argv[]);
 char *mylocalhost (void);
--- ./src/imapd/imapd.c~	2003-07-08 05:21:50.000000000 +0200
+++ ./src/imapd/imapd.c	2004-04-18 15:05:19.068400584 +0200
@@ -1163,6 +1163,7 @@ int main (int argc,char *argv[])
   }
   syslog (LOG_INFO,"Logout user=%.80s host=%.80s",user ? user : "???",
 	  tcp_clienthost ());
+  server_logout();
   exit (0);			/* all done */
   return 0;			/* stupid compilers */
 }
--- ./src/ipopd/ipop3d.c~	2003-01-17 17:49:31.000000000 +0100
+++ ./src/ipopd/ipop3d.c	2004-04-18 15:05:06.451318672 +0200
@@ -463,6 +463,7 @@ int main (int argc,char *argv[])
 	       tcp_clienthost ());
   PSOUT (sayonara);		/* "now it's time to say sayonara..." */
   PFLUSH ();			/* make sure output finished */
+  server_logout();
   exit (0);			/* all done */
   return 0;			/* stupid compilers */
 }
--- ./src/osdep/unix/env_unix.c~	2003-07-15 03:30:00.000000000 +0200
+++ ./src/osdep/unix/env_unix.c	2004-04-18 15:06:34.414946168 +0200
@@ -561,6 +561,11 @@ long server_login (char *user,char *pwd,
   sleep (3);			/* slow down possible cracker */
   return NIL;
 }
+
+void server_logout (void)
+{
+  destroy_cred();
+}
 
 /* Authenticated server log in
  * Accepts: user name string
--- ./src/osdep/unix/env_unix.h~	2002-02-23 05:03:45.000000000 +0100
+++ ./src/osdep/unix/env_unix.h	2004-04-18 15:13:01.000000000 +0200
@@ -91,6 +91,7 @@ void grim_pid_reap_status (int pid,int k
 long safe_write (int fd,char *buf,long nbytes);
 void *arm_signal (int sig,void *action);
 struct passwd *checkpw (struct passwd *pw,char *pass,int argc,char *argv[]);
+void destroy_cred (void);
 long loginpw (struct passwd *pw,int argc,char *argv[]);
 long pw_login (struct passwd *pw,char *auser,char *user,char *home,int argc,
 	       char *argv[]);
--- ./src/osdep/unix/ckp_pam.c~	2002-04-30 04:32:27.000000000 +0200
+++ ./src/osdep/unix/ckp_pam.c	2004-04-18 15:08:37.545227520 +0200
@@ -25,6 +25,8 @@ struct checkpw_cred {
   char *pass;			/* password */
 };
 
+static pam_handle_t *hdl = NULL;
+
 /* PAM conversation function
  * Accepts: number of messages
  *	    vector of messages
@@ -69,7 +71,6 @@ static int checkpw_conv (int num_msg,con
 
 struct passwd *checkpw (struct passwd *pw,char *pass,int argc,char *argv[])
 {
-  pam_handle_t *hdl;
   struct pam_conv conv;
   struct checkpw_cred cred;
   conv.conv = &checkpw_conv;
@@ -100,15 +101,14 @@ struct passwd *checkpw (struct passwd *p
    */
   pam_open_session (hdl,NIL);	/* make sure account doesn't go inactive */
 #endif
-#if 0
-  /*
-   * This is also a problem.  Apparently doing this breaks access to DFS home
-   * space (hence the #if 0), but there is a report that not doing it causes
-   * the credentials to stick around long after the server process is gone.
-   */
-				/* clean up */
-  pam_setcred (hdl,PAM_DELETE_CRED);
-#endif
-  pam_end (hdl,PAM_SUCCESS);	/* return success */
   return pw;
 }
+
+void destroy_cred (void)
+{
+  if(hdl == NULL)
+    return;
+  pam_close_session (hdl,NIL);
+  pam_setcred (hdl,PAM_DELETE_CRED);
+  pam_end (hdl,PAM_SUCCESS);
+}

Reply via email to