Репозиторий Sisyphus
Последнее обновление: 1 октября 2023 | Пакетов: 18631 | Посещений: 37048213
en ru br
Репозитории ALT
S:0.60-alt36
5.1: 0.60-alt26
4.1: 0.60-alt25
4.0: 0.60-alt25
3.0: 0.60-alt22
www.altlinux.org/Changes

Группа :: Система/Основа
Пакет: SimplePAMApps

 Главная   Изменения   Спек   Патчи   Sources   Загрузить   Gear   Bugs and FR  Repocop 

Патч: SimplePAMApps-0.60-owl-alt-su.patch
Скачать


diff -urp SimplePAMApps-0.60.orig/common/include/su_indep.h SimplePAMApps-0.60/common/include/su_indep.h
--- SimplePAMApps-0.60.orig/common/include/su_indep.h	Thu Dec 10 08:46:24 1998
+++ SimplePAMApps-0.60/common/include/su_indep.h	Sun Jan 12 19:24:44 2003
@@ -1,5 +1,11 @@
 #include <unistd.h>
 
+typedef struct
+{
+	const char *user, *command, *shell;
+	int login, fast;
+} su_context;
+
 extern int is_terminal;
 
 void store_terminal_modes();
@@ -12,7 +18,5 @@ void restore_terminal_owner();
 int make_process_unkillable(const char **callname
         , const char **err_descr);
 void make_process_killable();
-void usage();
-void parse_command_line(int argc, char *argv[]
-        , int *is_login, const char **user, const char **command);
+void parse_command_line(int argc, char *argv[], su_context *ctx);
 
diff -urp SimplePAMApps-0.60.orig/common/lib/shell_args.c SimplePAMApps-0.60/common/lib/shell_args.c
--- SimplePAMApps-0.60.orig/common/lib/shell_args.c	Tue Dec  8 17:02:48 1998
+++ SimplePAMApps-0.60/common/lib/shell_args.c	Sun Jan 12 19:24:44 2003
@@ -13,7 +13,7 @@
  * The assumptions used by this code are that a an argument list is
  * returned in the following cases:
  *
- *      1.  login is true [command is always ignored]
+ *      1.  login is true
  *
  *           - the user has a shell entry which is used
  *           - if the user does not have a shell entry NULL is returned
