pthread_cleanup_push与pthread_cleanup_pop的目的(作用)

2024-05-07 05:18

本文主要是介绍pthread_cleanup_push与pthread_cleanup_pop的目的(作用),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

比如thread1:
执行
pthread_mutex_lock(&mutex);

//一些会阻塞程序运行的调用,比如套接字的accept,等待客户连接
sock = accept(……); //这里是随便找的一个可以阻塞的接口

pthread_mutex_unlock(&mutex);
这个例子中,如果线程1执行accept时,线程会阻塞(也就是等在那里,有客户端连接的时候才返回,或则出现其他故障),线程等待中……

这时候线程2发现线程1等了很久,不赖烦了,他想关掉线程1,于是调用pthread_cancel()或者类似函数,请求线程1立即退出。

这时候线程1仍然在accept等待中,当它收到线程2的cancel信号后,就会从accept中退出,然后终止线程,注意这个时候线程1还没有执行:
pthread_mutex_unlock(&mutex);
也就是说锁资源没有释放,这回造成其他线程的死锁问题。

所以必须在线程接收到cancel后用一种方法来保证异常退出(也就是线程没达到终点)时可以做清理工作(主要是解锁方面),pthread_cleanup_push与pthread_cleanup_pop就是这样的。

pthread_cleanup_push(some_clean_func,…)
pthread_mutex_lock(&mutex);

//一些会阻塞程序运行的调用,比如套接字的accept,等待客户连接
sock = accept(……); //这里是随便找的一个可以阻塞的接口

pthread_mutex_unlock(&mutex);
pthread_cleanup_pop(0);
return NULL;
上面的代码,如果accept被cancel后线程退出,会自动调用some_clean_func函数,在这个函数中你可以释放锁资源。如果accept没有被cancel,那么线程继续执行,当pthread_mutex_unlock(&mutex);表示线程自己正确的释放资源了,而执行pthread_cleanup_pop(0);也就是取消掉前面的some_clean_func函数。接着return线程就正确的结束了。

不晓得你明白没,通俗点就是:
pthread_cleanup_push注册一个回调函数,如果你的线程在对应的pthread_cleanup_pop之前异常退出(return是正常退出,其他是异常),那么系统就会执行这个回调函数(回调函数要做什么你自己决定)。但是如果在pthread_cleanup_pop之前没有异常退出,pthread_cleanup_pop就把对应的回调函数取消了,

关于取消点的解释:

比如你执行:
printf(“thread sleep\n”);
sleep(10);
printf(“thread wake…\n”);
在sleep函数中,线程睡眠,结果收到cancel信号,这时候线程从sleep中醒来,但是线程不会立刻退出。这是因为pthread与C库方面的原因(具体是啥我也不清楚),pthread的建议是,如果一个函数是阻塞的,那么你必须在这个函数前后建立取消点,比如:
printf(“thread sleep\n”);
pthread_testcancel();
sleep(10);
pthread_testcancel();
printf(“thread wake…\n”);
这样,就添加了两个取消掉。在执行到pthread_testcancel的位置时,线程才可能响应cancel退出进程。

额外的知识:

对于cancel信号,线程有两种方法: 忽略,和响应。默认是响应
接收到cancel信号,线程有两种处理类型: 立即响应 和 延迟响应(在最近的取消点响应),默认是延迟响应

这篇关于pthread_cleanup_push与pthread_cleanup_pop的目的(作用)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/966430

相关文章

Java面试八股之JVM参数-XX:+UseCompressedOops的作用

JVM参数-XX:+UseCompressedOops的作用 JVM参数-XX:+UseCompressedOops的作用是启用对象指针压缩(Ordinary Object Pointers compression)。这一特性主要应用于64位的Java虚拟机中,目的是为了减少内存使用。在传统的64位系统中,对象引用(即指针)通常占用8字节(64位),而大部分应用程序实际上并不需要如此大的地址空间

Service在Android中的作用:技术难点、面试官关注点、回答吸引力与代码举例

