ImageVerifierCode 换一换
格式:DOCX , 页数:12 ,大小:29.79KB ,
资源ID:4355275      下载积分:3 金币
快捷下载
登录下载
邮箱/手机:
温馨提示:
快捷下载时,用户名和密码都是您填写的邮箱或者手机号,方便查询和重复下载(系统自动生成)。 如填写123,账号就是123,密码也是123。
特别说明:
请自助下载,系统不会自动发送文件的哦; 如果您已付费,想二次下载,请登录后访问:我的下载记录
支付方式: 支付宝    微信支付   
验证码:   换一换

加入VIP,免费下载
 

温馨提示:由于个人手机设置不同,如果发现不能下载,请复制以下地址【https://www.bdocx.com/down/4355275.html】到电脑端继续下载(重复下载不扣费)。

已注册用户请登录:
账号:
密码:
验证码:   换一换
  忘记密码?
三方登录: 微信登录   QQ登录  

下载须知

1: 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。
2: 试题试卷类文档,如果标题没有明确说明有答案则都视为没有答案,请知晓。
3: 文件的所有权益归上传用户所有。
4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
5. 本站仅提供交流平台,并不能对任何下载内容负责。
6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

版权提示 | 免责声明

本文(线程实现邮箱通信实验报告.docx)为本站会员(b****5)主动上传,冰豆网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。 若此文所含内容侵犯了您的版权或隐私,请立即通知冰豆网(发送邮件至service@bdocx.com或直接QQ联系客服),我们立即给予删除!

线程实现邮箱通信实验报告.docx

1、线程实现邮箱通信实验报告进程通信实验报告一、实验名称:进程通信二、实验目的:掌握用邮箱方式进行进程通信的方法,并通过设计实现简单邮箱理解进程通信中的同步问题以及解决该问题的方法。三、实验原理:邮箱机制类似于日常使用的信箱。对于用户而言使用起来比较方便,用户只需使用send()向对方邮箱发邮件 receive()从自己邮箱取邮件, send()和 receive()的内部操作用户无需关心。因为邮箱在内存中实现,其空间有大小限制。其实send()和 receive()的内部实现主要还是要解决生产者与消费者问题。四、实验内容:进程通信的邮箱方式由操作系统提供形如send()和receive()的系统

2、调用来支持,本实验要求学生首先查找资料了解所选用操作系统平台上用于进程通信的系统调用具体形式,然后使用该系统调用编写程序进行进程间的通信,要求程序运行结果可以直观地体现在界面上。在此基础上查找所选用操作系统平台上支持信号量机制的系统调用具体形式,运用生产者与消费者模型设计实现一个简单的信箱,该信箱需要有创建、发信、收信、撤销等函数,至少能够支持两个进程互相交换信息,比较自己实现的信箱与操作系统本身提供的信箱,分析两者之间存在的异同。五、背景知识介绍:1、sembuf数据结构struct sembuf unsigned short int sem_num; /semaphore number s

3、hort int sem_op; /semaphore operation short int sem_flg; /operation flag ;sem_num:操作信号在信号集中的编号,第一个信号的编号是0。sem_op:如果其值为正数,该值会加到现有的信号内含值中。通常用于释放所控资源的使用权;如果sem_op的值为负数,而其绝对值又大于信号的现 值,操作将会阻塞,直到信号值大于或等于sem_op的绝对值。通常用于获取资源的使用权;如果sem_op的值为0,则操作将暂时阻塞,直到信号的值变 为0。sem_flg:信号操作标志,可能的选择有两种IPC_NOWAIT /对信号的操作不能满足时

4、,semop()不会阻塞,并立即返回,同时设定错误信息。IPC_UNDO /程序结束时(不论正常或不正常),保证信号值会被重设为semop()调用前的值。这样做的目的在于避免程序在异常情况下结束时未将锁定的资源解锁,造成该资源永远锁定。2、 semop函数函数原型:int semop(int semid, struct sembuf *sops, unsigned nsops);参数说明:semid:信号集的识别码,可通过semget获取。sops:指向存储信号操作结构的数组指针。nsops:信号操作结构的数量,恒大于或等于1。返回说明:成功执行时,两个系统调用都返回0。失败返回-1,错误信息

