线程控制

线程创建
  进程被创建时,系统会为其创建一个主线程,而要在进程中创建新的线程,则可以调用pthread_create:

pthread_create(pthread_t *thread, const pthread_attr_t *attr, void *(start_routine)(void*), void *arg);

start_routine为新线程的入口函数,arg为传递给start_routine的参数。
  每个线程都有自己的线程ID,以便在进程内区分。线程ID在pthread_create调用时回返给创建线程的调用者;一个线程也可以在创建后使用pthread_self()调用获取自己的线程ID:

pthread_self (void) ;

线程退出
  线程的退出方式有三:
  (1)执行完成后隐式退出;
  (2)由线程本身显示调用pthread_exit 函数退出;

pthread_exit (void * retval) ;

  (3)被其他线程用pthread_cancel函数终止:

pthread_cancel(pthread_t thread) ;

线程互斥

  互斥意味着“排它”,即两个线程不能同时进入被互斥保护的代码。Linux下可以通过pthread_mutex_t 定义互斥体机制完成多线程的互斥操作,该机制的作用是对某个需要互斥的部分,在进入时先得到互斥体,如果没有得到互斥体,表明互斥部分被其它线程拥有,此时欲获取互斥体的线程阻塞,直到拥有该互斥体的线程完成互斥部分的操作为止。

下面的代码实现了对共享全局变量x 用互斥体mutex 进行保护的目的:
int x; // 进程中的全局变量
pthread_mutex_t mutex;
pthread_mutex_init(&mutex, NULL); //按缺省的属性初始化互斥体变量mutex
pthread_mutex_lock(&mutex); // 给互斥体变量加锁
… //对变量x 的操作
phtread_mutex_unlock(&mutex); // 给互斥体变量解除锁

线程同步

  同步就是线程等待某个事件的发生。只有当等待的事件发生线程才继续执行,否则线程挂起并放弃处理器。当多个线程协作时,相互作用的任务必须在一定的条件下同步。
  Linux下的C语言编程有多种线程同步机制,最典型的是条件变量(condition variable)。pthread_cond_init用来创建一个条件变量,其函数原型为:

pthread_cond_init (pthread_cond_t *cond, const pthread_condattr_t *attr);

pthread_cond_wait和pthread_cond_timedwait用来等待条件变量被设置,值得注意的是这两个等待调用需要一个已经上锁的互斥体mutex,这是为了防止在真正进入等待状态之前别的线程有可能设置该条件变量而产生竞争。pthread_cond_wait的函数原型为:
pthread_cond_wait (pthread_cond_t *cond, pthread_mutex_t *mutex);

pthread_cond_timedwait(pthread_cond_t * cond, pthread_mutex_t *mutex, const struct timespec * abstime)

经历abstime段时间后,即使条件变量不满足,阻塞也被解除。

等待的时间通过abstime参数(绝对系统时间,过了该时刻就超时)指定,超时则返回ETIMEDOUT错误码。

pthread_cond_broadcast用于设置条件变量,即使得事件发生,这样等待该事件的线程将不再阻塞:

pthread_cond_broadcast (pthread_cond_t *cond) ;

pthread_cond_signal函数的作用是发送一个信号给另外一个正在处于阻塞等待状态的线程,使其脱离阻塞状态,继续执行.如果没有线程处在阻塞等待状态,pthread_cond_signal也会成功返回。

但使用pthread_cond_signal不会有“惊群现象”产生,他最多只给一个线程发信号。假如有多个线程正在阻塞等待着这个条件变量的话,那么是根据各等待线程优先级的高低确定哪个线程接收到信号开始继续执行。如果各线程优先级相同,则根据等待时间的长短来确定哪个线程获得信号。但无论如何一个pthread_cond_signal调用最多发信一次。
pthread_cond_signal (pthread_cond_t *cond) ;

pthread_cond_destroy 则用于释放一个条件变量的资源。

