首页 > 系统相关 >随想录(linux下的pv操作)

随想录(linux下的pv操作)

时间:2022-11-23 11:33:55浏览次数:45  
标签:pv struct int 随想录 MSG linux msg sem NULL


      关于pv操作部分的内容,其实算不上什么新的东西。但是它对于我们理解信号量、消息处理部分的工作还是有很大帮助的。之前我们给出了一个win32的处理方案,但是实现的比较草率。所以我们今天可以利用linux上的信号量函数把这个功能重新实现一遍。


    (1)linux下面信号量的基本函数

    a)创建信号量  sem_init

    b)等待信号量 sem_wait

    c)释放信号量 sem_pos

    d)删除信号量 sem_destroy


    (2)编写pv操作函数

    之前在编写pv操作的时候,没有考虑到消息处理的时序问题,所以在某些极端的情况下可能会造成一些问题。所以本次pv操作采用了循环队列的形式,保持了消息的先后入队顺序。这样对于线程收到的各种消息就可以依次进行处理解决了。同样,我们文件编译的方法非常简单,shell下输入gcc sem.c -g -o sem -lpthread即可。


    可能有同学会问,单独的循环队列和pv操作处理上有什么差别?其实差别很简单,pv可以是不同线程向一个线程发送消息,而循环队列只能接受一个线程发送的消息,否则处理上就麻烦了。


#include <stdio.h>
#include <malloc.h>
#include <string.h>
#include <pthread.h>
#include <semaphore.h>

struct MSG
{
sem_t s_empty;
sem_t s_full;
sem_t s_msg;
int* p_buffer;
int start;
int end;
int count;
};


#define STATUS int
#define TRUE 1
#define FALSE 0
static struct MSG* p_msg = NULL;


struct MSG* alloc_msg(int count)
{
struct MSG* p_msg;
p_msg = (struct MSG*) malloc(sizeof(struct MSG));
if(NULL == p_msg)
{
goto error1;
}
memset(p_msg, 0, sizeof(struct MSG));
p_msg->count = count;

p_msg->p_buffer = (int*)malloc(sizeof(int)* count);
if(NULL == p_msg->p_buffer)
{
goto error2;
}

sem_init(&p_msg->s_empty, 0, count);
sem_init(&p_msg->s_full, 0, 0);
sem_init(&p_msg->s_msg, 0, 1);

return p_msg;

error2:
free(p_msg);

error1:
return;
}


void del_msg(struct MSG* p_msg)
{
if(p_msg)
{
if(p_msg->p_buffer)
{
free(p_msg->p_buffer);
}

sem_destroy(&p_msg->s_msg);
sem_destroy(&p_msg->s_full);
sem_destroy(&p_msg->s_empty);
free(p_msg);
}
}


STATUS put_msg(struct MSG* p_msg, int data)
{
if(NULL == p_msg )
{
return FALSE;
}

sem_wait(&p_msg->s_empty);
sem_wait(&p_msg->s_msg);
p_msg->p_buffer[p_msg->start] = data;
p_msg->start = (p_msg->start + 1) % p_msg->count;
sem_post(&p_msg->s_msg);
sem_post(&p_msg->s_full);

return TRUE;
}


STATUS get_msg(struct MSG* p_msg, int* p_buf)
{
if(NULL == p_msg || NULL == p_buf)
{
return FALSE;
}

sem_wait(&p_msg->s_full);
sem_wait(&p_msg->s_msg);
p_buf[0] = p_msg->p_buffer[p_msg->end];
p_msg->end = (p_msg->end + 1)% p_msg->count;
sem_post(&p_msg->s_msg);
sem_post(&p_msg->s_empty);

return TRUE;
}


void* set_func(void* args)
{
int index = 100;

while(1)
{
put_msg(p_msg, index);
printf("set %d\n", index);
index ++; sleep(1);
}

return NULL;
}


void* get_func(void* args)
{
int data;

while(1)
{
get_msg(p_msg, &data);
printf("get %d\n", data);
sleep(1);
}

return NULL;
}


int main(int argc, char* argv[])
{
pthread_t pid1, pid2;
int index;

p_msg = alloc_msg(10);
if(NULL == p_msg)
{
goto end;
}

if(pthread_create(&pid1, NULL, set_func, NULL))
{
goto end;
}

if(pthread_create(&pid2, NULL, get_func, NULL))
{
goto end;
}

while(1)
{
sleep(0);
}

end:
return 1;
}





标签:pv,struct,int,随想录,MSG,linux,msg,sem,NULL
From: https://blog.51cto.com/feixiaoxing/5880710

相关文章

  • 随想录(写给那些学校不是985、211的同学们)
       每年的6、7月份都是一年一度的毕业季。按照某些新闻机构的统计数字来说,现在每一年毕业的人数达到了600万之多。然而随着社会经济的放缓、贫富差距的拉开,找工作变得越......
  • 随想录(用memmove函数代替strncpy函数)
        有过C语言编程的朋友应该都有过指针越界的困扰。不管越界的地方是全局地址、还是局部地址,查起来都是非常麻烦,原因大多时候都来自于自己对char数组类型的误用。很多......
  • 随想录(编写简单资源管理代码)
      不管编写什么软件,我们都会涉及到模块的编写。说是模块,其实就是管理一片资源,这些资源的概念很广,可以是内存、锁、socket、字符串、文件、空间大小等等。所以不管是什么......
  • 随想录(设计软件模块的接口)
       开发软件是一件复杂而且辛苦的工作,不同的模块之间的逻辑需要考虑,应用层与底层的关系也需要考虑。模块之间的关系处理不好,就会给软件的编写质量带来影响。当然不管软......
  • MongoDB开机自启动(Linux环境)
    MongoDB开机自启动(Linux环境)MongoDB每次关机重启后,都要重新手动启动,这样很麻烦,那能否让计算机开机后自动启动MongoDB呢?答案:可以的一、MongoDB开机自启服务在/lib/sy......
  • 随想录(矩阵计算的几种方法)
    【声明:版权所有,欢迎转载,请勿用于商业用途。】   要进行图像处理,矩阵运算是少不了的。不管是加减乘除,还是旋转、求逆、矩阵分解,都需要lib来好好支持。下面,主要就说一......
  • 随想录(机器学习的生产应用)
    【声明:版权所有,欢迎转载,请勿用于商业用途。     从范围上讲,人工智能>机器学习>模式识别。最近机器学习愈演愈烈,特别是深度学习的发展,极大的推动了机器学习的应......
  • 随想录(嵌入式工程师的出路)
    【声明:版权所有,欢迎转载,请勿用于商业用途。  嵌入式工程师分布在各行各业上面。这其中包括了消费电子、工业电子、汽车电子和军用电子等等。从功能上面看,嵌入式本身包......
  • 随想录(对比着c学java)
    【声明:版权所有,欢迎转载,请勿用于商业用途。  对于java,有两种论调。一种是鄙视,认为java是个人都能学,完全体现不出程序员的水平。还有一种,就是拔高java,认为java无所不能,j......
  • 随想录(被高估的busybox)
    【声明:版权所有,欢迎转载,请勿用于商业用途。  传统的嵌入式系统都是uboot+kernel+rootfs。其中最简单的rootfs就是ramfs+busybox+/dev+/etc+/lib。至于etc目录中的initt......