1 /* $FreeBSD$ */
2
3 #include <sys/types.h>
4 #include <sys/wait.h>
5 #include <sys/mman.h>
6 #include <semaphore.h>
7 #include <stdio.h>
8 #include <stdlib.h>
9 #include <err.h>
10 #include <errno.h>
11 #include <fcntl.h>
12 #include <unistd.h>
13
14 #define SEM_NAME "/semtst"
15
16 int test_unnamed(void);
17 int test_named(void);
18 int test_named2(void);
19
20 int
test_unnamed(void)21 test_unnamed(void)
22 {
23 sem_t *s;
24 pid_t pid;
25 int status;
26
27 printf("testing unnamed process-shared semaphore\n");
28 s = (sem_t *)mmap(NULL, sizeof(sem_t), PROT_READ|PROT_WRITE, MAP_ANON|MAP_SHARED,
29 -1, 0);
30 if (s == MAP_FAILED)
31 err(1, "mmap failed");
32 if (sem_init(s, 1, 0))
33 err(2, "sem_init failed");
34 if ((pid = fork()) == 0) {
35 printf("child: sem_wait()\n");
36 if (sem_wait(s))
37 err(3, "sem_wait failed");
38 printf("child: sem_wait() returned\n");
39 exit(0);
40 } else {
41 sleep(1);
42 printf("parent: sem_post()\n");
43 if (sem_post(s))
44 err(4, "sem_post failed");
45 waitpid(pid, &status, 0);
46 if (WIFEXITED(status) && WEXITSTATUS(status) == 0)
47 printf("OK.\n");
48 else
49 printf("Failure.");
50 }
51 return (0);
52 }
53
54 int
test_named(void)55 test_named(void)
56 {
57 sem_t *s, *s2;
58 pid_t pid;
59 int status;
60
61 printf("testing named process-shared semaphore\n");
62 sem_unlink(SEM_NAME);
63 s = sem_open(SEM_NAME, O_CREAT, 0777, 0);
64 if (s == SEM_FAILED)
65 err(1, "sem_open failed");
66 s2 = sem_open(SEM_NAME, O_CREAT, 0777, 0);
67 if (s2 == SEM_FAILED)
68 err(2, "second sem_open call failed");
69 if (s != s2)
70 errx(3,
71 "two sem_open calls for same semaphore do not return same address");
72 if (sem_close(s2))
73 err(4, "sem_close failed");
74 if ((pid = fork()) == 0) {
75 printf("child: sem_wait()\n");
76 if (sem_wait(s))
77 err(5, "sem_wait failed");
78 printf("child: sem_wait() returned\n");
79 exit(0);
80 } else {
81 sleep(1);
82 printf("parent: sem_post()\n");
83 if (sem_post(s))
84 err(6, "sem_post failed");
85 waitpid(pid, &status, 0);
86 if (WIFEXITED(status) && WEXITSTATUS(status) == 0)
87 printf("OK.\n");
88 else
89 printf("Failure.");
90 }
91
92 if (sem_close(s))
93 err(7, "sem_close failed");
94
95 return (0);
96 }
97
98 int
test_named2(void)99 test_named2(void)
100 {
101 sem_t *s, *s2, *s3;
102
103 printf("testing named process-shared semaphore, O_EXCL cases\n");
104 sem_unlink(SEM_NAME);
105 s = sem_open(SEM_NAME, O_CREAT | O_EXCL, 0777, 0);
106 if (s == SEM_FAILED)
107 err(1, "sem_open failed");
108 s2 = sem_open(SEM_NAME, O_CREAT | O_EXCL, 0777, 0);
109 if (s2 != SEM_FAILED)
110 errx(2, "second sem_open call wrongly succeeded");
111 if (errno != EEXIST)
112 err(3, "second sem_open call failed with wrong errno");
113
114 s3 = sem_open(SEM_NAME, 0);
115 if (s3 == SEM_FAILED)
116 err(4, "third sem_open call failed");
117 if (s != s3)
118 errx(5,
119 "two sem_open calls for same semaphore do not return same address");
120 if (sem_close(s3))
121 err(6, "sem_close failed");
122
123 if (sem_close(s))
124 err(7, "sem_close failed");
125
126 printf("OK.\n");
127 return (0);
128 }
129
130 int
main(void)131 main(void)
132 {
133 test_unnamed();
134 test_named();
135 test_named2();
136 return (0);
137 }
138