summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDamien Miller <djm@mindrot.org>2003-11-17 21:41:42 +1100
committerDamien Miller <djm@mindrot.org>2003-11-17 21:41:42 +1100
commitc756e9b56e5b4649f120c417eb9bc99cf23db10f (patch)
tree70e3a7e326bddd3b46ebe457026e4f842bc3e7f9
parent9bdba70350919fced9ecdf5ca8a3709d22d69797 (diff)
- (djm) Export environment variables from authentication subprocess to
parent. Part of Bug #717
-rw-r--r--ChangeLog4
-rw-r--r--auth-pam.c83
-rw-r--r--auth-pam.h3
-rw-r--r--session.c7
4 files changed, 87 insertions, 10 deletions
diff --git a/ChangeLog b/ChangeLog
index b850f42dd..bec42ac50 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -45,6 +45,8 @@
45 return error on msg send/receive failure (rather than fatal); ok markus@ 45 return error on msg send/receive failure (rather than fatal); ok markus@
46 - (djm) Bug #632: Don't call pam_end indirectly from within kbd-int 46 - (djm) Bug #632: Don't call pam_end indirectly from within kbd-int
47 conversation function 47 conversation function
48 - (djm) Export environment variables from authentication subprocess to
49 parent. Part of Bug #717
48 50
4920031115 5120031115
50 - (dtucker) [regress/agent-ptrace.sh] Test for GDB output from Solaris and 52 - (dtucker) [regress/agent-ptrace.sh] Test for GDB output from Solaris and
@@ -1465,4 +1467,4 @@
1465 - Fix sshd BindAddress and -b options for systems using fake-getaddrinfo. 1467 - Fix sshd BindAddress and -b options for systems using fake-getaddrinfo.
1466 Report from murple@murple.net, diagnosis from dtucker@zip.com.au 1468 Report from murple@murple.net, diagnosis from dtucker@zip.com.au
1467 1469
1468$Id: ChangeLog,v 1.3110 2003/11/17 10:27:55 djm Exp $ 1470$Id: ChangeLog,v 1.3111 2003/11/17 10:41:42 djm Exp $
diff --git a/auth-pam.c b/auth-pam.c
index 4d2f9c597..92a3da406 100644
--- a/auth-pam.c
+++ b/auth-pam.c
@@ -31,7 +31,7 @@
31 31
32/* Based on $FreeBSD: src/crypto/openssh/auth2-pam-freebsd.c,v 1.11 2003/03/31 13:48:18 des Exp $ */ 32/* Based on $FreeBSD: src/crypto/openssh/auth2-pam-freebsd.c,v 1.11 2003/03/31 13:48:18 des Exp $ */
33#include "includes.h" 33#include "includes.h"
34RCSID("$Id: auth-pam.c,v 1.79 2003/11/17 10:27:55 djm Exp $"); 34RCSID("$Id: auth-pam.c,v 1.80 2003/11/17 10:41:42 djm Exp $");
35 35
36#ifdef USE_PAM 36#ifdef USE_PAM
37#include <security/pam_appl.h> 37#include <security/pam_appl.h>
@@ -117,6 +117,7 @@ static int sshpam_authenticated = 0;
117static int sshpam_new_authtok_reqd = 0; 117static int sshpam_new_authtok_reqd = 0;
118static int sshpam_session_open = 0; 118static int sshpam_session_open = 0;
119static int sshpam_cred_established = 0; 119static int sshpam_cred_established = 0;
120static char **sshpam_env = NULL;
120 121
121struct pam_ctxt { 122struct pam_ctxt {
122 sp_pthread_t pam_thread; 123 sp_pthread_t pam_thread;
@@ -128,6 +129,51 @@ struct pam_ctxt {
128static void sshpam_free_ctx(void *); 129static void sshpam_free_ctx(void *);
129static struct pam_ctxt *cleanup_ctxt; 130static struct pam_ctxt *cleanup_ctxt;
130 131
132/* Some PAM implementations don't implement this */
133#ifndef HAVE_PAM_GETENVLIST
134static char **
135pam_getenvlist(pam_handle_t *pamh)
136{
137 /*
138 * XXX - If necessary, we can still support envrionment passing
139 * for platforms without pam_getenvlist by searching for known
140 * env vars (e.g. KRB5CCNAME) from the PAM environment.
141 */
142 return NULL;
143}
144#endif
145
146/* Import regular and PAM environment from subprocess */
147static void
148import_environments(Buffer *b)
149{
150 char *env;
151 u_int i, num_env;
152 int err;
153
154 /* Import environment from subprocess */
155 num_env = buffer_get_int(b);
156 sshpam_env = xmalloc((num_env + 1) * sizeof(*sshpam_env));
157 debug3("PAM: num env strings %d", num_env);
158 for(i = 0; i < num_env; i++)
159 sshpam_env[i] = buffer_get_string(b, NULL);
160
161 sshpam_env[num_env] = NULL;
162
163 /* Import PAM environment from subprocess */
164 num_env = buffer_get_int(b);
165 debug("PAM: num PAM env strings %d", num_env);
166 for(i = 0; i < num_env; i++) {
167 env = buffer_get_string(b, NULL);
168
169 /* Errors are not fatal here */
170 if ((err = pam_putenv(sshpam_handle, env)) != PAM_SUCCESS) {
171 error("PAM: pam_putenv: %s",
172 pam_strerror(sshpam_handle, sshpam_err));
173 }
174 }
175}
176
131/* 177/*
132 * Conversation function for authentication thread. 178 * Conversation function for authentication thread.
133 */ 179 */
@@ -220,10 +266,14 @@ sshpam_thread(void *ctxtp)
220 Buffer buffer; 266 Buffer buffer;
221 struct pam_conv sshpam_conv; 267 struct pam_conv sshpam_conv;
222#ifndef USE_POSIX_THREADS 268#ifndef USE_POSIX_THREADS
269 extern char **environ;
270 char **env_from_pam;
271 u_int i;
223 const char *pam_user; 272 const char *pam_user;
224 273
225 pam_get_item(sshpam_handle, PAM_USER, (const void **)&pam_user); 274 pam_get_item(sshpam_handle, PAM_USER, (const void **)&pam_user);
226 setproctitle("%s [pam]", pam_user); 275 setproctitle("%s [pam]", pam_user);
276 environ[0] = NULL;
227#endif 277#endif
228 278
229 sshpam_conv.conv = sshpam_thread_conv; 279 sshpam_conv.conv = sshpam_thread_conv;
@@ -238,6 +288,24 @@ sshpam_thread(void *ctxtp)
238 if (sshpam_err != PAM_SUCCESS) 288 if (sshpam_err != PAM_SUCCESS)
239 goto auth_fail; 289 goto auth_fail;
240 buffer_put_cstring(&buffer, "OK"); 290 buffer_put_cstring(&buffer, "OK");
291
292#ifndef USE_POSIX_THREADS
293 /* Export any environment strings set in child */
294 for(i = 0; environ[i] != NULL; i++)
295 ; /* Count */
296 buffer_put_int(&buffer, i);
297 for(i = 0; environ[i] != NULL; i++)
298 buffer_put_cstring(&buffer, environ[i]);
299
300 /* Export any environment strings set by PAM in child */
301 env_from_pam = pam_getenvlist(sshpam_handle);
302 for(i = 0; env_from_pam != NULL && env_from_pam[i] != NULL; i++)
303 ; /* Count */
304 buffer_put_int(&buffer, i);
305 for(i = 0; env_from_pam != NULL && env_from_pam[i] != NULL; i++)
306 buffer_put_cstring(&buffer, env_from_pam[i]);
307#endif /* USE_POSIX_THREADS */
308
241 /* XXX - can't do much about an error here */ 309 /* XXX - can't do much about an error here */
242 ssh_msg_send(ctxt->pam_csock, sshpam_err, &buffer); 310 ssh_msg_send(ctxt->pam_csock, sshpam_err, &buffer);
243 buffer_free(&buffer); 311 buffer_free(&buffer);
@@ -440,6 +508,7 @@ sshpam_query(void *ctx, char **name, char **info,
440 **prompts = NULL; 508 **prompts = NULL;
441 } 509 }
442 if (type == PAM_SUCCESS) { 510 if (type == PAM_SUCCESS) {
511 import_environments(&buffer);
443 *num = 0; 512 *num = 0;
444 **echo_on = 0; 513 **echo_on = 0;
445 ctxt->pam_done = 1; 514 ctxt->pam_done = 1;
@@ -704,7 +773,6 @@ do_pam_chauthtok(void)
704 * modules can handle things like Kerberos/GSI credentials that appear 773 * modules can handle things like Kerberos/GSI credentials that appear
705 * during the ssh authentication process. 774 * during the ssh authentication process.
706 */ 775 */
707
708int 776int
709do_pam_putenv(char *name, char *value) 777do_pam_putenv(char *name, char *value)
710{ 778{
@@ -731,14 +799,15 @@ print_pam_messages(void)
731} 799}
732 800
733char ** 801char **
802fetch_pam_child_environment(void)
803{
804 return sshpam_env;
805}
806
807char **
734fetch_pam_environment(void) 808fetch_pam_environment(void)
735{ 809{
736#ifdef HAVE_PAM_GETENVLIST
737 debug("PAM: retrieving environment");
738 return (pam_getenvlist(sshpam_handle)); 810 return (pam_getenvlist(sshpam_handle));
739#else
740 return (NULL);
741#endif
742} 811}
743 812
744void 813void
diff --git a/auth-pam.h b/auth-pam.h
index 58176f013..fd62e9534 100644
--- a/auth-pam.h
+++ b/auth-pam.h
@@ -1,4 +1,4 @@
1/* $Id: auth-pam.h,v 1.22 2003/10/07 01:30:16 dtucker Exp $ */ 1/* $Id: auth-pam.h,v 1.23 2003/11/17 10:41:42 djm Exp $ */
2 2
3/* 3/*
4 * Copyright (c) 2000 Damien Miller. All rights reserved. 4 * Copyright (c) 2000 Damien Miller. All rights reserved.
@@ -42,6 +42,7 @@ void do_pam_chauthtok(void);
42int do_pam_putenv(char *, char *); 42int do_pam_putenv(char *, char *);
43void print_pam_messages(void); 43void print_pam_messages(void);
44char ** fetch_pam_environment(void); 44char ** fetch_pam_environment(void);
45char ** fetch_pam_child_environment(void);
45void free_pam_environment(char **); 46void free_pam_environment(char **);
46void sshpam_thread_cleanup(void); 47void sshpam_thread_cleanup(void);
47void sshpam_cleanup(void); 48void sshpam_cleanup(void);
diff --git a/session.c b/session.c
index 0f8032430..b1e6255f4 100644
--- a/session.c
+++ b/session.c
@@ -1095,8 +1095,13 @@ do_setup_env(Session *s, const char *shell)
1095 * been set by PAM. 1095 * been set by PAM.
1096 */ 1096 */
1097 if (options.use_pam) { 1097 if (options.use_pam) {
1098 char **p = fetch_pam_environment(); 1098 char **p;
1099
1100 p = fetch_pam_child_environment();
1101 copy_environment(p, &env, &envsize);
1102 free_pam_environment(p);
1099 1103
1104 p = fetch_pam_environment();
1100 copy_environment(p, &env, &envsize); 1105 copy_environment(p, &env, &envsize);
1101 free_pam_environment(p); 1106 free_pam_environment(p);
1102 } 1107 }