Changeset 1770 in MondoRescue for branches/stable/mindi-busybox/loginutils/sulogin.c
- Timestamp:
- Nov 6, 2007, 11:01:53 AM (16 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
branches/stable/mindi-busybox/loginutils/sulogin.c
r902 r1770 1 1 /* vi: set sw=4 ts=4: */ 2 #include <fcntl.h> 3 #include <signal.h> 4 #include <stdio.h> 5 #include <stdlib.h> 6 #include <string.h> 2 /* 3 * Mini sulogin implementation for busybox 4 * 5 * Licensed under GPLv2 or later, see file LICENSE in this tarball for details. 6 */ 7 7 8 #include <syslog.h> 8 #include <unistd.h>9 #include <utmp.h>10 #include <sys/resource.h>11 #include <sys/stat.h>12 #include <sys/types.h>13 #include <ctype.h>14 #include <time.h>15 9 16 #include " busybox.h"10 #include "libbb.h" 17 11 18 19 #define SULOGIN_PROMPT "\nGive root password for system maintenance\n" \ 20 "(or type Control-D for normal startup):" 21 22 static const char * const forbid[] = { 12 static const char *const forbid[] = { 23 13 "ENV", 24 14 "BASH_ENV", … … 39 29 40 30 41 42 31 static void catchalarm(int ATTRIBUTE_UNUSED junk) 43 32 { … … 46 35 47 36 37 int sulogin_main(int argc, char **argv); 48 38 int sulogin_main(int argc, char **argv) 49 39 { 50 40 char *cp; 51 char *device = NULL;52 const char *name = "root";53 41 int timeout = 0; 54 55 #define pass bb_common_bufsiz1 56 57 struct passwd pwent; 42 char *timeout_arg; 43 const char *const *p; 58 44 struct passwd *pwd; 59 const char * const *p;45 const char *shell; 60 46 #if ENABLE_FEATURE_SHADOWPASSWDS 61 struct spwd *spwd = NULL; 47 /* Using _r function to avoid pulling in static buffers */ 48 char buffer[256]; 49 struct spwd spw; 50 struct spwd *result; 62 51 #endif 63 52 64 openlog("sulogin", LOG_PID | LOG_CONS | LOG_NOWAIT, LOG_AUTH); 65 if (argc > 1) { 66 if (strncmp(argv[1], "-t", 2) == 0) { 67 if (argv[1][2] == '\0') { /* -t NN */ 68 if (argc > 2) { 69 timeout = atoi(argv[2]); 70 if (argc > 3) { 71 device = argv[3]; 72 } 73 } 74 } else { /* -tNNN */ 75 timeout = atoi(&argv[1][2]); 76 if (argc > 2) { 77 device = argv[2]; 78 } 79 } 80 } else { 81 device = argv[1]; 82 } 83 if (device) { 84 close(0); 85 close(1); 86 close(2); 87 if (open(device, O_RDWR) == 0) { 88 dup(0); 89 dup(0); 90 } else { 91 syslog(LOG_WARNING, "cannot open %s\n", device); 92 exit(EXIT_FAILURE); 93 } 94 } 95 } 96 if (access(bb_path_passwd_file, 0) == -1) { 97 syslog(LOG_WARNING, "No password file\n"); 98 bb_error_msg_and_die("No password file\n"); 99 } 100 if (!isatty(0) || !isatty(1) || !isatty(2)) { 101 exit(EXIT_FAILURE); 53 logmode = LOGMODE_BOTH; 54 openlog(applet_name, 0, LOG_AUTH); 55 56 if (getopt32(argv, "t:", &timeout_arg)) { 57 timeout = xatoi_u(timeout_arg); 102 58 } 103 59 60 if (argv[optind]) { 61 close(0); 62 close(1); 63 dup(xopen(argv[optind], O_RDWR)); 64 close(2); 65 dup(0); 66 } 67 68 if (!isatty(0) || !isatty(1) || !isatty(2)) { 69 logmode = LOGMODE_SYSLOG; 70 bb_error_msg_and_die("not a tty"); 71 } 104 72 105 73 /* Clear out anything dangerous from the environment */ … … 107 75 unsetenv(*p); 108 76 77 signal(SIGALRM, catchalarm); 109 78 110 signal(SIGALRM, catchalarm); 111 if (!(pwd = getpwnam(name))) { 112 syslog(LOG_WARNING, "No password entry for `root'\n"); 113 bb_error_msg_and_die("No password entry for `root'\n"); 79 pwd = getpwuid(0); 80 if (!pwd) { 81 goto auth_error; 114 82 } 115 pwent = *pwd; 83 116 84 #if ENABLE_FEATURE_SHADOWPASSWDS 117 spwd = NULL; 118 if (pwd && ((strcmp(pwd->pw_passwd, "x") == 0) 119 || (strcmp(pwd->pw_passwd, "*") == 0))) { 120 endspent(); 121 spwd = getspnam(name); 122 if (spwd) { 123 pwent.pw_passwd = spwd->sp_pwdp; 85 if (getspnam_r(pwd->pw_name, &spw, buffer, sizeof(buffer), &result)) { 86 goto auth_error; 87 } 88 pwd->pw_passwd = spw.sp_pwdp; 89 #endif 90 91 while (1) { 92 /* cp points to a static buffer that is zeroed every time */ 93 cp = bb_askpass(timeout, 94 "Give root password for system maintenance\n" 95 "(or type Control-D for normal startup):"); 96 97 if (!cp || !*cp) { 98 bb_info_msg("Normal startup"); 99 return 0; 124 100 } 125 } 126 #endif 127 while (1) { 128 cp = bb_askpass(timeout, SULOGIN_PROMPT); 129 if (!cp || !*cp) { 130 puts("\n"); 131 fflush(stdout); 132 syslog(LOG_INFO, "Normal startup\n"); 133 exit(EXIT_SUCCESS); 134 } else { 135 safe_strncpy(pass, cp, sizeof(pass)); 136 memset(cp, 0, strlen(cp)); 137 } 138 if (strcmp(pw_encrypt(pass, pwent.pw_passwd), pwent.pw_passwd) == 0) { 101 if (strcmp(pw_encrypt(cp, pwd->pw_passwd), pwd->pw_passwd) == 0) { 139 102 break; 140 103 } 141 104 bb_do_delay(FAIL_DELAY); 142 puts("Login incorrect"); 143 fflush(stdout); 144 syslog(LOG_WARNING, "Incorrect root password\n"); 105 bb_error_msg("login incorrect"); 145 106 } 146 memset( pass, 0, strlen(pass));107 memset(cp, 0, strlen(cp)); 147 108 signal(SIGALRM, SIG_DFL); 148 puts("Entering System Maintenance Mode\n");149 fflush(stdout);150 syslog(LOG_INFO, "System Maintenance Mode\n");151 109 152 #if ENABLE_SELINUX 153 renew_current_security_context(); 154 #endif 110 bb_info_msg("System Maintenance Mode"); 155 111 156 run_shell(pwent.pw_shell, 1, 0, 0);112 USE_SELINUX(renew_current_security_context()); 157 113 158 return (0); 114 shell = getenv("SUSHELL"); 115 if (!shell) shell = getenv("sushell"); 116 if (!shell) { 117 shell = "/bin/sh"; 118 if (pwd->pw_shell[0]) 119 shell = pwd->pw_shell; 120 } 121 run_shell(shell, 1, 0, 0); 122 /* never returns */ 123 124 auth_error: 125 bb_error_msg_and_die("no password entry for 'root'"); 159 126 }
Note:
See TracChangeset
for help on using the changeset viewer.