关闭

Linux Advance--线程清理处理函数

标签: linux线程
309人阅读 评论(0) 收藏 举报
分类:

线程可以安排它退出时需要调用的函数,这与进程可以用atexit函数安排进程退出时需要调用的函数是类似的。这样的函数称为线程清理处理程序 (thread cleanup handler) 。线程可以建立多个清理处理程序。处理程序记录在栈中,也就是说它们的执行顺序与它们注册时的顺序相反。

函数原型声明如下:

#include <pthread.h>

void pthread_cleanup_push(void (*rtn) (void *), void *arg);

void pthread_cleanup_pop(int execute);

当线程执行以下动作时调用清理函数,调用参数为arg,清理函数rtn调用顺序是由pthread_cleanup_push函数来安排的。

×调用pthread_exit时。

×响应取消请求时。

×用非零execute参数调用pthread_cleanup_pop时。

如果execute参数设置为0,清理函数将不会被调用。无论哪种情况,pthread_cleanup_pop都将删除上次pthread_cleanup_push调用建立的清理处理程序。

下面是例子:

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

void cleanup(void *arg)
{
	printf("cleanup: %s\n", (char *)arg);
}

void *thr_fn1(void *arg)
{
	printf("thread 1 start\n");
	pthread_cleanup_push(cleanup, "thread 1 first handler");
	pthread_cleanup_push(cleanup, "thread 1 second handler");
	printf("thread 1 push complete\n");
	if (arg)
		return ((void *)0);
	pthread_cleanup_pop(0);
	pthread_cleanup_pop(0);
	pthread_exit((void *)1);
}

void *thr_fn2(void *arg)
{
	printf("thread 2 start\n");
	pthread_cleanup_push(cleanup, "thread 2 first handler");
	pthread_cleanup_push(cleanup, "thread 2 second handler");
	if (arg)
		pthread_exit((void *)2);
	pthread_cleanup_pop(0);
	pthread_cleanup_pop(0);
	pthread_exit((void *)2);
}

int main()
{
	int			err;
	pthread_t	tid1, tid2;
	void		*tret;

	err = pthread_create(&tid1, 0, thr_fn1, (void *)1);
	if (err != 0) {
		printf("can't create thread 1: %s\n", strerror(err));
		exit(1);
	}
    err = pthread_create(&tid2, 0, thr_fn2, (void *)2);
    if (err != 0) {
		printf("can't create thread 2: %s\n", strerror(err));
		exit(1);
    }
    err = pthread_join(tid1, &tret);
    if (err != 0) {
		printf("can't join with thread 1: %s\n", strerror(err));
		exit(1);
    }
    printf("thread 1 exit code %d\n", (int)tret);
    err = pthread_join(tid2, &tret);
    if (err != 0) {
		printf("can't join with thread 2: %s\n", strerror(err));
		exit(1);
	}
	printf("thread 2 exit code %d\n", (int)tret);
    exit(0);
}

可能的运行结果:



从输出结果可以看出,两个线程都正确地启动和退出了,但是只调用了第二个线程的清理处理程序,所以如果线程是通过从它的启动例程中返回而终止的话,那么它的清理处理程序就不会被调用,还要注意清理处理程序是按照与它们安装时相反的顺序被调用的。


1
0
查看评论

Linux pthread_exit及线程清理函数

pthread_exit 关于线程的终止 单个线程可以通过下列三种方式退出,在不终止整个进程的情况下停止它的控制流。 (1)线程只是从例程中返回,返回线程的退出码。 (2)线程可以被同一进程中的其他线程取消。 (3)线程调用pthread_exit。 头文件 #includ...
  • CSLQM
  • CSLQM
  • 2016-11-20 09:11
  • 3011

Linux 线程操作函数总结

线程操作函数总结 1、线程创建函数int pthread_create(pthread_t *restrict tidp, const pthread_attr_t *restrict attr, void *(*start_rtn)(void), void *restrict arg); ...
  • yoli_c_world
  • yoli_c_world
  • 2015-08-18 23:49
  • 2106

Linux 线程操作函数技能总结

线程操作函数总结 1、线程创建函数int pthread_create(pthread_t *restrict tidp, const pthread_attr_t *restrict attr, void *(*start_rtn)(void), void *restrict arg); ...
  • shaderdx
  • shaderdx
  • 2016-01-07 14:16
  • 1652

Linux Advance--线程和fork

当线程调用 fork 时,就为子进程创建了整个进程地址空间的副本。子进程通过继承整个地址空间的副本,也从父进程那里继承了所有互斥量、读写锁和条件变量的状态。如果父进程包含多个进程,子进程在 fork 返回之后,如果紧接着不是马上调用 exec 的话,就需要清理锁状态。 要清除锁状态,可以通过调用 ...
  • qq_20480611
  • qq_20480611
  • 2015-11-22 15:59
  • 281

线程清理处理函数 pthread_cleanup_push、pthread_cleanup_pop

原文:http://blog.csdn.net/yanook/article/details/6579955 线程可以安排它退出时需要调用的函数,这样的函数称为线程清理处理程序,线程可以建立多个清理处理程序。处理程序记录在栈中,也就是说它们的执行顺序与它们注册时的顺序相反。 ...
  • labrary
  • labrary
  • 2013-05-04 10:24
  • 520

Linux异步信号处理函数引发的死锁及解决方法

异步信号处理方式使用不当会发生死锁。异步信号处理函数不推荐做太多工作,如果调用函数需要是reentrant。reentrant可重新进入的,可以理解为一次调用发生后,不会对该函数的再次调用发生任何影响。即reentrant函数中不可以有static或global变量,不可以分配释放内存,通常不可以使...
  • u014070695
  • u014070695
  • 2016-03-05 17:09
  • 1863

linux线程退出时执行的程序(线程清理处理程序)简单例子

/********************************** pthread_exit.c **************************************/ #include #include #include #include void exe_exi...
  • bbs598598
  • bbs598598
  • 2012-05-05 10:06
  • 2751

线程清理处理程序

linux提供了一对函数用于自动释放资源,声明如下: #include <pthread.h> void pthread_cleanup_push(void (*routine)(void *), void *arg); void pthread_cleanup_pop(in...
  • zhuxinquan61
  • zhuxinquan61
  • 2015-08-03 10:54
  • 1193

Windows线程函数概述 - 《C++编程艺术》

Windows提供了多组支持 多线程的应用程序接口(API)函数。许多读者已经对Windows提供的多线程函数有一定程度的了解,但是对于那些不熟悉这些的读者,本章提供了这些函 数的概述。记住,Windows提供了许多其他的基于多线程的函数,这些函数需要您自己去探索。为了使用Windows的多线程函数...
  • lcj8
  • lcj8
  • 2007-11-18 17:19
  • 1582

Linux — 信号 信号处理和信号处理函数详解(一)

信号处理(一)在Linux下当我们想强制结束一个程序的时候,我们通常会给它发送一个信号然后该进程捕捉到信号,再然后该进程执行一定操作最终被终止.信号是UNIX和Linux系统响应某些条件而产生的一个事件,接收到该信号的进程会相应地采取一些行动。通常信号是由一个错误产生的。但它们还可以作为进程间通信或...
  • Dawn_sf
  • Dawn_sf
  • 2017-07-03 11:49
  • 1244
    个人资料
    • 访问:558869次
    • 积分:10868
    • 等级:
    • 排名:第1783名
    • 原创:517篇
    • 转载:3篇
    • 译文:0篇
    • 评论:45条