#include #include #include #include #include #include #include #include #include #include #include #include int nIter = 1000000; #define LATCH_TIMEOUT 50000000L #include "latch.h" #include "unix_latch.c" int selfLatch, otherLatch; Latch *latchArray; #ifdef LINUX_SEM int semId = -1; #endif void DoWork(int selfLatch); void sigusr1handler(int n) { DEBUG("sigusr handler\n"); latch_sigusr1_handler(); } main() { int child; int i; int shmid; for (i = 0; i < 1000; i++) { shmid = shmget(6500 + i, sizeof(Latch) * 2, IPC_CREAT | IPC_EXCL|0x1ff); if (shmid < 0) { DEBUG("shmget error %d %d\n", shmid, errno); if (i == 999) { printf("Can't get shm, aborting test\n"); exit (1); } } else { break; } } latchArray = shmat(shmid, NULL, 0); if ((long)latchArray < 0) { printf("shmat error %ld %d\n", (long)latchArray, errno); exit(1); } InitSharedLatch(&latchArray[0]); InitSharedLatch(&latchArray[1]); child = fork(); if (child < 0) { printf("fork error %d %d\n", child, errno); exit(1); } MyProcPid = getpid(); signal(SIGUSR1, sigusr1handler); DoWork(child != 0); } static int WaitForOther(int latch) { int ret; Latch *l = &latchArray[latch]; DEBUG("Wait %p\n", l); ret = WaitLatch(l, LATCH_TIMEOUT); ResetLatch(l); return ret; } static void SignalOther(int latch) { Latch *l = &latchArray[latch]; DEBUG("Signal %p\n", l); SetLatch(l); } void DoWork(int l) { int i; struct timeval tv1, tv2; struct timezone tz; float diff; selfLatch = l, otherLatch = selfLatch ^ 1; Latch *self = &latchArray[selfLatch]; Latch *other = &latchArray[otherLatch ^ 1]; OwnLatch(self); sleep(2); /* Cheat: pseudo-barrier. */ printf("Start Test:"); #if defined(LINUX_SEM) printf("Using semaphores\n"); #elif defined(PIPE) printf("Using pipe\n"); #else printf("Using signal\n"); #endif /* Set one of the latches in the beginning. */ if (selfLatch == 0) { SignalOther(otherLatch); } gettimeofday(&tv1, &tz); for (i = 0; i < nIter; i++) { if (WaitForOther(selfLatch) != 1) { printf("BUG BUG BUG\n"); exit(1); } SignalOther(otherLatch); } gettimeofday(&tv2, &tz); diff = (tv2.tv_sec - tv1.tv_sec) * 1000000 + (tv2.tv_usec - tv1.tv_usec); printf("%ld iterations took %.2f sec (%.2f usec/iter)\n", nIter, diff/1000000, diff/nIter); }