- (dtucker) [auth-pam.c auth-pam.h session.c] Make PAM use the new static
   cleanup functions.  With & ok djm@
diff --git a/ChangeLog b/ChangeLog
index ae55bf6..9ae28db 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,7 @@
 20031007
  - (djm) Delete autom4te.cache after autoreconf
+ - (dtucker) [auth-pam.c auth-pam.h session.c] Make PAM use the new static
+   cleanup functions.  With & ok djm@
 
 20031003
  - OpenBSD CVS Sync
@@ -1282,4 +1284,4 @@
  - Fix sshd BindAddress and -b options for systems using fake-getaddrinfo.
    Report from murple@murple.net, diagnosis from dtucker@zip.com.au
 
-$Id: ChangeLog,v 1.3057 2003/10/07 00:18:22 djm Exp $
+$Id: ChangeLog,v 1.3058 2003/10/07 01:30:15 dtucker Exp $
diff --git a/auth-pam.c b/auth-pam.c
index 75e2d16..f5f030f 100644
--- a/auth-pam.c
+++ b/auth-pam.c
@@ -31,7 +31,7 @@
 
 /* Based on $FreeBSD: src/crypto/openssh/auth2-pam-freebsd.c,v 1.11 2003/03/31 13:48:18 des Exp $ */
 #include "includes.h"
-RCSID("$Id: auth-pam.c,v 1.74 2003/09/23 12:12:38 djm Exp $");
+RCSID("$Id: auth-pam.c,v 1.75 2003/10/07 01:30:16 dtucker Exp $");
 
 #ifdef USE_PAM
 #include <security/pam_appl.h>
@@ -126,6 +126,7 @@
 };
 
 static void sshpam_free_ctx(void *);
+static struct pam_ctxt *cleanup_ctxt;
 
 /*
  * Conversation function for authentication thread.
@@ -245,15 +246,19 @@
 	return (NULL); /* Avoid warning for non-pthread case */
 }
 
-static void
-sshpam_thread_cleanup(void *ctxtp)
+void
+sshpam_thread_cleanup(void)
 {
-	struct pam_ctxt *ctxt = ctxtp;
+	struct pam_ctxt *ctxt = cleanup_ctxt;
 
-	pthread_cancel(ctxt->pam_thread);
-	pthread_join(ctxt->pam_thread, NULL);
-	close(ctxt->pam_psock);
-	close(ctxt->pam_csock);
+	if (ctxt != NULL && ctxt->pam_thread != 0) {
+		pthread_cancel(ctxt->pam_thread);
+		pthread_join(ctxt->pam_thread, NULL);
+		close(ctxt->pam_psock);
+		close(ctxt->pam_csock);
+		memset(ctxt, 0, sizeof(*ctxt));
+		cleanup_ctxt = NULL;
+	}
 }
 
 static int
@@ -265,10 +270,9 @@
 
 static struct pam_conv null_conv = { sshpam_null_conv, NULL };
 
-static void
-sshpam_cleanup(void *arg)
+void
+sshpam_cleanup(void)
 {
-	(void)arg;
 	debug("PAM: cleanup");
 	if (sshpam_handle == NULL)
 		return;
@@ -299,7 +303,6 @@
 		    PAM_USER, (const void **)&pam_user);
 		if (sshpam_err == PAM_SUCCESS && strcmp(user, pam_user) == 0)
 			return (0);
-		fatal_remove_cleanup(sshpam_cleanup, NULL);
 		pam_end(sshpam_handle, sshpam_err);
 		sshpam_handle = NULL;
 	}
@@ -333,7 +336,6 @@
 		return (-1);
 	}
 #endif
-	fatal_add_cleanup(sshpam_cleanup, NULL);
 	return (0);
 }
 
@@ -354,7 +356,7 @@
 	}
 
 	ctxt = xmalloc(sizeof *ctxt);
-	ctxt->pam_done = 0;
+	memset(ctxt, 0, sizeof(*ctxt));
 
 	/* Start the authentication thread */
 	if (socketpair(AF_UNIX, SOCK_STREAM, PF_UNSPEC, socks) == -1) {
@@ -372,7 +374,7 @@
 		xfree(ctxt);
 		return (NULL);
 	}
-	fatal_add_cleanup(sshpam_thread_cleanup, ctxt);
+	cleanup_ctxt = ctxt;
 	return (ctxt);
 }
 
@@ -481,8 +483,7 @@
 {
 	struct pam_ctxt *ctxt = ctxtp;
 
-	fatal_remove_cleanup(sshpam_thread_cleanup, ctxt);
-	sshpam_thread_cleanup(ctxtp);
+	sshpam_thread_cleanup();
 	xfree(ctxt);
 	/*
 	 * We don't call sshpam_cleanup() here because we may need the PAM
@@ -524,8 +525,7 @@
 void
 finish_pam(void)
 {
-	fatal_remove_cleanup(sshpam_cleanup, NULL);
-	sshpam_cleanup(NULL);
+	sshpam_cleanup();
 }
 
 u_int
diff --git a/auth-pam.h b/auth-pam.h
index 5c952f3..58176f0 100644
--- a/auth-pam.h
+++ b/auth-pam.h
@@ -1,4 +1,4 @@
-/* $Id: auth-pam.h,v 1.21 2003/09/02 13:18:53 djm Exp $ */
+/* $Id: auth-pam.h,v 1.22 2003/10/07 01:30:16 dtucker Exp $ */
 
 /*
  * Copyright (c) 2000 Damien Miller.  All rights reserved.
@@ -43,5 +43,7 @@
 void print_pam_messages(void);
 char ** fetch_pam_environment(void);
 void free_pam_environment(char **);
+void sshpam_thread_cleanup(void);
+void sshpam_cleanup(void);
 
 #endif /* USE_PAM */
diff --git a/session.c b/session.c
index ccdc424..8aa2b90 100644
--- a/session.c
+++ b/session.c
@@ -2165,6 +2165,13 @@
 		ssh_gssapi_cleanup_creds();
 #endif
 
+#ifdef USE_PAM
+	if (options.use_pam) {
+		sshpam_cleanup();
+		sshpam_thread_cleanup();
+	}
+#endif
+
 	/* remove agent socket */
 	auth_sock_cleanup_proc(authctxt->pw);