Linux semaphore practice (2) and linux semaphore practice
Semaphores API Comprehensive Practices
// Practice 1: encapsulate the PV primitive union mySemUn {int val; // Value for SETVAL // struct semid_ds * buf; // Buffer for IPC_STAT, IPC_SET // unsigned short * array; // Array for GETALL, SETALL // struct seminfo * _ buf; // Buffer for IPC_INFO (Linux-specific )//}; // encapsulate the V operation int sem_V (int semid) {struct sembuf buf = {0, + 1, 0}; return semop (semid, & buf, 1 );} // encapsulate the P operation int sem_P (int semid) {struct sembuf buf = {0,-}; return semop (semid, & B Uf, 1);} int main () {// create or obtain the semaphore int semid = semget (0x12345670,1, 0666 | IPC_CREAT); if (semid =-1) {err_exit ("semget error");} // set the semaphore value int valueForSetSem = 0; cout <"Please input the value to set sem:"; cin> valueForSetSem; union mySemUn setValue; setValue. val = valueForSetSem; // set the semaphores if (semctl (semid, 0, SETVAL, setValue )! = 0) {err_exit ("semctl SETVAL error");} // enter the critical section sem_P (semid); cout <"Hello Xiaofang! "<Endl; // exit sem_V (semid) in the critical section; return 0 ;}
// Practice 2: Comprehensive Practice of threads and semaphores union mySemUn {int val; // Value for SETVAL // struct semid_ds * buf; // Buffer for IPC_STAT, IPC_SET // unsigned short * array; // Array for GETALL, SETALL // struct seminfo * _ buf; // Buffer for IPC_INFO (Linux-specific )//}; // encapsulate the V operation int sem_V (int semid) {struct sembuf buf = {0, + 1, 0}; return semop (semid, & buf, 1 );} // encapsulate the P operation int sem_P (int semid) {struct sembuf buf = {0,-1, 0}; return semop (semi D, & buf, 1) ;}unsigned long int count = 0; void * threadForAddCount (void * arg) {int semid = * static_cast <int *> (arg ); for (;) {sem_P (semid); ++ count; sem_V (semid);} pthread_exit (NULL);} void * threadForPrintCount (void * arg) {for (;) {cout <"count =" <count <endl; sleep (1) ;}pthread_exit (NULL) ;}int main () {// create or obtain the semaphore int semid = semget (0x12345670,1, 0666 | IPC_CREAT); if (semid =-1) {er R_exit ("semget error");} // set the semaphore value int valueForSetSem = 0; cout <"Please input the value to set sem:"; cin> valueForSetSem; union mySemUn setValue; setValue. val = valueForSetSem; // set the semaphores if (semctl (semid, 0, SETVAL, setValue )! = 0) {err_exit ("semctl SETVAL error");} pthread_t addThread [2]; pthread_t printThread; // create a thread for (int I = 0; I <2; ++ I) {pthread_create (& addThread [I], NULL, threadForAddCount, & semid);} pthread_create (& printThread, NULL, threadForPrintCount, NULL ); // wait for the thread to terminate for (int I = 0; I <2; ++ I) {pthread_join (addThread [I], NULL);} pthread_join (printThread, NULL ); return 0;} void err_exit (std: string str) {perror (str. c_str (); exit (EXIT_FAILURE );}
Appendix-Makefile
CC = g++ CPPFLAGS = -Wall -g -pthreadBIN = mainSOURCES = $(BIN.=.cpp).PHONY: clean all all: $(BIN)$(BIN): $(SOURCES)clean: -rm -rf $(BIN) bin/ obj/ core