OS实验二 线程同步与通信

(简单了解信号量函数(semget、semop、semctl)及其范例:https://blog.csdn.net/guoping16/article/details/6584043

1 实验目的与要求

1、掌握Linux下线程的概念;

2、了解Linux线程同步与通信的主要机制;

3、通过信号灯操作实现线程间的同步与互斥。

2 实验内容

通过Linux多线程与信号灯机制,设计并实现计算机线程与I/O线程共享缓冲区的同步与通信。

程序要求:两个线程,共享公共变量a

线程1负责计算(1到100的累加,每次加一个数)

线程2负责打印(输出累加的中间结果)

#include <stdio.h>
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/sem.h>
#include <pthread.h>

union semun {
    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 */
};

int i=0,sum=0;
int semid;//信号量集合首地址
pthread_t p1,p2;
union semun arg;
void P(int semid, int index);
void V(int semid, int index);
/***对信号量数组index编号的信号量做P操作***/
void P(int semid, int index){
	struct sembuf sem={index,-1,0};
    semop(semid,&sem,1);
}

/***对信号量数组index编号的信号量做V操作***/
void V(int semid, int index){
    struct sembuf sem={index,+1,0};
    semop(semid,&sem,1);
}

/*线程一*/      
void thread_1(void){  
    for(;i<=100;i++){ 
    P(semid,0);   
    printf("This is a pthread_1.\ni=%d\n",i);  
    sum+=i;
    V(semid,1); 
    }
	return;  
}  
      
/*线程二*/  
void thread_2(void){    
    for(;;){
    P(semid,1); 
    printf("This is a pthread_2.\nsum=%d\n",sum); 
    if(i==101)return;
    V(semid,0);
    }
}  


int main(){
	int key ;
    int ret;
	key=ftok("/tmp", 0x66 ) ;
    if(key<0){
        perror("ftok key error") ;
        return -1 ;
    }
    /***创建两个信号量***/
    semid=semget(key,2,IPC_CREAT|0666);
    if(semid==-1){
         perror("create semget error");
         return ;
    }
    /***对0号信号量设置初始值***/
	arg.val=1;
    ret=semctl(semid,0,SETVAL,arg);//信号量semid【0】为1
	arg.val=0;
	ret =semctl(semid,1,SETVAL,arg);//信号量semid【1】为0
    if (ret < 0 ){
        perror("ctl sem error");
        semctl(semid,0,IPC_RMID,arg);
        return -1 ;
    }
    /*创建线程一*/  
    ret=pthread_create(&p1,NULL,(void  *) thread_1,NULL);  
    if(ret!=0)  {  
        printf("Create pthread error!\n");  
        return -1;  
    }  
    /*创建线程二*/  
     ret=pthread_create(&p2,NULL,(void  *) thread_2,NULL);  
    if(ret!=0)  {  
        printf("Create pthread error!\n");  
        return -1;  
    }  
    /*等待线程结束*/  
    pthread_join(p1,NULL);  
    pthread_join(p2,NULL);  
    /***删除信号量***/
    semctl(semid,0,IPC_RMID,arg);
    semctl(semid,1,IPC_RMID,arg);
    return 0;  
}

运行结果:

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值