用生产者与消费者的关系来看。
例如,有一个生产者,2个消费者。
//定义全局的 互斥对象和条件等待对象
pthread_mutex_t mtx;pthread_cond_t   cond;//消费者线程函数:
void threadproc(void * parm){while(1){pthread_mutex_lock(&mtx);//锁定mtx ,以防其他消费者线程 并发等待pthread_cond_wait(&cond,&mtx);//首先解锁mtx,让其消费者线程或者生产者线程 获得机会去执行。然后休眠,不消耗任何CPU时间,等待被生产者唤醒//...dosomthing
pthread_mutex_unlock(&mtx);//解锁}pthread_exit(0);}//生产者线程
void pdthreadproc(void * parm)
{while(1){pthread_mutex_lock(&mtx);//锁定mtx ,以防其他消费者线程 并发等待//...dosomthing
pthread_cond_broadcast(&cond,&mtx);//唤醒所有消费者线程,再次锁定mtx       pthread_mutex_unlock(&mtx);//解锁      }pthread_exit(0);
}

pthread_cond_wait 未返回之前一直处于睡眠状态,那么当消费者线程被唤醒之后,它首先要去锁定mtx,获得独占权,其他线程干等!执行完毕之后再解锁,其他消费者线程 执行被唤醒之后的过程。

转载于:https://www.cnblogs.com/gildoringlorin/p/3967937.html

Linux多线程通信相关推荐

  1. linux下串口多线程通信 ,多串口收发数据错乱问题解决办法

    最近在写AM335x平台的串口测试工具,最开始的时候写的第一版本,测试一直很ok,但是存在一些缺陷,于是就想改进一下,没想到后面在新的板子测试,竟然发现了以个很致命的问题,在旧系统旧内核测试一切正常, ...

  2. linux 内核信号量与用户态信号量(system v,信号量在Linux多线程机制中的应用

    [摘 要]本文以信号量原理为基础,重点阐述信号量在Linux多线程同步机制中的实现特色. [关键词]信号量:Linux:多线程:同步 1 信号量 1965年E. W. Dijkstra首次提出信号量的 ...

  3. 新书预告:《Linux 多线程服务端编程——使用 muduo C++ 网络库》

    看完了 W. Richard Stevens 的传世经典<UNIX 网络编程>, 能照着例子用 Sockets API 编写 echo 服务, 却仍然对稍微复杂一点的网络编程任务感到无从下 ...

  4. linux多线程编写哲学家,Linux系统编程(三) ------ 多线程编程

    一.线程的创建和调度 1.线程是程序执行的某一条指令流的映像. 为了进一步减少处理机制的空转时间,支持多处理器及减少上下文切换开销,进程在演化中出现了另一个概念--线程.它是进程内独立的一条运行路线, ...

  5. Linux进程通信的四种方式——共享内存、信号量、无名管道、消息队列|实验、代码、分析、总结

    Linux进程通信的四种方式--共享内存.信号量.无名管道.消息队列|实验.代码.分析.总结 每个进程各自有不同的用户地址空间,任何一个进程的全局变量在另一个进程中都看不到,所以进程之间要交换数据必须 ...

  6. ZT 为什么pthread_cond_t要和pthread_mutex_t同时使用 || pthread/Linux多线程编程

    为什么线程同步的时候pthread_cond_t要和pthread_mutex_t同时使用 (2009-10-27 11:07:23) 转载▼ 标签: 杂谈 分类: 计算机 举一个例子(http:// ...

  7. Linux多线程编程之员工信息管理系统

    员工信息管理系统是基于Linux 多线程并发服务器编程,由服务器端和客户端构成,客户端可以运行在多个不同的主机上连接服务器,服务器对员工信息的操作结果通过"员工信息文件"来保存,即 ...

  8. 《Linux多线程服务端编程:使用muduoC++网络库》学习笔记

    文章目录 第1章 线程安全的对象生命期管理 1.1 当析构函数遇到多线程 1.1.1 线程安全的定义 1.1.3 线程安全实例 1.2 对象的创建很简单 1.3 销毁很难 1.4 线程安全的Obser ...

  9. Linux 多线程编程(实现生产者消费者模型)

    Linux 多线程编程 线程分类 线程按照其调度者可以分为用户级线程和内核级线程两种. 内核级线程 在一个系统上实现线程模型的方式有好几种,因内核和用户空间提供的支持而有一定程度的级别差异.最简单的模 ...

  10. c/c++ Linux多线程编程

    Linux多线程编程 线程概念 线程是指运行中的程序的调度单位.一个线程指的是进程中一个单一顺序的控制流,也被称为轻量级线程.它是系统独立调度和分配的基本单位.同一进程中的多个线程将共享该系统中的全部 ...

最新文章

  1. 微软MCITP系列课程(二七)管理域和林信任
  2. 好程序员web前端教程分享JavaScript验证API
  3. Revit API导出GBXML
  4. ASP.NET 2.0 之 Master Page 学习笔记 --zt
  5. 记录一个解决了一个下午加一个晚上的问题,关于springMVC上传文件的功能
  6. Silverlight 5 Features
  7. 社交媒体电影视频网HTML5模板
  8. DNS 教育訓練教程
  9. linux中的进程、环境变量和虚拟地址
  10. intelRealsense D435 python开发环境搭建
  11. python学生信息管理
  12. iOS开发之Xcode项目文件自动展开问题的解决办法
  13. 化学堵水剂处理油井出水问题
  14. 中职计算机专业考试时间,中职学业水平考试时间表出炉!这些不得不提前知晓...
  15. nios程序烧写到epcs方法
  16. 如何将图片中的表格变成Excel?这几个操作很简单
  17. win10 1903错误应用程序无法正常启动0xc0000135解决
  18. 电脑中如何打开进程管理器?
  19. 小红书严惩刷量行为:如何才能优雅的种草
  20. Win10如何运行经典200M游戏CS反恐精英(附安装包)

热门文章

  1. 经验 | 我的研究生这三年
  2. dtreeviz 画树模型
  3. 每日算法系列【LeetCode 1186】删除一次得到子数组最大和
  4. bug1-tensorflow中自定义模型的bug-input_signature
  5. 循环队列的实现笔记-c++
  6. key没有引号的字符串如何转json变为字典格式
  7. 博文视点新书快讯第78期
  8. SaaS基础架构—云计算
  9. Scikit-learn:聚类clustering
  10. html表格 溢出,html – 如何创建在溢出时滚动的表格单元格