|
|
1.1 ! root 1: /* ! 2: * Rec'd from Lauren Weinstein, 7-16-84. ! 3: * Substitute user-id temporarily or become super user (as you wish). ! 4: * Compile -s -n -i. ! 5: * Hacked by steve 10/4/90 to correct password bug and for clarity. ! 6: */ ! 7: ! 8: #include <stdio.h> ! 9: #include <pwd.h> ! 10: ! 11: extern char *getenv(); ! 12: extern char *getpass(); ! 13: extern char *malloc(); ! 14: ! 15: #define ACCNAME "remacc" /* Remote access password dummy username */ ! 16: #define DEFSHELL "/bin/sh" /* Default shell pathname */ ! 17: #define PASSLEN 13 /* Encrypted password length */ ! 18: ! 19: #define bye() fatal("Sorry") ! 20: ! 21: /* Forward. */ ! 22: extern void addenviron(); ! 23: extern void fatal(); ! 24: extern void getuname(); ! 25: ! 26: /* Globals. */ ! 27: char *defargs[] = { "su", NULL }; ! 28: /* The following are all set by getuname(). */ ! 29: short gid; ! 30: char *password; ! 31: char salt[3]; ! 32: short uid; ! 33: ! 34: main(argc, argv) int argc; char *argv[]; ! 35: { ! 36: register int ouid, ogid; ! 37: char *command, *prompta, *promptb, *passp; ! 38: char **args; ! 39: ! 40: getuname(argc>1 ? argv[1] : "0"); /* check username */ ! 41: if (password[0] != '\0' && getuid()) { /* check password if not already su */ ! 42: passp = getpass("Password: "); /* get input password choice */ ! 43: if ((strlen(password) != PASSLEN) ! 44: || (strcmp(crypt(passp, salt), password) != 0)) { ! 45: ouid = uid; ! 46: ogid = gid; ! 47: getuname("0"); /* check root password too */ ! 48: if ((strlen(password) != PASSLEN) ! 49: || (strcmp(crypt(passp, salt), password) != 0)) ! 50: bye(); /* failure */ ! 51: uid = ouid; ! 52: gid = ogid; ! 53: } ! 54: } ! 55: ! 56: if (argc > 2) { ! 57: command = argv[2]; ! 58: args = &argv[2]; ! 59: } else { ! 60: command = getenv("SHELL"); ! 61: if (command == NULL || strlen(command) < 1) ! 62: command = DEFSHELL; ! 63: args = defargs; ! 64: } ! 65: setgid(gid); ! 66: setuid(uid); ! 67: prompta = getenv("PSN"); /* check for normal prompt */ ! 68: promptb = getenv("PSS"); /* check for desired su prompt */ ! 69: addenviron(uid == 0 ? (promptb ? promptb : "# ") ! 70: : (prompta ? prompta : "$ ")); ! 71: /* change prompt as appropriate */ ! 72: execvp(command, args); ! 73: fatal("%s: not found", command); ! 74: } ! 75: ! 76: /* ! 77: * Add string 's' to the environment as "PS1". ! 78: */ ! 79: void ! 80: addenviron(s) char *s; ! 81: { ! 82: extern char **environ; ! 83: register char **epp1, **epp2; ! 84: register char **newenv; ! 85: int n; ! 86: char *prompt; ! 87: static char prbuf[50]; ! 88: ! 89: for (epp1 = environ; *epp1!=NULL; epp1++) ! 90: ; ! 91: n = (epp1-environ+2) * sizeof (char *); ! 92: if ((newenv = (char **)malloc(n)) == NULL) ! 93: fatal("Out of memory for environments"); ! 94: prompt = prbuf; ! 95: strcpy(prompt, "PS1="); ! 96: strcat(prompt, s); ! 97: for (epp1=environ, epp2=newenv; *epp1 != NULL; epp1++) ! 98: if (strncmp(*epp1, "PS1=", 4) != 0) ! 99: *epp2++ = *epp1; ! 100: else { ! 101: *epp2++ = prompt; ! 102: prompt = NULL; ! 103: } ! 104: *epp2++ = prompt; ! 105: *epp2 = NULL; ! 106: environ = newenv; ! 107: } ! 108: ! 109: void ! 110: fatal(s) char *s; ! 111: { ! 112: fprintf(stderr, "%r\n", &s); ! 113: exit(1); ! 114: } ! 115: ! 116: /* ! 117: * Get a user-name from string 's'. ! 118: * If the string starts with a numeric, use it directly as a uid. ! 119: * Set globals password, salt[], gid and uid with the user's password info. ! 120: * Die if not found or illegal. ! 121: */ ! 122: void ! 123: getuname(s) register char *s; ! 124: { ! 125: register struct passwd *pwp; ! 126: ! 127: if (*s >= '0' && *s <= '9') { ! 128: uid = atoi(s); ! 129: if ((pwp = getpwuid(uid)) == NULL) ! 130: fatal("%d: bad user number", uid); ! 131: } else if ((pwp = getpwnam(s)) == NULL) ! 132: fatal("%s: not a user name", s); ! 133: if (strcmp(pwp->pw_name, ACCNAME) == 0) /* dummy access username? */ ! 134: bye(); /* yes, sorry */ ! 135: password = pwp->pw_passwd; ! 136: salt[0] = pwp->pw_passwd[0]; ! 137: salt[1] = pwp->pw_passwd[1]; ! 138: salt[2] = '\0'; ! 139: gid = pwp->pw_gid; ! 140: uid = pwp->pw_uid; ! 141: } ! 142: ! 143: /* end of su.c */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.