xref: /minix3/minix/tests/test88.c (revision 5ef5b27fc158620d80785f43f03fc1ff30cbe16f)
1 /* Tests for System V IPC semaphores - by D.C. van Moolenbroek */
2 /* This test must be run as root, as it includes permission checking tests. */
3 #include <stdlib.h>
4 #include <limits.h>
5 #include <pwd.h>
6 #include <grp.h>
7 #include <sys/ipc.h>
8 #include <sys/sem.h>
9 #include <sys/wait.h>
10 #include <sys/mman.h>
11 #include <signal.h>
12 
13 #include "common.h"
14 
15 #define ITERATIONS	3
16 
17 #define WAIT_USECS	100000		/* time for processes to get ready */
18 
19 #define KEY_A		0x73570001
20 #define KEY_B		(KEY_A + 1)
21 #define KEY_C		(KEY_A + 2)
22 
23 #define ROOT_USER	"root"		/* name of root */
24 #define ROOT_GROUP	"operator"	/* name of root's group */
25 #define NONROOT_USER	"bin"		/* name of any unprivileged user */
26 #define NONROOT_GROUP	"bin"		/* name of any unprivileged group */
27 
28 enum {
29 	DROP_NONE,
30 	DROP_USER,
31 	DROP_ALL,
32 };
33 
34 enum {
35 	SUGID_NONE,
36 	SUGID_ROOT_USER,
37 	SUGID_NONROOT_USER,
38 	SUGID_ROOT_GROUP,
39 	SUGID_NONROOT_GROUP,
40 };
41 
42 struct link {
43 	pid_t pid;
44 	int sndfd;
45 	int rcvfd;
46 };
47 
48 /*
49  * Test semaphore properties.  This is a macro, so that it prints useful line
50  * information if an error occurs.
51  */
52 #define TEST_SEM(id, num, val, pid, ncnt, zcnt) do { \
53 	if (semctl(id, num, GETVAL) != val) e(0); \
54 	if (pid != -1 && semctl(id, num, GETPID) != pid) e(1); \
55 	if (ncnt != -1 && semctl(id, num, GETNCNT) != ncnt) e(2); \
56 	if (zcnt != -1 && semctl(id, num, GETZCNT) != zcnt) e(3); \
57 } while (0);
58 
59 static int nr_signals = 0;
60 
61 static size_t page_size;
62 static char *page_ptr;
63 static void *bad_ptr;
64 
65 /*
66  * Spawn a child process, with a pair of pipes to talk to it bidirectionally.
67  * Drop user and group privileges in the child process if requested.
68  */
69 static void
70 spawn(struct link * link, void (* proc)(), int drop)
71 {
72 	struct passwd *pw;
73 	struct group *gr;
74 	int up[2], dn[2];
75 
76 	fflush(stdout);
77 	fflush(stderr);
78 
79 	if (pipe(up) != 0) e(0);
80 	if (pipe(dn) != 0) e(0);
81 
82 	link->pid = fork();
83 
84 	switch (link->pid) {
85 	case 0:
86 		close(up[1]);
87 		close(dn[0]);
88 
89 		link->pid = getppid();
90 		link->rcvfd = up[0];
91 		link->sndfd = dn[1];
92 
93 		errct = 0;
94 
95 		switch (drop) {
96 		case DROP_ALL:
97 			if (setgroups(0, NULL) != 0) e(0);
98 
99 			if ((gr = getgrnam(NONROOT_GROUP)) == NULL) e(0);
100 
101 			if (setgid(gr->gr_gid) != 0) e(0);
102 			if (setegid(gr->gr_gid) != 0) e(0);
103 
104 			/* FALLTHROUGH */
105 		case DROP_USER:
106 			if ((pw = getpwnam(NONROOT_USER)) == NULL) e(0);
107 
108 			/* FIXME: this may rely on a MINIXism. */
109 			if (setuid(pw->pw_uid) != 0) e(0);
110 			if (seteuid(pw->pw_uid) != 0) e(0);
111 		}
112 
113 		proc(link);
114 
115 		/* Close our pipe FDs on exit, so that we can make zombies. */
116 		exit(errct);
117 	case -1:
118 		e(0);
119 		break;
120 	}
121 
122 	close(up[0]);
123 	close(dn[1]);
124 
125 	link->sndfd = up[1];
126 	link->rcvfd = dn[0];
127 }
128 
129 /*
130  * Wait for a child process to terminate, and clean up.
131  */
132 static void
133 collect(struct link * link)
134 {
135 	int status;
136 
137 	close(link->sndfd);
138 	close(link->rcvfd);
139 
140 	if (waitpid(link->pid, &status, 0) != link->pid) e(0);
141 
142 	if (!WIFEXITED(status)) e(0);
143 	else errct += WEXITSTATUS(status);
144 }
145 
146 /*
147  * Forcibly terminate a child process, and clean up.
148  */
149 static void
150 terminate(struct link * link)
151 {
152 	int status;
153 
154 	if (kill(link->pid, SIGKILL) != 0) e(0);
155 
156 	close(link->sndfd);
157 	close(link->rcvfd);
158 
159 	if (waitpid(link->pid, &status, 0) <= 0) e(0);
160 
161 	if (WIFSIGNALED(status)) {
162 		if (WTERMSIG(status) != SIGKILL) e(0);
163 	} else {
164 		if (!WIFEXITED(status)) e(0);
165 		else errct += WEXITSTATUS(status);
166 	}
167 }
168 
169 /*
170  * Send an integer value to the child or parent.
171  */
172 static void
173 snd(struct link * link, int val)
174 {
175 
176 	if (write(link->sndfd, (void *)&val, sizeof(val)) != sizeof(val)) e(0);
177 }
178 
179 /*
180  * Receive an integer value from the child or parent, or -1 on EOF.
181  */
182 static int
183 rcv(struct link * link)
184 {
185 	int r, val;
186 
187 	if ((r = read(link->rcvfd, (void *)&val, sizeof(val))) == 0)
188 		return -1;
189 
190 	if (r != sizeof(val)) e(0);
191 
192 	return val;
193 }
194 
195 /*
196  * Child procedure that creates semaphore sets.
197  */
198 static void
199 test_perm_child(struct link * parent)
200 {
201 	struct passwd *pw;
202 	struct group *gr;
203 	struct semid_ds semds;
204 	uid_t uid;
205 	gid_t gid;
206 	int mask, rmask, sugid, id[3];
207 
208 	/*
209 	 * Repeatedly create a number of semaphores with the masks provided by
210 	 * the parent process.
211 	 */
212 	while ((mask = rcv(parent)) != -1) {
213 		rmask = rcv(parent);
214 		sugid = rcv(parent);
215 
216 		/*
217 		 * Create the semaphores.  For KEY_A, if we are going to set
218 		 * the mode through IPC_SET anyway, start with a zero mask to
219 		 * check that the replaced mode is used (thus testing IPC_SET).
220 		 */
221 		if ((id[0] = semget(KEY_A, 3,
222 		    IPC_CREAT | IPC_EXCL |
223 		    ((sugid == SUGID_NONE) ? mask : 0))) == -1) e(0);
224 		if ((id[1] = semget(KEY_B, 3,
225 		    IPC_CREAT | IPC_EXCL | mask | rmask)) == -1) e(0);
226 		if ((id[2] = semget(KEY_C, 3,
227 		    IPC_CREAT | IPC_EXCL | rmask)) == -1) e(0);
228 
229 		uid = geteuid();
230 		gid = getegid();
231 		if (sugid != SUGID_NONE) {
232 			switch (sugid) {
233 			case SUGID_ROOT_USER:
234 				if ((pw = getpwnam(ROOT_USER)) == NULL) e(0);
235 				uid = pw->pw_uid;
236 				break;
237 			case SUGID_NONROOT_USER:
238 				if ((pw = getpwnam(NONROOT_USER)) == NULL)
239 					e(0);
240 				uid = pw->pw_uid;
241 				break;
242 			case SUGID_ROOT_GROUP:
243 				if ((gr = getgrnam(ROOT_GROUP)) == NULL) e(0);
244 				gid = gr->gr_gid;
245 				break;
246 			case SUGID_NONROOT_GROUP:
247 				if ((gr = getgrnam(NONROOT_GROUP)) == NULL)
248 					e(0);
249 				gid = gr->gr_gid;
250 				break;
251 			}
252 
253 			semds.sem_perm.uid = uid;
254 			semds.sem_perm.gid = gid;
255 			semds.sem_perm.mode = mask;
256 			if (semctl(id[0], 0, IPC_SET, &semds) != 0) e(0);
257 			semds.sem_perm.mode = mask | rmask;
258 			if (semctl(id[1], 0, IPC_SET, &semds) != 0) e(0);
259 			semds.sem_perm.mode = rmask;
260 			if (semctl(id[2], 0, IPC_SET, &semds) != 0) e(0);
261 		}
262 
263 		/* Do a quick test to confirm the right privileges. */
264 		if (mask & IPC_R) {
265 			if (semctl(id[0], 0, IPC_STAT, &semds) != 0) e(0);
266 			if (semds.sem_perm.mode != (SEM_ALLOC | mask)) e(0);
267 			if (semds.sem_perm.uid != uid) e(0);
268 			if (semds.sem_perm.gid != gid) e(0);
269 			if (semds.sem_perm.cuid != geteuid()) e(0);
270 			if (semds.sem_perm.cgid != getegid()) e(0);
271 		}
272 
273 		snd(parent, id[0]);
274 		snd(parent, id[1]);
275 		snd(parent, id[2]);
276 
277 		/* The other child process runs here. */
278 
279 		if (rcv(parent) != 0) e(0);
280 
281 		/*
282 		 * For owner tests, the other child may already have removed
283 		 * the semaphore sets, so ignore return values here.
284 		 */
285 		(void)semctl(id[0], 0, IPC_RMID);
286 		(void)semctl(id[1], 0, IPC_RMID);
287 		(void)semctl(id[2], 0, IPC_RMID);
288 	}
289 }
290 
291 /*
292  * Perform a permission test.  The given procedure will be called for various
293  * access masks, which it can use to determine whether operations on three
294  * created semaphore sets should succeed or fail.  The first two semaphore sets
295  * are created with appropriate privileges, the third one is not.  If the
296  * 'owner_test' variable is set, the test will change slightly so as to allow
297  * testing of operations that require a matching uid/cuid.
298  */
299 static void
300 test_perm(void (* proc)(struct link *), int owner_test)
301 {
302 	struct link child1, child2;
303 	int n, shift, bit, mask, rmask, drop1, drop2, sugid, id[3];
304 
305 	for (n = 0; n < 7; n++) {
306 		/*
307 		 * Child 1 creates the semaphores, and child 2 opens them.
308 		 * For shift 6 (0700), child 1 drops its privileges to match
309 		 * child 2's (n=0).  For shift 3 (0070), child 2 drops its user
310 		 * privileges (n=3).  For shift 0 (0007), child 2 drops its
311 		 * group in addition to its user privileges (n=6).  Also try
312 		 * with differing uid/cuid (n=1,2) and gid/cgid (n=4,5), where
313 		 * the current ownership (n=1,4) or the creator's ownership
314 		 * (n=2,5) is tested.
315 		 */
316 		switch (n) {
317 		case 0:
318 			shift = 6;
319 			drop1 = DROP_ALL;
320 			drop2 = DROP_ALL;
321 			sugid = SUGID_NONE;
322 			break;
323 		case 1:
324 			shift = 6;
325 			drop1 = DROP_NONE;
326 			drop2 = DROP_ALL;
327 			sugid = SUGID_NONROOT_USER;
328 			break;
329 		case 2:
330 			shift = 6;
331 			drop1 = DROP_USER;
332 			drop2 = DROP_ALL;
333 			sugid = SUGID_ROOT_USER;
334 			break;
335 		case 3:
336 			shift = 3;
337 			drop1 = DROP_NONE;
338 			drop2 = DROP_USER;
339 			sugid = SUGID_NONE;
340 			break;
341 		case 4:
342 			shift = 3;
343 			drop1 = DROP_NONE;
344 			drop2 = DROP_ALL;
345 			sugid = SUGID_NONROOT_GROUP;
346 			break;
347 		case 5:
348 			/* The root group has no special privileges. */
349 			shift = 3;
350 			drop1 = DROP_NONE;
351 			drop2 = DROP_USER;
352 			sugid = SUGID_NONROOT_GROUP;
353 			break;
354 		case 6:
355 			shift = 0;
356 			drop1 = DROP_NONE;
357 			drop2 = DROP_ALL;
358 			sugid = SUGID_NONE;
359 			break;
360 		}
361 
362 		spawn(&child1, test_perm_child, drop1);
363 		spawn(&child2, proc, drop2);
364 
365 		for (bit = 0; bit <= 7; bit++) {
366 			mask = bit << shift;
367 			rmask = 0777 & ~(7 << shift);
368 
369 			snd(&child1, mask);
370 			snd(&child1, rmask);
371 			snd(&child1, sugid);
372 			id[0] = rcv(&child1);
373 			id[1] = rcv(&child1);
374 			id[2] = rcv(&child1);
375 
376 			snd(&child2, (owner_test) ? shift : bit);
377 			snd(&child2, id[0]);
378 			snd(&child2, id[1]);
379 			snd(&child2, id[2]);
380 			if (rcv(&child2) != 0) e(0);
381 
382 			snd(&child1, 0);
383 		}
384 
385 		/* We use a bitmask of -1 to terminate the children. */
386 		snd(&child1, -1);
387 		snd(&child2, -1);
388 
389 		collect(&child1);
390 		collect(&child2);
391 	}
392 }
393 
394 /*
395  * Test semget(2) permission checks.  Please note that the checks are advisory:
396  * nothing keeps a process from opening a semaphore set with fewer privileges
397  * than required by the operations the process subsequently issues on the set.
398  */
399 static void
400 test88a_perm(struct link * parent)
401 {
402 	int r, tbit, bit, mask, id[3];
403 
404 	while ((tbit = rcv(parent)) != -1) {
405 		id[0] = rcv(parent);
406 		id[1] = rcv(parent);
407 		id[2] = rcv(parent);
408 
409 		/*
410 		 * We skip setting lower bits, as it is not clear what effect
411 		 * that should have.  We assume that zero bits should result in
412 		 * failure.
413 		 */
414 		for (bit = 0; bit <= 7; bit++) {
415 			mask = bit << 6;
416 
417 			/*
418 			 * Opening semaphore set A must succeed iff the given
419 			 * bits are all set in the relevant three-bit section
420 			 * of the creation mask.
421 			 */
422 			r = semget(KEY_A, 0, mask);
423 			if (r < 0 && (r != -1 || errno != EACCES)) e(0);
424 			if ((bit != 0 && (bit & tbit) == bit) != (r != -1))
425 				e(0);
426 			if (r != -1 && r != id[0]) e(0);
427 
428 			/*
429 			 * Same for semaphore set B, which was created with all
430 			 * irrelevant mode bits inverted.
431 			 */
432 			r = semget(KEY_B, 0, mask);
433 			if (r < 0 && (r != -1 || errno != EACCES)) e(0);
434 			if ((bit != 0 && (bit & tbit) == bit) != (r != -1))
435 				e(0);
436 			if (r != -1 && r != id[1]) e(0);
437 
438 			/*
439 			 * Semaphore set C was created with only irrelevant
440 			 * mode bits set, so opening it must always fail.
441 			 */
442 			if (semget(KEY_C, 0, mask) != -1) e(0);
443 			if (errno != EACCES) e(0);
444 		}
445 
446 		snd(parent, 0);
447 	}
448 }
449 
450 /*
451  * Test the basic semget(2) functionality.
452  */
453 static void
454 test88a(void)
455 {
456 	struct seminfo seminfo;
457 	struct semid_ds semds;
458 	time_t now;
459 	unsigned int i, j;
460 	int id[3], *idp;
461 
462 	subtest = 0;
463 
464 	/*
465 	 * The key IPC_PRIVATE must always yield a new semaphore set identifier
466 	 * regardless of whether IPC_CREAT and IPC_EXCL are supplied.
467 	 */
468 	if ((id[0] = semget(IPC_PRIVATE, 1, IPC_CREAT | 0600)) < 0) e(0);
469 
470 	if ((id[1] = semget(IPC_PRIVATE, 1, IPC_CREAT | IPC_EXCL | 0600)) < 0)
471 		e(0);
472 
473 	if ((id[2] = semget(IPC_PRIVATE, 1, 0600)) < 0) e(0);
474 
475 	if (id[0] == id[1]) e(0);
476 	if (id[1] == id[2]) e(0);
477 	if (id[0] == id[2]) e(0);
478 
479 	if (semctl(id[0], 0, IPC_RMID) != 0) e(0);
480 	if (semctl(id[1], 0, IPC_RMID) != 0) e(0);
481 	if (semctl(id[2], 0, IPC_RMID) != 0) e(0);
482 
483 	/* Remove any leftovers from previous test runs. */
484 	if ((id[0] = semget(KEY_A, 0, 0600)) >= 0 &&
485 	    semctl(id[0], 0, IPC_RMID) == -1) e(0);
486 	if ((id[0] = semget(KEY_B, 0, 0600)) >= 0 &&
487 	    semctl(id[0], 0, IPC_RMID) == -1) e(0);
488 
489 	/*
490 	 * For non-IPC_PRIVATE keys, open(2)-like semantics apply with respect
491 	 * to IPC_CREAT and IPC_EXCL flags.  The behavior of supplying IPC_EXCL
492 	 * without IPC_CREAT is undefined, so we do not test for that here.
493 	 */
494 	if (semget(KEY_A, 1, 0600) != -1) e(0);
495 	if (errno != ENOENT);
496 
497 	if ((id[0] = semget(KEY_A, 1, IPC_CREAT | IPC_EXCL | 0600)) < 0) e(0);
498 
499 	if (semget(KEY_B, 1, 0600) != -1) e(0);
500 	if (errno != ENOENT);
501 
502 	if ((id[1] = semget(KEY_B, 1, IPC_CREAT | 0600)) < 0) e(0);
503 
504 	if (id[0] == id[1]) e(0);
505 
506 	if ((id[2] = semget(KEY_A, 1, 0600)) < 0) e(0);
507 	if (id[2] != id[0]) e(0);
508 
509 	if ((id[2] = semget(KEY_B, 1, IPC_CREAT | 0600)) < 0) e(0);
510 	if (id[2] != id[2]) e(0);
511 
512 	if (semget(KEY_A, 1, IPC_CREAT | IPC_EXCL | 0600) != -1) e(0);
513 	if (errno != EEXIST) e(0);
514 
515 	if (semctl(id[0], 0, IPC_RMID) != 0) e(0);
516 	if (semctl(id[1], 0, IPC_RMID) != 0) e(0);
517 
518 	/*
519 	 * Check that we get the right error when we run out of semaphore sets.
520 	 * It is possible that other processes in the system are using sets
521 	 * right now, so see if we can anywhere from three (the number we had
522 	 * already) to SEMMNI semaphore sets, and check for ENOSPC after that.
523 	 */
524 	if (semctl(0, 0, IPC_INFO, &seminfo) == -1) e(0);
525 	if (seminfo.semmni < 3 || seminfo.semmni > USHRT_MAX) e(0);
526 
527 	if ((idp = malloc(sizeof(int) * (seminfo.semmni + 1))) == NULL) e(0);
528 
529 	for (i = 0; i < seminfo.semmni + 1; i++) {
530 		if ((idp[i] = semget(KEY_A + i, 1, IPC_CREAT | 0600)) < 0)
531 			break;
532 
533 		/* Ensure that there are no ID collisions.  O(n**2). */
534 		for (j = 0; j < i; j++)
535 			if (idp[i] == idp[j]) e(0);
536 	}
537 
538 	if (errno != ENOSPC) e(0);
539 	if (i < 3) e(0);
540 	if (i == seminfo.semmni + 1) e(0);
541 
542 	while (i-- > 0)
543 		if (semctl(idp[i], 0, IPC_RMID) != 0) e(0);
544 
545 	free(idp);
546 
547 	/*
548 	 * The given number of semaphores must be within bounds.
549 	 */
550 	if (semget(KEY_A, -1, IPC_CREAT | 0600) != -1) e(0);
551 	if (errno != EINVAL) e(0);
552 
553 	if (semget(KEY_A, 0, IPC_CREAT | 0600) != -1) e(0);
554 	if (errno != EINVAL) e(0);
555 
556 	if (seminfo.semmsl < 3 || seminfo.semmsl > USHRT_MAX) e(0);
557 	if (semget(KEY_A, seminfo.semmsl + 1, IPC_CREAT | 0600) != -1) e(0);
558 	if (errno != EINVAL) e(0);
559 
560 	if ((id[0] = semget(KEY_A, seminfo.semmsl, IPC_CREAT | 0600)) < 0)
561 		e(0);
562 	if (semctl(id[0], 0, IPC_RMID) != 0) e(0);
563 
564 	if ((id[0] = semget(KEY_A, 2, IPC_CREAT | 0600)) < 0) e(0);
565 
566 	if ((id[1] = semget(KEY_A, 0, 0600)) < 0) e(0);
567 	if (id[0] != id[1]) e(0);
568 
569 	if ((id[1] = semget(KEY_A, 1, 0600)) < 0) e(0);
570 	if (id[0] != id[1]) e(0);
571 
572 	if ((id[1] = semget(KEY_A, 2, 0600)) < 0) e(0);
573 	if (id[0] != id[1]) e(0);
574 
575 	if ((id[1] = semget(KEY_A, 3, 0600)) != -1) e(0);
576 	if (errno != EINVAL) e(0);
577 
578 	if ((id[1] = semget(KEY_A, seminfo.semmsl + 1, 0600)) != -1) e(0);
579 	if (errno != EINVAL) e(0);
580 
581 	if (semctl(id[0], 0, IPC_RMID) != 0) e(0);
582 
583 	/*
584 	 * Verify that the initial values for the semaphore set are as
585 	 * expected.
586 	 */
587 	time(&now);
588 	if (seminfo.semmns < 3 + seminfo.semmsl) e(0);
589 	if ((id[0] = semget(IPC_PRIVATE, 3, IPC_CREAT | IPC_EXCL | 0642)) < 0)
590 		e(0);
591 	if ((id[1] = semget(KEY_A, seminfo.semmsl, IPC_CREAT | 0613)) < 0)
592 		e(0);
593 
594 	if (semctl(id[0], 0, IPC_STAT, &semds) != 0) e(0);
595 	if (semds.sem_perm.uid != geteuid()) e(0);
596 	if (semds.sem_perm.gid != getegid()) e(0);
597 	if (semds.sem_perm.cuid != geteuid()) e(0);
598 	if (semds.sem_perm.cgid != getegid()) e(0);
599 	if (semds.sem_perm.mode != (SEM_ALLOC | 0642)) e(0);
600 	if (semds.sem_perm._key != IPC_PRIVATE) e(0);
601 	if (semds.sem_nsems != 3) e(0);
602 	if (semds.sem_otime != 0) e(0);
603 	if (semds.sem_ctime < now || semds.sem_ctime >= now + 10) e(0);
604 
605 	for (i = 0; i < semds.sem_nsems; i++)
606 		TEST_SEM(id[0], i, 0, 0, 0, 0);
607 
608 	if (semctl(id[1], 0, IPC_STAT, &semds) != 0) e(0);
609 	if (semds.sem_perm.uid != geteuid()) e(0);
610 	if (semds.sem_perm.gid != getegid()) e(0);
611 	if (semds.sem_perm.cuid != geteuid()) e(0);
612 	if (semds.sem_perm.cgid != getegid()) e(0);
613 	if (semds.sem_perm.mode != (SEM_ALLOC | 0613)) e(0);
614 	if (semds.sem_perm._key != KEY_A) e(0);
615 	if (semds.sem_nsems != seminfo.semmsl) e(0);
616 	if (semds.sem_otime != 0) e(0);
617 	if (semds.sem_ctime < now || semds.sem_ctime >= now + 10) e(0);
618 
619 	for (i = 0; i < semds.sem_nsems; i++)
620 		TEST_SEM(id[1], i, 0, 0, 0, 0);
621 
622 	if (semctl(id[1], 0, IPC_RMID) != 0) e(0);
623 	if (semctl(id[0], 0, IPC_RMID) != 0) e(0);
624 
625 	/*
626 	 * Finally, perform a number of permission-related checks.  Since the
627 	 * main test program is running with superuser privileges, most of the
628 	 * permission tests use an unprivileged child process.
629 	 */
630 	/* The superuser can always open and destroy a semaphore set. */
631 	if ((id[0] = semget(KEY_A, 1, IPC_CREAT | IPC_EXCL | 0000)) < 0) e(0);
632 
633 	if ((id[1] = semget(KEY_A, 0, 0600)) < 0) e(0);
634 	if (id[0] != id[1]) e(0);
635 
636 	if ((id[1] = semget(KEY_A, 0, 0000)) < 0) e(0);
637 	if (id[0] != id[1]) e(0);
638 
639 	if (semctl(id[0], 0, IPC_RMID) != 0) e(0);
640 
641 	/*
642 	 * When an unprivileged process tries to open a semaphore set, the
643 	 * given upper three permission bits from the mode (0700) are tested
644 	 * against the appropriate permission bits from the semaphore set.
645 	 */
646 	test_perm(test88a_perm, 0 /*owner_test*/);
647 }
648 
649 /*
650  * Test semop(2) permission checks.
651  */
652 static void
653 test88b_perm(struct link * parent)
654 {
655 	struct sembuf sops[2];
656 	size_t nsops;
657 	int i, r, tbit, bit, id[3];
658 
659 	while ((tbit = rcv(parent)) != -1) {
660 		id[0] = rcv(parent);
661 		id[1] = rcv(parent);
662 		id[2] = rcv(parent);
663 
664 		/*
665 		 * This loop is designed such that failure of any bit-based
666 		 * subset will not result in subsequent operations blocking.
667 		 */
668 		for (i = 0; i < 8; i++) {
669 			memset(sops, 0, sizeof(sops));
670 
671 			switch (i) {
672 			case 0:
673 				nsops = 1;
674 				bit = 4;
675 				break;
676 			case 1:
677 				sops[0].sem_op = 1;
678 				nsops = 1;
679 				bit = 2;
680 				break;
681 			case 2:
682 				sops[0].sem_op = -1;
683 				nsops = 1;
684 				bit = 2;
685 				break;
686 			case 3:
687 				sops[1].sem_op = 1;
688 				nsops = 2;
689 				bit = 6;
690 				break;
691 			case 4:
692 				sops[0].sem_num = 1;
693 				sops[1].sem_op = -1;
694 				nsops = 2;
695 				bit = 6;
696 				break;
697 			case 5:
698 				sops[1].sem_num = 1;
699 				nsops = 2;
700 				bit = 4;
701 				break;
702 			case 6:
703 				/*
704 				 * Two operations on the same semaphore.  As
705 				 * such, this verifies that operations are
706 				 * processed in array order.
707 				 */
708 				sops[0].sem_op = 1;
709 				sops[1].sem_op = -1;
710 				nsops = 2;
711 				bit = 2;
712 				break;
713 			case 7:
714 				/*
715 				 * Test the order of checks.  Since IPC_STAT
716 				 * requires read permission, it is reasonable
717 				 * that the check against sem_nsems be done
718 				 * only after the permission check as well.
719 				 * For this test we rewrite EFBIG to OK below.
720 				 */
721 				sops[0].sem_num = USHRT_MAX;
722 				nsops = 2;
723 				bit = 4;
724 				break;
725 			}
726 
727 			r = semop(id[0], sops, nsops);
728 			if (i == 7 && r == -1 && errno == EFBIG) r = 0;
729 			if (r < 0 && (r != -1 || errno != EACCES)) e(0);
730 			if (((bit & tbit) == bit) != (r != -1)) e(0);
731 
732 			r = semop(id[1], sops, nsops);
733 			if (i == 7 && r == -1 && errno == EFBIG) r = 0;
734 			if (r < 0 && (r != -1 || errno != EACCES)) e(0);
735 			if (((bit & tbit) == bit) != (r != -1)) e(0);
736 
737 			if (semop(id[2], sops, nsops) != -1) e(0);
738 			if (errno != EACCES) e(0);
739 		}
740 
741 		snd(parent, 0);
742 	}
743 }
744 
745 /*
746  * Signal handler.
747  */
748 static void
749 got_signal(int sig)
750 {
751 
752 	if (sig != SIGHUP) e(0);
753 	if (nr_signals != 0) e(0);
754 	nr_signals++;
755 }
756 
757 /*
758  * Child process for semop(2) tests, mainly testing blocking operations.
759  */
760 static void
761 test88b_child(struct link * parent)
762 {
763 	struct sembuf sops[5];
764 	struct sigaction act;
765 	int id;
766 
767 	id = rcv(parent);
768 
769 	memset(sops, 0, sizeof(sops));
770 	if (semop(id, sops, 1) != 0) e(0);
771 
772 	if (rcv(parent) != 1) e(0);
773 
774 	sops[0].sem_op = -3;
775 	if (semop(id, sops, 1) != 0) e(0);
776 
777 	if (rcv(parent) != 2) e(0);
778 
779 	sops[0].sem_num = 2;
780 	sops[0].sem_op = 2;
781 	sops[1].sem_num = 1;
782 	sops[1].sem_op = -1;
783 	sops[2].sem_num = 0;
784 	sops[2].sem_op = 1;
785 	if (semop(id, sops, 3) != 0) e(0);
786 
787 	if (rcv(parent) != 3) e(0);
788 
789 	sops[0].sem_num = 1;
790 	sops[0].sem_op = 0;
791 	sops[1].sem_num = 1;
792 	sops[1].sem_op = 1;
793 	sops[2].sem_num = 0;
794 	sops[2].sem_op = 0;
795 	sops[3].sem_num = 2;
796 	sops[3].sem_op = 0;
797 	sops[4].sem_num = 2;
798 	sops[4].sem_op = 1;
799 	if (semop(id, sops, 5) != 0) e(0);
800 
801 	if (rcv(parent) != 4) e(0);
802 
803 	sops[0].sem_num = 1;
804 	sops[0].sem_op = -2;
805 	sops[1].sem_num = 2;
806 	sops[1].sem_op = 0;
807 	if (semop(id, sops, 2) != 0) e(0);
808 
809 	if (rcv(parent) != 5) e(0);
810 
811 	sops[0].sem_num = 0;
812 	sops[0].sem_op = -1;
813 	sops[1].sem_num = 1;
814 	sops[1].sem_op = -1;
815 	sops[1].sem_flg = IPC_NOWAIT;
816 	if (semop(id, sops, 2) != 0) e(0);
817 
818 	if (rcv(parent) != 6) e(0);
819 
820 	sops[0].sem_num = 1;
821 	sops[0].sem_op = 0;
822 	sops[1].sem_num = 0;
823 	sops[1].sem_op = 0;
824 	sops[1].sem_flg = IPC_NOWAIT;
825 	if (semop(id, sops, 2) != -1) e(0);
826 	if (errno != EAGAIN) e(0);
827 
828 	if (rcv(parent) != 7) e(0);
829 
830 	sops[0].sem_num = 0;
831 	sops[0].sem_op = 0;
832 	sops[1].sem_num = 1;
833 	sops[1].sem_op = 1;
834 	sops[1].sem_flg = 0;
835 	if (semop(id, sops, 2) != 0) e(0);
836 
837 	if (rcv(parent) != 8) e(0);
838 
839 	sops[0].sem_num = 0;
840 	sops[0].sem_op = -1;
841 	sops[1].sem_num = 1;
842 	sops[1].sem_op = 2;
843 	if (semop(id, sops, 2) != -1) e(0);
844 	if (errno != ERANGE) e(0);
845 
846 	memset(&act, 0, sizeof(act));
847 	act.sa_handler = got_signal;
848 	sigfillset(&act.sa_mask);
849 	if (sigaction(SIGHUP, &act, NULL) != 0) e(0);
850 
851 	if (rcv(parent) != 9) e(0);
852 
853 	memset(sops, 0, sizeof(sops));
854 	sops[0].sem_num = 0;
855 	sops[0].sem_op = 0;
856 	sops[1].sem_num = 0;
857 	sops[1].sem_op = 1;
858 	sops[2].sem_num = 1;
859 	sops[2].sem_op = 0;
860 	if (semop(id, sops, 3) != -1)
861 	if (errno != EINTR) e(0);
862 	if (nr_signals != 1) e(0);
863 
864 	TEST_SEM(id, 0, 0, parent->pid, 0, 0);
865 	TEST_SEM(id, 1, 1, parent->pid, 0, 0);
866 
867 	if (rcv(parent) != 10) e(0);
868 
869 	memset(sops, 0, sizeof(sops));
870 	sops[0].sem_op = -3;
871 	if (semop(id, sops, 1) != -1) e(0);
872 	if (errno != EIDRM) e(0);
873 
874 	id = rcv(parent);
875 
876 	sops[0].sem_num = 0;
877 	sops[0].sem_op = -1;
878 	sops[1].sem_num = 1;
879 	sops[1].sem_op = 1;
880 	if (semop(id, sops, 2) != -1) e(0);
881 	if (errno != ERANGE) e(0);
882 
883 	if (rcv(parent) != 11) e(0);
884 
885 	sops[0].sem_num = 1;
886 	sops[0].sem_op = 0;
887 	sops[1].sem_num = 0;
888 	sops[1].sem_op = -1;
889 	if (semop(id, sops, 2) != 0) e(0);
890 
891 	id = rcv(parent);
892 
893 	sops[0].sem_num = 0;
894 	sops[0].sem_op = -1;
895 	sops[1].sem_num = 1;
896 	sops[1].sem_op = 0;
897 	if (semop(id, sops, 2) != 0) e(0);
898 
899 	snd(parent, errct);
900 	if (rcv(parent) != 12) e(0);
901 
902 	/* The child will be killed during this call.  It should not return. */
903 	sops[0].sem_num = 1;
904 	sops[0].sem_op = -1;
905 	sops[1].sem_num = 0;
906 	sops[1].sem_op = 3;
907 	(void)semop(id, sops, 2);
908 
909 	e(0);
910 }
911 
912 /*
913  * Test the basic semop(2) functionality.
914  */
915 static void
916 test88b(void)
917 {
918 	struct seminfo seminfo;
919 	struct semid_ds semds;
920 	struct sembuf *sops, *sops2;
921 	size_t size;
922 	struct link child;
923 	time_t now;
924 	unsigned short val[2];
925 	int id;
926 
927 	subtest = 1;
928 
929 	/* Allocate a buffer for operations. */
930 	if (semctl(0, 0, IPC_INFO, &seminfo) == -1) e(0);
931 
932 	if (seminfo.semopm < 3 || seminfo.semopm > USHRT_MAX) e(0);
933 
934 	size = sizeof(sops[0]) * (seminfo.semopm + 1);
935 	if ((sops = malloc(size)) == NULL) e(0);
936 	memset(sops, 0, size);
937 
938 	/* Do a few first tests with a set containing one semaphore. */
939 	if ((id = semget(IPC_PRIVATE, 1, IPC_CREAT | 0600)) == -1) e(0);
940 
941 	/* If no operations are given, the call should succeed. */
942 	if (semop(id, NULL, 0) != 0) e(0);
943 
944 	/*
945 	 * If any operations are given, the pointer must be valid.  Moreover,
946 	 * partially valid buffers must never be processed partially.
947 	 */
948 	if (semop(id, NULL, 1) != -1) e(0);
949 	if (errno != EFAULT) e(0);
950 
951 	if (semop(id, bad_ptr, 1) != -1) e(0);
952 	if (errno != EFAULT) e(0);
953 
954 	memset(page_ptr, 0, page_size);
955 	sops2 = ((struct sembuf *)bad_ptr) - 1;
956 	sops2->sem_op = 1;
957 	if (semop(id, sops2, 2) != -1) e(0);
958 	if (errno != EFAULT) e(0);
959 
960 	TEST_SEM(id, 0, 0, 0, 0, 0);
961 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
962 	if (semds.sem_otime != 0) e(0);
963 
964 	/*
965 	 * A new semaphore set is initialized to an all-zeroes state, and a
966 	 * zeroed operation tests for a zeroed semaphore.  This should pass.
967 	 */
968 	time(&now);
969 	if (semop(id, sops, 1) != 0) e(0);
970 
971 	TEST_SEM(id, 0, 0, getpid(), 0, 0);
972 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
973 	if (semds.sem_otime < now || semds.sem_otime >= now + 10) e(0);
974 
975 	/* Test the limit on the number of operations. */
976 	if (semop(id, sops, seminfo.semopm) != 0) e(0);
977 
978 	if (semop(id, sops, seminfo.semopm + 1) != -1) e(0);
979 	if (errno != E2BIG) e(0);
980 
981 	if (semop(id, sops, SIZE_MAX) != -1) e(0);
982 	if (errno != E2BIG) e(0);
983 
984 	/* Test the range check on the semaphore numbers. */
985 	sops[1].sem_num = 1;
986 	if (semop(id, sops, 2) != -1) e(0);
987 	if (errno != EFBIG) e(0);
988 
989 	sops[1].sem_num = USHRT_MAX;
990 	if (semop(id, sops, 2) != -1) e(0);
991 	if (errno != EFBIG) e(0);
992 
993 	/*
994 	 * Test nonblocking operations on a single semaphore, starting with
995 	 * value limit and overflow cases.
996 	 */
997 	if (seminfo.semvmx < 3 || seminfo.semvmx > SHRT_MAX) e(0);
998 
999 	sops[0].sem_flg = IPC_NOWAIT;
1000 
1001 	/* This block does not trigger on MINIX3. */
1002 	if (seminfo.semvmx < SHRT_MAX) {
1003 		sops[0].sem_op = seminfo.semvmx + 1;
1004 		if (semop(id, sops, 1) != -1) e(0);
1005 		if (errno != ERANGE) e(0);
1006 		if (semctl(id, 0, GETVAL) != 0) e(0);
1007 	}
1008 
1009 	sops[0].sem_op = seminfo.semvmx;
1010 	if (semop(id, sops, 1) != 0) e(0);
1011 	if (semctl(id, 0, GETVAL) != seminfo.semvmx) e(0);
1012 
1013 	/* As of writing, the proper checks for this is missing on NetBSD. */
1014 	sops[0].sem_op = 1;
1015 	if (semop(id, sops, 1) != -1) e(0);
1016 	if (errno != ERANGE) e(0);
1017 	if (semctl(id, 0, GETVAL) != seminfo.semvmx) e(0);
1018 
1019 	sops[0].sem_op = seminfo.semvmx;
1020 	if (semop(id, sops, 1) != -1) e(0);
1021 	if (errno != ERANGE) e(0);
1022 	if (semctl(id, 0, GETVAL) != seminfo.semvmx) e(0);
1023 
1024 	sops[0].sem_op = SHRT_MAX;
1025 	if (semop(id, sops, 1) != -1) e(0);
1026 	if (errno != ERANGE) e(0);
1027 	if (semctl(id, 0, GETVAL) != seminfo.semvmx) e(0);
1028 
1029 	/* This block does trigger on MINIX3. */
1030 	if (seminfo.semvmx < -(int)SHRT_MIN) {
1031 		sops[0].sem_op = -seminfo.semvmx - 1;
1032 		if (semop(id, sops, 1) != -1) e(0);
1033 		if (errno != EAGAIN) e(0);
1034 		if (semctl(id, 0, GETVAL) != seminfo.semvmx) e(0);
1035 	}
1036 
1037 	sops[0].sem_op = -seminfo.semvmx;
1038 	if (semop(id, sops, 1) != 0) e(0);
1039 	if (semctl(id, 0, GETVAL) != 0) e(0);
1040 
1041 	/*
1042 	 * Test basic nonblocking operations on a single semaphore.
1043 	 */
1044 	sops[0].sem_op = 0;
1045 	if (semop(id, sops, 1) != 0) e(0);
1046 
1047 	sops[0].sem_op = 2;
1048 	if (semop(id, sops, 1) != 0) e(0);
1049 	if (semctl(id, 0, GETVAL) != 2) e(0);
1050 
1051 	sops[0].sem_op = 0;
1052 	if (semop(id, sops, 1) != -1) e(0);
1053 	if (errno != EAGAIN) e(0);
1054 
1055 	sops[0].sem_op = -3;
1056 	if (semop(id, sops, 1) != -1) e(0);
1057 	if (errno != EAGAIN) e(0);
1058 
1059 	sops[0].sem_op = 1;
1060 	if (semop(id, sops, 1) != 0) e(0);
1061 	if (semctl(id, 0, GETVAL) != 3) e(0);
1062 
1063 	sops[0].sem_op = -1;
1064 	if (semop(id, sops, 1) != 0) e(0);
1065 	if (semctl(id, 0, GETVAL) != 2) e(0);
1066 
1067 	sops[0].sem_op = 0;
1068 	if (semop(id, sops, 1) != -1) e(0);
1069 	if (errno != EAGAIN) e(0);
1070 
1071 	sops[0].sem_op = -2;
1072 	if (semop(id, sops, 1) != 0) e(0);
1073 	if (semctl(id, 0, GETVAL) != 0) e(0);
1074 
1075 	sops[0].sem_op = 0;
1076 	if (semop(id, sops, 1) != 0) e(0);
1077 
1078 	/* Make sure that not too much data is being read in. */
1079 	sops2->sem_op = 0;
1080 	sops2--;
1081 	if (semop(id, sops2, 2) != 0) e(0);
1082 
1083 	/* Even if no operations are given, the identifier must be valid. */
1084 	if (semctl(id, 0, IPC_RMID) != 0) e(0);
1085 
1086 	if (semop(id, NULL, 0) != -1) e(0);
1087 	if (errno != EINVAL) e(0);
1088 
1089 	if (semop(-1, NULL, 0) != -1) e(0);
1090 	if (errno != EINVAL) e(0);
1091 
1092 	if (semop(INT_MIN, NULL, 0) != -1) e(0);
1093 	if (errno != EINVAL) e(0);
1094 
1095 	memset(&semds, 0, sizeof(semds));
1096 	id = IXSEQ_TO_IPCID(seminfo.semmni, semds.sem_perm);
1097 	if (semop(id, NULL, 0) != -1) e(0);
1098 	if (errno != EINVAL) e(0);
1099 
1100 	/*
1101 	 * Test permission checks.  As part of this, test basic nonblocking
1102 	 * multi-operation calls, including operation processing in array order
1103 	 * and the order of (permission vs other) checks.
1104 	 */
1105 	test_perm(test88b_perm, 0 /*owner_test*/);
1106 
1107 	/*
1108 	 * Test blocking operations, starting with a single blocking operation.
1109 	 */
1110 	if ((id = semget(IPC_PRIVATE, 3, 0600)) == -1) e(0);
1111 
1112 	memset(sops, 0, sizeof(sops[0]));
1113 	sops[0].sem_op = 1;
1114 	if (semop(id, sops, 1) != 0) e(0);
1115 
1116 	TEST_SEM(id, 0, 1, getpid(), 0, 0);
1117 
1118 	spawn(&child, test88b_child, DROP_NONE);
1119 
1120 	snd(&child, id);
1121 
1122 	/*
1123 	 * In various places, we have to sleep in order to allow the child to
1124 	 * get itself blocked in a semop(2) call.
1125 	 */
1126 	usleep(WAIT_USECS);
1127 
1128 	TEST_SEM(id, 0, 1, getpid(), 0, 1);
1129 
1130 	sops[0].sem_op = -1;
1131 	if (semop(id, sops, 1) != 0) e(0);
1132 
1133 	usleep(WAIT_USECS);
1134 
1135 	TEST_SEM(id, 0, 0, child.pid, 0, 0);
1136 
1137 	sops[0].sem_op = 1;
1138 	if (semop(id, sops, 1) != 0) e(0);
1139 
1140 	TEST_SEM(id, 0, 1, getpid(), 0, 0);
1141 
1142 	snd(&child, 1);
1143 
1144 	usleep(WAIT_USECS);
1145 
1146 	TEST_SEM(id, 0, 1, getpid(), 1, 0);
1147 
1148 	/* This should cause a (fruitless) retry of the blocking operation. */
1149 	sops[0].sem_op = 1;
1150 	if (semop(id, sops, 1) != 0) e(0);
1151 
1152 	usleep(WAIT_USECS);
1153 
1154 	TEST_SEM(id, 0, 2, getpid(), 1, 0);
1155 
1156 	sops[0].sem_op = 1;
1157 	if (semop(id, sops, 1) != 0) e(0);
1158 
1159 	usleep(WAIT_USECS);
1160 
1161 	TEST_SEM(id, 0, 0, child.pid, 0, 0);
1162 
1163 	/*
1164 	 * Test blocking operations, verifying the correct operation of
1165 	 * multiple (partially) blocking operations and atomicity.
1166 	 */
1167 	memset(sops, 0, sizeof(sops[0]) * 2);
1168 	if (semop(id, sops, 1) != 0) e(0);
1169 
1170 	/* One blocking operation. */
1171 	snd(&child, 2);
1172 
1173 	usleep(WAIT_USECS);
1174 
1175 	TEST_SEM(id, 0, 0, getpid(), 0, 0);
1176 	TEST_SEM(id, 1, 0, 0, 1, 0);
1177 	TEST_SEM(id, 2, 0, 0, 0, 0);
1178 
1179 	sops[0].sem_num = 1;
1180 	sops[0].sem_op = 1;
1181 	if (semop(id, sops, 1) != 0) e(0);
1182 
1183 	usleep(WAIT_USECS);
1184 
1185 	TEST_SEM(id, 0, 1, child.pid, 0, 0);
1186 	TEST_SEM(id, 1, 0, child.pid, 0, 0);
1187 	TEST_SEM(id, 2, 2, child.pid, 0, 0);
1188 
1189 	/* Two blocking operations in one call, resolved at once. */
1190 	snd(&child, 3);
1191 
1192 	usleep(WAIT_USECS);
1193 
1194 	TEST_SEM(id, 0, 1, child.pid, 0, 1);
1195 	TEST_SEM(id, 1, 0, child.pid, 0, 0);
1196 	TEST_SEM(id, 2, 2, child.pid, 0, 0);
1197 
1198 	sops[0].sem_num = 0;
1199 	sops[0].sem_op = -1;
1200 	sops[1].sem_num = 2;
1201 	sops[1].sem_op = -2;
1202 	if (semop(id, sops, 2) != 0) e(0);
1203 
1204 	usleep(WAIT_USECS);
1205 
1206 	TEST_SEM(id, 0, 0, child.pid, 0, 0);
1207 	TEST_SEM(id, 1, 1, child.pid, 0, 0);
1208 	TEST_SEM(id, 2, 1, child.pid, 0, 0);
1209 
1210 	/* Two blocking operations in one call, resolved one by one. */
1211 	snd(&child, 4);
1212 
1213 	usleep(WAIT_USECS);
1214 
1215 	TEST_SEM(id, 0, 0, child.pid, 0, 0);
1216 	TEST_SEM(id, 1, 1, child.pid, 1, 0);
1217 	TEST_SEM(id, 2, 1, child.pid, 0, 0);
1218 
1219 	sops[0].sem_num = 1;
1220 	sops[0].sem_op = 1;
1221 	if (semop(id, sops, 1) != 0) e(0);
1222 
1223 	usleep(WAIT_USECS);
1224 
1225 	TEST_SEM(id, 0, 0, child.pid, 0, 0);
1226 	TEST_SEM(id, 1, 2, getpid(), 0, 0);
1227 	TEST_SEM(id, 2, 1, child.pid, 0, 1);
1228 
1229 	sops[0].sem_num = 2;
1230 	sops[0].sem_op = -1;
1231 	if (semop(id, sops, 1) != 0) e(0);
1232 
1233 	usleep(WAIT_USECS);
1234 
1235 	TEST_SEM(id, 0, 0, child.pid, 0, 0);
1236 	TEST_SEM(id, 1, 0, child.pid, 0, 0);
1237 	TEST_SEM(id, 2, 0, child.pid, 0, 0);
1238 
1239 	/* One blocking op followed by a nonblocking one, cleared at once. */
1240 	sops[0].sem_num = 0;
1241 	sops[0].sem_op = 0;
1242 	sops[1].sem_num = 1;
1243 	sops[1].sem_op = 0;
1244 	if (semop(id, sops, 2) != 0) e(0);
1245 
1246 	snd(&child, 5);
1247 
1248 	usleep(WAIT_USECS);
1249 
1250 	TEST_SEM(id, 0, 0, getpid(), 1, 0);
1251 	TEST_SEM(id, 1, 0, getpid(), 0, 0);
1252 
1253 	sops[0].sem_num = 0;
1254 	sops[0].sem_op = 1;
1255 	sops[1].sem_num = 1;
1256 	sops[1].sem_op = 1;
1257 	if (semop(id, sops, 2) != 0) e(0);
1258 
1259 	usleep(WAIT_USECS);
1260 
1261 	TEST_SEM(id, 0, 0, child.pid, 0, 0);
1262 	TEST_SEM(id, 1, 0, child.pid, 0, 0);
1263 
1264 	/* One blocking op followed by a nonblocking one, only one cleared. */
1265 	sops[0].sem_num = 0;
1266 	sops[0].sem_op = 1;
1267 	sops[1].sem_num = 1;
1268 	sops[1].sem_op = 1;
1269 	if (semop(id, sops, 2) != 0) e(0);
1270 
1271 	snd(&child, 6);
1272 
1273 	usleep(WAIT_USECS);
1274 
1275 	TEST_SEM(id, 0, 1, getpid(), 0, 0);
1276 	TEST_SEM(id, 1, 1, getpid(), 0, 1);
1277 
1278 	sops[0].sem_num = 1;
1279 	sops[0].sem_op = -1;
1280 	if (semop(id, sops, 1) != 0) e(0);
1281 
1282 	usleep(WAIT_USECS);
1283 
1284 	TEST_SEM(id, 0, 1, getpid(), 0, 0);
1285 	TEST_SEM(id, 1, 0, getpid(), 0, 0);
1286 
1287 	/*
1288 	 * Ensure that all semaphore numbers are checked immediately, which
1289 	 * given the earlier test results also implies that permissions are
1290 	 * checked immediately (so we don't have to recheck that too).  We do
1291 	 * not check whether permissions are rechecked after a blocking
1292 	 * operation, because the specification does not describe the intended
1293 	 * behavior on this point.
1294 	 */
1295 	sops[0].sem_num = 0;
1296 	sops[0].sem_op = 0;
1297 	sops[1].sem_num = 4;
1298 	sops[1].sem_op = 0;
1299 	if (semop(id, sops, 2) != -1) e(0);
1300 	if (errno != EFBIG) e(0);
1301 
1302 	/*
1303 	 * Ensure that semaphore value overflow is detected properly, at the
1304 	 * moment that the operation is actually processed.
1305 	 */
1306 	sops[0].sem_num = 1;
1307 	sops[0].sem_op = seminfo.semvmx;
1308 	if (semop(id, sops, 1) != 0) e(0);
1309 
1310 	snd(&child, 7);
1311 
1312 	usleep(WAIT_USECS);
1313 
1314 	TEST_SEM(id, 0, 1, getpid(), 0, 1);
1315 	TEST_SEM(id, 1, seminfo.semvmx, getpid(), 0, 0);
1316 
1317 	sops[0].sem_num = 0;
1318 	sops[0].sem_op = -1;
1319 	sops[1].sem_num = 1;
1320 	sops[1].sem_op = -1;
1321 	if (semop(id, sops, 2) != 0) e(0);
1322 
1323 	TEST_SEM(id, 0, 0, child.pid, 0, 0);
1324 	TEST_SEM(id, 1, seminfo.semvmx, child.pid, 0, 0);
1325 
1326 	sops[0].sem_num = 1;
1327 	sops[0].sem_op = -2;
1328 	if (semop(id, sops, 1) != 0) e(0);
1329 
1330 	snd(&child, 8);
1331 
1332 	usleep(WAIT_USECS);
1333 
1334 	TEST_SEM(id, 0, 0, child.pid, 1, 0);
1335 	TEST_SEM(id, 1, seminfo.semvmx - 2, getpid(), 0, 0);
1336 
1337 	sops[0].sem_num = 0;
1338 	sops[0].sem_op = 1;
1339 	sops[1].sem_num = 1;
1340 	sops[1].sem_op = 1;
1341 	if (semop(id, sops, 2) != 0) e(0);
1342 
1343 	TEST_SEM(id, 0, 1, getpid(), 0, 0);
1344 	TEST_SEM(id, 1, seminfo.semvmx - 1, getpid(), 0, 0);
1345 
1346 	sops[0].sem_num = 0;
1347 	sops[0].sem_op = seminfo.semvmx - 1;
1348 	sops[1].sem_num = 0;
1349 	sops[1].sem_op = seminfo.semvmx - 1;
1350 	sops[2].sem_num = 0;
1351 	sops[2].sem_op = 2;
1352 	/*
1353 	 * With the current SEMVMX, the sum of the values is now USHRT_MAX-1,
1354 	 * which if processed could result in a zero semaphore value.  That
1355 	 * should not happen.  Looking at you, NetBSD.
1356 	 */
1357 	if (semop(id, sops, 3) != -1) e(0);
1358 	if (errno != ERANGE) e(0);
1359 
1360 	TEST_SEM(id, 0, 1, getpid(), 0, 0);
1361 
1362 	/*
1363 	 * Check that a blocking semop(2) call fails with EINTR if a signal is
1364 	 * caught by the process after the call has blocked.
1365 	 */
1366 	if (semctl(id, 1, SETVAL, 0) != 0) e(0);
1367 	sops[0].sem_num = 0;
1368 	sops[0].sem_op = -1;
1369 	sops[1].sem_num = 1;
1370 	sops[1].sem_op = 1;
1371 	if (semop(id, sops, 2) != 0) e(0);
1372 
1373 	TEST_SEM(id, 0, 0, getpid(), 0, 0);
1374 	TEST_SEM(id, 1, 1, getpid(), 0, 0);
1375 
1376 	snd(&child, 9);
1377 
1378 	usleep(WAIT_USECS);
1379 
1380 	TEST_SEM(id, 0, 0, getpid(), 0, 0);
1381 	TEST_SEM(id, 1, 1, getpid(), 0, 1);
1382 
1383 	kill(child.pid, SIGHUP);
1384 	/*
1385 	 * Kills are not guaranteed to be delivered immediately to processes
1386 	 * other than the caller of kill(2), so let the child perform checks.
1387 	 */
1388 
1389 	/*
1390 	 * Check that a blocking semop(2) call fails with EIDRM if the
1391 	 * semaphore set is removed after the call has blocked.
1392 	 */
1393 	snd(&child, 10);
1394 
1395 	usleep(WAIT_USECS);
1396 
1397 	if (semctl(id, 0, IPC_RMID) != 0) e(0);
1398 
1399 	/*
1400 	 * Check if sem_otime is updated correctly.  Instead of sleeping for
1401 	 * whole seconds so as to be able to detect differences, use SETVAL,
1402 	 * which does not update sem_otime at all.  This doubles as a first
1403 	 * test to see if SETVAL correctly wakes up a blocked semop(2) call.
1404 	 */
1405 	if ((id = semget(IPC_PRIVATE, 2, 0600)) == -1) e(0);
1406 
1407 	snd(&child, id);
1408 
1409 	usleep(WAIT_USECS);
1410 
1411 	TEST_SEM(id, 0, 0, 0, 1, 0);
1412 	TEST_SEM(id, 1, 0, 0, 0, 0);
1413 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
1414 	if (semds.sem_otime != 0) e(0);
1415 
1416 	if (semctl(id, 1, SETVAL, seminfo.semvmx) != 0) e(0);
1417 
1418 	TEST_SEM(id, 0, 0, 0, 1, 0);
1419 	TEST_SEM(id, 1, seminfo.semvmx, 0, 0, 0);
1420 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
1421 	if (semds.sem_otime != 0) e(0);
1422 
1423 	if (semctl(id, 0, SETVAL, 1) != 0) e(0);
1424 	TEST_SEM(id, 0, 1, 0, 0, 0);
1425 	TEST_SEM(id, 1, seminfo.semvmx, 0, 0, 0);
1426 
1427 	if (semctl(id, 0, SETVAL, 0) != 0) e(0);
1428 
1429 	snd(&child, 11);
1430 
1431 	usleep(WAIT_USECS);
1432 
1433 	TEST_SEM(id, 0, 0, 0, 0, 0);
1434 	TEST_SEM(id, 1, seminfo.semvmx, 0, 0, 1);
1435 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
1436 	if (semds.sem_otime != 0) e(0);
1437 
1438 	if (semctl(id, 1, SETVAL, 0) != 0) e(0);
1439 
1440 	TEST_SEM(id, 0, 0, 0, 1, 0);
1441 	TEST_SEM(id, 1, 0, 0, 0, 0);
1442 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
1443 	if (semds.sem_otime != 0) e(0);
1444 
1445 	time(&now);
1446 	if (semctl(id, 0, SETVAL, 2) != 0) e(0);
1447 
1448 	TEST_SEM(id, 0, 1, child.pid, 0, 0);
1449 	TEST_SEM(id, 1, 0, child.pid, 0, 0);
1450 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
1451 	if (semds.sem_otime < now || semds.sem_otime >= now + 10) e(0);
1452 
1453 	if (semctl(id, 0, IPC_RMID) != 0) e(0);
1454 
1455 	/*
1456 	 * Perform a similar test for SETALL, ensuring that it causes an
1457 	 * ongoing semop(2) to behave correctly.
1458 	 */
1459 	if ((id = semget(IPC_PRIVATE, 2, 0600)) == -1) e(0);
1460 
1461 	snd(&child, id);
1462 
1463 	usleep(WAIT_USECS);
1464 
1465 	TEST_SEM(id, 0, 0, 0, 1, 0);
1466 	TEST_SEM(id, 1, 0, 0, 0, 0);
1467 
1468 	val[0] = 1;
1469 	val[1] = 1;
1470 	if (semctl(id, 0, SETALL, val) != 0) e(0);
1471 
1472 	TEST_SEM(id, 0, 1, 0, 0, 0);
1473 	TEST_SEM(id, 1, 1, 0, 0, 1);
1474 
1475 	val[0] = 0;
1476 	val[1] = 1;
1477 	if (semctl(id, 0, SETALL, val) != 0) e(0);
1478 
1479 	TEST_SEM(id, 0, 0, 0, 1, 0);
1480 	TEST_SEM(id, 1, 1, 0, 0, 0);
1481 
1482 	val[0] = 1;
1483 	val[1] = 1;
1484 	if (semctl(id, 0, SETALL, val) != 0) e(0);
1485 
1486 	TEST_SEM(id, 0, 1, 0, 0, 0);
1487 	TEST_SEM(id, 1, 1, 0, 0, 1);
1488 
1489 	val[0] = 0;
1490 	val[1] = 0;
1491 	if (semctl(id, 0, SETALL, val) != 0) e(0);
1492 
1493 	TEST_SEM(id, 0, 0, 0, 1, 0);
1494 	TEST_SEM(id, 1, 0, 0, 0, 0);
1495 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
1496 	if (semds.sem_otime != 0) e(0);
1497 
1498 	time(&now);
1499 	val[0] = 1;
1500 	val[1] = 0;
1501 	if (semctl(id, 0, SETALL, val) != 0) e(0);
1502 
1503 	TEST_SEM(id, 0, 0, child.pid, 0, 0);
1504 	TEST_SEM(id, 1, 0, child.pid, 0, 0);
1505 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
1506 	if (semds.sem_otime < now || semds.sem_otime >= now + 10) e(0);
1507 
1508 	/*
1509 	 * Finally, ensure that if the child is killed, its blocked semop(2)
1510 	 * call is properly cancelled.
1511 	 */
1512 	sops[0].sem_num = 0;
1513 	sops[0].sem_op = 0;
1514 	sops[1].sem_num = 1;
1515 	sops[1].sem_op = 0;
1516 	if (semop(id, sops, 2) != 0) e(0);
1517 
1518 	TEST_SEM(id, 0, 0, getpid(), 0, 0);
1519 	TEST_SEM(id, 1, 0, getpid(), 0, 0);
1520 
1521 	/* We'll be terminating the child, so let it report its errors now. */
1522 	if (rcv(&child) != 0) e(0);
1523 
1524 	snd(&child, 12);
1525 
1526 	usleep(WAIT_USECS);
1527 
1528 	TEST_SEM(id, 0, 0, getpid(), 0, 0);
1529 	TEST_SEM(id, 1, 0, getpid(), 1, 0);
1530 
1531 	terminate(&child);
1532 
1533 	TEST_SEM(id, 0, 0, getpid(), 0, 0);
1534 	TEST_SEM(id, 1, 0, getpid(), 0, 0);
1535 
1536 	if (semctl(id, 0, IPC_RMID) != 0) e(0);
1537 
1538 	free(sops);
1539 }
1540 
1541 /*
1542  * Test semctl(2) permission checks, part 1: regular commands.
1543  */
1544 static void
1545 test88c_perm1(struct link * parent)
1546 {
1547 	static const int cmds[] = { GETVAL, GETPID, GETNCNT, GETZCNT };
1548 	struct semid_ds semds;
1549 	struct seminfo seminfo;
1550 	unsigned short val[3];
1551 	int i, r, tbit, bit, id[3], cmd;
1552 	void *ptr;
1553 
1554 	while ((tbit = rcv(parent)) != -1) {
1555 		id[0] = rcv(parent);
1556 		id[1] = rcv(parent);
1557 		id[2] = rcv(parent);
1558 
1559 		/* First the read-only, no-argument cases. */
1560 		bit = 4;
1561 		for (i = 0; i < __arraycount(cmds); i++) {
1562 			r = semctl(id[0], 0, cmds[i]);
1563 			if (r < 0 && (r != -1 || errno != EACCES)) e(0);
1564 			if (((bit & tbit) == bit) != (r != -1)) e(0);
1565 
1566 			r = semctl(id[1], 0, cmds[i]);
1567 			if (r < 0 && (r != -1 || errno != EACCES)) e(0);
1568 			if (((bit & tbit) == bit) != (r != -1)) e(0);
1569 
1570 			if (semctl(id[2], 0, cmds[i]) != -1) e(0);
1571 			if (errno != EACCES) e(0);
1572 		}
1573 
1574 		/*
1575 		 * Then SETVAL, which requires write permission and is the only
1576 		 * one that takes an integer argument.
1577 		 */
1578 		bit = 2;
1579 		r = semctl(id[0], 0, SETVAL, 0);
1580 		if (r < 0 && (r != -1 || errno != EACCES)) e(0);
1581 		if (((bit & tbit) == bit) != (r != -1)) e(0);
1582 
1583 		r = semctl(id[1], 0, SETVAL, 0);
1584 		if (r < 0 && (r != -1 || errno != EACCES)) e(0);
1585 		if (((bit & tbit) == bit) != (r != -1)) e(0);
1586 
1587 		if (semctl(id[2], 0, SETVAL, 0) != -1) e(0);
1588 		if (errno != EACCES) e(0);
1589 
1590 		/*
1591 		 * Finally the commands that require read or write permission
1592 		 * and take a pointer as argument.
1593 		 */
1594 		memset(val, 0, sizeof(val));
1595 
1596 		for (i = 0; i < 4; i++) {
1597 			switch (i) {
1598 			case 0:
1599 				cmd = GETALL;
1600 				ptr = val;
1601 				bit = 4;
1602 				break;
1603 			case 1:
1604 				cmd = SETALL;
1605 				ptr = val;
1606 				bit = 2;
1607 				break;
1608 			case 2:
1609 				cmd = IPC_STAT;
1610 				ptr = &semds;
1611 				bit = 4;
1612 				break;
1613 			}
1614 
1615 			r = semctl(id[0], 0, cmd, ptr);
1616 			if (r < 0 && (r != -1 || errno != EACCES)) e(0);
1617 			if (((bit & tbit) == bit) != (r != -1)) e(0);
1618 
1619 			r = semctl(id[1], 0, cmd, ptr);
1620 			if (r < 0 && (r != -1 || errno != EACCES)) e(0);
1621 			if (((bit & tbit) == bit) != (r != -1)) e(0);
1622 
1623 			if (semctl(id[2], 0, cmd, ptr) != -1) e(0);
1624 			if (errno != EACCES) e(0);
1625 		}
1626 
1627 		/*
1628 		 * I was hoping to avoid this, but otherwise we have to make
1629 		 * the other child iterate through all semaphore sets to find
1630 		 * the right index for each of the identifiers.  As noted in
1631 		 * the IPC server itself as well, duplicating these macros is
1632 		 * not a big deal since the split is firmly hardcoded through
1633 		 * the exposure of IXSEQ_TO_IPCID to userland.
1634 		 */
1635 #ifndef IPCID_TO_IX
1636 #define IPCID_TO_IX(id)		((id) & 0xffff)
1637 #endif
1638 
1639 		bit = 4;
1640 
1641 		r = semctl(IPCID_TO_IX(id[0]), 0, SEM_STAT, &semds);
1642 		if (r < 0 && (r != -1 || errno != EACCES)) e(0);
1643 		if (((bit & tbit) == bit) != (r != -1)) e(0);
1644 
1645 		r = semctl(IPCID_TO_IX(id[1]), 0, SEM_STAT, &semds);
1646 		if (r < 0 && (r != -1 || errno != EACCES)) e(0);
1647 		if (((bit & tbit) == bit) != (r != -1)) e(0);
1648 
1649 		if (semctl(IPCID_TO_IX(id[2]), 0, SEM_STAT, &semds) != -1)
1650 			e(0);
1651 		if (errno != EACCES) e(0);
1652 
1653 		/*
1654 		 * IPC_INFO and SEM_INFO should always succeed.  They do not
1655 		 * even take a semaphore set identifier.
1656 		 */
1657 		if (semctl(0, 0, IPC_INFO, &seminfo) == -1) e(0);
1658 		if (semctl(0, 0, SEM_INFO, &seminfo) == -1) e(0);
1659 
1660 		snd(parent, 0);
1661 	}
1662 }
1663 
1664 /*
1665  * Test semctl(2) permission checks, part 2: the IPC_SET command.
1666  */
1667 static void
1668 test88c_perm2(struct link * parent)
1669 {
1670 	struct semid_ds semds;
1671 	int r, shift, id[3];
1672 
1673 	while ((shift = rcv(parent)) != -1) {
1674 		id[0] = rcv(parent);
1675 		id[1] = rcv(parent);
1676 		id[2] = rcv(parent);
1677 
1678 		/*
1679 		 * Test IPC_SET.  Ideally, we would set the permissions to what
1680 		 * they currently are, but we do not actually know what they
1681 		 * are, and IPC_STAT requires read permission which we may not
1682 		 * have!  However, no matter what we do, we cannot prevent the
1683 		 * other child from being able to remove the semaphore sets
1684 		 * afterwards.  So, we just set the permissions to all-zeroes;
1685 		 * even though those values are meaningful (mode 0000, uid 0,
1686 		 * gid 0) they could be anything: the API will accept anything.
1687 		 * This does mean we need to test IPC_RMID permissions from
1688 		 * another procedure, because we may now be locking ourselves
1689 		 * out.  The System V IPC interface is pretty strange that way.
1690 		 */
1691 		memset(&semds, 0, sizeof(semds));
1692 
1693 		r = semctl(id[0], 0, IPC_SET, &semds);
1694 		if (r < 0 && (r != -1 || errno != EPERM)) e(0);
1695 		if ((shift == 6) != (r != -1)) e(0);
1696 
1697 		r = semctl(id[1], 0, IPC_SET, &semds);
1698 		if (r < 0 && (r != -1 || errno != EPERM)) e(0);
1699 		if ((shift == 6) != (r != -1)) e(0);
1700 
1701 		/* For once, this too should succeed. */
1702 		r = semctl(id[2], 0, IPC_SET, &semds);
1703 		if (r < 0 && (r != -1 || errno != EPERM)) e(0);
1704 		if ((shift == 6) != (r != -1)) e(0);
1705 
1706 		snd(parent, 0);
1707 	}
1708 }
1709 
1710 /*
1711  * Test semctl(2) permission checks, part 3: the IPC_RMID command.
1712  */
1713 static void
1714 test88c_perm3(struct link * parent)
1715 {
1716 	int r, shift, id[3];
1717 
1718 	while ((shift = rcv(parent)) != -1) {
1719 		id[0] = rcv(parent);
1720 		id[1] = rcv(parent);
1721 		id[2] = rcv(parent);
1722 
1723 		r = semctl(id[0], 0, IPC_RMID);
1724 		if (r < 0 && (r != -1 || errno != EPERM)) e(0);
1725 		if ((shift == 6) != (r != -1)) e(0);
1726 
1727 		r = semctl(id[1], 0, IPC_RMID);
1728 		if (r < 0 && (r != -1 || errno != EPERM)) e(0);
1729 		if ((shift == 6) != (r != -1)) e(0);
1730 
1731 		/* Okay, twice then. */
1732 		r = semctl(id[2], 0, IPC_RMID);
1733 		if (r < 0 && (r != -1 || errno != EPERM)) e(0);
1734 		if ((shift == 6) != (r != -1)) e(0);
1735 
1736 		snd(parent, 0);
1737 	}
1738 }
1739 
1740 /*
1741  * Test the basic semctl(2) functionality.
1742  */
1743 static void
1744 test88c(void)
1745 {
1746 	static const int cmds[] = { GETVAL, GETPID, GETNCNT, GETZCNT };
1747 	struct seminfo seminfo;
1748 	struct semid_ds semds, osemds;
1749 	unsigned short val[4], seen[2];
1750 	char statbuf[sizeof(struct semid_ds) + 1];
1751 	unsigned int i, j;
1752 	time_t now;
1753 	int r, id, id2, badid1, badid2, cmd;
1754 
1755 	subtest = 2;
1756 
1757 	if (semctl(0, 0, IPC_INFO, &seminfo) == -1) e(0);
1758 
1759 	/*
1760 	 * Start with permission checks on the commands.  IPC_SET and IPC_RMID
1761 	 * are special: they check for ownership (uid/cuid) and return EPERM
1762 	 * rather than EACCES on permission failure.
1763 	 */
1764 	test_perm(test88c_perm1, 0 /*owner_test*/);
1765 	test_perm(test88c_perm2, 1 /*owner_test*/);
1766 	test_perm(test88c_perm3, 1 /*owner_test*/);
1767 
1768 	/* Create identifiers known to be invalid. */
1769 	if ((badid1 = semget(IPC_PRIVATE, 1, 0600)) < 0) e(0);
1770 
1771 	if (semctl(badid1, 0, IPC_RMID) != 0) e(0);
1772 
1773 	memset(&semds, 0, sizeof(semds));
1774 	badid2 = IXSEQ_TO_IPCID(seminfo.semmni, semds.sem_perm);
1775 
1776 	if ((id = semget(IPC_PRIVATE, 3, IPC_CREAT | 0600)) < 0) e(0);
1777 
1778 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
1779 	if (semds.sem_otime != 0) e(0);
1780 	if (semds.sem_ctime == 0) e(0);
1781 
1782 	/* In this case we can't avoid sleeping for longer periods.. */
1783 	while (time(&now) == semds.sem_ctime)
1784 		usleep(250000);
1785 
1786 	/*
1787 	 * Test the simple GET commands.  The actual functionality of these
1788 	 * commands have already been tested thoroughly as part of the
1789 	 * semop(2) part of the test set, so we do not repeat that here.
1790 	 */
1791 	for (i = 0; i < __arraycount(cmds); i++) {
1792 		for (j = 0; j < 3; j++)
1793 			if (semctl(id, j, cmds[i]) != 0) e(0);
1794 
1795 		if (semctl(badid1, 0, cmds[i]) != -1) e(0);
1796 		if (errno != EINVAL) e(0);
1797 
1798 		if (semctl(badid2, 0, cmds[i]) != -1) e(0);
1799 		if (errno != EINVAL) e(0);
1800 
1801 		if (semctl(-1, 0, cmds[i]) != -1) e(0);
1802 		if (errno != EINVAL) e(0);
1803 
1804 		if (semctl(INT_MIN, 0, cmds[i]) != -1) e(0);
1805 		if (errno != EINVAL) e(0);
1806 
1807 		if (semctl(id, -1, cmds[i]) != -1) e(0);
1808 		if (errno != EINVAL) e(0);
1809 
1810 		if (semctl(id, 3, cmds[i]) != -1) e(0);
1811 		if (errno != EINVAL) e(0);
1812 
1813 		/* These commands should not update ctime or otime. */
1814 		if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
1815 		if (semds.sem_otime != 0) e(0);
1816 		if (semds.sem_ctime >= now) e(0);
1817 	}
1818 
1819 	/*
1820 	 * Test the GETALL command.
1821 	 */
1822 	/*
1823 	 * Contrary to what the Open Group specification suggests, actual
1824 	 * implementations agree that the semnum parameter is to be ignored for
1825 	 * calls not involving a specific semaphore in the set.
1826 	 */
1827 	for (j = 0; j < 5; j++) {
1828 		for (i = 0; i < __arraycount(val); i++)
1829 			val[i] = USHRT_MAX;
1830 
1831 		if (semctl(id, (int)j - 1, GETALL, val) != 0) e(0);
1832 		for (i = 0; i < 3; i++)
1833 			if (val[i] != 0) e(0);
1834 		if (val[i] != USHRT_MAX) e(0);
1835 	}
1836 
1837 	for (i = 0; i < __arraycount(val); i++)
1838 		val[i] = USHRT_MAX;
1839 
1840 	if (semctl(badid1, 0, GETALL, val) != -1) e(0);
1841 	if (errno != EINVAL) e(0);
1842 
1843 	if (semctl(badid2, 0, GETALL, val) != -1) e(0);
1844 	if (errno != EINVAL) e(0);
1845 
1846 	if (semctl(-1, 0, GETALL, val) != -1) e(0);
1847 	if (errno != EINVAL) e(0);
1848 
1849 	if (semctl(INT_MIN, 0, GETALL, val) != -1) e(0);
1850 	if (errno != EINVAL) e(0);
1851 
1852 	for (i = 0; i < __arraycount(val); i++)
1853 		if (val[i] != USHRT_MAX) e(0);
1854 
1855 	if (semctl(id, 0, GETALL, NULL) != -1) e(0);
1856 	if (errno != EFAULT) e(0);
1857 
1858 	if (semctl(id, 0, GETALL, bad_ptr) != -1) e(0);
1859 	if (errno != EFAULT) e(0);
1860 
1861 	if (semctl(id, 0, GETALL, ((unsigned short *)bad_ptr) - 2) != -1) e(0);
1862 	if (errno != EFAULT) e(0);
1863 
1864 	if (semctl(id, 0, GETALL, ((unsigned short *)bad_ptr) - 3) != 0) e(0);
1865 
1866 	/* Still no change in either otime or ctime. */
1867 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
1868 	if (semds.sem_otime != 0) e(0);
1869 	if (semds.sem_ctime >= now) e(0);
1870 
1871 	/*
1872 	 * Test the IPC_STAT command.  This is the last command we are testing
1873 	 * here that does not affect sem_ctime, so in order to avoid extra
1874 	 * sleep times, we test this command first now.
1875 	 */
1876 	/*
1877 	 * The basic IPC_STAT functionality has already been tested heavily as
1878 	 * part of the semget(2) and permission tests, so we do not repeat that
1879 	 * here.
1880 	 */
1881 	memset(statbuf, 0x5a, sizeof(statbuf));
1882 
1883 	if (semctl(badid1, 0, IPC_STAT, statbuf) != -1) e(0);
1884 	if (errno != EINVAL) e(0);
1885 
1886 	if (semctl(badid2, 0, IPC_STAT, statbuf) != -1) e(0);
1887 	if (errno != EINVAL) e(0);
1888 
1889 	if (semctl(-1, 0, IPC_STAT, statbuf) != -1) e(0);
1890 	if (errno != EINVAL) e(0);
1891 
1892 	if (semctl(INT_MIN, 0, IPC_STAT, statbuf) != -1) e(0);
1893 	if (errno != EINVAL) e(0);
1894 
1895 	for (i = 0; i < sizeof(statbuf); i++)
1896 		if (statbuf[i] != 0x5a) e(0);
1897 
1898 	if (semctl(id, 0, IPC_STAT, statbuf) != 0) e(0);
1899 
1900 	if (statbuf[sizeof(statbuf) - 1] != 0x5a) e(0);
1901 
1902 	if (semctl(id, 0, IPC_STAT, NULL) != -1) e(0);
1903 	if (errno != EFAULT) e(0);
1904 
1905 	if (semctl(id, 0, IPC_STAT, bad_ptr) != -1) e(0);
1906 	if (errno != EFAULT) e(0);
1907 
1908 	if (semctl(id, 0, IPC_STAT, ((struct semid_ds *)bad_ptr) - 1) != 0)
1909 		e(0);
1910 
1911 	if (semctl(id, -1, IPC_STAT, &semds) != 0) e(0);
1912 	if (semds.sem_otime != 0) e(0);
1913 	if (semds.sem_ctime >= now) e(0);
1914 
1915 	/*
1916 	 * Test SEM_STAT.
1917 	 */
1918 	if ((id2 = semget(KEY_A, seminfo.semmsl, IPC_CREAT | 0642)) < 0) e(0);
1919 
1920 	memset(statbuf, 0x5a, sizeof(statbuf));
1921 
1922 	if (semctl(-1, 0, SEM_STAT, statbuf) != -1) e(0);
1923 	if (errno != EINVAL) e(0);
1924 
1925 	if (semctl(seminfo.semmni, 0, SEM_STAT, statbuf) != -1) e(0);
1926 	if (errno != EINVAL) e(0);
1927 
1928 	for (i = 0; i < sizeof(statbuf); i++)
1929 		if (statbuf[i] != 0x5a) e(0);
1930 
1931 	memset(seen, 0, sizeof(seen));
1932 
1933 	for (i = 0; i < seminfo.semmni; i++) {
1934 		errno = 0;
1935 		if ((r = semctl(i, i / 2 - 1, SEM_STAT, statbuf)) == -1) {
1936 			if (errno != EINVAL) e(0);
1937 			continue;
1938 		}
1939 		if (r < 0) e(0);
1940 		memcpy(&semds, statbuf, sizeof(semds));
1941 		if (!(semds.sem_perm.mode & SEM_ALLOC)) e(0);
1942 		if (semds.sem_ctime == 0) e(0);
1943 		if (IXSEQ_TO_IPCID(i, semds.sem_perm) != r) e(0);
1944 		if (r == id) {
1945 			seen[0]++;
1946 			if (semds.sem_perm.mode != (SEM_ALLOC | 0600)) e(0);
1947 			if (semds.sem_perm.uid != geteuid()) e(0);
1948 			if (semds.sem_perm.gid != getegid()) e(0);
1949 			if (semds.sem_perm.cuid != semds.sem_perm.uid) e(0);
1950 			if (semds.sem_perm.cgid != semds.sem_perm.gid) e(0);
1951 			if (semds.sem_perm._key != IPC_PRIVATE) e(0);
1952 			if (semds.sem_nsems != 3) e(0);
1953 			if (semds.sem_otime != 0) e(0);
1954 
1955 			/* This is here because we need a valid index. */
1956 			if (semctl(i, 0, SEM_STAT, NULL) != -1) e(0);
1957 			if (errno != EFAULT) e(0);
1958 
1959 			if (semctl(i, 0, SEM_STAT, bad_ptr) != -1) e(0);
1960 			if (errno != EFAULT) e(0);
1961 		} else if (r == id2) {
1962 			seen[1]++;
1963 			if (semds.sem_perm.mode != (SEM_ALLOC | 0642)) e(0);
1964 			if (semds.sem_perm.uid != geteuid()) e(0);
1965 			if (semds.sem_perm.gid != getegid()) e(0);
1966 			if (semds.sem_perm.cuid != semds.sem_perm.uid) e(0);
1967 			if (semds.sem_perm.cgid != semds.sem_perm.gid) e(0);
1968 			if (semds.sem_perm._key != KEY_A) e(0);
1969 			if (semds.sem_nsems != seminfo.semmsl) e(0);
1970 		}
1971 	}
1972 
1973 	if (seen[0] != 1) e(0);
1974 	if (seen[1] != 1) e(0);
1975 
1976 	if (statbuf[sizeof(statbuf) - 1] != 0x5a) e(0);
1977 
1978 	if (semctl(id, 5, IPC_STAT, &semds) != 0) e(0);
1979 	if (semds.sem_otime != 0) e(0);
1980 	if (semds.sem_ctime >= now) e(0);
1981 
1982 	/*
1983 	 * Test SETVAL.  We start with all the failure cases, so as to be able
1984 	 * to check that sem_ctime is not changed in those cases.
1985 	 */
1986 	if (semctl(badid1, 0, SETVAL, 1) != -1) e(0);
1987 	if (errno != EINVAL) e(0);
1988 
1989 	if (semctl(badid2, 0, SETVAL, 1) != -1) e(0);
1990 	if (errno != EINVAL) e(0);
1991 
1992 	if (semctl(-1, 0, SETVAL, 1) != -1) e(0);
1993 	if (errno != EINVAL) e(0);
1994 
1995 	if (semctl(INT_MIN, 0, SETVAL, 1) != -1) e(0);
1996 	if (errno != EINVAL) e(0);
1997 
1998 	if (semctl(id, -1, SETVAL, 1) != -1) e(0);
1999 	if (errno != EINVAL) e(0);
2000 
2001 	if (semctl(id, 3, SETVAL, 1) != -1) e(0);
2002 	if (errno != EINVAL) e(0);
2003 
2004 	if (semctl(id, 0, SETVAL, -1) != -1) e(0);
2005 	if (errno != ERANGE) e(0);
2006 
2007 	if (semctl(id, 0, SETVAL, seminfo.semvmx + 1) != -1) e(0);
2008 	if (errno != ERANGE) e(0);
2009 
2010 	TEST_SEM(id, 0, 0, 0, 0, 0);
2011 
2012 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
2013 	if (semds.sem_otime != 0) e(0);
2014 	if (semds.sem_ctime >= now) e(0);
2015 
2016 	/* Alright, there we go.. */
2017 	if (semctl(id, 1, SETVAL, 0) != 0) e(0);
2018 
2019 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
2020 	if (semds.sem_otime != 0) e(0);
2021 	if (semds.sem_ctime < now || semds.sem_ctime >= now + 10) e(0);
2022 
2023 	TEST_SEM(id, 1, 0, 0, 0, 0);
2024 
2025 	if (semctl(id, 2, SETVAL, seminfo.semvmx) != 0) e(0);
2026 
2027 	TEST_SEM(id, 2, seminfo.semvmx, 0, 0, 0);
2028 
2029 	if (semctl(id, 0, SETVAL, 1) != 0) e(0);
2030 
2031 	TEST_SEM(id, 0, 1, 0, 0, 0);
2032 	TEST_SEM(id, 1, 0, 0, 0, 0);
2033 	TEST_SEM(id, 2, seminfo.semvmx, 0, 0, 0);
2034 
2035 	if (semctl(id, 0, GETALL, val) != 0) e(0);
2036 	if (val[0] != 1) e(0);
2037 	if (val[1] != 0) e(0);
2038 	if (val[2] != seminfo.semvmx) e(0);
2039 
2040 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
2041 
2042 	while (time(&now) == semds.sem_ctime)
2043 		usleep(250000);
2044 
2045 	/*
2046 	 * Test SETALL.  Same idea: failure cases first.
2047 	 */
2048 	if (semctl(badid1, 0, SETALL, 1) != -1) e(0);
2049 	if (errno != EINVAL) e(0);
2050 
2051 	if (semctl(badid2, 0, SETALL, 1) != -1) e(0);
2052 	if (errno != EINVAL) e(0);
2053 
2054 	if (semctl(-1, 0, SETALL, 1) != -1) e(0);
2055 	if (errno != EINVAL) e(0);
2056 
2057 	if (semctl(INT_MIN, 0, SETALL, 1) != -1) e(0);
2058 	if (errno != EINVAL) e(0);
2059 
2060 	val[0] = seminfo.semvmx + 1;
2061 	val[1] = 0;
2062 	val[2] = 0;
2063 	if (semctl(id, 0, SETALL, val) != -1) e(0);
2064 	if (errno != ERANGE) e(0);
2065 
2066 	val[0] = 0;
2067 	val[1] = 1;
2068 	val[2] = seminfo.semvmx + 1;
2069 	if (semctl(id, 0, SETALL, val) != -1) e(0);
2070 	if (errno != ERANGE) e(0);
2071 
2072 	if (semctl(id, 0, SETALL, NULL) != -1) e(0);
2073 	if (errno != EFAULT) e(0);
2074 
2075 	if (semctl(id, 0, SETALL, bad_ptr) != -1) e(0);
2076 	if (errno != EFAULT) e(0);
2077 
2078 	if (semctl(id, 0, SETALL, ((unsigned short *)bad_ptr) - 2) != -1) e(0);
2079 	if (errno != EFAULT) e(0);
2080 
2081 	TEST_SEM(id, 0, 1, 0, 0, 0);
2082 	TEST_SEM(id, 1, 0, 0, 0, 0);
2083 	TEST_SEM(id, 2, seminfo.semvmx, 0, 0, 0);
2084 
2085 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
2086 	if (semds.sem_otime != 0) e(0);
2087 	if (semds.sem_ctime >= now) e(0);
2088 
2089 	val[0] = seminfo.semvmx;
2090 	val[1] = 0;
2091 	val[2] = 0;
2092 	if (semctl(id, 0, SETALL, val) != 0) e(0);
2093 
2094 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
2095 	if (semds.sem_otime != 0) e(0);
2096 	if (semds.sem_ctime < now || semds.sem_ctime >= now + 10) e(0);
2097 
2098 	TEST_SEM(id, 0, seminfo.semvmx, 0, 0, 0);
2099 	TEST_SEM(id, 1, 0, 0, 0, 0);
2100 	TEST_SEM(id, 2, 0, 0, 0, 0);
2101 
2102 	val[0] = 0;
2103 	val[1] = 1;
2104 	val[2] = seminfo.semvmx;
2105 	if (semctl(id, INT_MAX, SETALL, val) != 0) e(0);
2106 
2107 	TEST_SEM(id, 0, 0, 0, 0, 0);
2108 	TEST_SEM(id, 1, 1, 0, 0, 0);
2109 	TEST_SEM(id, 2, seminfo.semvmx, 0, 0, 0);
2110 
2111 	memset(page_ptr, 0, page_size);
2112 	if (semctl(id, 0, SETALL, ((unsigned short *)bad_ptr) - 3) != 0) e(0);
2113 
2114 	TEST_SEM(id, 0, 0, 0, 0, 0);
2115 	TEST_SEM(id, 1, 0, 0, 0, 0);
2116 	TEST_SEM(id, 2, 0, 0, 0, 0);
2117 
2118 	while (time(&now) == semds.sem_ctime)
2119 		usleep(250000);
2120 
2121 	/*
2122 	 * Test IPC_SET.  Its core functionality has already been tested
2123 	 * thoroughly as part of the permission tests.
2124 	 */
2125 	if (semctl(badid1, 0, IPC_SET, &semds) != -1) e(0);
2126 	if (errno != EINVAL) e(0);
2127 
2128 	if (semctl(badid2, 0, IPC_SET, &semds) != -1) e(0);
2129 	if (errno != EINVAL) e(0);
2130 
2131 	if (semctl(-1, 0, IPC_SET, &semds) != -1) e(0);
2132 	if (errno != EINVAL) e(0);
2133 
2134 	if (semctl(INT_MIN, 0, IPC_SET, &semds) != -1) e(0);
2135 	if (errno != EINVAL) e(0);
2136 
2137 	if (semctl(id, 0, IPC_SET, NULL) != -1) e(0);
2138 	if (errno != EFAULT) e(0);
2139 
2140 	if (semctl(id, 0, IPC_SET, bad_ptr) != -1) e(0);
2141 	if (errno != EFAULT) e(0);
2142 
2143 	if (semctl(id, 0, IPC_STAT, &osemds) != 0) e(0);
2144 	if (osemds.sem_otime != 0) e(0);
2145 	if (osemds.sem_ctime >= now) e(0);
2146 
2147 	/*
2148 	 * Only mode, uid, gid may be set.  While the given mode is sanitized
2149 	 * in our implementation (see below; the open group specification
2150 	 * leaves this undefined), the uid and gid are not (we do not test this
2151 	 * exhaustively).  The other given fields must be ignored.  The ctime
2152 	 * field will be updated.
2153 	 */
2154 	memset(&semds, 0x5b, sizeof(semds));
2155 	semds.sem_perm.mode = 0712;
2156 	semds.sem_perm.uid = UID_MAX;
2157 	semds.sem_perm.gid = GID_MAX - 1;
2158 	if (semctl(id, 0, IPC_SET, &semds) != 0) e(0);
2159 
2160 	if (semctl(id, 0, IPC_STAT, &semds) != 0) e(0);
2161 	if (semds.sem_perm.mode != (SEM_ALLOC | 0712)) e(0);
2162 	if (semds.sem_perm.uid != UID_MAX) e(0);
2163 	if (semds.sem_perm.gid != GID_MAX - 1) e(0);
2164 	if (semds.sem_perm.cuid != osemds.sem_perm.cuid) e(0);
2165 	if (semds.sem_perm.cgid != osemds.sem_perm.cgid) e(0);
2166 	if (semds.sem_perm._seq != osemds.sem_perm._seq) e(0);
2167 	if (semds.sem_perm._key != osemds.sem_perm._key) e(0);
2168 	if (semds.sem_nsems != osemds.sem_nsems) e(0);
2169 	if (semds.sem_otime != osemds.sem_otime) e(0);
2170 	if (semds.sem_ctime < now || semds.sem_ctime >= now + 10) e(0);
2171 
2172 	/* It should be possible to set any mode, but mask 0777 is applied. */
2173 	semds.sem_perm.uid = osemds.sem_perm.uid;
2174 	semds.sem_perm.gid = osemds.sem_perm.gid;
2175 	for (i = 0; i < 0777; i++) {
2176 		semds.sem_perm.mode = i;
2177 		if (semctl(id, i / 2 - 1, IPC_SET, &semds) != 0) e(0);
2178 
2179 		if (semctl(id, i / 2 - 2, IPC_STAT, &semds) != 0) e(0);
2180 		if (semds.sem_perm.mode != (SEM_ALLOC | i)) e(0);
2181 
2182 		semds.sem_perm.mode = ~0777 | i;
2183 		if (semctl(id, i / 2 - 3, IPC_SET, &semds) != 0) e(0);
2184 
2185 		if (semctl(id, i / 2 - 4, IPC_STAT, &semds) != 0) e(0);
2186 		if (semds.sem_perm.mode != (SEM_ALLOC | i)) e(0);
2187 	}
2188 	if (semds.sem_perm.uid != osemds.sem_perm.uid) e(0);
2189 	if (semds.sem_perm.gid != osemds.sem_perm.gid) e(0);
2190 
2191 	if (semctl(id, 0, IPC_SET, ((struct semid_ds *)bad_ptr) - 1) != 0)
2192 		e(0);
2193 
2194 	/*
2195 	 * Test IPC_RMID.  Its basic functionality has already been tested
2196 	 * multiple times over, so there is not much left to do here.
2197 	 */
2198 	if (semctl(badid1, 0, IPC_RMID) != -1) e(0);
2199 	if (errno != EINVAL) e(0);
2200 
2201 	if (semctl(badid2, 0, IPC_RMID) != -1) e(0);
2202 	if (errno != EINVAL) e(0);
2203 
2204 	if (semctl(-1, 0, IPC_RMID) != -1) e(0);
2205 	if (errno != EINVAL) e(0);
2206 
2207 	if (semctl(INT_MIN, 0, IPC_RMID) != -1) e(0);
2208 	if (errno != EINVAL) e(0);
2209 
2210 	if (semctl(id, 0, IPC_RMID) != 0) e(0);
2211 
2212 	if (semctl(id, 0, IPC_RMID) != -1) e(0);
2213 	if (errno != EINVAL) e(0);
2214 
2215 	if (semctl(id, 0, IPC_STAT, &semds) != -1) e(0);
2216 	if (errno != EINVAL) e(0);
2217 
2218 	if (semctl(id2, 1, IPC_RMID) != 0) e(0);
2219 
2220 	if (semctl(id2, 1, IPC_RMID) != -1) e(0);
2221 	if (errno != EINVAL) e(0);
2222 
2223 	/*
2224 	 * Test IPC_INFO and SEM_INFO.  Right now, for all practical purposes,
2225 	 * these identifiers behave pretty much the same.
2226 	 */
2227 	if ((id = semget(IPC_PRIVATE, 3, 0600)) == -1) e(0);
2228 	if ((id2 = semget(IPC_PRIVATE, 1, 0600)) == -1) e(0);
2229 
2230 	for (i = 0; i <= 1; i++) {
2231 		cmd = (i == 0) ? IPC_INFO : SEM_INFO;
2232 
2233 		memset(&seminfo, 0xff, sizeof(seminfo));
2234 
2235 		if ((r = semctl(0, 0, cmd, &seminfo)) == -1) e(0);
2236 
2237 		/*
2238 		 * These commands return the index of the highest in-use slot
2239 		 * in the semaphore set table.  Bad idea of course, because
2240 		 * that means the value 0 has two potential meanings.  Since we
2241 		 * cannot guarantee that no other running application is using
2242 		 * semaphores, we settle for "at least" tests based on the two
2243 		 * semaphore sets we just created.
2244 		 */
2245 		if (r < 1 || r >= seminfo.semmni) e(0);
2246 
2247 		/*
2248 		 * Many of these checks are rather basic because of missing
2249 		 * SEM_UNDO support.  The only difference between IPC_INFO and
2250 		 * SEM_INFO is the meaning of the semusz and semaem fields.
2251 		 */
2252 		if (seminfo.semmap < 0) e(0);
2253 		if (seminfo.semmni < 3 || seminfo.semmni > USHRT_MAX) e(0);
2254 		if (seminfo.semmns < 3 || seminfo.semmns > USHRT_MAX) e(0);
2255 		if (seminfo.semmnu < 0) e(0);
2256 		if (seminfo.semmsl < 3 || seminfo.semmsl > USHRT_MAX) e(0);
2257 		if (seminfo.semopm < 3 || seminfo.semopm > USHRT_MAX) e(0);
2258 		if (seminfo.semume < 0) e(0);
2259 		if (cmd == SEM_INFO) {
2260 			if (seminfo.semusz < 2) e(0);
2261 		} else
2262 			if (seminfo.semusz < 0) e(0);
2263 		if (seminfo.semvmx < 3 || seminfo.semvmx > SHRT_MAX) e(0);
2264 		if (cmd == SEM_INFO) {
2265 			if (seminfo.semaem < 4) e(0);
2266 		} else
2267 			if (seminfo.semaem < 0) e(0);
2268 
2269 		if (semctl(INT_MAX, -1, cmd, &seminfo) == -1) e(0);
2270 		if (semctl(-1, INT_MAX, cmd, &seminfo) == -1) e(0);
2271 
2272 		if (semctl(0, 0, cmd, NULL) != -1) e(0);
2273 		if (errno != EFAULT) e(0);
2274 
2275 		if (semctl(0, 0, cmd, bad_ptr) != -1) e(0);
2276 		if (errno != EFAULT) e(0);
2277 
2278 		if (semctl(0, 0, cmd, ((struct seminfo *)bad_ptr) - 1) == -1)
2279 			e(0);
2280 	}
2281 
2282 	if (semctl(id2, 0, IPC_RMID) != 0) e(0);
2283 
2284 	/*
2285 	 * Finally, test invalid commands.  Well, hopefully invalid commands,
2286 	 * anyway.
2287 	 */
2288 	if (semctl(id, 0, INT_MIN) != -1) e(0);
2289 	if (errno != EINVAL) e(0);
2290 
2291 	if (semctl(id, 0, INT_MAX) != -1) e(0);
2292 	if (errno != EINVAL) e(0);
2293 
2294 	if (semctl(id, 0, IPC_RMID) != 0) e(0);
2295 }
2296 
2297 /*
2298  * Test SEM_UNDO support.  Right now this functionality is missing altogether.
2299  * For now, we test that any attempt to use SEM_UNDO fails.
2300  */
2301 static void
2302 test88d(void)
2303 {
2304 	struct sembuf sop;
2305 	int id;
2306 
2307 	subtest = 3;
2308 
2309 	if ((id = semget(IPC_PRIVATE, 1, 0600)) == -1) e(0);
2310 
2311 	/*
2312 	 * Use an all-ones (but positive) flag field.  This will include
2313 	 * SEM_UNDO, but also tell the IPC server to report no warning.
2314 	 */
2315 	if (!(SHRT_MAX & SEM_UNDO)) e(0);
2316 	sop.sem_num = 0;
2317 	sop.sem_op = 1;
2318 	sop.sem_flg = SHRT_MAX;
2319 	if (semop(id, &sop, 1) != -1) e(0);
2320 	if (errno != EINVAL) e(0);
2321 
2322 	if (semctl(id, 0, IPC_RMID) != 0) e(0);
2323 }
2324 
2325 enum {
2326 	RESUME_SEMOP,	/* use semop() to resume blocked parties */
2327 	RESUME_SETVAL,	/* use semctl(SETVAL) to resume blocked parties */
2328 	RESUME_SETALL,	/* use semctl(SETALL) to resume blocked parties */
2329 	NR_RESUMES
2330 };
2331 
2332 enum {
2333 	MATCH_FIRST,	/* first match completes, blocks second match */
2334 	MATCH_SECOND,	/* first match does not complete, second match does */
2335 	MATCH_KILL,	/* second match completes after first is aborted */
2336 	MATCH_BOTH,	/* first and second match both complete */
2337 	MATCH_CASCADE,	/* completed match in turn causes another match */
2338 	MATCH_ALL,	/* a combination of the last two */
2339 	NR_MATCHES
2340 };
2341 
2342 /*
2343  * Auxiliary child procedure.  The auxiliary children will deadlock until the
2344  * semaphore set is removed.
2345  */
2346 static void
2347 test88e_childaux(struct link * parent)
2348 {
2349 	struct sembuf sops[3];
2350 	struct seminfo seminfo;
2351 	int child, id, num;
2352 
2353 	child = rcv(parent);
2354 	id = rcv(parent);
2355 	num = rcv(parent);
2356 
2357 	memset(sops, 0, sizeof(sops));
2358 
2359 	/* These operations are guaranteed to never return successfully. */
2360 	switch (child) {
2361 	case 1:
2362 		sops[0].sem_num = num;
2363 		sops[0].sem_op = 1;
2364 		sops[1].sem_num = num;
2365 		sops[1].sem_op = 0;
2366 		sops[2].sem_num = 0;
2367 		sops[2].sem_op = 1;
2368 		break;
2369 	case 2:
2370 		if (semctl(0, 0, IPC_INFO, &seminfo) == -1) e(0);
2371 		sops[0].sem_num = num;
2372 		sops[0].sem_op = -seminfo.semvmx;
2373 		sops[1].sem_num = num;
2374 		sops[1].sem_op = -seminfo.semvmx;
2375 		sops[2].sem_num = 0;
2376 		sops[2].sem_op = 1;
2377 		break;
2378 	default:
2379 		e(0);
2380 	}
2381 
2382 	snd(parent, 0);
2383 
2384 	if (semop(id, sops, 3) != -1) e(0);
2385 	if (errno != EIDRM) e(0);
2386 }
2387 
2388 /*
2389  * First child procedure.
2390  */
2391 static void
2392 test88e_child1(struct link * parent)
2393 {
2394 	struct sembuf sops[3];
2395 	size_t nsops;
2396 	int match, id, expect;
2397 
2398 	match = rcv(parent);
2399 	id = rcv(parent);
2400 
2401 	/* Start off with some defaults, then refine by match type. */
2402 	memset(sops, 0, sizeof(sops));
2403 	sops[0].sem_num = 2;
2404 	sops[0].sem_op = -1;
2405 	nsops = 2;
2406 	expect = 0;
2407 	switch (match) {
2408 	case MATCH_FIRST:
2409 		sops[1].sem_num = 3;
2410 		sops[1].sem_op = 1;
2411 		break;
2412 	case MATCH_SECOND:
2413 		sops[1].sem_num = 3;
2414 		sops[1].sem_op = -1;
2415 		sops[2].sem_num = 0;
2416 		sops[2].sem_op = 1;
2417 		nsops = 3;
2418 		expect = -1;
2419 		break;
2420 	case MATCH_KILL:
2421 		sops[1].sem_num = 0;
2422 		sops[1].sem_op = 1;
2423 		expect = INT_MIN;
2424 		break;
2425 	case MATCH_BOTH:
2426 	case MATCH_CASCADE:
2427 	case MATCH_ALL:
2428 		sops[1].sem_num = 3;
2429 		sops[1].sem_op = 1;
2430 		break;
2431 	default:
2432 		e(0);
2433 	}
2434 
2435 	snd(parent, 0);
2436 
2437 	if (semop(id, sops, nsops) != expect) e(0);
2438 	if (expect == -1 && errno != EIDRM) e(0);
2439 }
2440 
2441 /*
2442  * Second child procedure.
2443  */
2444 static void
2445 test88e_child2(struct link * parent)
2446 {
2447 	struct sembuf sops[2];
2448 	size_t nsops;
2449 	int match, id, expect;
2450 
2451 	match = rcv(parent);
2452 	id = rcv(parent);
2453 
2454 	/* Start off with some defaults, then refine by match type. */
2455 	memset(sops, 0, sizeof(sops));
2456 	sops[0].sem_num = 2;
2457 	sops[0].sem_op = -1;
2458 	nsops = 2;
2459 	expect = 0;
2460 	switch (match) {
2461 	case MATCH_FIRST:
2462 		sops[1].sem_num = 0;
2463 		sops[1].sem_op = 1;
2464 		expect = -1;
2465 		break;
2466 	case MATCH_SECOND:
2467 	case MATCH_KILL:
2468 		nsops = 1;
2469 		break;
2470 	case MATCH_BOTH:
2471 	case MATCH_ALL:
2472 		sops[1].sem_num = 3;
2473 		sops[1].sem_op = 1;
2474 		break;
2475 	case MATCH_CASCADE:
2476 		sops[0].sem_num = 3;
2477 		nsops = 1;
2478 		break;
2479 	default:
2480 		e(0);
2481 	}
2482 
2483 	snd(parent, 0);
2484 
2485 	if (semop(id, sops, nsops) != expect) e(0);
2486 	if (expect == -1 && errno != EIDRM) e(0);
2487 }
2488 
2489 /*
2490  * Third child procedure.
2491  */
2492 static void
2493 test88e_child3(struct link * parent)
2494 {
2495 	struct sembuf sops[1];
2496 	size_t nsops;
2497 	int match, id;
2498 
2499 	match = rcv(parent);
2500 	id = rcv(parent);
2501 
2502 	/* Things are a bit simpler here. */
2503 	memset(sops, 0, sizeof(sops));
2504 	nsops = 1;
2505 	switch (match) {
2506 	case MATCH_ALL:
2507 		sops[0].sem_num = 3;
2508 		sops[0].sem_op = -2;
2509 		break;
2510 	default:
2511 		e(0);
2512 	}
2513 
2514 	snd(parent, 0);
2515 
2516 	if (semop(id, sops, nsops) != 0) e(0);
2517 }
2518 
2519 /*
2520  * Perform one test for operations affecting multiple processes.
2521  */
2522 static void
2523 sub88e(unsigned int match, unsigned int resume, unsigned int aux)
2524 {
2525 	struct link aux1, aux2, child1, child2, child3;
2526 	struct sembuf sop;
2527 	unsigned short val[4];
2528 	int id, inc, aux_zcnt, aux_ncnt;
2529 
2530 	/*
2531 	 * For this test we use one single semaphore set, with four semaphores.
2532 	 * The first semaphore is increased in the case that an operation that
2533 	 * should never complete does complete, and thus should stay zero.
2534 	 * Depending on 'aux', the second or third semaphore is used by the
2535 	 * auxiliary children (if any, also depending on 'aux') to deadlock on.
2536 	 * The third and higher semaphores are used in the main operations.
2537 	 */
2538 	if ((id = semget(IPC_PRIVATE, __arraycount(val), 0666)) == -1) e(0);
2539 
2540 	aux_zcnt = aux_ncnt = 0;
2541 
2542 	/* Start the first auxiliary child if desired, before all others. */
2543 	if (aux & 1) {
2544 		spawn(&aux1, test88e_childaux, DROP_ALL);
2545 
2546 		snd(&aux1, 1);
2547 		snd(&aux1, id);
2548 		snd(&aux1, (aux & 4) ? 2 : 1);
2549 
2550 		if (rcv(&aux1) != 0) e(0);
2551 
2552 		if (aux & 4)
2553 			aux_zcnt++;
2554 	}
2555 
2556 	/* Start and configure all children for this specific match test. */
2557 	spawn(&child1, test88e_child1, DROP_ALL);
2558 
2559 	snd(&child1, match);
2560 	snd(&child1, id);
2561 
2562 	if (rcv(&child1) != 0) e(0);
2563 
2564 	/*
2565 	 * For fairness tests, we must ensure that the first child blocks on
2566 	 * the semaphore before the second child does.
2567 	 */
2568 	switch (match) {
2569 	case MATCH_FIRST:
2570 	case MATCH_SECOND:
2571 	case MATCH_KILL:
2572 		usleep(WAIT_USECS);
2573 		break;
2574 	}
2575 
2576 	spawn(&child2, test88e_child2, DROP_NONE);
2577 
2578 	snd(&child2, match);
2579 	snd(&child2, id);
2580 
2581 	if (rcv(&child2) != 0) e(0);
2582 
2583 	if (match == MATCH_ALL) {
2584 		spawn(&child3, test88e_child3, DROP_USER);
2585 
2586 		snd(&child3, match);
2587 		snd(&child3, id);
2588 
2589 		if (rcv(&child3) != 0) e(0);
2590 	}
2591 
2592 	/* Start the second auxiliary child if desired, after all others. */
2593 	if (aux & 2) {
2594 		spawn(&aux2, test88e_childaux, DROP_NONE);
2595 
2596 		snd(&aux2, 2);
2597 		snd(&aux2, id);
2598 		snd(&aux2, (aux & 4) ? 2 : 1);
2599 
2600 		if (rcv(&aux2) != 0) e(0);
2601 
2602 		if (aux & 4)
2603 			aux_ncnt++;
2604 	}
2605 
2606 	usleep(WAIT_USECS);
2607 
2608 	/*
2609 	 * Test semaphore values and determine the value with which to increase
2610 	 * the third semaphore.  For MATCH_KILL, also kill the first child.
2611 	 */
2612 	inc = 1;
2613 	switch (match) {
2614 	case MATCH_FIRST:
2615 	case MATCH_SECOND:
2616 		TEST_SEM(id, 2, 0, 0, 2 + aux_ncnt, aux_zcnt);
2617 		TEST_SEM(id, 3, 0, 0, 0, 0);
2618 		break;
2619 	case MATCH_KILL:
2620 		TEST_SEM(id, 2, 0, 0, 2 + aux_ncnt, aux_zcnt);
2621 
2622 		terminate(&child1);
2623 
2624 		/* As stated before, non-self kills need not be instant. */
2625 		usleep(WAIT_USECS);
2626 
2627 		TEST_SEM(id, 2, 0, 0, 1 + aux_ncnt, aux_zcnt);
2628 		TEST_SEM(id, 3, 0, 0, 0, 0);
2629 		break;
2630 	case MATCH_BOTH:
2631 		TEST_SEM(id, 2, 0, 0, 2 + aux_ncnt, aux_zcnt);
2632 		TEST_SEM(id, 3, 0, 0, 0, 0);
2633 		inc = 2;
2634 		break;
2635 	case MATCH_CASCADE:
2636 		TEST_SEM(id, 2, 0, 0, 1 + aux_ncnt, aux_zcnt);
2637 		TEST_SEM(id, 3, 0, 0, 1, 0);
2638 		break;
2639 	case MATCH_ALL:
2640 		TEST_SEM(id, 2, 0, 0, 2 + aux_ncnt, aux_zcnt);
2641 		TEST_SEM(id, 3, 0, 0, 1, 0);
2642 		inc = 2;
2643 		break;
2644 	default:
2645 		e(0);
2646 	}
2647 
2648 	TEST_SEM(id, 0, 0, 0, 0, 0);
2649 	TEST_SEM(id, 1, 0, 0, -1, -1);
2650 
2651 	/* Resume the appropriate set of children. */
2652 	switch (resume) {
2653 	case RESUME_SEMOP:
2654 		memset(&sop, 0, sizeof(sop));
2655 		sop.sem_num = 2;
2656 		sop.sem_op = inc;
2657 		if (semop(id, &sop, 1) != 0) e(0);
2658 		break;
2659 	case RESUME_SETVAL:
2660 		if (semctl(id, 2, SETVAL, inc) != 0) e(0);
2661 		break;
2662 	case RESUME_SETALL:
2663 		memset(val, 0, sizeof(val));
2664 		val[2] = inc;
2665 		if (semctl(id, 0, SETALL, val) != 0) e(0);
2666 		break;
2667 	default:
2668 		e(0);
2669 	}
2670 
2671 	/*
2672 	 * See if the right children were indeed resumed, and retest the
2673 	 * semaphore values.
2674 	 */
2675 	switch (match) {
2676 	case MATCH_FIRST:
2677 		TEST_SEM(id, 2, 0, child1.pid, 1 + aux_ncnt, aux_zcnt);
2678 		TEST_SEM(id, 3, 1, child1.pid, 0, 0);
2679 		collect(&child1);
2680 		break;
2681 	case MATCH_SECOND:
2682 		TEST_SEM(id, 2, 0, child2.pid, 1 + aux_ncnt, aux_zcnt);
2683 		TEST_SEM(id, 3, 0, 0, 0, 0);
2684 		collect(&child2);
2685 		break;
2686 	case MATCH_KILL:
2687 		TEST_SEM(id, 2, 0, child2.pid, aux_ncnt, aux_zcnt);
2688 		TEST_SEM(id, 3, 0, 0, 0, 0);
2689 		collect(&child2);
2690 		break;
2691 	case MATCH_BOTH:
2692 		/*
2693 		 * The children are not ordered in this case, so we do not know
2694 		 * which one gets access to the semaphores last.
2695 		 */
2696 		TEST_SEM(id, 2, 0, -1, aux_ncnt, aux_zcnt);
2697 		TEST_SEM(id, 3, 2, -1, 0, 0);
2698 		collect(&child1);
2699 		collect(&child2);
2700 		break;
2701 	case MATCH_CASCADE:
2702 		TEST_SEM(id, 2, 0, child1.pid, aux_ncnt, aux_zcnt);
2703 		TEST_SEM(id, 3, 0, child2.pid, 0, 0);
2704 		collect(&child1);
2705 		collect(&child2);
2706 		break;
2707 	case MATCH_ALL:
2708 		TEST_SEM(id, 2, 0, -1, aux_ncnt, aux_zcnt);
2709 		TEST_SEM(id, 3, 0, child3.pid, 0, 0);
2710 		collect(&child1);
2711 		collect(&child2);
2712 		collect(&child3);
2713 		break;
2714 	default:
2715 		e(0);
2716 	}
2717 
2718 	TEST_SEM(id, 0, 0, 0, 0, 0);
2719 	TEST_SEM(id, 1, 0, 0, -1, -1);
2720 
2721 	/* Remove the semaphore set.  This should unblock remaining callers. */
2722 	if (semctl(id, 0, IPC_RMID) != 0) e(0);
2723 
2724 	/* Wait for the children that were not resumed, but should be now. */
2725 	switch (match) {
2726 	case MATCH_FIRST:
2727 		collect(&child2);
2728 		break;
2729 	case MATCH_SECOND:
2730 		collect(&child1);
2731 		break;
2732 	case MATCH_KILL:
2733 	case MATCH_BOTH:
2734 	case MATCH_CASCADE:
2735 	case MATCH_ALL:
2736 		break;
2737 	default:
2738 		e(0);
2739 	}
2740 
2741 	/* Wait for the auxiliary children as well. */
2742 	if (aux & 1)
2743 		collect(&aux1);
2744 	if (aux & 2)
2745 		collect(&aux2);
2746 }
2747 
2748 /*
2749  * Test operations affecting multiple processes, ensuring the following points:
2750  * 1) an operation resumes all possible waiters; 2) a resumed operation in turn
2751  * correctly resumes other now-unblocked operations; 3) a basic level of FIFO
2752  * fairness is provided between blocked parties; 4) all the previous points are
2753  * unaffected by additional waiters that are not being resumed; 5) identifier
2754  * removal properly resumes all affected waiters.
2755  */
2756 static void
2757 test88e(void)
2758 {
2759 	unsigned int resume, match, aux;
2760 
2761 	subtest = 4;
2762 
2763 	for (match = 0; match < NR_MATCHES; match++)
2764 		for (resume = 0; resume < NR_RESUMES; resume++)
2765 			for (aux = 1; aux <= 8; aux++) /* 0 and 4 are equal */
2766 				sub88e(match, resume, aux);
2767 }
2768 
2769 /*
2770  * Initialize the test.
2771  */
2772 static void
2773 test88_init(void)
2774 {
2775 	struct group *gr;
2776 
2777 	/* Start with full root privileges. */
2778 	setuid(geteuid());
2779 
2780 	if ((gr = getgrnam(ROOT_GROUP)) == NULL) e(0);
2781 
2782 	setgid(gr->gr_gid);
2783 	setegid(gr->gr_gid);
2784 
2785 	page_size = getpagesize();
2786 	page_ptr = mmap(NULL, page_size * 2, PROT_READ | PROT_WRITE,
2787 	    MAP_ANON | MAP_PRIVATE, -1, 0);
2788 	if (page_ptr == MAP_FAILED) e(0);
2789 	bad_ptr = page_ptr + page_size;
2790 	if (munmap(bad_ptr, page_size) != 0) e(0);
2791 }
2792 
2793 /*
2794  * Test program for SysV IPC semaphores.
2795  */
2796 int
2797 main(int argc, char ** argv)
2798 {
2799 	int i, m;
2800 
2801 	start(88);
2802 
2803 	test88_init();
2804 
2805 	if (argc == 2)
2806 		m = atoi(argv[1]);
2807 	else
2808 		m = 0xFF;
2809 
2810 	for (i = 0; i < ITERATIONS; i++) {
2811 		if (m & 0x01) test88a();
2812 		if (m & 0x02) test88b();
2813 		if (m & 0x04) test88c();
2814 		if (m & 0x08) test88d();
2815 		if (m & 0x10) test88e();
2816 	}
2817 
2818 	quit();
2819 }
2820