122095Smckusick /* 2*36215Sbostic * Copyright (c) 1988 The Regents of the University of California. 3*36215Sbostic * All rights reserved. 4*36215Sbostic * 5*36215Sbostic * Redistribution and use in source and binary forms are permitted 6*36215Sbostic * provided that the above copyright notice and this paragraph are 7*36215Sbostic * duplicated in all such forms and that any documentation, 8*36215Sbostic * advertising materials, and other materials related to such 9*36215Sbostic * distribution and use acknowledge that the software was developed 10*36215Sbostic * by the University of California, Berkeley. The name of the 11*36215Sbostic * University may not be used to endorse or promote products derived 12*36215Sbostic * from this software without specific prior written permission. 13*36215Sbostic * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR 14*36215Sbostic * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED 15*36215Sbostic * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. 1622095Smckusick */ 1722095Smckusick 1826560Sdonn #if defined(LIBC_SCCS) && !defined(lint) 19*36215Sbostic static char sccsid[] = "@(#)getpwent.c 5.3 (Berkeley) 11/14/88"; 20*36215Sbostic #endif /* LIBC_SCCS and not lint */ 2122095Smckusick 22*36215Sbostic #include <sys/types.h> 23*36215Sbostic #include <sys/file.h> 242019Swnj #include <stdio.h> 252019Swnj #include <pwd.h> 2616416Sralph #include <ndbm.h> 272019Swnj 28*36215Sbostic static DBM *_pw_db; 29*36215Sbostic static FILE *_pw_fp; 30*36215Sbostic static struct passwd _pw_passwd; 31*36215Sbostic static int _pw_set; 32*36215Sbostic static char *_pw_file = "/etc/passwd"; 332019Swnj 34*36215Sbostic #define MAXLINELENGTH 200 35*36215Sbostic static char line[MAXLINELENGTH]; 3617759Sserge 37*36215Sbostic static 38*36215Sbostic pwscan() 392019Swnj { 40*36215Sbostic register char *cp; 41*36215Sbostic char *fgets(), *strsep(); 42*36215Sbostic 43*36215Sbostic for (;;) { 44*36215Sbostic if (!(cp = fgets(line, sizeof(line), _pw_fp))) 45*36215Sbostic return(0); 46*36215Sbostic _pw_passwd.pw_name = strsep(cp, ":\n"); 47*36215Sbostic _pw_passwd.pw_passwd = strsep((char *)NULL, ":\n"); 48*36215Sbostic if (!(cp = strsep((char *)NULL, ":\n"))) 49*36215Sbostic continue; 50*36215Sbostic _pw_passwd.pw_uid = atoi(cp); 51*36215Sbostic if (!(cp = strsep((char *)NULL, ":\n"))) 52*36215Sbostic continue; 53*36215Sbostic _pw_passwd.pw_gid = atoi(cp); 54*36215Sbostic _pw_passwd.pw_gecos = strsep((char *)NULL, ":\n"); 55*36215Sbostic _pw_passwd.pw_dir = strsep((char *)NULL, ":\n"); 56*36215Sbostic _pw_passwd.pw_shell = strsep((char *)NULL, ":\n"); 57*36215Sbostic if (_pw_passwd.pw_shell) { 58*36215Sbostic _pw_passwd.pw_quota = 0; 59*36215Sbostic _pw_passwd.pw_comment = ""; 60*36215Sbostic return(1); 61*36215Sbostic } 62*36215Sbostic } 63*36215Sbostic /* NOTREACHED */ 642019Swnj } 652019Swnj 66*36215Sbostic static 67*36215Sbostic fetchpw(key) 68*36215Sbostic datum key; 692019Swnj { 70*36215Sbostic register char *cp, *tp; 71*36215Sbostic 72*36215Sbostic if (_pw_db == (DBM *)NULL && 73*36215Sbostic (_pw_db = dbm_open(_pw_file, O_RDONLY, 0)) == (DBM *)NULL) 74*36215Sbostic return(0); 75*36215Sbostic if (flock(dbm_dirfno(_pw_db), LOCK_SH)) { 7617028Sralph dbm_close(_pw_db); 77*36215Sbostic _pw_db = NULL; 78*36215Sbostic return(0); 7916416Sralph } 80*36215Sbostic key = dbm_fetch(_pw_db, key); 81*36215Sbostic (void)flock(dbm_dirfno(_pw_db), LOCK_UN); 82*36215Sbostic if ((cp = key.dptr) == 0) 83*36215Sbostic return(0); 84*36215Sbostic 85*36215Sbostic tp = line; 86*36215Sbostic #define EXPAND(e) _pw_passwd.e = tp; while (*tp++ = *cp++); 87*36215Sbostic EXPAND(pw_name); 88*36215Sbostic EXPAND(pw_passwd); 89*36215Sbostic bcopy(cp, (char *)&_pw_passwd.pw_uid, sizeof(int)); 90*36215Sbostic cp += sizeof(int); 91*36215Sbostic bcopy(cp, (char *)&_pw_passwd.pw_gid, sizeof(int)); 92*36215Sbostic cp += sizeof(int); 93*36215Sbostic bcopy(cp, (char *)&_pw_passwd.pw_quota, sizeof(int)); 94*36215Sbostic cp += sizeof(int); 95*36215Sbostic EXPAND(pw_comment); 96*36215Sbostic EXPAND(pw_gecos); 97*36215Sbostic EXPAND(pw_dir); 98*36215Sbostic EXPAND(pw_shell); 99*36215Sbostic return(1); 1002019Swnj } 1012019Swnj 102*36215Sbostic struct passwd * 103*36215Sbostic getpwent() 1042019Swnj { 105*36215Sbostic if (!_pw_fp && !setpwent() || !pwscan()) 106*36215Sbostic return((struct passwd *)NULL); 107*36215Sbostic return(&_pw_passwd); 1082019Swnj } 1092019Swnj 1102019Swnj struct passwd * 111*36215Sbostic getpwnam(nam) 112*36215Sbostic char *nam; 1132019Swnj { 114*36215Sbostic datum key; 1152019Swnj 116*36215Sbostic key.dptr = nam; 117*36215Sbostic key.dsize = strlen(nam); 118*36215Sbostic if (!fetchpw(key)) { 119*36215Sbostic if (setpwent()) 120*36215Sbostic while (pwscan()) 121*36215Sbostic if (!strcmp(nam, _pw_passwd.pw_name)) 122*36215Sbostic return(&_pw_passwd); 123*36215Sbostic return((struct passwd *)NULL); 1242019Swnj } 125*36215Sbostic return(&_pw_passwd); 1262019Swnj } 12716507Sralph 128*36215Sbostic struct passwd * 129*36215Sbostic getpwuid(uid) 130*36215Sbostic uid_t uid; 131*36215Sbostic { 132*36215Sbostic datum key; 133*36215Sbostic 134*36215Sbostic key.dptr = (char *)&uid; 135*36215Sbostic key.dsize = sizeof(uid); 136*36215Sbostic if (!fetchpw(key)) { 137*36215Sbostic if (setpwent()) 138*36215Sbostic while (pwscan()) 139*36215Sbostic if (_pw_passwd.pw_uid == uid) 140*36215Sbostic return(&_pw_passwd); 141*36215Sbostic return((struct passwd *)NULL); 142*36215Sbostic } 143*36215Sbostic return(&_pw_passwd); 144*36215Sbostic } 145*36215Sbostic 146*36215Sbostic void 14716507Sralph setpwfile(file) 14816507Sralph char *file; 14916507Sralph { 15017759Sserge _pw_file = file; 151*36215Sbostic _pw_set = 1; 15216507Sralph } 153*36215Sbostic 154*36215Sbostic setpwent() 155*36215Sbostic { 156*36215Sbostic if (_pw_set) 157*36215Sbostic endpwent(); 158*36215Sbostic if (_pw_fp) 159*36215Sbostic rewind(_pw_fp); 160*36215Sbostic else if ((_pw_fp = fopen(_pw_file, "r")) == NULL) 161*36215Sbostic return(0); 162*36215Sbostic _pw_set = 0; 163*36215Sbostic return(1); 164*36215Sbostic } 165*36215Sbostic 166*36215Sbostic void 167*36215Sbostic endpwent() 168*36215Sbostic { 169*36215Sbostic if (_pw_fp) { 170*36215Sbostic (void)fclose(_pw_fp); 171*36215Sbostic _pw_fp = (FILE *)NULL; 172*36215Sbostic } 173*36215Sbostic if (_pw_db) { 174*36215Sbostic dbm_close(_pw_db); 175*36215Sbostic _pw_db = (DBM *)NULL; 176*36215Sbostic } 177*36215Sbostic } 178