I. Purpose of the experiment
Implement a C program that simulates solving a limited buffering problem where consumers and producers generate and consume random numbers
Two. Experimental content
- Buffer
The metadata type is Buffer_item, an array of size 1000, processed by the ring queue
- Producer and Consumer Threads
Producers continue to perform the following two operations: consume a random number and produce two random numbers
Consumers continue to perform the following two operations: producing a random number, consuming two random numbers
3.Pthead Thread Creation
Use Pthread_create to create 5 producer threads, 5 consumer threads, and the main program waits for all threads to exit
Three. Experimental environment
Ubuntu Gnome 14.04
MinGW 4.8.1
Codeblocks 13.12
Four. Experimental results
The basic use of semaphore to achieve the topic requirements, which
The Psem is used to indicate whether it can be produced (whether the quantity exceeds the buffer size), the initial amount is 1000, each time it consumes +1,
The CSEM is used to indicate whether it is consumable, the initial quantity is 0, each production is +1,
SEM is used to indicate whether a buffer can be modified
However, the following conditions can occur, causing the program to deadlock:
For example: 5 consumers produce 5 random numbers and then consume these 5 random numbers, then the producer cannot consume the random number first to reproduce
Five. Appendix
Commissioning Experience:
1. The limited buffering problem may indeed deadlock
2. Pthread_create (Tid,attr,func_name,arg) The last parameter represents a parameter that is uniquely passed to the thread
3. void *func_name (void *arg) return requires Pthread_exit (), which functions to terminate the thread that invokes it and return a pointer to an object, but calling exit (0) directly causes the entire process to exit. If the main thread calls Pthread_exit, then it exits, and the child thread does not exit. If it is return 0 it will exit directly.
4. Use the function Pthread_exit to exit the thread, which is the thread's active behavior; because multiple threads in a process are shared data segments, the resources consumed by the exit thread are usually freed after the thread exits, but can be used with pthread_join () function to synchronize and release resources. In Linux, by default, after a thread is created, you must use this function to recycle the created thread, but you can set threads attributes to set the system resources that are consumed by this thread when a thread ends.
5. The thread function needs to be connected to the library function at compile time,-lpthread
#include <stdio.h>#include<pthread.h>#include<semaphore.h>#include<cstdlib>#include<cstring>using namespaceStd;typedefintitem;Const intBsize = +;Const intPnum =5;Const intCnum =Ten;Const intLooptimes =10000; sem_t Sem,psem,csem;structque{item a[bsize]; intHead,tail,n; Que () {memset (a),0,sizeof(a)); Head=tail=n=0; }}q;voidPChar* STR,intnum) { while(num--) {sem_wait (&Psem); Sem_wait (&SEM); Q.a[q.head]=rand ()%Ten; Q.N++; printf ("%s:produce a[%d]:%d, now there are%d numbers in queue\n", STR,Q.HEAD,Q.A[Q.HEAD],Q.N); Q.head= (q.head+1)%bsize; Sem_post (&Csem); Sem_post (&SEM); }}voidCChar*STR,intnum) { while(num--) {sem_wait (&Csem); Sem_wait (&SEM); Q.N--; printf ("%s:consume a[%d]:%d, now there are%d numbers in queue\n", STR,Q.TAIL,Q.A[Q.TAIL],Q.N); Q.tail= (q.tail+1)%bsize; Sem_post (&Psem); Sem_post (&SEM); }}void* Producer (void*Arg) { for(intI=0; i<looptimes;i++) {C (Char*) ARG,1); P ((Char*) ARG,2); } pthread_exit (0);}void* Consumer (void*Arg) { for(intI=0; i<looptimes;i++) {p (Char*) ARG,1); C ((Char*) ARG,2); } pthread_exit (0);}intMain () {Sem_init (&sem,0,1); Sem_init (&psem,0, +); Sem_init (&csem,0,0); Charpname[5][3]={"P1","P2","P3","P4","P5"}; Charcname[5][3]={"C1","C2","C3","C4","c5"}; pthread_t ptid[5],ctid[5]; pthread_attr_t pattr[5],cattr[5]; for(intI=0;i<5; i++) {pthread_attr_init (pattr+i); Pthread_create (Ptid+i,pattr+I,producer,pname[i]); Pthread_attr_init (cattr+i); Pthread_create (Ctid+i,cattr+I,consumer,cname[i]); } for(intI=0;i<5; i++) {pthread_join (ptid[i],null); Pthread_join (Ctid[i],null); } puts ("End"); return 0;}
Operating System Concepts Project: Producer-Consumer issue thread