1997-04-16 19:48:30 +00:00
|
|
|
*** sshd.c.orig Sun Apr 6 03:57:00 1997
|
|
|
|
--- sshd.c Wed Apr 16 23:27:28 1997
|
1996-11-12 00:13:38 +00:00
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 379,384 ****
|
|
|
|
--- 379,388 ----
|
1997-03-28 23:30:39 +00:00
|
|
|
#include "firewall.h" /* TIS authsrv authentication */
|
1997-02-27 00:44:35 +00:00
|
|
|
#endif
|
|
|
|
|
|
|
|
+ #ifdef HAVE_LOGIN_CAP_H
|
|
|
|
+ #include <login_cap.h>
|
|
|
|
+ #endif
|
|
|
|
+
|
|
|
|
#ifdef _PATH_BSHELL
|
|
|
|
#define DEFAULT_SHELL _PATH_BSHELL
|
|
|
|
#else
|
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 2617,2622 ****
|
|
|
|
--- 2621,2629 ----
|
|
|
|
struct sockaddr_in from;
|
|
|
|
int fromlen;
|
|
|
|
struct pty_cleanup_context cleanup_context;
|
|
|
|
+ #ifdef HAVE_LOGIN_CAP_H
|
|
|
|
+ login_cap_t *lc;
|
|
|
|
+ #endif
|
|
|
|
|
|
|
|
/* We no longer need the child running on user's privileges. */
|
|
|
|
userfile_uninit();
|
|
|
|
***************
|
|
|
|
*** 2688,2698 ****
|
|
|
|
record_login(pid, ttyname, pw->pw_name, pw->pw_uid, hostname,
|
|
|
|
&from);
|
|
|
|
|
|
|
|
/* Check if .hushlogin exists. Note that we cannot use userfile
|
|
|
|
here because we are in the child. */
|
|
|
|
sprintf(line, "%.200s/.hushlogin", pw->pw_dir);
|
|
|
|
quiet_login = stat(line, &st) >= 0;
|
|
|
|
!
|
|
|
|
/* If the user has logged in before, display the time of last login.
|
|
|
|
However, don't display anything extra if a command has been
|
|
|
|
specified (so that ssh can be used to execute commands on a remote
|
|
|
|
--- 2695,2713 ----
|
|
|
|
record_login(pid, ttyname, pw->pw_name, pw->pw_uid, hostname,
|
|
|
|
&from);
|
|
|
|
|
|
|
|
+ #ifdef HAVE_LOGIN_CAP_H
|
|
|
|
+ lc = login_getclass(pw);
|
|
|
|
+ #endif
|
|
|
|
+
|
|
|
|
/* Check if .hushlogin exists. Note that we cannot use userfile
|
|
|
|
here because we are in the child. */
|
|
|
|
sprintf(line, "%.200s/.hushlogin", pw->pw_dir);
|
|
|
|
quiet_login = stat(line, &st) >= 0;
|
|
|
|
!
|
|
|
|
! #ifdef HAVE_LOGIN_CAP_H
|
|
|
|
! quiet_login = login_getcapbool(lc, "hushlogin", quiet_login);
|
|
|
|
! #endif
|
|
|
|
!
|
|
|
|
/* If the user has logged in before, display the time of last login.
|
|
|
|
However, don't display anything extra if a command has been
|
|
|
|
specified (so that ssh can be used to execute commands on a remote
|
|
|
|
***************
|
|
|
|
*** 2712,2717 ****
|
|
|
|
--- 2727,2755 ----
|
1996-11-12 01:47:39 +00:00
|
|
|
printf("Last login: %s from %s\r\n", time_string, buf);
|
|
|
|
}
|
|
|
|
|
|
|
|
+ #ifdef __FreeBSD__
|
|
|
|
+ if (command == NULL && !quiet_login)
|
|
|
|
+ {
|
1997-04-16 19:48:30 +00:00
|
|
|
+ #ifdef HAVE_LOGIN_CAP_H
|
|
|
|
+ char *cw;
|
|
|
|
+ FILE *f;
|
|
|
|
+
|
|
|
|
+ cw = login_getcapstr(lc, "copyright", NULL, NULL);
|
|
|
|
+ if (cw != NULL && (f = fopen(cw, "r")) != NULL)
|
|
|
|
+ {
|
|
|
|
+ while (fgets(line, sizeof(line), f))
|
|
|
|
+ fputs(line, stdout);
|
|
|
|
+ fclose(f);
|
|
|
|
+ }
|
|
|
|
+ else
|
|
|
|
+ #endif
|
|
|
|
+ printf("%s\n\t%s %s\n\n",
|
1996-11-12 01:47:39 +00:00
|
|
|
+ "Copyright (c) 1980, 1983, 1986, 1988, 1990, 1991, 1993, 1994",
|
1997-04-16 19:48:30 +00:00
|
|
|
+ "The Regents of the University of California. ",
|
|
|
|
+ "All rights reserved.");
|
1996-11-12 01:47:39 +00:00
|
|
|
+ }
|
|
|
|
+ #endif
|
|
|
|
+
|
|
|
|
/* Print /etc/motd unless a command was specified or printing it was
|
|
|
|
disabled in server options. Note that some machines appear to
|
|
|
|
print it in /etc/profile or similar. */
|
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 2721,2727 ****
|
|
|
|
--- 2759,2769 ----
|
|
|
|
FILE *f;
|
|
|
|
|
|
|
|
/* Print /etc/motd if it exists. */
|
|
|
|
+ #ifdef HAVE_LOGIN_CAP_H
|
|
|
|
+ f = fopen(login_getcapstr(lc, "welcome", "/etc/motd", "/etc/motd"), "r");
|
|
|
|
+ #else
|
|
|
|
f = fopen("/etc/motd", "r");
|
|
|
|
+ #endif
|
|
|
|
if (f)
|
|
|
|
{
|
|
|
|
while (fgets(line, sizeof(line), f))
|
|
|
|
***************
|
|
|
|
*** 2729,2734 ****
|
|
|
|
--- 2771,2799 ----
|
1996-11-12 01:47:39 +00:00
|
|
|
fclose(f);
|
|
|
|
}
|
|
|
|
}
|
1996-11-12 00:13:38 +00:00
|
|
|
+ #ifdef __FreeBSD__
|
1996-11-12 01:47:39 +00:00
|
|
|
+ if (command == NULL && !quiet_login)
|
|
|
|
+ {
|
1997-04-16 21:07:36 +00:00
|
|
|
+ #ifdef broken_HAVE_LOGIN_CAP_H
|
1997-04-16 19:48:30 +00:00
|
|
|
+ char *mp = getenv("MAIL");
|
|
|
|
+
|
|
|
|
+ if (mp != NULL)
|
|
|
|
+ {
|
|
|
|
+ strncpy(line, mp, sizeof line);
|
|
|
|
+ line[sizeof line - 1] = '\0';
|
|
|
|
+ }
|
|
|
|
+ else
|
|
|
|
+ #endif
|
1996-11-12 01:47:39 +00:00
|
|
|
+ sprintf(line, "%s/%.200s", _PATH_MAILDIR, pw->pw_name);
|
|
|
|
+ if (stat(line, &st) == 0 && st.st_size != 0)
|
|
|
|
+ printf("You have %smail.\n",
|
|
|
|
+ (st.st_mtime > st.st_atime) ? "new " : "");
|
|
|
|
+ }
|
1997-04-16 19:48:30 +00:00
|
|
|
+ #endif
|
|
|
|
+
|
|
|
|
+ #ifdef HAVE_LOGIN_CAP_H
|
|
|
|
+ login_close(lc);
|
1996-11-12 00:13:38 +00:00
|
|
|
+ #endif
|
|
|
|
|
1996-11-12 01:47:39 +00:00
|
|
|
/* Do common processing for the child, such as execing the command. */
|
|
|
|
do_child(command, pw, term, display, auth_proto, auth_data, ttyname);
|
1997-02-27 00:44:35 +00:00
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 2986,2992 ****
|
1997-02-27 00:44:35 +00:00
|
|
|
char *user_shell;
|
|
|
|
char *remote_ip;
|
|
|
|
int remote_port;
|
|
|
|
!
|
|
|
|
/* Check /etc/nologin. */
|
|
|
|
f = fopen("/etc/nologin", "r");
|
|
|
|
if (f)
|
1997-04-16 19:48:30 +00:00
|
|
|
--- 3051,3063 ----
|
1997-02-27 00:44:35 +00:00
|
|
|
char *user_shell;
|
|
|
|
char *remote_ip;
|
|
|
|
int remote_port;
|
|
|
|
! #ifdef HAVE_LOGIN_CAP_H
|
|
|
|
! login_cap_t *lc;
|
|
|
|
! char *real_shell;
|
|
|
|
!
|
|
|
|
! lc = login_getuserclass(pw);
|
|
|
|
! auth_checknologin(lc);
|
|
|
|
! #else /* !HAVE_LOGIN_CAP_H */
|
|
|
|
/* Check /etc/nologin. */
|
|
|
|
f = fopen("/etc/nologin", "r");
|
|
|
|
if (f)
|
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 3000,3005 ****
|
|
|
|
--- 3071,3077 ----
|
1997-03-28 23:30:39 +00:00
|
|
|
if (pw->pw_uid != UID_ROOT)
|
1997-02-27 00:44:35 +00:00
|
|
|
exit(254);
|
|
|
|
}
|
|
|
|
+ #endif /* HAVE_LOGIN_CAP_H */
|
|
|
|
|
|
|
|
if (command != NULL)
|
|
|
|
{
|
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 3012,3018 ****
|
1997-02-27 00:44:35 +00:00
|
|
|
else
|
|
|
|
log_msg("executing remote command as user %.200s", pw->pw_name);
|
|
|
|
}
|
|
|
|
!
|
|
|
|
#ifdef HAVE_SETLOGIN
|
|
|
|
/* Set login name in the kernel. Warning: setsid() must be called before
|
|
|
|
this. */
|
1997-04-16 19:48:30 +00:00
|
|
|
--- 3084,3091 ----
|
1997-02-27 00:44:35 +00:00
|
|
|
else
|
|
|
|
log_msg("executing remote command as user %.200s", pw->pw_name);
|
|
|
|
}
|
|
|
|
!
|
|
|
|
! #ifndef HAVE_LOGIN_CAP_H
|
|
|
|
#ifdef HAVE_SETLOGIN
|
|
|
|
/* Set login name in the kernel. Warning: setsid() must be called before
|
|
|
|
this. */
|
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 3033,3038 ****
|
|
|
|
--- 3106,3112 ----
|
1997-02-27 00:44:35 +00:00
|
|
|
if (setpcred((char *)pw->pw_name, NULL))
|
|
|
|
log_msg("setpcred %.100s: %.100s", strerror(errno));
|
|
|
|
#endif /* HAVE_USERSEC_H */
|
1997-03-28 23:30:39 +00:00
|
|
|
+ #endif /* !HAVE_LOGIN_CAP_H */
|
1997-02-27 00:44:35 +00:00
|
|
|
|
|
|
|
/* Save some data that will be needed so that we can do certain cleanups
|
|
|
|
before we switch to user's uid. (We must clear all sensitive data
|
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 3103,3108 ****
|
|
|
|
--- 3177,3240 ----
|
1997-03-28 23:30:39 +00:00
|
|
|
if (command != NULL || !options.use_login)
|
|
|
|
#endif /* USELOGIN */
|
|
|
|
{
|
1997-02-27 00:44:35 +00:00
|
|
|
+ #ifdef HAVE_LOGIN_CAP_H
|
1997-03-28 23:30:39 +00:00
|
|
|
+ char *p, *s, **tmpenv;
|
1997-02-27 00:44:35 +00:00
|
|
|
+
|
1997-03-28 23:30:39 +00:00
|
|
|
+ /* Save previous environment array
|
|
|
|
+ */
|
|
|
|
+ tmpenv = environ;
|
|
|
|
+ /* Initialize the new environment.
|
|
|
|
+ */
|
|
|
|
+ envsize = 64;
|
|
|
|
+ environ = env = xmalloc(envsize * sizeof(char *));
|
|
|
|
+ env[0] = NULL;
|
1997-02-27 00:44:35 +00:00
|
|
|
+
|
1997-03-28 23:30:39 +00:00
|
|
|
+ child_set_env(&env, &envsize, "PATH", DEFAULT_PATH);
|
1997-02-27 00:44:35 +00:00
|
|
|
+
|
|
|
|
+ #ifdef MAIL_SPOOL_DIRECTORY
|
1997-03-28 23:30:39 +00:00
|
|
|
+ sprintf(buf, "%.200s/%.50s", MAIL_SPOOL_DIRECTORY, user_name);
|
|
|
|
+ child_set_env(&env, &envsize, "MAIL", buf);
|
1997-02-27 00:44:35 +00:00
|
|
|
+ #else /* MAIL_SPOOL_DIRECTORY */
|
|
|
|
+ #ifdef MAIL_SPOOL_FILE
|
1997-03-28 23:30:39 +00:00
|
|
|
+ sprintf(buf, "%.200s/%.50s", user_dir, MAIL_SPOOL_FILE);
|
|
|
|
+ child_set_env(&env, &envsize, "MAIL", buf);
|
1997-02-27 00:44:35 +00:00
|
|
|
+ #endif /* MAIL_SPOOL_FILE */
|
|
|
|
+ #endif /* MAIL_SPOOL_DIRECTORY */
|
|
|
|
+
|
1997-03-28 23:30:39 +00:00
|
|
|
+ /* Let it inherit timezone if we have one. */
|
|
|
|
+ if (getenv("TZ"))
|
|
|
|
+ child_set_env(&env, &envsize, "TZ", getenv("TZ"));
|
|
|
|
+
|
|
|
|
+ /* Set the user's login environment
|
|
|
|
+ */
|
|
|
|
+ if (setusercontext(lc, pw, user_uid, LOGIN_SETALL) < 0)
|
|
|
|
+ {
|
|
|
|
+ perror("setusercontext");
|
|
|
|
+ exit(1);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ p = getenv("PATH");
|
|
|
|
+ s = xmalloc((p != NULL ? strlen(p) + 1 : 0) + sizeof(SSH_BINDIR));
|
|
|
|
+ *s = '\0';
|
|
|
|
+ if (p != NULL)
|
|
|
|
+ {
|
|
|
|
+ strcat(s, p);
|
|
|
|
+ strcat(s, ":");
|
|
|
|
+ }
|
|
|
|
+ strcat(s, SSH_BINDIR);
|
|
|
|
+
|
|
|
|
+ env = environ;
|
|
|
|
+ environ = tmpenv; /* Restore parent environment */
|
|
|
|
+ for (envsize = 0; env[envsize] != NULL; ++envsize)
|
|
|
|
+ ;
|
|
|
|
+ /* Reallocate this to what is expected */
|
|
|
|
+ envsize = (envsize < 100) ? 100 : envsize + 16;
|
|
|
|
+ env = xrealloc(env, envsize * sizeof(char *));
|
|
|
|
+
|
|
|
|
+ child_set_env(&env, &envsize, "PATH", s);
|
|
|
|
+ xfree(s);
|
|
|
|
+
|
1997-02-27 00:44:35 +00:00
|
|
|
+ #else /* !HAVE_LOGIN_CAP_H */
|
1997-03-28 23:30:39 +00:00
|
|
|
/* Set uid, gid, and groups. */
|
|
|
|
if (getuid() == UID_ROOT || geteuid() == UID_ROOT)
|
|
|
|
{
|
1997-02-27 00:44:35 +00:00
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 3134,3139 ****
|
|
|
|
--- 3266,3272 ----
|
1997-03-28 23:30:39 +00:00
|
|
|
|
|
|
|
if (getuid() != user_uid || geteuid() != user_uid)
|
|
|
|
fatal("Failed to set uids to %d.", (int)user_uid);
|
1997-02-27 00:44:35 +00:00
|
|
|
+ #endif /* HAVE_LOGIN_CAP_H */
|
1997-03-28 23:30:39 +00:00
|
|
|
}
|
|
|
|
|
1997-02-27 00:44:35 +00:00
|
|
|
/* Reset signals to their default settings before starting the user
|
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 3144,3154 ****
|
|
|
|
--- 3277,3292 ----
|
1997-02-27 00:44:35 +00:00
|
|
|
and means /bin/sh. */
|
|
|
|
shell = (user_shell[0] == '\0') ? DEFAULT_SHELL : user_shell;
|
|
|
|
|
|
|
|
+ #ifdef HAVE_LOGIN_CAP_H
|
|
|
|
+ real_shell = login_getcapstr(lc, "shell", (char*)shell, (char*)shell);
|
1997-03-28 23:30:39 +00:00
|
|
|
+ login_close(lc);
|
1997-02-27 00:44:35 +00:00
|
|
|
+ #else /* !HAVE_LOGIN_CAP_H */
|
|
|
|
/* Initialize the environment. In the first part we allocate space for
|
|
|
|
all environment variables. */
|
|
|
|
envsize = 100;
|
|
|
|
env = xmalloc(envsize * sizeof(char *));
|
|
|
|
env[0] = NULL;
|
|
|
|
+ #endif /* HAVE_LOGIN_CAP_H */
|
|
|
|
|
1997-03-28 23:30:39 +00:00
|
|
|
#ifdef USELOGIN
|
|
|
|
if (command != NULL || !options.use_login)
|
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 3158,3163 ****
|
|
|
|
--- 3296,3303 ----
|
1997-03-28 23:30:39 +00:00
|
|
|
child_set_env(&env, &envsize, "HOME", user_dir);
|
|
|
|
child_set_env(&env, &envsize, "USER", user_name);
|
|
|
|
child_set_env(&env, &envsize, "LOGNAME", user_name);
|
1997-02-27 00:44:35 +00:00
|
|
|
+
|
1997-03-28 23:30:39 +00:00
|
|
|
+ #ifndef HAVE_LOGIN_CAP_H
|
|
|
|
child_set_env(&env, &envsize, "PATH", DEFAULT_PATH ":" SSH_BINDIR);
|
|
|
|
|
|
|
|
#ifdef MAIL_SPOOL_DIRECTORY
|
1997-02-27 00:44:35 +00:00
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 3169,3174 ****
|
|
|
|
--- 3309,3315 ----
|
1997-03-28 23:30:39 +00:00
|
|
|
child_set_env(&env, &envsize, "MAIL", buf);
|
1997-02-27 00:44:35 +00:00
|
|
|
#endif /* MAIL_SPOOL_FILE */
|
|
|
|
#endif /* MAIL_SPOOL_DIRECTORY */
|
1997-03-28 23:30:39 +00:00
|
|
|
+ #endif /* !HAVE_LOGIN_CAP_H */
|
|
|
|
|
1997-02-27 00:44:35 +00:00
|
|
|
#ifdef HAVE_ETC_DEFAULT_LOGIN
|
1997-03-28 23:30:39 +00:00
|
|
|
/* Read /etc/default/login; this exists at least on Solaris 2.x. Note
|
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 3184,3192 ****
|
|
|
|
--- 3325,3335 ----
|
1997-03-28 23:30:39 +00:00
|
|
|
child_set_env(&env, &envsize, "SSH_ORIGINAL_COMMAND",
|
|
|
|
original_command);
|
|
|
|
|
|
|
|
+ #ifndef HAVE_LOGIN_CAP_H
|
|
|
|
/* Let it inherit timezone if we have one. */
|
|
|
|
if (getenv("TZ"))
|
|
|
|
child_set_env(&env, &envsize, "TZ", getenv("TZ"));
|
|
|
|
+ #endif /* !HAVE_LOGIN_CAP_H */
|
|
|
|
|
|
|
|
/* Set custom environment options from RSA authentication. */
|
|
|
|
while (custom_environment)
|
1997-02-27 00:44:35 +00:00
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 3406,3412 ****
|
|
|
|
--- 3549,3559 ----
|
1997-03-28 23:30:39 +00:00
|
|
|
/* Execute the shell. */
|
|
|
|
argv[0] = buf;
|
|
|
|
argv[1] = NULL;
|
1997-02-27 00:44:35 +00:00
|
|
|
+ #ifdef HAVE_LOGIN_CAP_H
|
1997-03-28 23:30:39 +00:00
|
|
|
+ execve(real_shell, argv, env);
|
1997-02-27 00:44:35 +00:00
|
|
|
+ #else
|
1997-03-28 23:30:39 +00:00
|
|
|
execve(shell, argv, env);
|
1997-02-27 00:44:35 +00:00
|
|
|
+ #endif /* HAVE_LOGIN_CAP_H */
|
1997-03-28 23:30:39 +00:00
|
|
|
/* Executing the shell failed. */
|
|
|
|
perror(shell);
|
|
|
|
exit(1);
|
1997-02-27 00:44:35 +00:00
|
|
|
***************
|
1997-04-16 19:48:30 +00:00
|
|
|
*** 3427,3433 ****
|
|
|
|
--- 3574,3584 ----
|
1997-02-27 00:44:35 +00:00
|
|
|
argv[1] = "-c";
|
|
|
|
argv[2] = (char *)command;
|
|
|
|
argv[3] = NULL;
|
|
|
|
+ #ifdef HAVE_LOGIN_CAP_H
|
|
|
|
+ execve(real_shell, argv, env);
|
|
|
|
+ #else
|
|
|
|
execve(shell, argv, env);
|
|
|
|
+ #endif /* HAVE_LOGIN_CAP_H */
|
|
|
|
perror(shell);
|
|
|
|
exit(1);
|
|
|
|
}
|