@@ -56,9 +56,6 @@ char * const *build_shell_args(const cha
     const char **args=NULL;             /* array of PATH+ARGS+NULL pointers */
 
     D(("called."));
-    if (login) {
-	command = NULL;                 /* command always ignored for login */
-    }
 
     if (pw_shell && *pw_shell != '\0') {
 	char *line;
diff -urp SimplePAMApps-0.60.orig/common/lib/su_indep.c SimplePAMApps-0.60/common/lib/su_indep.c
--- SimplePAMApps-0.60.orig/common/lib/su_indep.c	Mon Feb  1 08:25:05 1999
+++ SimplePAMApps-0.60/common/lib/su_indep.c	Tue Apr 15 09:37:55 2003
@@ -15,6 +15,8 @@
 #include <stdarg.h>
 #include <syslog.h>
 #include <errno.h>
+#include <getopt.h>
+#include "../include/su_indep.h"
 
 /* -------------------------------------------- */
 /* ------ declarations ------------------------ */
@@ -184,71 +186,98 @@ void make_process_killable()
 
 /* ------ command line parser ----------------- */
 
-void usage()
+__attribute__ ((__noreturn__))
+static void usage (int status)
 {
-    (void) fprintf(stderr,"usage: su [-] [-c \"command\"] [username]\n");
-    exit(1);
+	fprintf (stderr, "usage: su [-|-l] [-c \"command\"] [-s \"shell\"] [username]\n");
+	exit (status);
 }
 
-void parse_command_line(int argc, char *argv[]
-	, int *is_login, const char **user, const char **command)
+void parse_command_line(int argc, char *argv[], su_context *ctx)
 {
-    int username_present, command_present;
-
-    *is_login = 0;
-    *user = NULL;
-    *command = NULL;
-    username_present = command_present = 0;
-
-    while ( --argc > 0 ) {
-	const char *token;
-
-	token = *++argv;
-	if (*token == '-') {
-	    switch (*++token) {
-	    case '\0':             /* su as a login shell for the user */
-		if (*is_login)
-		    usage();
-		*is_login = 1;
-		break;
-	    case 'c':
-		if (command_present) {
-		    usage();
-		} else {               /* indicate we are running commands */
-		    if (*++token != '\0') {
-			command_present = 1;
-			*command = token;
-		    } else if (--argc > 0) {
-			command_present = 1;
-			*command = *++argv;
-		    } else
-			usage();
+	int optc;
+	struct option const longopts[] =
+	{
+		{ "command", required_argument, 0, 'c' },
+		{ "login", no_argument, 0, 'l' },
+		{ "shell", required_argument, 0, 's' },
+		{ "help", no_argument, 0, 'h' },
+		{ 0, 0, 0, 0 }
+	};
+
+	if (argc < 1)
+		usage (EXIT_FAILURE);
+
+	memset (ctx, 0, sizeof(*ctx));
+
+	while ((optc = getopt_long (argc, argv, "c:ls:", longopts, 0)) != -1)
+	{
+		switch (optc)
+		{
+			case 'c':
+				if (ctx->command)
+				    usage (EXIT_FAILURE);
+				ctx->command = optarg;
+				break;
+
+			case 'l':
+				if (ctx->login)
+				    usage (EXIT_FAILURE);
+				ctx->login = 1;
+				break;
+
+			case 's':
+				if (ctx->shell)
+				    usage (EXIT_FAILURE);
+				ctx->shell = optarg;
+				break;
+
+			case 'h':
+				usage (EXIT_SUCCESS);
+
+			default:
+				usage (EXIT_FAILURE);
 		}
-		break;
-	    default:
-		usage();
-	    }
-	} else {                       /* must be username */
-	    if (username_present)
-		usage();
-	    username_present = 1;
-	    *user = *argv;
 	}
-    }
 
-    if (!username_present) {           /* default user is superuser */
-	const struct passwd *pw;
+	if (optind < argc && !strcmp (argv[optind], "-"))
+	{
+		if (ctx->login)
+		    usage (EXIT_FAILURE);
+		ctx->login = 1;
+		++optind;
+	}
+
+	if (optind < argc)
+		ctx->user = argv[optind++];
+
+	if (optind < argc)
+	    usage (EXIT_FAILURE);
+
+	if (!ctx->user)
+	{	/* default user is superuser */
+		const struct passwd *pw = getpwuid (ROOT_UID);
+		if (!(pw && pw->pw_name))	/* No ROOT_UID!? */
+		{
+			fprintf (stderr, "su: no access to superuser identity (%d)!\n", ROOT_UID);
+			exit (EXIT_FAILURE);
+		}
+
+		ctx->user = strdup (pw->pw_name);
+		endpwent();
+	}
 
-	pw = getpwuid(ROOT_UID);
-	if (pw == NULL)                               /* No ROOT_UID!? */
+	if (ctx->shell)
 	{
-	    printf ("\nsu:no access to superuser identity!? (%d)\n", 
-				ROOT_UID);
-	    exit (1);
-	}
-	
-	*user = NULL;
-	if (pw->pw_name != NULL)
-	    *user = strdup(pw->pw_name);
-    }
+		if (getuid())
+		{
+			fprintf (stderr, "su: setting shell: permission denied\n");
+			exit (EXIT_FAILURE);
+		}
+		if (access (ctx->shell, X_OK) < 0)
+		{
+			fprintf (stderr, "su: setting shell: %s\n", strerror (errno));
+			exit (EXIT_FAILURE);
+		}
+	}
 }
diff -urp SimplePAMApps-0.60.orig/pamapps/lib/wtmp-gate.c SimplePAMApps-0.60/pamapps/lib/wtmp-gate.c
--- SimplePAMApps-0.60.orig/pamapps/lib/wtmp-gate.c	Wed Nov 25 12:33:32 1998
+++ SimplePAMApps-0.60/pamapps/lib/wtmp-gate.c	Mon Nov 19 04:47:15 2001
@@ -35,6 +35,7 @@ int utmp_open_session(pam_handle_t *pamh
         *err_descr = pam_strerror(pamh, retval);
         return -1;
     }
+    if (!terminal) terminal = "???";
     retval = pam_get_item(pamh, PAM_RHOST, (const void **)&rhost);
     if (retval != PAM_SUCCESS)
         rhost = NULL;
@@ -55,6 +56,7 @@ int utmp_close_session(pam_handle_t *pam
         *err_descr = pam_strerror(pamh, retval);
         return -1;
     }
+    if (!terminal) terminal = "???";
 
     return
         utmp_do_close_session(terminal, callname, err_descr);
diff -urp SimplePAMApps-0.60.orig/pamapps/su/su.1 SimplePAMApps-0.60/pamapps/su/su.1
--- SimplePAMApps-0.60.orig/pamapps/su/su.1	Fri Jun 12 17:11:04 1998
+++ SimplePAMApps-0.60/pamapps/su/su.1	Tue Apr 15 12:44:09 2003
@@ -8,7 +8,8 @@
 su \- assume a user's identity
 
 .SH SYNOPSIS
-.B su [-] [-c "command"] [username]
+.B su
+[\fB-\fR|\fB-l\fR] [\fB-c \fIcommand\fR] [\fB-s \fIshell\fR] [\fIusername\fR]
 .sp 2
 .SH DESCRIPTION
 .B Su
@@ -85,49 +86,28 @@ encountering an accounting failure, a wa
 .BR su
 will proceed to invoke the sought user's shell.
 
-.sp
-A simple entry in the
-.I Linux-PAM
-configuration file for this service would be:
-.br
-  
-.br
- #
-.br
- # su service, authentication not required for root.
-.br
- # For other users authentication is provided via
-.br
- # pwdb. Some account management done with time module
-.br
- #
-.br
- su auth sufficient  pam_rootok.so
-.br
- su auth required    pam_pwdb.so
-.br
- su account required pam_pwdb.so
- su account required pam_time.so
-.br
- su session required pam_pwdb.so
-.br
- #
-
-.sp
-(For the equivalent
-.B /etc/pam.d/su
-file, you should delete the first field ("su") from the above
-example).  Note, the
-.BR password
-module-type is not required for this application to function
-correctly.
-
-.sp
-For continuity of service, the administrator might wish to make the
-.BR login "(1)"
-and
-.BR su
-configurations similar.
+.SH OPTIONS
+.TP
+.BI "\-c " command ", \-\-command=" command
+Pass
+.IR command,
+a single command line to run, to the shell with a
+.B \-c
+option instead of starting an interactive shell.
+.TP
+.B "\-, \-l, \-\-login"
+Invoke the shell as a login shell.
+.TP
+.BI "\-s, \-\-shell " shell
+.RI "Superuser may run " shell " instead of " user 's
+command-shell, unless the user running
+.B su
+is not the superuser and
+.IR user 's
+shell is restricted.
+.TP
+.B "\-\-help"
+Print a usage message on standard output and exit successfully.
 
 .SH "EXIT CODE"
 
diff -urp SimplePAMApps-0.60.orig/pamapps/su/su.c SimplePAMApps-0.60/pamapps/su/su.c
--- SimplePAMApps-0.60.orig/pamapps/su/su.c	Thu Feb 18 12:29:50 1999
+++ SimplePAMApps-0.60/pamapps/su/su.c	Tue Apr 15 09:40:54 2003
@@ -18,9 +18,10 @@
 #define DEFAULT_SHELL             "/bin/sh"
 #define SLEEP_TO_KILL_CHILDREN    3  /* seconds to wait after SIGTERM before
 					SIGKILL */
-#define SU_FAIL_DELAY     2000000    /* usec on authentication failure */
+#define SU_FAIL_DELAY             0  /* usec on authentication failure */
 
 #include <stdlib.h>
+#include <stdarg.h>
 #include <signal.h>
 #include <stdio.h>
 #include <sys/stat.h>
@@ -65,8 +66,8 @@ static int state;
 #define SU_STATE_TERMINAL_REOWNED    7
 #define SU_STATE_UTMP_WRITTEN        8
 
-static void exit_now(int exit_code, const char *format, ...);
-static void exit_child_now(int exit_code, const char *format, ...);
+static void exit_now(int exit_code, const char *format, ...) __attribute__ ((__noreturn__));
+static void exit_child_now(int exit_code, const char *format, ...) __attribute__ ((__noreturn__));
 static void do_pam_init(const char *user, int is_login);
 static void su_exec_shell(const char *shell, uid_t uid, int is_login
 			  , const char *command, const char *user);
@@ -75,12 +76,11 @@ static void su_exec_shell(const char *sh
 /* ------ the application itself -------------- */
 /* -------------------------------------------- */
 
-void main(int argc, char *argv[])
+int main(int argc, char *argv[])
 {
-    int retcode, is_login, status;
+    int retcode, status;
     int retval, final_retval; /* PAM_xxx return values */
-    const char *command, *user;
-    const char *shell;
+    su_context ctx;
     pid_t child;
     uid_t uid;
     const char *place, *err_descr;
@@ -102,7 +102,7 @@ void main(int argc, char *argv[])
 
     /* ------------ parse the argument list ----------- */
 
-    parse_command_line(argc, argv, &is_login, &user, &command);
+    parse_command_line(argc, argv, &ctx);
 
     /* ------ initialize the Linux-PAM interface ------ */
 
@@ -112,8 +112,8 @@ void main(int argc, char *argv[])
 	exit_now(1, "su: failed\n");
 #endif
 
-    do_pam_init(user, is_login);      /* call pam_start and set PAM items */
-    user = NULL;                      /* get this info later (it may change) */
+    do_pam_init(ctx.user, ctx.login); /* call pam_start and set PAM items */
+    ctx.user = NULL;                  /* get this info later (it may change) */
 
     /*
      * Note. We have forgotten everything about the user. We will get
@@ -166,10 +166,14 @@ void main(int argc, char *argv[])
 	 * Obtain all of the new credentials of the user
 	 */
 	place = "set_user_credentials";
-        retval = set_user_credentials(pamh, is_login, &user, &uid, &shell);
-	if (retval != PAM_SUCCESS) {
-	    (void) pam_close_session(pamh,retval);
-	    break;
+	{
+		const char *shell;
+	        retval = set_user_credentials(pamh, ctx.login, &ctx.user, &uid, &shell);
+		if (retval != PAM_SUCCESS) {
+		    (void) pam_close_session(pamh, retval);
+		    break;
+		}
+		if (!ctx.shell) ctx.shell = shell;
 	}
 	state = SU_STATE_CREDENTIALS_GOTTEN;
 	
@@ -183,8 +187,7 @@ void main(int argc, char *argv[])
         /*
          * ... setup terminal, ...
          */
-        retcode = change_terminal_owner(uid, is_login
-                , &place, &err_descr);
+        retcode = change_terminal_owner(uid, ctx.login, &place, &err_descr);
 	if (retcode > 0) {
 	    (void) fprintf(stderr, "su: %s: %s\n", place, err_descr);
 	    err_descr = NULL; /* forget about the problem */
@@ -195,7 +198,7 @@ void main(int argc, char *argv[])
         /*
          * ... make [uw]tmp entries.
          */
-        if (is_login) {
+        if (ctx.login) {
             /*
              * Note: we use the parent pid as a session identifier for
              * the logging.
@@ -218,14 +221,14 @@ void main(int argc, char *argv[])
         }
 
         if (child == 0) {       /* child exec's shell */
-            su_exec_shell(shell, uid, is_login, command, user);
+            su_exec_shell(ctx.shell, uid, ctx.login, ctx.command, ctx.user);
             /* never reached */
         }
 
 	/* wait for child to terminate */
 
         /* job control is off for login sessions */
-        prepare_for_job_control(!is_login && command != NULL);
+        prepare_for_job_control(!ctx.login && ctx.command);
 	status = wait_for_child(child);
 	if (status != 0)
 	    D(("shell returned %d", status));
@@ -293,7 +296,7 @@ void main(int argc, char *argv[])
     if (reset_terminal_modes() != 0 && !status)
 	status = 1;
 
-    exit(status);                 /* transparent exit */
+    return status;
 }
 
 /* -------------------------------------------- */
@@ -380,7 +383,7 @@ static void do_pam_init(const char *user
 	if (terminal) {
 	    retval = pam_set_item(pamh, PAM_TTY, (const void *)terminal);
 	} else {
-	    retval = PAM_PERM_DENIED;                /* how did we get here? */
+	    if (getuid() != 0) retval = PAM_PERM_DENIED;
 	}
 	terminal = NULL;
     }
@@ -389,8 +392,6 @@ static void do_pam_init(const char *user
 	const char *ruser = getlogin();      /* Who is running this program? */
 	if (ruser) {
 	    retval = pam_set_item(pamh, PAM_RUSER, (const void *)ruser);
-	} else {
-	    retval = PAM_PERM_DENIED;             /* must be known to system */
 	}
 	ruser = NULL;
     }
@@ -403,7 +404,7 @@ static void do_pam_init(const char *user
 	exit_now(1, "su: problem establishing environment\n");
     }
 
-#ifdef HAVE_PAM_FAIL_DELAY
+#if defined(HAVE_PAM_FAIL_DELAY) && SU_FAIL_DELAY
     /* have to pause on failure. At least this long (doubles..) */
     retval = pam_fail_delay(pamh, SU_FAIL_DELAY);
     if (retval != PAM_SUCCESS) {
@@ -472,6 +473,9 @@ static void su_exec_shell(const char *sh
     if (shell_args == NULL) {
 	exit_child_now(1, "su: could not identify appropriate shell\n");
     }
+
+    retval = pam_misc_setenv(pamh, "SHELL", shell_args[0], 0);
+    D(("pam_misc_setenv: SHELL=%s: retval=%d", shell_args[0], retval));
 
     /*
      * and now copy the environment for non-PAM use
 
дизайн и разработка: Vladimir Lettiev aka crux © 2004-2005, Andrew Avramenko aka liks © 2007-2008
текущий майнтейнер: Michael Shigorin