#include #include #include #include #include #include #include static int timed_out = 0; void timeout(int sig) { timed_out = 1; } int main() { static const char* sem_name = "/myhappysemaphore"; sem_t* ps = sem_open(sem_name, O_RDWR); if (ps) sem_close(ps); // clean up old semaphore; we probably crashed ps = sem_open(sem_name, O_CREAT, 0600, 0); if (ps == SEM_FAILED) { perror("sem_open"); return 1; } puts("Created semamphore."); pid_t pid = fork(); switch (pid) { case -1: // error perror("fork"); return 2; case 0: // child signal(SIGALRM, timeout); while (1) { alarm(1); int ret = sem_wait(ps); if (ret == -1) { if (timed_out) { if (errno == EINTR) { puts("Child timed out normally waiting " "for the semaphore."); timed_out = 0; } else { puts("Child timed out ABNORMALLY waiting " "for the semaphore!"); exit(99); } } else { perror("sem_wait"); exit(69); } } else { puts("Child got the semaphore! " "How the spit did that happen?"); exit(42); } } break; default: { // parent puts("Created child. Posting the deathwatch."); int status; while (1) { pid_t ret = waitpid(pid, &status, 0); if (ret > 0) { if (WIFEXITED(status)) { printf("Child %d died peacefully, code %d.\n", ret, WEXITSTATUS(status)); break; } else { printf("Child %d died screaming, status 0x%08X.\n", ret, status); return 3; } } else { perror("waitpid"); return 4; } } } } return 0; }