在Android开发中,Service是一个重要的后台服务组件,它允许应用程序在后台执行长时间运行的操作,而无需与用户进行直接交互。Service在多种场景下发挥着关键作用,下面我们将从技术难点、面试官关注点、回答吸引力和代码举例四个方面,对Service的作用进行详细阐述。 一、技术难点 生命周期管理:Service的生命周期相对独立,与Activity和Fragment等组件不同。因此

#ifndef #define #endif 和 extern C的作用

ifndef #define #endif 防止头文件被重复引用 被重复引用”是指一个头文件在同一个cpp文件中被include了多次,这种错误常常是由于include嵌套造成的。比如:存在a.h文件#include "c.h"而此时b.cpp文件导入了#include “a.h” 和#include "c.h"此时就会造成c.h重复引用。 头文件被重复引用引起的后果: 有些头文件重复引用只是

linux关于epoll概述(各项组成,以及作用)

在 Linux 中,多个进程可以各自创建自己的 epoll 对象,每个进程都有独立的 epoll 实例,即拥有独立的 eventpoll 结构体和相关的数据结构(如红黑树、就绪列表等)。 当一个进程调用 epoll_create 函数时,Linux 内核会为该进程创建一个 eventpoll 对象。这个对象用于管理该进程所关注的文件描述符及其相关事件。 每个进程通过 epoll_ctl 函数向

android libuvc FORTIFY: pthread_mutex_lock called on a destroyed mutex

libuvc在安卓上的一个bug 需要修改libuvc和libusb源码 拷贝github上的一个项目 https://github.com/jiangdongguo/AndroidUSBCamera.git 替换libusb和libuvc就行了

ThreadLock 项目中的作用

ThreadLock 为本地线程,为每一个线程提供一个局部变量,也就是说只有当前线层可以访问,是线程安全的。原理:为每一个线程分配一个对象来工作,并不是由ThreadLock 来完成的,而是需要在应用层面保证的,ThreadLock 只是起到了一个容器的作用。原理为ThreadLock 的 set()跟 get()方法。 具体实现代码 public void set(T value)

深度学习常见概念解释(四)——损失函数定义,作用与种类(附公式和代码)

损失函数 前言定义作用种类1. 均方误差损失(Mean Squared Error Loss,MSE)公式特点和优点缺点使用场景示例代码在机器学习框架中的使用总结 2. 交叉熵损失(Cross-Entropy Loss)公式特点和优点使用场景示例代码在机器学习框架中的使用总结 总结 前言 在机器学习和深度学习中,损失函数(Loss Function)起着至关重要的作用。它是模型

「生信Debug」OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable

BLAS(Basic Linear Algebra Subprograms),翻译为基础线性代数子程序库,里面拥有大量已经编写好的关于线性代数运算的程序。OpenBLAS是其中一个实现了相关运算的开源程序库,其他软件在开发的时候就不需要额外造轮子,直接调用相关的API即可。 之前在使用OrthoFinder遇到了类似的问题,见https://github.com/davidemms/OrthoF

web工程中的web.xml文件有什么作用呢?

eb工程中的web.xml文件有什么作用呢?它是每个web.xml工程都必须的吗? 一个web中完全可以没有web.xml文件,也就是说,web.xml文件并不是web工程必须的。 那什么时候需要,什么时候可以不需要呢? 要想回答上面的问题,得先了解web.xml文件使用来干什么的。web.xml文件是用来配置:欢迎页、servlet、filter等的。当你的web工程没用到这些时,你可以

Java面试题:通过实例说明工厂模式和抽象工厂模式的用法,以及它们在解耦中的作用

工厂模式和抽象工厂模式是创建型设计模式中的两种,主要用于对象的创建,并且通过将对象的创建过程封装起来,来实现代码的解耦和灵活性。下面通过具体实例来说明这两种模式的用法及其在解耦中的作用。 工厂模式(Factory Method Pattern) 工厂模式通过定义一个创建对象的接口,让子类决定实例化哪一个类。工厂方法使一个类的实例化延迟到其子类。 实例说明 假设我们有一个交通工具接口 Veh