1/* 2 * Copyright (C) 2008 The Android Open Source Project 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * * Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * * Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in 12 * the documentation and/or other materials provided with the 13 * distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 16 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 17 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 18 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 19 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 20 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 21 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS 22 * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 23 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 24 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT 25 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26 * SUCH DAMAGE. 27 */ 28#include <pthread.h> 29#include <semaphore.h> 30#include <errno.h> 31#include <stdio.h> 32#include <time.h> 33#include <string.h> 34#include <unistd.h> 35 36/* a simple semaphore test, using three threads 37 * 38 * a semaphore is initialized with a value of 1 39 * 40 * Thread 1, 2 and 3 start at the same time 41 * 42 * Thread 1 takes the semaphore, then sleeps for 2 seconds, then post the semaphore 43 * Thread 2 sleeps for 1 second, then waits the semaphore, sleeps for 2 seconds, then post the semaphoe 44 * Thread 3 sleeps 3 seconds, waits for the semaphore 45 */ 46 47static sem_t semaphore; 48 49static void* 50_thread1( void* unused ) 51{ 52 printf( "thread 1: waiting for semaphore\n" ); 53 if ( sem_wait( &semaphore ) < 0 ) { 54 printf( "thread 1: could not wait for semaphore: %s\n", strerror(errno) ); 55 return NULL; 56 } 57 printf( "thread 1: got the semaphore ! sleeping for 2 seconds\n" ); 58 sleep( 2 ); 59 printf( "thread 1: awake !! posting semaphore\n" ); 60 if ( sem_post( &semaphore ) < 0 ) { 61 printf( "thread 2: could not post semaphore: %s\n", strerror(errno) ); 62 } 63 printf( "thread 1: quitting\n" ); 64 return NULL; 65} 66 67static void* 68_thread2( void* unused ) 69{ 70 printf( "thread 2: sleeping for 1 second\n" ); 71 sleep(1); 72 printf( "thread 2: awake !! waiting for semaphore\n" ); 73 if ( sem_wait( &semaphore ) < 0 ) { 74 printf( "thread 2: could not wait for semaphore: %s\n", strerror(errno) ); 75 return NULL; 76 } 77 printf( "thread 2: got the semaphore ! sleeping for 2 seconds\n" ); 78 sleep( 2 ); 79 printf( "thread 2: awake !! posting semaphore\n" ); 80 if ( sem_post( &semaphore ) < 0 ) { 81 printf( "thread 2: could not post semaphore: %s\n", strerror(errno) ); 82 } 83 printf( "thread 2: quitting\n" ); 84 return NULL; 85} 86 87 88static void* 89_thread3( void* unused ) 90{ 91 printf( "thread 3: sleeping for 3 seconds\n" ); 92 sleep(3); 93 printf( "thread 3: awake !! waiting for semaphore\n" ); 94 if ( sem_wait( &semaphore ) < 0 ) { 95 printf( "thread 3: could not wait for semaphore: %s\n", strerror(errno) ); 96 return NULL; 97 } 98 printf( "thread 3: got semaphore. quitting\n" ); 99 return NULL; 100} 101 102typedef void* (*thread_func)(void*); 103 104static const thread_func thread_routines[] = 105{ 106 &_thread1, 107 &_thread2, 108 &_thread3 109}; 110 111int main( void ) 112{ 113 pthread_t t[3]; 114 int nn; 115 116 if ( sem_init( &semaphore, 0, 1 ) < 0 ) { 117 printf( "could not initialize semaphore: %s\n", strerror(errno) ); 118 return -1; 119 } 120 121 for ( nn = 0; nn < 3; nn++ ) { 122 if ( pthread_create( &t[nn], NULL, thread_routines[nn], NULL ) < 0 ) { 123 printf("could not create thread %d: %s\n", nn+1, strerror(errno) ); 124 return -2; 125 } 126 } 127 sleep( 5 ); 128 return 0; 129} 130