📄 getpwent.c
字号:
char bindbuf[64]; struct passwd *pw = NULL; sprintf(bindbuf, "passwd-%d", svc_getpwbind);#ifdef DEBUG fprintf(stderr, "getpwent_bind(%s)\n", bindbuf);#endif DEBUG if ((pw = getpwnam_bind(bindbuf)) == NULL) return(NULL); svc_getpwbind++; return(pw);}struct passwd *getpwent_yp(){ char line1[BUFSIZ+1]; static struct passwd *savepw; struct passwd *pw; char *user = NULL; char *mach = NULL; char *dom = NULL;#ifdef DEBUG fprintf(stderr, "getpwent_yp()\n");#endif DEBUG if (pwf == NULL) if((pwf=fopen(_pw_file, "r")) == NULL) return NULL; if((domain=yellowup(1)) == NULL) return NULL; for (;;) { if (yp) { pw = interpretwithsave(yp, yplen, savepw); free(yp); getnextfromyellow(); if (pw != NULL && !onminuslist(pw)) { return(pw); } } else if (getnetgrent(&mach,&user,&dom)) { if (user) { pw = getnamefromyellow(user, savepw); if (pw != NULL && !onminuslist(pw)) { return(pw); } } } else { endnetgrent(); do { if (fgets(line1, BUFSIZ, pwf) == NULL) { return(NULL); } pw = interpret(line1, strlen(line1)); } while(pw == NULL); switch(line1[0]) { case '+': if (strcmp(pw->pw_name, "+") == 0) { getfirstfromyellow(); savepw = save(pw); } else if (line1[1] == '@') { savepw = save(pw); if (innetgr(pw->pw_name+2,(char *) NULL, "*",domain)) { /* include the whole yp database */ getfirstfromyellow(); } else { setnetgrent(pw->pw_name+2); } } else { /* * else look up this entry * in yellow pages */ savepw = save(pw); pw = getnamefromyellow(pw->pw_name+1, savepw); if (pw != NULL && !onminuslist(pw)) { return(pw); } } break; case '-': if (line1[1] == '@') { if (innetgr(pw->pw_name+2,(char *) NULL, "*",domain)) { /* everybody was subtracted */ return(NULL); } setnetgrent(pw->pw_name+2); while (getnetgrent(&mach,&user,&dom)) { if (user) { addtominuslist(user); } } endnetgrent(); } else { addtominuslist(pw->pw_name+1); } break; default: if (!onminuslist(pw)) { return(pw); } break; } } }}staticmatchname(line1, pwp, name) register char *line1; register struct passwd **pwp; register char *name;{ register struct passwd *savepw; register struct passwd *pw = *pwp; switch(line1[0]) { case '+': if (strcmp(pw->pw_name, "+") == 0) { savepw = save(pw); pw = getnamefromyellow(name, savepw); if (pw) { *pwp = pw; return(1); } else return(0); } if (line1[1] == '@') { if (innetgr(pw->pw_name+2,(char *) NULL, name,domain)) { savepw = save(pw); pw = getnamefromyellow(name,savepw); if (pw) { *pwp = pw; return(1); } } return(0); } if (strcmp(pw->pw_name+1, name) == 0) { savepw = save(pw); pw = getnamefromyellow(pw->pw_name+1, savepw); if (pw) { *pwp = pw; return(1); } else return(0); } break; case '-': if (line1[1] == '@') { if (innetgr(pw->pw_name+2,(char *) NULL, name,domain)) { *pwp = NULL; return(1); } } else if (strcmp(pw->pw_name+1, name) == 0) { *pwp = NULL; return(1); } break; default: if (pw->pw_name[0] == name[0]) /* avoid calls */ if (strcmp(pw->pw_name, name) == 0) return(1); } return(0);}staticmatchuid(line1, pwp, uid) register char *line1; register struct passwd **pwp; register int uid;{ register struct passwd *savepw; register struct passwd *pw = *pwp; char group[256]; switch(line1[0]) { case '+': if (strcmp(pw->pw_name, "+") == 0) { savepw = save(pw); pw = getuidfromyellow(uid, savepw); if (pw) { *pwp = pw; return(1); } else { return(0); } } if (line1[1] == '@') { (void) strcpy(group,pw->pw_name+2); savepw = save(pw); pw = getuidfromyellow(uid,savepw); if (pw && innetgr(group,(char *) NULL, pw->pw_name,domain)) { *pwp = pw; return(1); } else { return(0); } } savepw = save(pw); pw = getnamefromyellow(pw->pw_name+1, savepw); if (pw && pw->pw_uid == uid) { *pwp = pw; return(1); } else return(0); case '-': if (line1[1] == '@') { (void) strcpy(group,pw->pw_name+2); pw = getuidfromyellow(uid,&NULLPW); if (pw && innetgr(group,(char *) NULL, pw->pw_name,domain)) { *pwp = NULL; return(1); } } else if (uid == uidof(pw->pw_name+1)) { *pwp = NULL; return(1); } break; default: if (pw->pw_uid == uid) return(1); } return(0);}staticuidof(name) char *name;{ struct passwd *pw; struct passwd nullpw; nullpw = NULLPW; pw = getnamefromyellow(name, &nullpw); if (pw) return(pw->pw_uid); else return(MAXINT);}staticgetnextfromyellow(){ int reason = 0; char *key = NULL; int keylen = 0; reason = yp_next(domain, "passwd.byname",oldyp, oldyplen, &key, &keylen,&yp,&yplen); if (reason) {#ifdef DEBUG fprintf(stderr, "reason yp_next failed is %d\n", reason);#endif DEBUG yp = NULL; } if (oldyp) free(oldyp); oldyp = key; oldyplen = keylen;}staticgetfirstfromyellow(){ int reason = 0; char *key = NULL; int keylen = 0; reason = yp_first(domain, "passwd.byname", &key, &keylen, &yp, &yplen); if (reason) {#ifdef DEBUG fprintf(stderr, "reason yp_first failed is %d\n", reason);#endif DEBUG yp = NULL; } if (oldyp) free(oldyp); oldyp = key; oldyplen = keylen;}static struct passwd *getnamefromyellow(name, savepw) char *name; struct passwd *savepw;{ struct passwd *pw; int reason = 0; char *val = NULL; int vallen = 0; reason = yp_match(domain, "passwd.byname", name, strlen(name) , &val, &vallen); if (reason) {#ifdef DEBUG fprintf(stderr, "reason yp_next failed is %d\n", reason);#endif DEBUG return(NULL); } else { pw = interpret(val, vallen); if (pw == NULL) return(NULL); free(val); if (savepw->pw_passwd && *savepw->pw_passwd) pw->pw_passwd = savepw->pw_passwd; if (savepw->pw_gecos && *savepw->pw_gecos) pw->pw_gecos = savepw->pw_gecos; if (savepw->pw_dir && *savepw->pw_dir) pw->pw_dir = savepw->pw_dir; if (savepw->pw_shell && *savepw->pw_shell) pw->pw_shell = savepw->pw_shell; return(pw); }}static struct passwd *getuidfromyellow(uid, savepw) int uid; struct passwd *savepw;{ struct passwd *pw; int reason = 0; char *val = NULL; int vallen = 0; char uidstr[20]; (void) sprintf(uidstr, "%d", uid); reason = yp_match(domain, "passwd.byuid", uidstr, strlen(uidstr) , &val, &vallen); if (reason) {#ifdef DEBUG fprintf(stderr, "reason yp_next failed is %d\n", reason);#endif DEBUG return(NULL); } else { pw = interpret(val, vallen); if (pw == NULL) return(NULL); free(val); if (savepw->pw_passwd && *savepw->pw_passwd) pw->pw_passwd = savepw->pw_passwd; if (savepw->pw_gecos && *savepw->pw_gecos) pw->pw_gecos = savepw->pw_gecos; if (savepw->pw_dir && *savepw->pw_dir) pw->pw_dir = savepw->pw_dir; if (savepw->pw_shell && *savepw->pw_shell) pw->pw_shell = savepw->pw_shell; return(pw); }}static struct passwd *interpretwithsave(val, len, savepw) register char *val; register struct passwd *savepw;{ register struct passwd *pw; pw = interpret(val, len); if (pw == NULL) return(NULL); if (savepw->pw_passwd && *savepw->pw_passwd) pw->pw_passwd = savepw->pw_passwd; if (savepw->pw_gecos && *savepw->pw_gecos) pw->pw_gecos = savepw->pw_gecos; if (savepw->pw_dir && *savepw->pw_dir) pw->pw_dir = savepw->pw_dir; if (savepw->pw_shell && *savepw->pw_shell) pw->pw_shell = savepw->pw_shell; return(pw);}/* * Build a passwd structure from the passwd file entry line in val. * A pointer to the created passwd structure will be returned, unless the * passwd entry in val is "bad". A bad entry is defined to be one * that has less than 4 colons and that does not start with a '+' or * a '-' (for yp). */static struct passwd *interpret(val, len) char *val; int len;{ register char *p, *v; register int i; int colon_count = 0; static struct passwd passwd; static char line[BUFSIZ+1]; register struct passwd *pw = &passwd; p = line; v = val; for (i = 0; i < len; i++) { if ((*p++ = *v++) == '\0') { while (++i < len) *p++ = '\0'; break; } } *p++ = '\n'; *p = 0; p = line; pw->pw_name = p; PWSKIP(p); pw->pw_passwd = p; PWSKIP(p); if (colon_count < 2 && (pw->pw_name[0] != '+' && pw->pw_name[0] != '-')) pw->pw_uid = NOBODY; else ATOI(p,pw->pw_uid); PWSKIP(p); if (colon_count < 3 && (pw->pw_name[0] != '+' && pw->pw_name[0] != '-')) pw->pw_gid = NOBODY; else ATOI(p,pw->pw_gid); /* The only difference in the pwd structure between ULTRIX * and System V is in the definition of the following field. * However, both systems ignore it because it is not present * in the actual password file. */#ifndef SYSTEM_FIVE pw->pw_quota = 0;#else SYSTEM_FIVE pw->pw_age = (char *) 0;#endif SYSTEM_FIVE pw->pw_comment = EMPTY; PWSKIP(p); pw->pw_gecos = p; PWSKIP(p); pw->pw_dir = p; PWSKIP(p); pw->pw_shell = p; while(*p && *p != '\n') p++; *p = '\0'; if (colon_count < 4 && (pw->pw_name[0] != '+' && pw->pw_name[0] != '-')) return(NULL); else return(pw);}staticfreeminuslist(){ struct list *ls; for (ls = minuslist; ls != NULL; ls = ls->nxt) { free(ls->name); free((char *) ls); } minuslist = NULL;}staticaddtominuslist(name) char *name;{ struct list *ls; char *buf; ls = (struct list *) malloc(sizeof(struct list)); buf = malloc((unsigned) strlen(name) + 1); (void) strcpy(buf, name); ls->name = buf; ls->nxt = minuslist; minuslist = ls;}/* * save away psswd, gecos, dir and shell fields, which are the only * ones which can be specified in a local + entry to override the * value in the yellow pages */static struct passwd *save(pw) struct passwd *pw;{ static struct passwd *sv; /* free up stuff from last call */ if (sv) { free(sv->pw_passwd); free(sv->pw_gecos); free(sv->pw_dir); free(sv->pw_shell); free((char *) sv); } sv = (struct passwd *) malloc(sizeof(struct passwd)); sv->pw_passwd = malloc((unsigned) strlen(pw->pw_passwd) + 1); (void) strcpy(sv->pw_passwd, pw->pw_passwd); sv->pw_gecos = malloc((unsigned) strlen(pw->pw_gecos) + 1); (void) strcpy(sv->pw_gecos, pw->pw_gecos); sv->pw_dir = malloc((unsigned) strlen(pw->pw_dir) + 1); (void) strcpy(sv->pw_dir, pw->pw_dir); sv->pw_shell = malloc((unsigned) strlen(pw->pw_shell) + 1); (void) strcpy(sv->pw_shell, pw->pw_shell); return(sv);}staticonminuslist(pw) struct passwd *pw;{ struct list *ls; register char *nm; nm = pw->pw_name; for (ls = minuslist; ls != NULL; ls = ls->nxt) { if (strcmp(ls->name,nm) == 0) { return(1); } } return(0);} staticstruct passwd *pwcommon(pp)char **pp;{ register char *p; if (pp == NULL) return(NULL); /* choose only the first response (only 1 expected) */ strcpy(buf, pp[0]); while(*pp) free(*pp++); /* necessary to avoid leaks */ p = buf; passwd.pw_name = p; p = pwskip(p); passwd.pw_passwd = p; p = pwskip(p); passwd.pw_uid = atoi(p); p = pwskip(p); passwd.pw_gid = atoi(p);#ifndef SYSTEM_FIVE passwd.pw_quota = 0;#else passwd.pw_age = (char *) 0;#endif passwd.pw_comment = EMPTY; p = pwskip(p); passwd.pw_gecos = p; p = pwskip(p); passwd.pw_dir = p; p = pwskip(p); passwd.pw_shell = p; while (*p && *p != '\n') p++; *p = '\0'; return(&passwd);}static char *pwskip(p)register char *p;{ while (*p && *p != ':' && *p != '\n') ++p; if (*p) *p++ = 0; return(p);}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -