[ZLG-ARM] Linux内核相结合之同步实例(三)

[复制链接]
 楼主| lpc2410 发表于 2009-7-3 13:32 | 显示全部楼层 |阅读模式
在操作系统中讲到进程同步的问题的时候,都会讲一些经典的例子,其中最经典的当属“生产者和消费者的问题”。生产者和消费者的规则是生产者生产一个产品后,消费者才能消费,并且在消费者还没有消费已经生产的产品的时候,生产者是不能再进行生产的。牛涛写的这个例子演示了这一过程:<br /><br />#include&ltlinux/init.h&gt<br />#include&ltlinux/module.h&gt<br />#include&ltlinux/sem.h&gt<br />#include&ltlinux/sched.h&gt<br />MODULE_LICENSE('Dual&nbsp;BSD/GPL');<br />struct&nbsp;semaphore&nbsp;sem_producer;/*'生产需求证',在产品没有被消费的时候不能再进行生产*/<br />struct&nbsp;semaphore&nbsp;sem_consumer;/*'消费证',在有产品的时候(可以获得该锁)才可以消费*/<br />char&nbsp;product[10];/*'产品'存放地*/<br />int&nbsp;exit_flags;/*生产线开启标志*/<br />int&nbsp;producer(void&nbsp;*product);/*生产者*/<br />int&nbsp;consumer(void&nbsp;*product);/*消费者*/<br />static&nbsp;int&nbsp;procon_init(void)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;printk(KERN_INFO'show&nbsp;producer&nbsp;and&nbsp;consumer\n');<br />&nbsp;&nbsp;&nbsp;&nbsp;init_MUTEX(&sem_producer);/*购买'生产需求证',并且准许生产*/<br />&nbsp;&nbsp;&nbsp;&nbsp;init_MUTEX_LOCKED(&sem_consumer);/*购买'消费证',但不可消费*/<br />&nbsp;&nbsp;&nbsp;&nbsp;exit_flags=0;/*生产线可以开工*/<br />&nbsp;&nbsp;&nbsp;&nbsp;kernel_thread(producer,product,CLONE_KERNEL);/*启动生产者*/<br />&nbsp;&nbsp;&nbsp;&nbsp;kernel_thread(consumer,product,CLONE_KERNEL);/*启动消费者*/<br />&nbsp;&nbsp;&nbsp;&nbsp;return&nbsp;0;<br />}<br />static&nbsp;void&nbsp;procon_exit(void)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;printk(KERN_INFO'exit&nbsp;producer&nbsp;and&nbsp;consumer\n');<br />}<br />/*<br />*&nbsp;生产者,负责生产十个产品<br />*/<br />int&nbsp;producer(void&nbsp;*p)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;char&nbsp;*product=(char&nbsp;*)p;<br />&nbsp;&nbsp;&nbsp;&nbsp;int&nbsp;i;<br />&nbsp;&nbsp;&nbsp;&nbsp;for(i=0;i&lt10;i++)&nbsp;{&nbsp;/*总共生产十个产品*/<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;/*&nbsp;查看'生产需求证',如果产品已经被消费,<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;则准许生产。否则在此等待直到需要生产<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*/<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;down(&sem_producer);<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;snprintf(product,10,'product-%d',i);/*生产产品*/<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;printk(KERN_INFO'producer&nbsp;produce&nbsp;%s\n',product);/*生产者提示已经生产*/<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;up(&sem_consumer);/*为消费者发放'消费证'*/<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;exit_flags=1;/*生产完毕,关闭生产线*/<br />&nbsp;&nbsp;&nbsp;&nbsp;return&nbsp;0;<br />}<br />/*<br />*&nbsp;消费者,如果有产品,则消费产品<br />*/<br />int&nbsp;consumer(void&nbsp;*p)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;char&nbsp;*product=(char&nbsp;*)p;<br />&nbsp;&nbsp;&nbsp;&nbsp;for(;;)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(exit_flags)&nbsp;/*如果生产工厂已经关闭,则停止消费*/<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;break;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;/*获取'消费证',如果有产品,则可以获取,<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*进行消费。否则等待直到有产品。<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*/<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;down(&sem_consumer);<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;printk(KERN_INFO'consumer&nbsp;consume&nbsp;%s\n',product);/*消费者提示获得了产品*/<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;memset(product,'\&nbsp;0',10);/*消费产品*/<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;up(&sem_producer);/*向生产者提出生产需求*/<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;return&nbsp;0;<br />}<br />module_init(procon_init);<br />module_exit(procon_exit);<br />MODULE_AUTHOR('Niu&nbsp;Tao');<br />MODULE_DESCRIPTION('producer&nbsp;and&nbsp;consumer&nbsp;Module');<br />MODULE_ALIAS('a&nbsp;simplest&nbsp;module');<br /><br />Makefile:<br /><br />obj-m&nbsp;:=procon.o<br />CURRENT_PATH&nbsp;:=&nbsp;$(shell&nbsp;pwd)<br />LINUX_KERNEL&nbsp;:=&nbsp;$(shell&nbsp;uname&nbsp;-r)<br />LINUX_KERNEL_PATH&nbsp;:=&nbsp;/usr/src/linux-headers-$(LINUX_KERNEL)<br />all:<br />&nbsp;&nbsp;&nbsp;&nbsp;make&nbsp;-C&nbsp;$(LINUX_KERNEL_PATH)&nbsp;M=$(CURRENT_PATH)&nbsp;modules&nbsp;<br />clean:<br />&nbsp;&nbsp;&nbsp;&nbsp;rm&nbsp;-rf&nbsp;.*.cmd&nbsp;*.o&nbsp;*.mod.c&nbsp;*.ko&nbsp;.tmp_versions&nbsp;Module.symvers&nbsp;.Makefile.swp<br /><br />运行结果:<br />[&nbsp;5684.818139]&nbsp;show&nbsp;producer&nbsp;and&nbsp;consumer<br />[&nbsp;5684.818352]&nbsp;producer&nbsp;produce&nbsp;product-0<br />[&nbsp;5684.819746]&nbsp;consumer&nbsp;consume&nbsp;product-0<br />[&nbsp;5684.819811]&nbsp;producer&nbsp;produce&nbsp;product-1<br />[&nbsp;5684.820061]&nbsp;consumer&nbsp;consume&nbsp;product-1<br />[&nbsp;5684.820065]&nbsp;producer&nbsp;produce&nbsp;product-2<br />[&nbsp;5684.820267]&nbsp;consumer&nbsp;consume&nbsp;product-2<br />[&nbsp;5684.820271]&nbsp;producer&nbsp;produce&nbsp;product-3<br />[&nbsp;5684.820498]&nbsp;consumer&nbsp;consume&nbsp;product-3<br />[&nbsp;5684.820503]&nbsp;producer&nbsp;produce&nbsp;product-4<br />[&nbsp;5684.820822]&nbsp;consumer&nbsp;consume&nbsp;product-4<br />[&nbsp;5684.820828]&nbsp;producer&nbsp;produce&nbsp;product-5<br />[&nbsp;5684.821062]&nbsp;consumer&nbsp;consume&nbsp;product-5<br />[&nbsp;5684.821067]&nbsp;producer&nbsp;produce&nbsp;product-6<br />[&nbsp;5684.821274]&nbsp;consumer&nbsp;consume&nbsp;product-6<br />[&nbsp;5684.821279]&nbsp;producer&nbsp;produce&nbsp;product-7<br />[&nbsp;5684.821475]&nbsp;consumer&nbsp;consume&nbsp;product-7<br />[&nbsp;5684.821479]&nbsp;producer&nbsp;produce&nbsp;product-8<br />[&nbsp;5684.821681]&nbsp;consumer&nbsp;consume&nbsp;product-8<br />[&nbsp;5684.821685]&nbsp;producer&nbsp;produce&nbsp;product-9<br />[&nbsp;5684.821897]&nbsp;consumer&nbsp;consume&nbsp;product-9<br />[&nbsp;5705.169930]&nbsp;exit&nbsp;producer&nbsp;and&nbsp;consumer<br />
qtopia 发表于 2009-7-4 12:59 | 显示全部楼层

多谢

  
 楼主| lpc2410 发表于 2009-7-6 13:21 | 显示全部楼层

学习了

  
tmake 发表于 2009-7-9 13:31 | 显示全部楼层

路过

  
armqt 发表于 2009-7-24 18:14 | 显示全部楼层

学习

  
您需要登录后才可以回帖 登录 | 注册

本版积分规则

19

主题

124

帖子

0

粉丝
快速回复 在线客服 返回列表 返回顶部

19

主题

124

帖子

0

粉丝
快速回复 在线客服 返回列表 返回顶部