//2010-01-19 yaojianming 摘自unix网络编程2卷
//以下为多生产者,单消费者的互斥锁,条件变量的实现
# include < stdio. h> # include < unistd. h> # include < pthread. h> # define MAXNITEMS 100000 # define MAXNTHREADS 10 int nitems = MAXNITEMS; int buff[ MAXNITEMS] ; struct val { pthread_mutex_t mutex; int nput; int nval; } put = { PTHREAD_MUTEX_INITIALIZER , 0, 0 } ; struct mutex_cond { pthread_mutex_t mutex; pthread_cond_t cond; int nready; } nready = { PTHREAD_MUTEX_INITIALIZER , PTHREAD_COND_INITIALIZER, 0 } ; void * produce( void * arg ) { while ( 1) { pthread_mutex_lock ( & put. mutex) ; if ( put. nput > = nitems) { pthread_mutex_unlock ( & put. mutex) ; return NULL ; } buff[ put. nput] = put. nval; put. nput+ + ; put. nval+ + ; pthread_mutex_unlock ( & put. mutex) ; int dosignal; pthread_mutex_lock ( & nready. mutex) ; dosignal = ( nready. nready = = 0) ; nready. nready+ + ; pthread_mutex_unlock ( & nready. mutex) ; if ( dosignal) pthread_cond_signal ( & nready. cond) ; * ( ( int * ) arg ) + = 1; } } void * consume( void * arg ) { for ( int i= 0; i< nitems; + + i) { pthread_mutex_lock ( & nready. mutex) ; while ( nready. nready = = 0) pthread_cond_wait ( & nready. cond, & nready. mutex) ; nready. nready- - ; pthread_mutex_unlock ( & nready. mutex) ; if ( buff[ i] ! = i) printf ( "buff[%d] = %d\n" , i, buff[ i] ) ; } } int main( ) { int nthreads = MAXNTHREADS; int count [ MAXNTHREADS] ; pthread_t tid_produce[ MAXNTHREADS] ; pthread_t tid_consume; for ( int i= 0; i< nthreads; + + i) { count [ i] = 0; pthread_create ( & tid_produce[ i] , NULL , produce, & count [ i] ) ; } pthread_create ( & tid_consume, NULL , consume, NULL ) ; for ( int i= 0; i< nthreads; + + i) { pthread_join ( tid_produce[ i] , NULL ) ; printf ( "count[%d] = %d\n" , i, count [ i] ) ; } printf ( "produce success\n" ) ; pthread_join ( tid_consume, NULL ) ; printf ( "consume success\n" ) ; return 0; }
//2010-01-21 yaojianming 摘自unix网络编程2卷
//多个读者和多个写者的进程间通讯,采用读写锁 # include < stdio. h> # include < unistd. h> # include < pthread. h> # include < stdio. h> # include < unistd. h> # include < pthread. h> # define READERS 100 # define WRITERS 10 struct val { pthread_rwlock_t rwlock; int nval; } put = { PTHREAD_RWLOCK_INITIALIZER, 0 } ; void * thread_read( void * arg ) { int n = ( * ( int * ) arg ) ; pthread_rwlock_rdlock ( & put. rwlock) ; printf ( "%d:---%d\n" , n, put. nval) ; pthread_rwlock_unlock ( & put. rwlock) ; } void * thread_write( void * arg ) { int n = ( * ( int * ) arg ) ; pthread_rwlock_wrlock ( & put. rwlock) ; put. nval+ + ; pthread_rwlock_unlock ( & put. rwlock) ; } int main( ) { int count_read[ READERS] ; int count_write[ WRITERS] ; pthread_t tid_read[ READERS] ; pthread_t tid_write[ WRITERS] ; for ( int i= 0; i< READERS; + + i) { count_read[ i] = i; pthread_create ( & tid_read[ i] , NULL , thread_read, & count_read[ i] ) ; } for ( int i= 0; i< WRITERS; + + i) { count_write[ i] = i; pthread_create ( & tid_write[ i] , NULL , thread_write, & count_write[ i] ) ; } for ( int i= 0; i< READERS; + + i) { pthread_join ( tid_read[ i] , NULL ) ; } for ( int i= 0; i< WRITERS; + + i) { pthread_join ( tid_write[ i] , NULL ) ; } return 0; }
//2010-01-26 yaojianming 摘自unix网络编程2卷
//单生产者,单消费者的posix信号灯的实现 # include < stdio. h> # include < pthread. h> # include < semaphore. h> # define NBUFF 10 # define NITEMS 100 struct val { int buff[ NBUFF] ; sem_t mutex, nempty, nstored; } shared; int nitems = NITEMS; void * produce( void * arg ) { for ( int i= 0; i< nitems; + + i) { sem_wait( & shared. nempty) ; sem_wait( & shared. mutex) ; printf ( "producen\n" ) ; shared. buff[ i% NBUFF] = i; sem_post( & shared. mutex) ; sem_post( & shared. nstored) ; } } void * consume( void * arg ) { for ( int i= 0; i< nitems; + + i) { sem_wait( & shared. nstored) ; sem_wait( & shared. mutex) ; printf ( "consume\n" ) ; if ( shared. buff[ i% NBUFF] ! = i) { printf ( "buff[%d] = %d\n" , i, shared. buff[ i% NBUFF] ) ; } sem_post( & shared. mutex) ; sem_post( & shared. nempty) ; } } int main( ) { pthread_t tid_produce; pthread_t tid_consume; sem_init( & shared. mutex, 0, 1) ; sem_init( & shared. nempty, 0, NBUFF) ; sem_init( & shared. nstored, 0, 0) ; pthread_create ( & tid_produce, NULL , produce, NULL ) ; pthread_create ( & tid_consume, NULL , consume, NULL ) ; pthread_join ( tid_produce, NULL ) ; pthread_join ( tid_produce, NULL ) ; sem_destroy( & shared. mutex) ; sem_destroy( & shared. nempty) ; sem_destroy( & shared. nstored) ; return 0; }
//2010-01-26 yaojianming 摘自unix网络编程2卷
//多生产者,单消费者的posix信号灯的实现 # include < stdio. h> # include < pthread. h> # include < semaphore. h> # define NBUFF 10 # define NITEMS 10000 # define MAXTHREADS 5 struct val { int buff[ NBUFF] ; sem_t mutex, nempty, nstored; int nput; int nval; } shared; int nitems = NITEMS; void * produce( void * arg ) { while ( 1) { sem_wait( & shared. nempty) ; sem_wait( & shared. mutex) ; if ( shared. nput > = nitems) { sem_post( & shared. mutex) ; sem_post( & shared. nempty) ; return NULL ; } shared. buff[ shared. nput % NBUFF] = shared. nval; + + shared. nput; + + shared. nval; sem_post( & shared. mutex) ; sem_post( & shared. nstored) ; * ( ( int * ) arg ) + = 1; } } void * consume( void * arg ) { for ( int i= 0; i< nitems; + + i) { sem_wait( & shared. nstored) ; sem_wait( & shared. mutex) ; if ( shared. buff[ i% NBUFF] ! = i) printf ( "buff[%d] = %d\n" , i, shared. buff[ i% NBUFF] ) ; sem_post( & shared. mutex) ; sem_post( & shared. nempty) ; } } int main( ) { int count [ MAXTHREADS] ; pthread_t tid_produce[ MAXTHREADS] ; pthread_t tid_consume; sem_init( & shared. mutex, 0, 1) ; sem_init( & shared. nempty, 0, NBUFF) ; sem_init( & shared. nstored, 0, 0) ; for ( int i= 0; i< MAXTHREADS; + + i) { count [ i] = 0; pthread_create ( & tid_produce[ i] , NULL , produce, & count [ i] ) ; } pthread_create ( & tid_consume, NULL , consume, NULL ) ; for ( int i= 0; i< MAXTHREADS; + + i) { pthread_join ( tid_produce[ i] , NULL ) ; printf ( "produce[%d] = %d\n" , i, count [ i] ) ; } pthread_join ( tid_consume, NULL ) ; sem_destroy( & shared. mutex) ; sem_destroy( & shared. nempty) ; sem_destroy( & shared. nstored) ; return 0; }
//2010-01-26 yaojianming 摘自unix网络编程2卷
//多生产者,多消费者的posix信号灯的实现 # include < stdio. h> # include < semaphore. h> # include < pthread. h> # define NBUFF 10 int nitems = 10000; int nproduce = 15; int nconsume = 15; struct val { int buff[ NBUFF] ; int nput; int nputval; int nget; int ngetval; sem_t mutex, nempty, nstored; } shared; void * produce( void * arg ) { while ( 1) { sem_wait( & shared. nempty) ; sem_wait( & shared. mutex) ; if ( shared. nput > = nitems) { sem_post( & shared. nstored) ; sem_post( & shared. mutex) ; sem_post( & shared. nempty) ; return NULL ; } shared. buff[ shared. nput % NBUFF] = shared. nputval; shared. nput+ + ; shared. nputval+ + ; sem_post( & shared. mutex) ; sem_post( & shared. nstored) ; * ( ( int * ) arg ) + = 1; } } void * consume( void * arg ) { while ( 1) { sem_wait( & shared. nstored) ; sem_wait( & shared. mutex) ; if ( shared. nget > = nitems) { sem_post( & shared. mutex) ; sem_post( & shared. nstored) ; return NULL ; } int i = shared. nget % NBUFF; if ( shared. buff[ i] ! = shared. ngetval) printf ( "error buff[%d] = %d\n" , i, shared. buff[ i] ) ; shared. nget+ + ; shared. ngetval+ + ; sem_post( & shared. mutex) ; sem_post( & shared. nempty) ; * ( ( int * ) arg ) + = 1; } } int main( ) { int prodcount[ 30] , conscount[ 30] ; pthread_t tid_produce[ 30] , tid_consume[ 30] ; sem_init( & shared. mutex, 0, 1) ; sem_init( & shared. nempty, 0, NBUFF) ; sem_init( & shared. nstored, 0, 0) ; for ( int i= 0; i< nproduce; + + i) { prodcount[ i] = 0; pthread_create ( & tid_produce[ i] , NULL , produce, & prodcount[ i] ) ; } for ( int i= 0; i< nconsume; + + i) { conscount[ i] = 0; pthread_create ( & tid_consume[ i] , NULL , consume, & conscount[ i] ) ; } for ( int i= 0; i< nproduce; + + i) { pthread_join ( tid_produce[ i] , NULL ) ; printf ( "producer count[%d] = %d\n" , i, prodcount[ i] ) ; } for ( int i= 0; i< nconsume; + + i) { pthread_join ( tid_consume[ i] , NULL ) ; printf ( "consume count[%d] = %d\n" , i, conscount[ i] ) ; } sem_destroy( & shared. mutex) ; sem_destroy( & shared. nempty) ; sem_destroy( & shared. nstored) ; return 0; }
//http://blog.csdn.net/KataDoc360/archive/2008/11/21/3348023.aspx //进程间共享内存和信号灯同时使用 //share.h # define sem_key 2010 # define shm_key 2011 # define SEM_PERM 0600 # define SHM_PERM 0600 struct content { int nput; int nval; } ; //client.cpp # include < stdio. h> # include < stdlib. h> # include < sys/ types. h> # include < sys/ ipc. h> # include < sys/ sem. h> # include < sys/ shm. h> # include "share.h" void lock_sem( ) { struct sembuf ops[ 2] ; ops[ 0] . sem_num = 0; ops[ 0] . sem_op = 0; ops[ 0] . sem_flg = 0; ops[ 1] . sem_num = 0; ops[ 1] . sem_op = 1; ops[ 1] . sem_flg = SEM_UNDO; int nsemid = semget( sem_key, 1, SEM_PERM| IPC_CREAT) ; if ( nsemid < 0) { perror ( "semget" ) ; } int nret = semop( nsemid, & ops[ 0] , 2) ; if ( nret < 0) { perror ( "semop" ) ; } } void unlock_sem( ) { struct sembuf ops[ 1] ; ops[ 0] . sem_num = 0; ops[ 0] . sem_op = - 1; ops[ 0] . sem_flg = SEM_UNDO| IPC_NOWAIT; int nsemid = semget( sem_key, 1, SEM_PERM| IPC_CREAT) ; if ( nsemid < 0) { perror ( "semget" ) ; } int nret = semop( nsemid, & ops[ 0] , 1) ; if ( nret < 0) { perror ( "semop" ) ; } } int main( ) { int nshmid = shmget( shm_key, sizeof ( content) , SHM_PERM| IPC_CREAT) ; if ( nshmid < 0) { perror ( "shmget" ) ; } struct content* p = ( content* ) shmat( nshmid, NULL , 0) ; lock_sem( ) ; p- > nput+ + ; p- > nval+ + ; unlock_sem( ) ; return 0; } //server.cpp # include < stdio. h> # include < stdlib. h> # include < sys/ types. h> # include < sys/ ipc. h> # include < sys/ sem. h> # include < sys/ shm. h> # include "share.h" void lock_sem( ) { struct sembuf ops[ 2] ; ops[ 0] . sem_num = 0; ops[ 0] . sem_op = 0; ops[ 0] . sem_flg = 0; ops[ 1] . sem_num = 0; ops[ 1] . sem_op = 1; ops[ 1] . sem_flg = SEM_UNDO; int nsemid = semget( sem_key, 1, SEM_PERM| IPC_CREAT) ; if ( nsemid < 0) { perror ( "semget" ) ; } int nret = semop( nsemid, & ops[ 0] , 2) ; if ( nret < 0) { perror ( "semop" ) ; } } void unlock_sem( ) { struct sembuf ops[ 1] ; ops[ 0] . sem_num = 0; ops[ 0] . sem_op = - 1; ops[ 0] . sem_flg = SEM_UNDO| IPC_NOWAIT; int nsemid = semget( sem_key, 1, SEM_PERM| IPC_CREAT) ; if ( nsemid < 0) { perror ( "semget" ) ; } int nret = semop( nsemid, & ops[ 0] , 1) ; if ( nret < 0) { perror ( "semop" ) ; } } void delete_sem( ) { int nsemid = semget( sem_key, 1, SEM_PERM| IPC_CREAT) ; if ( nsemid < 0) { perror ( "semget" ) ; } semctl( nsemid, 0, IPC_RMID) ; } int main( ) { int nshmid = shmget( shm_key, sizeof ( content) , SHM_PERM| IPC_CREAT) ; if ( nshmid < 0) { perror ( "shmget" ) ; } struct content * p = ( content* ) shmat( nshmid, NULL , 0) ; lock_sem( ) ; printf ( "nput:%d = %d\n" , p- > nput, p- > nval) ; unlock_sem( ) ; shmctl( nshmid, IPC_RMID, 0) ; delete_sem( ) ; return 0; }
from:http://blog.chinaunix.net/uid-14348211-id-2821145.html