From: nekral-guest Date: Mon, 13 Jun 2011 18:25:57 +0000 (+0000) Subject: * src/su.c: Move definition of change_environment and shellstr X-Git-Tag: 4.1.5~197 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=2f71935616b332b3841b07e0044c4b907c720893;p=shadow * src/su.c: Move definition of change_environment and shellstr after the switch to the final subsystem. The previous architecture forced to always change the environment (the shell starts with a '*' and was thus restricted, and change_environment could not be reset to false). --- diff --git a/ChangeLog b/ChangeLog index 7a46c87b..28c6c9f2 100644 --- a/ChangeLog +++ b/ChangeLog @@ -4,8 +4,13 @@ definition of shellstr, PATH and IFS is not influenced (getenv, getdef, restricted_shell) by and does not influence (addenv does not change environ) the authentication. And the authentication - does not overwrite those definitions. This will ease an extraction + did not overwrite those definitions. This will ease an extraction from the big main() function. + * src/su.c: Move definition of change_environment and shellstr + after the switch to the final subsystem. The previous architecture + forced to always change the environment (the shell starts with a + '*' and was thus restricted, and change_environment could not be + reset to false). * src/su.c: No need to change the user's shell in case of subsystem root. Update the comments. diff --git a/src/su.c b/src/su.c index 118cdd05..c4b5ccbd 100644 --- a/src/su.c +++ b/src/su.c @@ -652,116 +652,6 @@ int main (int argc, char **argv) #endif /* !USE_PAM */ pwent = *pw; - /* If su is not called by root, and the target user has a restricted - * shell, the environment must be changed. - */ - change_environment |= (restricted_shell (pwent.pw_shell) && !amroot); - - /* - * If a new login is being set up, the old environment will be - * ignored and a new one created later on. - * (note: in the case of a subsystem, the shell will be restricted, - * and this won't be executed on the first pass) - */ - if (change_environment && fakelogin) { - /* - * The terminal type will be left alone if it is present in - * the environment already. - */ - cp = getenv ("TERM"); - if (NULL != cp) { - addenv ("TERM", cp); - } - - /* - * For some terminals COLORTERM seems to be the only way - * for checking for that specific terminal. For instance, - * gnome-terminal sets its TERM as "xterm" but its - * COLORTERM as "gnome-terminal". The COLORTERM variable - * is also of use when running GNU screen since it sets - * TERM to "screen" but doesn't touch COLORTERM. - */ - cp = getenv ("COLORTERM"); - if (NULL != cp) { - addenv ("COLORTERM", cp); - } - -#ifndef USE_PAM - cp = getdef_str ("ENV_TZ"); - if (NULL != cp) { - addenv (('/' == *cp) ? tz (cp) : cp, NULL); - } - - /* - * The clock frequency will be reset to the login value if required - */ - cp = getdef_str ("ENV_HZ"); - if (NULL != cp) { - addenv (cp, NULL); /* set the default $HZ, if one */ - } -#endif /* !USE_PAM */ - - /* - * Also leave DISPLAY and XAUTHORITY if present, else - * pam_xauth will not work. - */ - cp = getenv ("DISPLAY"); - if (NULL != cp) { - addenv ("DISPLAY", cp); - } - cp = getenv ("XAUTHORITY"); - if (NULL != cp) { - addenv ("XAUTHORITY", cp); - } - } else { - while (NULL != *envp) { - addenv (*envp, NULL); - envp++; - } - } - - /* If the user do not want to change the environment, - * use the current SHELL. - * (unless another shell is required by the command line) - */ - if ((NULL == shellstr) && !change_environment) { - shellstr = getenv ("SHELL"); - } - /* For users with non null UID, if this user has a restricted - * shell, the shell must be the one specified in /etc/passwd - */ - if ( (NULL != shellstr) - && !amroot - && restricted_shell (pwent.pw_shell)) { - shellstr = NULL; - } - /* If the shell is not set at this time, use the shell specified - * in /etc/passwd. - */ - if (NULL == shellstr) { - shellstr = (char *) strdup (pwent.pw_shell); - } - - /* - * Set the default shell. - */ - if ((NULL == shellstr) || ('\0' == shellstr[0])) { - shellstr = SHELL; - } - - cp = getdef_str ((pwent.pw_uid == 0) ? "ENV_SUPATH" : "ENV_PATH"); - if (NULL == cp) { - addenv ((pwent.pw_uid == 0) ? "PATH=/sbin:/bin:/usr/sbin:/usr/bin" : "PATH=/bin:/usr/bin", NULL); - } else if (strchr (cp, '=') != NULL) { - addenv (cp, NULL); - } else { - addenv ("PATH", cp); - } - - if (getenv ("IFS") != NULL) { /* don't export user IFS ... */ - addenv ("IFS= \t\n", NULL); /* ... instead, set a safe IFS */ - } - #ifndef USE_PAM /* * BSD systems only allow "wheel" to SU to root. USG systems don't, @@ -914,6 +804,114 @@ int main (int argc, char **argv) goto top; /* authenticate in the subsystem */ } + /* If su is not called by root, and the target user has a restricted + * shell, the environment must be changed. + */ + change_environment |= (restricted_shell (pwent.pw_shell) && !amroot); + + /* + * If a new login is being set up, the old environment will be + * ignored and a new one created later on. + */ + if (change_environment && fakelogin) { + /* + * The terminal type will be left alone if it is present in + * the environment already. + */ + cp = getenv ("TERM"); + if (NULL != cp) { + addenv ("TERM", cp); + } + + /* + * For some terminals COLORTERM seems to be the only way + * for checking for that specific terminal. For instance, + * gnome-terminal sets its TERM as "xterm" but its + * COLORTERM as "gnome-terminal". The COLORTERM variable + * is also of use when running GNU screen since it sets + * TERM to "screen" but doesn't touch COLORTERM. + */ + cp = getenv ("COLORTERM"); + if (NULL != cp) { + addenv ("COLORTERM", cp); + } + +#ifndef USE_PAM + cp = getdef_str ("ENV_TZ"); + if (NULL != cp) { + addenv (('/' == *cp) ? tz (cp) : cp, NULL); + } + + /* + * The clock frequency will be reset to the login value if required + */ + cp = getdef_str ("ENV_HZ"); + if (NULL != cp) { + addenv (cp, NULL); /* set the default $HZ, if one */ + } +#endif /* !USE_PAM */ + + /* + * Also leave DISPLAY and XAUTHORITY if present, else + * pam_xauth will not work. + */ + cp = getenv ("DISPLAY"); + if (NULL != cp) { + addenv ("DISPLAY", cp); + } + cp = getenv ("XAUTHORITY"); + if (NULL != cp) { + addenv ("XAUTHORITY", cp); + } + } else { + while (NULL != *envp) { + addenv (*envp, NULL); + envp++; + } + } + + /* If the user do not want to change the environment, + * use the current SHELL. + * (unless another shell is required by the command line) + */ + if ((NULL == shellstr) && !change_environment) { + shellstr = getenv ("SHELL"); + } + /* For users with non null UID, if this user has a restricted + * shell, the shell must be the one specified in /etc/passwd + */ + if ( (NULL != shellstr) + && !amroot + && restricted_shell (pwent.pw_shell)) { + shellstr = NULL; + } + /* If the shell is not set at this time, use the shell specified + * in /etc/passwd. + */ + if (NULL == shellstr) { + shellstr = (char *) strdup (pwent.pw_shell); + } + + /* + * Set the default shell. + */ + if ((NULL == shellstr) || ('\0' == shellstr[0])) { + shellstr = SHELL; + } + + cp = getdef_str ((pwent.pw_uid == 0) ? "ENV_SUPATH" : "ENV_PATH"); + if (NULL == cp) { + addenv ((pwent.pw_uid == 0) ? "PATH=/sbin:/bin:/usr/sbin:/usr/bin" : "PATH=/bin:/usr/bin", NULL); + } else if (strchr (cp, '=') != NULL) { + addenv (cp, NULL); + } else { + addenv ("PATH", cp); + } + + if (getenv ("IFS") != NULL) { /* don't export user IFS ... */ + addenv ("IFS= \t\n", NULL); /* ... instead, set a safe IFS */ + } + sulog (tty, true, oldname, name); /* save SU information */ endpwent (); endspent ();