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 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 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 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 131 main(void) 132 { 133 test_unnamed(); 134 test_named(); 135 test_named2(); 136 return (0); 137 } 138