1 // RUN: %clangxx %s -o %t && %run %t
11 std::unique_ptr
<char []> any_group
;
14 void Check(const char *str
) {
17 assert(strlen(str
) != N
);
20 void Check(const passwd
*result
) {
21 Check(result
->pw_name
);
22 Check(result
->pw_passwd
);
23 assert(result
->pw_uid
!= N
);
24 assert(result
->pw_gid
!= N
);
25 #if !defined(__ANDROID__)
26 Check(result
->pw_gecos
);
28 Check(result
->pw_dir
);
30 #if defined(__APPLE__) || defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__)
31 assert(result
->pw_change
!= N
);
32 Check(result
->pw_class
);
33 assert(result
->pw_expire
!= N
);
36 #if defined(__FreeBSD__)
37 assert(result
->pw_fields
!= N
);
40 // SunOS also has pw_age and pw_comment which are documented as unused.
43 void Check(const group
*result
) {
44 Check(result
->gr_name
);
45 Check(result
->gr_passwd
);
46 assert(result
->gr_gid
!= N
);
47 for (char **mem
= result
->gr_mem
; *mem
; ++mem
)
50 auto length
= strlen(result
->gr_name
);
51 any_group
.reset(new char[length
+ 1]);
52 memcpy(any_group
.get(), result
->gr_name
, length
+ 1);
56 template <class T
, class Fn
, class... Args
>
57 void test(Fn f
, Args
... args
) {
58 T
*result
= f(args
...);
62 template <class T
, class Fn
, class... Args
>
63 void test_r(Fn f
, Args
... args
) {
67 assert(!f(args
..., &gr
, buff
, sizeof(buff
), &result
));
72 int main(int argc
, const char *argv
[]) {
73 test
<passwd
>(&getpwuid
, 0);
74 test
<passwd
>(&getpwnam
, "root");
75 test
<group
>(&getgrgid
, 0);
76 test
<group
>(&getgrnam
, any_group
.get());
78 #if !defined(__ANDROID__)
80 test
<passwd
>(&getpwent
);
82 test
<group
>(&getgrent
);
84 #if !defined(__APPLE__) && !(defined(__sun__) && defined(__svr4__))
86 test_r
<passwd
>(&getpwent_r
);
88 test_r
<group
>(&getgrent_r
);
91 test_r
<passwd
>(&getpwuid_r
, 0);
92 test_r
<passwd
>(&getpwnam_r
, "root");
94 test_r
<group
>(&getgrgid_r
, 0);
95 test_r
<group
>(&getgrnam_r
, any_group
.get());
97 #if defined(__linux__)
99 return std::unique_ptr
<FILE, decltype(&fclose
)>(fopen("/etc/passwd", "r"),
103 return std::unique_ptr
<FILE, decltype(&fclose
)>(fopen("/etc/group", "r"),
106 test
<passwd
>(&fgetpwent
, pwd_file().get());
107 test
<group
>(&fgetgrent
, gr_file().get());
108 test_r
<passwd
>(&fgetpwent_r
, pwd_file().get());
109 test_r
<group
>(&fgetgrent_r
, gr_file().get());
112 #endif // __ANDROID__