5、保存在errno中。3、semget函数函数原型:int semget(key_t key,int nsems,int semflg);参数说明:key:关键字值一般是由系统调用ftok()返回的nsems:指出了一个新的信号量集中应该创建的信号量的个数semflg:打开和存取操作与参数semflg中的内容相关。返回说明:如果成功,则返回信号量集的IPC标识符。如果失败,返回-1,错误信息保存在errno中。4、semctl函数函数原型:int semctl(int semid,int semnum,int cmd,union semun arg);参数说明:senid:关键字值semnum:

6、信号量数目cmd:要操作的具体命令arg:semnu的一个联合类型的副本。返回说明:返回值:如果成功,则为一个正数。如果失败,则为-1。错误信息保存在errno中。5、pthread_create函数函数原型:int pthread_create(pthread_t *restrict tidp,const pthread_attr_t *restrict attr,void*(*start_rtn)(void*),void *restrict arg);参数说明:tidp:指向线程标识符的指针。attr:用来设置线程属性。第三个参数是线程运行函数的起始地址。arg:运行函数的参数。六、设计方

7、案:1、定义两个数组当作两个邮箱int a_buf5,b_buf5;邮箱的容量为5。2、定义两个指针指向邮箱的顶部int a_buf_top=0,b_buf_top=0;初始时邮箱都为空3、定义semaphore_P和semaphore_V两个函数实现P.V原语操作,用P.V原语实现进程的互斥。4、定义发送和接收信息的函数,其中void * A_Send(void *arg)为A发送信息,void * B_Send(void *arg)为B发送信息,void *A_Receive(void *arg)为A接收信息;void *B_Receive(void *arg)为B接收信息。5、调用创建线

8、程函数,让上述四个函数并行运行。七、预计的实验结果:A_Receive()和 B_Receive()分别接收B_Send()和 A_Send()发出的信息,发送的信息和接受的信息应该一样。八、关键代码的分析:/* * P原语操作 * */int semaphore_P(int sem_id) struct sembuf p; p.sem_num=0; p.sem_op=-1; p.sem_flg=SEM_UNDO; if(semop(sem_id,&p,1)=-1) printf(errno); return 0; return 1;/* * V原语操作 * */int semaphore_V

9、(int sem_id) struct sembuf v; v.sem_num=0; v.sem_op=1; v.sem_flg=SEM_UNDO; if(semop(sem_id,&v,1)=-1) printf(errno); return 0; return 1;/* * A向B发送信息 * */void * A_Send(void *arg) int i; for(i=0;i10;i+) semaphore_P(sem_idAs); /P操作 semaphore_P(a_mutex_semaphore); /互斥 int number=rand(); /随机数为发送的邮件 printf

10、(A send to B:%dn,number); b_bufb_buf_top=number;/邮箱B中接收A发送的邮件 b_buf_top+=1;/A向B发送邮件,B的邮件数量加一 semaphore_V(a_mutex_semaphore); /互斥 semaphore_V(sem_idBr);/V操作 sleep(1); 九、调试记录:于pthread库不是Linux系统默认的库,连接时需要使用库libpthread.a, 所以在使用pthread_create创建线程时,在编译中要加-lpthread参数 gcc -w -lpthread semaphore.c十、实际的实验结果:a

11、daada-desktop:/OS$ gcc -w -o semaphore -lpthread semaphore.c adaada-desktop:/OS$ ./semaphore B send to A:1804289383A receive from B:1804289383A send to B:846930886B receive from A: 846930886B send to A:1681692777A receive from B:1681692777A send to B:1714636915B receive from A: 1714636915B send to A

12、:1957747793A receive from B:1957747793A send to B:424238335B receive from A: 424238335B send to A:719885386A receive from B:719885386A send to B:1649760492B receive from A: 1649760492B send to A:596516649A receive from B:596516649A send to B:1189641421B receive from A: 1189641421B send to A:10252023

13、62A receive from B:1025202362A send to B:1350490027B receive from A: 1350490027B send to A:783368690A receive from B:783368690A send to B:1102520059B receive from A: 1102520059B send to A:2044897763A receive from B:2044897763A send to B:1967513926B receive from A: 1967513926B send to A:1365180540A r

14、eceive from B:1365180540A send to B:1540383426B receive from A: 1540383426B send to A:304089172A receive from B:304089172A send to B:1303455736B receive from A: 1303455736adaada-desktop:/OS$ 十一、实验结果分析:四个线程并发运行, A_Send()和 B_Send()发出信息,同时打印出发出的信息内容; A_Receive()和 B_Receive()分别接收B_Send()和 A_Send()发出的信息,

