1: /* 2: * Copyright (c) 1988 The Regents of the University of California. 3: * All rights reserved. 4: * 5: * Redistribution and use in source and binary forms are permitted 6: * provided that the above copyright notice and this paragraph are 7: * duplicated in all such forms and that any documentation, 8: * advertising materials, and other materials related to such 9: * distribution and use acknowledge that the software was developed 10: * by the University of California, Berkeley. The name of the 11: * University may not be used to endorse or promote products derived 12: * from this software without specific prior written permission. 13: * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR 14: * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED 15: * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. 16: */ 17: 18: #ifndef lint 19: static char sccsid[] = "@(#)field.c 5.8 (Berkeley) 3/16/89"; 20: #endif /* not lint */ 21: 22: #include <sys/param.h> 23: #include <pwd.h> 24: #include <grp.h> 25: #include <strings.h> 26: #include <stdio.h> 27: #include <ctype.h> 28: #include <chpass.h> 29: #include "pathnames.h" 30: 31: /* ARGSUSED */ 32: p_login(p, pw, ep) 33: char *p; 34: struct passwd *pw; 35: struct entry *ep; 36: { 37: if (!*p) { 38: (void)fprintf(stderr, "chpass: empty login field.\n"); 39: return(1); 40: } 41: if (*p == '-') { 42: (void)fprintf(stderr, 43: "chpass: login names may not begin with a hyphen.\n"); 44: return(1); 45: } 46: if (!(pw->pw_name = strdup(p))) { 47: (void)fprintf(stderr, "chpass: can't save entry.\n"); 48: return(1); 49: } 50: if (index(p, '.')) 51: (void)fprintf(stderr, 52: "chpass: \'.\' is dangerous in a login name.\n"); 53: for (; *p; ++p) 54: if (isupper(*p)) { 55: (void)fprintf(stderr, 56: "chpass: upper-case letters are dangerous in a login name.\n"); 57: break; 58: } 59: return(0); 60: } 61: 62: /* ARGSUSED */ 63: p_passwd(p, pw, ep) 64: char *p; 65: struct passwd *pw; 66: struct entry *ep; 67: { 68: if (!*p) 69: pw->pw_passwd = ""; /* "NOLOGIN"; */ 70: else if (!(pw->pw_passwd = strdup(p))) { 71: (void)fprintf(stderr, "chpass: can't save password entry.\n"); 72: return(1); 73: } 74: 75: return(0); 76: } 77: 78: /* ARGSUSED */ 79: p_uid(p, pw, ep) 80: register char *p; 81: struct passwd *pw; 82: struct entry *ep; 83: { 84: int id; 85: 86: if (!*p) { 87: (void)fprintf(stderr, "chpass: empty uid field.\n"); 88: return(1); 89: } 90: if (!isdigit(*p)) { 91: (void)fprintf(stderr, "chpass: illegal uid.\n"); 92: return(1); 93: } 94: id = atoi(p); 95: if ((u_int)id > USHRT_MAX) { 96: (void)fprintf(stderr, "chpass: %d > max uid value (%d).\n", 97: id, USHRT_MAX); 98: return(1); 99: } 100: pw->pw_uid = id; 101: return(0); 102: } 103: 104: /* ARGSUSED */ 105: p_gid(p, pw, ep) 106: register char *p; 107: struct passwd *pw; 108: struct entry *ep; 109: { 110: struct group *gr; 111: int id; 112: 113: if (!*p) { 114: (void)fprintf(stderr, "chpass: empty gid field.\n"); 115: return(1); 116: } 117: if (!isdigit(*p)) { 118: if (!(gr = getgrnam(p))) { 119: (void)fprintf(stderr, 120: "chpass: unknown group %s.\n", p); 121: return(1); 122: } 123: pw->pw_gid = gr->gr_gid; 124: return(0); 125: } 126: id = atoi(p); 127: if ((u_int)id > USHRT_MAX) { 128: (void)fprintf(stderr, "chpass: %d > max gid value (%d).\n", 129: id, USHRT_MAX); 130: return(1); 131: } 132: pw->pw_gid = id; 133: return(0); 134: } 135: 136: /* ARGSUSED */ 137: p_class(p, pw, ep) 138: char *p; 139: struct passwd *pw; 140: struct entry *ep; 141: { 142: if (!*p) 143: pw->pw_class = ""; 144: else if (!(pw->pw_class = strdup(p))) { 145: (void)fprintf(stderr, "chpass: can't save entry.\n"); 146: return(1); 147: } 148: 149: return(0); 150: } 151: 152: /* ARGSUSED */ 153: p_change(p, pw, ep) 154: char *p; 155: struct passwd *pw; 156: struct entry *ep; 157: { 158: if (!atot(p, &pw->pw_change)) 159: return(0); 160: (void)fprintf(stderr, "chpass: illegal date for change field.\n"); 161: return(1); 162: } 163: 164: /* ARGSUSED */ 165: p_expire(p, pw, ep) 166: char *p; 167: struct passwd *pw; 168: struct entry *ep; 169: { 170: if (!atot(p, &pw->pw_expire)) 171: return(0); 172: (void)fprintf(stderr, "chpass: illegal date for expire field.\n"); 173: return(1); 174: } 175: 176: /* ARGSUSED */ 177: p_gecos(p, pw, ep) 178: char *p; 179: struct passwd *pw; 180: struct entry *ep; 181: { 182: if (!*p) 183: ep->save = ""; 184: else if (!(ep->save = strdup(p))) { 185: (void)fprintf(stderr, "chpass: can't save entry.\n"); 186: return(1); 187: } 188: return(0); 189: } 190: 191: /* ARGSUSED */ 192: p_hdir(p, pw, ep) 193: char *p; 194: struct passwd *pw; 195: struct entry *ep; 196: { 197: if (!*p) { 198: (void)fprintf(stderr, "chpass: empty home directory field.\n"); 199: return(1); 200: } 201: if (!(pw->pw_dir = strdup(p))) { 202: (void)fprintf(stderr, "chpass: can't save entry.\n"); 203: return(1); 204: } 205: return(0); 206: } 207: 208: /* ARGSUSED */ 209: p_shell(p, pw, ep) 210: register char *p; 211: struct passwd *pw; 212: struct entry *ep; 213: { 214: register char *sh, *t; 215: char *getusershell(); 216: 217: if (!*p) { 218: pw->pw_shell = _PATH_BSHELL; 219: return(0); 220: } 221: setusershell(); 222: for (;;) { 223: if (!(sh = getusershell())) { 224: /* only admin can set "restricted" shells */ 225: if (!uid) 226: break; 227: (void)fprintf(stderr, 228: "chpass: %s: non-standard shell.\n", p); 229: return(1); 230: } 231: if (!strcmp(p, sh)) 232: break; 233: /* allow just shell name */ 234: if ((t = rindex(sh, '/')) && !strcmp(p, t)) { 235: p = t; 236: break; 237: } 238: } 239: if (!(pw->pw_shell = strdup(p))) { 240: (void)fprintf(stderr, "chpass: can't save entry.\n"); 241: return(1); 242: } 243: return(0); 244: }