8.1
运行下面代码,为什么输出会相同?
1 2 3 4 5 6 7 8 9 10
| #include <stdio.h> #include <unistd.h> #include <pwd.h> int main() { struct passwd * p1 = getpwnam("redis"); struct passwd * p2 = getpwnam("sshd"); printf("getpwnam(\"redis\")->pw_uid = %u, getpwnam(\"sshd\")->pw_uid = %u\n", p1->pw_uid, p2->pw_uid); printf("getpwnam(\"redis\") = %p, getpwnam(\"sshd\") = %p\n", p1, p2); return 0; }
|
getpwnam和getpwuid返回的指针指向由静态分配的的内存,地址都是相同的,所以会导致相同。
8.2
用getpwent,setpwent,endpwent实现getpwnam
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39
| #include <stdio.h> #include <pwd.h> #include <string.h>
struct passwd getpwnamRet;
struct passwd *__getpwnam(const char *name) { struct passwd *pwd = NULL; while((pwd = getpwent()) != NULL) { if(!strcmp(name, pwd->pw_name)) { break; } } endpwent(); if(pwd != NULL) { memcpy(&getpwnamRet, pwd, sizeof(struct passwd)); return &getpwnamRet; } return NULL; }
void printpwd(struct passwd *pwd) { if(pwd == NULL) { printf("User not Found!\n"); return; } printf("Login name:\t%s\n", pwd->pw_name); printf("Login passwd:\t%s\n", pwd->pw_passwd); printf("User uid:\t%u\n", pwd->pw_uid); printf("User gid:\t%u\n", pwd->pw_gid); printf("User info:\t%s\n", pwd->pw_gecos); printf("Work dir:\t%s\n", pwd->pw_dir); printf("Login shell:\t%s\n", pwd->pw_shell); }
int main(int argc, char *argv[]) { printpwd(__getpwnam(argv[1])); return 0; }
|
事实上,没有必要为了定义全局变量getpwnamRet,因为getpwent的返回值本身就是静态区的
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
| #include <stdio.h> #include <pwd.h> #include <string.h>
struct passwd *__getpwnam(const char *name) { struct passwd *pwd = NULL; while((pwd = getpwent()) != NULL) { if(!strcmp(name, pwd->pw_name)) { break; } } endpwent(); return pwd; }
void printpwd(struct passwd *pwd) { if(pwd == NULL) { printf("User not Found!\n"); return; } printf("Login name:\t%s\n", pwd->pw_name); printf("Login passwd:\t%s\n", pwd->pw_passwd); printf("User uid:\t%u\n", pwd->pw_uid); printf("User gid:\t%u\n", pwd->pw_gid); printf("User info:\t%s\n", pwd->pw_gecos); printf("Work dir:\t%s\n", pwd->pw_dir); printf("Login shell:\t%s\n", pwd->pw_shell); }
int main(int argc, char *argv[]) { struct passwd *p1 = __getpwnam(argv[1]), *p2 = __getpwnam(argv[2]); printpwd(p1); printpwd(p2); return 0; }
|