15、并打印出接受的信息内容。发出的内容和接收的内容一样,符合时间情况。十二、附代码#include#include#include#include#include#include#include#include#includeint a_buf5,b_buf5; /邮箱的容量为5int a_buf_top=0,b_buf_top=0;/假设初始时邮箱都为空int sem_idAs,sem_idBs; /例如sem_idAs代表A此时最多可以向B发送的邮件数int sem_idAr,sem_idBr; /例如sem_idAr代表A此时邮箱中受到的邮件数int a_mutex_semaphore,b_

16、mutex_semaphore; /互斥信号量/* * P原语操作 * */int semaphore_P(int sem_id) struct sembuf p; p.sem_num=0; p.sem_op=-1; p.sem_flg=SEM_UNDO; if(semop(sem_id,&p,1)=-1) printf(errno); return 0; return 1;/* * V原语操作 * */int semaphore_V(int sem_id) struct sembuf v; v.sem_num=0; v.sem_op=1; v.sem_flg=SEM_UNDO; if(sem

17、op(sem_id,&v,1)=-1) printf(errno); return 0; return 1;/* * A向B发送信息 * */void * A_Send(void *arg) int i; for(i=0;i10;i+) semaphore_P(sem_idAs); /P操作 semaphore_P(a_mutex_semaphore); /互斥 int number=rand(); /随机数为发送的邮件 printf(A send to B:%dn,number);b_buf*b_top = num+;/邮箱B中接收A发送的邮件, (*b_top)+=1;/A向B发送邮件,B

18、的邮件数量加一 semaphore_V(a_mutex_semaphore); /互斥 semaphore_V(sem_idBr);/V操作 sleep(1); /* * A接收B的信息 * */void *A_Receive(void *arg) int i; for( i=0;i10;i+ ) semaphore_P(sem_idAr);/P操作 semaphore_P(b_mutex_semaphore);/互斥 a_buf_top-=1;/A接收B发送邮件,A的邮件数量减一 printf(A receive from B:%dn,a_bufa_buf_top); semaphore_V

19、(b_mutex_semaphore); /互斥 semaphore_V(sem_idBs);/V操作 sleep(1); /* * B向A发送信息 * */void *B_Send(void *arg) int i; for(i=0;i10;i+) semaphore_P(sem_idBs); semaphore_P(b_mutex_semaphore); int number=rand(); printf(B send to A:%dn,number); a_bufa_buf_top=number; a_buf_top+=1; semaphore_V(b_mutex_semaphore);

20、 semaphore_V(sem_idAr); sleep(1); /* * B接收A的信息 * */void *B_Receive(void *arg) int i; for( i=0;i10;i+) semaphore_P(sem_idBr); semaphore_P(a_mutex_semaphore); b_buf_top-=1; printf(B receive from A: %dn,b_bufb_buf_top); semaphore_V(a_mutex_semaphore); semaphore_V(sem_idAs); sleep(1); int main()/*创建线程1*

21、/ pthread_t thread1; pthread_t thread2; pthread_t thread3; pthread_t thread4;/*创建信号量*/ if( (sem_idAs=semget( (key_t)1,1,IPC_CREAT|0660) )=-1 ) return 1; if( (sem_idBs=semget( (key_t)2,1,IPC_CREAT|0660) )=-1 ) return 1; if( (sem_idAr=semget( (key_t)3,1,IPC_CREAT|0660) )=-1 ) return 1; if( (sem_idBr=s

22、emget( (key_t)4,1,IPC_CREAT|0660) )=-1 ) return 1; if( (a_mutex_semaphore=semget( (key_t)5,1,IPC_CREAT|0660) )=-1 ) return 1; if( (b_mutex_semaphore=semget( (key_t)6,1,IPC_CREAT|0660) )=-1 ) return 1;/*控制信号队列的运作*/ semctl(sem_idAs,0,SETVAL,0); semctl(sem_idBs,0,SETVAL,0); semctl(sem_idAr,0,SETVAL,0);

23、 semctl(sem_idBr,0,SETVAL,0); semctl(a_mutex_semaphore,0,SETVAL,1); semctl(b_mutex_semaphore,0,SETVAL,1);/调用四个线程,让四个函数并行运行 pthread_create(&thread1, NULL, A_Send, NULL); pthread_create(&thread2, NULL, B_Send, NULL); pthread_create(&thread3, NULL, A_Receive, NULL); pthread_create(&thread4, NULL, B_Receive, NULL); sleep(60);/保证主程序退出之前邮箱操作已经完成 return 0;

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1