diff options
Diffstat (limited to 'tests/spin4.c')
-rw-r--r-- | tests/spin4.c | 65 |
1 files changed, 65 insertions, 0 deletions
diff --git a/tests/spin4.c b/tests/spin4.c new file mode 100644 index 0000000..a435d04 --- /dev/null +++ b/tests/spin4.c @@ -0,0 +1,65 @@ +/* + * spin4.c + * + * Declare a spinlock object, lock it, spin on it, + * and then unlock it again. + * + * For this to work on a single processor machine we have + * to static initialise the spinlock. This bypasses the + * check of the number of processors done by pthread_spin_init. + * This is a non-portable side-effect of this implementation. + */ + +#include "test.h" +#include <sys/timeb.h> + +pthread_spinlock_t lock = PTHREADS_SPINLOCK_INITIALIZER; +struct _timeb currSysTimeStart; +struct _timeb currSysTimeStop; + +#define GetDurationMilliSecs(_TStart, _TStop) ((_TStop.time*1000+_TStop.millitm) \ + - (_TStart.time*1000+_TStart.millitm)) + +static int washere = 0; + +void * func(void * arg) +{ + _ftime(&currSysTimeStart); + assert(pthread_spin_lock(&lock) == 0); + assert(pthread_spin_unlock(&lock) == 0); + _ftime(&currSysTimeStop); + washere = 1; + + return (void *) GetDurationMilliSecs(currSysTimeStart, currSysTimeStop); +} + +int +main() +{ + long result = 0; + pthread_t t; + + assert(pthread_spin_lock(&lock) == 0); + + assert(pthread_create(&t, NULL, func, NULL) == 0); + + /* + * This should relinqish the CPU to the func thread enough times + * to waste approximately 2000 millisecs only if the lock really + * is spinning in the func thread (assuming 10 millisec CPU quantum). + for (i = 0; i < 200; i++) + { + sched_yield(); + } + + assert(pthread_spin_unlock(&lock) == 0); + + assert(pthread_join(t, (void *) &result) == 0); + assert(result > 1000); + + assert(pthread_spin_destroy(&lock) == 0); + + assert(washere == 1); + + return 0; +} |