Chinaunix首页 | 论坛 | 博客
  • 博客访问: 782777
  • 博文数量: 37
  • 博客积分: 575
  • 博客等级: 中士
  • 技术积分: 320
  • 用 户 组: 普通用户
  • 注册时间: 2010-05-12 10:43
个人简介

活到老,学到老!

文章分类

全部博文(37)

文章存档

2019年(4)

2018年(4)

2015年(1)

2014年(14)

2011年(1)

2010年(13)

我的朋友

分类: LINUX

2010-05-13 10:38:18

线程间通信机制
 
应用环境:
    应用程序的线程1模拟端机设备接收UDP的图片数据包,并写入文件;
    线程2读取文件,并再次通过UDP包发出去;
    线程2阻塞,直到线程1收完数据并关闭文件后,唤醒并开始工作;
 
通信机制:
    互斥锁
        以排他方式防止数据结构被并发的修改;
    定义互斥锁:pthread_mutex_t lock;
    互斥锁管理:1.互斥锁属性控制(范围、属性、协议、优先级、强健)
                2.互斥锁基本操作(锁定、解锁、非阻塞锁定)
    使用宏初始化静态分配的互斥锁:不需要调用pthread_mutex_init
        pthread_mutex_t lock = PTHREAD_MUTEX_INITIALIZER;
    锁定及解锁:pthread_mutex_lock()
                pthread_mutex_trylock()
                pthread_mutex_unlock()
    条件变量
        根据保护数据的当前值来调整线程的行为;
        条件变量与互斥锁始终一起使用;
        使用条件变量可以以原子方式阻塞线程,直到某个特定条件为真为止;
        如果条件为假,线程基于条件变量阻塞,并以原子方式释放等待条件变
化的互斥锁;
        如果其他线程更改了条件,会向相关的条件变量发出信号,从而使一个
或多个等待的线程执行如下操作:唤醒、再次评估互斥锁、重新评估条件
    定义条件变量:pthread_cond_t condition;
    条件变量管理:1.条件变量属性控制(初始化、删除、范围)
                  2.条件变量基本操作(阻塞、解阻塞、定时阻塞)
    条件变量初始化及销毁:pthread_cond_init()
                          pthread_cond_destroy()
    取消阻塞:pthread_cond_signal()
              pthread_cond_broadcast()
    等待或定时条件变量:pthread_cond_wait()
                        pthread_cond_timedwait()
应用实例:
    主函数创建2个线程,定义全局结构体,并初始化互斥锁和条件变量;
    线程2 bs_rcv_pic_thread使用条件变量阻塞,线程1 ms_snd_pic_thread在recvfrom处阻塞等待UDP数据包,所以在线程1不能给互斥锁上锁,当接收到数据并写完文件后,向条件变量发出信号,以唤醒等待线程2,bs_rcv_pic_thread开始工作。
 

#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>

pthread_mutex_t main_lock = PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t main_cond;


struct global
{
    pthread_mutex_t lock ; //互斥锁
    pthread_cond_t cond;   //条件变量
}global;


int main()
{
    struct global gbl;
    //pthread_mutex_init(&main_lock,NULL);    //初始化互斥锁
    pthread_cond_init(&main_cond,NULL);    //初始化条件变量

    gbl.lock = main_lock;
    gbl.cond = main_cond;

    pthread_t p0,p1;  //创建2个线程,并传递全局参数
    pthread_create(&p0, NULL, ms_snd_pic_thread, (void *)&gbl);
    pthread_create(&p1, NULL, bs_rcv_pic_thread, (void *)&gbl);

    while(1)
    {
    }
    pthread_join(p0, NULL);
    pthread_join(p1, NULL);
    pthread_mutex_destroy(&main_lock);  //销毁互斥锁
    return 0;
}


void* ms_snd_pic_thread(void *arg)
{
    printf("%s\n",__FUNCTION__);
    struct global *gbl = (struct global *)arg;
    //pthread_mutex_lock(&gbl->lock);
    ……
    recvfrom();    //阻塞等待接收UDP
    ……
    printf("rcv %d finish! \n",count);
    printf("signal cond \n");
    pthread_cond_signal(&gbl->cond);  //向条件变量发出信号
    //pthread_mutex_unlock(&gbl->lock);
}


void* bs_rcv_pic_thread(void *arg)
{
    printf("%s\n",__FUNCTION__);
    struct global *gbl = (struct global *)arg;
    //pthread_mutex_lock(&gbl->lock);

    printf("block wait cond signal! \n");
    pthread_cond_wait(&gbl->cond,&gbl->lock);  //阻塞等待条件变量更改
    printf("unblock \n");
    ……
    //pthread_mutex_unlock(&gbl->lock);
    printf("all %d bytes send\n",count);
    return;
}


阅读(2717) | 评论(0) | 转发(0) |
0

上一篇:没有了

下一篇:网络编程与多线程设计 VC6.0

给主人留下些什么吧!~~