关于这两个函数请参考
线程引入 pthread_self 和 pthread_equal 原因 ——解决不同平台的问题! - 无影的日志 - 网易博客
http://blog.163.com/xychenbaihu@yeah/blog/static/1322296552010102533746418/
pthread_self, pthread_equal - MemoryGarden's Blog - C++博客
http://www.cppblog.com/MemoryGarden/archive/2011/06/06/148140.html
关于这两个函数的问题参考
pthread_cleanup_push与pthread_cleanup_pop的目的 作用 - slj_win的专栏 - 博客频道 - CSDN.NET
http://blog.csdn.net/slj_win/article/details/7267483
pthread_cleanup_push/pop成对出现的意义 - LevinYan的专栏 - 博客频道 - CSDN.NET
http://blog.csdn.net/yangyiwei524386/article/details/21821095
pthread_clean_push与pthread_cleanup_pop函数详解-hededisanan00-ChinaUnix博客
http://blog.chinaunix.net/uid-26772137-id-3369725.html
pthread_cleanup_push()/pthread_cleanup_pop()的详解 - caianye的专栏 - 博客频道 - CSDN.NET
http://blog.csdn.net/caianye/article/details/5912172
一些示例
//线程的建立与等待
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
void *thread1_fun(void *arg)
{
<span style="white-space:pre"> </span>printf("this thread1 id is %lx \n",pthread_self());
<span style="white-space:pre"> </span>return NULL;
}
void *thread2_fun(void *arg)
{
<span style="white-space:pre"> </span>printf("this thread2 id is %lx \n",pthread_self());
<span style="white-space:pre"> </span>return NULL;
}
int main(void)
{
<span style="white-space:pre"> </span>pthread_t thread1;
<span style="white-space:pre"> </span>pthread_t thread2;
<span style="white-space:pre"> </span>pthread_create(&thread1,NULL,thread1_fun,NULL);
<span style="white-space:pre"> </span>pthread_create(&thread2,NULL,thread2_fun,NULL);
<span style="white-space:pre"> </span>pthread_join(thread2,NULL);
<span style="white-space:pre"> </span>pthread_join(thread1,NULL);
<span style="white-space:pre"> </span>printf("the main over\n");
<span style="white-space:pre"> </span>return 0;
}
</pre><pre name="code" class="cpp">运行结果
xfliu@ubuntu:线程的创建终止清理$ ./bin/1
this thread2 id is b6cf4b40
this thread1 id is b74f5b40
the main over
</pre><p></p><p><pre name="code" class="cpp">//异常退出之<pre name="code" class="cpp">//pthread_cleanup_pop();
</pre>#include <stdio.h>#include <stdlib.h>#include <pthread.h>void *thread1_fun(void *arg);void *thread2_fun(void *arg);void thread1_clean(void *arg);void thread2_clean(void *arg);int main(int argc,char *argv[]){int a=atoi(argv[1]);int b=atoi(argv[2]);pthread_t thread1;pthread_t thread2;pthread_create(&thread1,NULL,thread1_fun,&a);pthread_create(&thread2,NULL,thread2_fun,&b);pthread_join(thread2,NULL);pthread_join(thread1,NULL);printf("the main over\n");return 0;}void *thread1_fun(void *arg){pthread_cleanup_push(thread1_clean,NULL);printf("this thread1 id is %lx \n",pthread_self());pthread_cleanup_pop(*(int*)arg);printf("thread1 active\n");return NULL;}void *thread2_fun(void *arg){pthread_cleanup_push(thread2_clean,NULL);printf("this thread2 id is %lx \n",pthread_self());pthread_cleanup_pop(*(int*)arg);printf("thread2 active\n");return NULL;}void thread1_clean(void *arg){printf("thread1 was cleaned\n");}void thread2_clean(void *arg){printf("thread2 was cleaned\n");}<pre>
运行结果
xfliu@ubuntu:线程的创建终止清理$ ./bin/2 0 0
this thread1 id is b75d0b40
thread1 active
this thread2 id is b6dcfb40
thread2 active
the main over
xfliu@ubuntu:线程的创建终止清理$ ./bin/2 1 0
this thread2 id is b6cfab40
thread2 active
this thread1 id is b74fbb40
thread1 was cleaned
thread1 active
the main over
xfliu@ubuntu:线程的创建终止清理$ ./bin/2 0 1
this thread1 id is b757fb40
thread1 active
this thread2 id is b6d7eb40
thread2 was cleaned
thread2 active
the main over
xfliu@ubuntu:线程的创建终止清理$ ./bin/2 1 1
this thread1 id is b753db40
thread1 was cleaned
thread1 active
this thread2 id is b6d3cb40
thread2 was cleaned
thread2 active
the main over
xfliu@ubuntu:线程的创建终止清理$
分析:
pthread_cleanup_push(thread1_clean,NULL);
注册终止处理函数
pthread_cleanup_pop(*(int*)arg);
参数为1时,调用注册函数,执行完毕再回来
<pre name="code" class="cpp">pthread_join(thread2,NULL);
此函数并不能安排线程的执行顺序,只是让主线程再次等待该线程
//异常退出之pthread_exit;
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
void *thread1_fun(void *arg);
void *thread2_fun(void *arg);
void thread1_clean(void *arg);
void thread2_clean(void *arg);
int main(int argc,char *argv[])
{
pthread_t thread1;
pthread_t thread2;
pthread_create(&thread1,NULL,thread1_fun,NULL);
pthread_create(&thread2,NULL,thread2_fun,NULL);
pthread_join(thread2,NULL);
pthread_join(thread1,NULL);
printf("the main over\n");
return 0;
}
void *thread1_fun(void *arg)
{
pthread_cleanup_push(thread1_clean,NULL);
printf("this thread1 id is %lx \n",pthread_self());
pthread_exit(NULL);//下面不执行
pthread_cleanup_pop(0);
printf("thread1 active\n");
return NULL;
}
void *thread2_fun(void *arg)
{
pthread_cleanup_push(thread2_clean,NULL);
printf("this thread2 id is %lx \n",pthread_self());
pthread_exit(NULL);
pthread_cleanup_pop(0);
printf("thread2 active\n");
return NULL;
}
void thread1_clean(void *arg)
{
printf("thread1 was cleaned\n");
}
void thread2_clean(void *arg)
{
printf("thread2 was cleaned\n");
}
结果
xfliu@ubuntu:线程的创建终止清理$ ./bin/3
this thread2 id is b6d97b40
this thread1 id is b7598b40
thread2 was cleaned
thread1 was cleaned
the main over
xfliu@ubuntu:线程的创建终止清理$ ./bin/3
this thread1 id is b750eb40
thread1 was cleaned
this thread2 id is b6d0db40
thread2 was cleaned
the main over
xfliu@ubuntu:线程的创建终止清理$ ./bin/3
this thread1 id is b7534b40
this thread2 id is b6d33b40
thread1 was cleaned
thread2 was cleaned
the main over
xfliu@ubuntu:线程的创建终止清理$ ./bin/3
this thread2 id is b6d33b40
this thread1 id is b7534b40
thread1 was cleaned
thread2 was cleaned
the main over
xfliu@ubuntu:线程的创建终止清理$ ./bin/3
this thread1 id is b758ab40
this thread2 id is b6d89b40
thread1 was cleaned
thread2 was cleaned
the main over
xfliu@ubuntu:线程的创建终止清理$
联想return与exit
//异常退出之pthread_cancel;
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <unistd.h>
pthread_t thread1;
pthread_t thread2;
void *thread1_fun(void *arg);
void *thread2_fun(void *arg);
void thread1_clean(void *arg);
void thread2_clean(void *arg);
int main(int argc,char *argv[])
{
pthread_create(&thread1,NULL,thread1_fun,NULL);
pthread_create(&thread2,NULL,thread2_fun,NULL);
//sleep(3);
//pthread_cancel(thread1);
//pthread_cancel(thread2);
pthread_join(thread2,NULL);
//pthread_join(thread1,NULL);
//sleep(3);
printf("the main over\n");
return 0;
}
void *thread1_fun(void *arg)
{
pthread_cleanup_push(thread1_clean,NULL);
printf("this thread1 id is %lx \n",pthread_self());
sleep(10);//此处使用while(1);清理函数不能想响应,为why?
这里要注意,如果将sleep(100);换成while(1);的话,程序会一直暂停.push和pop要成对出现.
//因为while(1);运行的太快,线程不接受cancel信号
//while(1);
pthread_cleanup_pop(0);
printf("thread1 active\n");
return NULL;
}
void *thread2_fun(void *arg)
{
pthread_cleanup_push(thread2_clean,NULL);
printf("this thread2 id is %lx \n",pthread_self());
sleep(1);
pthread_cancel(thread1);
sleep(4);
pthread_cleanup_pop(0);
printf("thread2 active\n");
return NULL;
}
void thread1_clean(void *arg)
{
printf("thread1 was cleaned\n");
}
void thread2_clean(void *arg)
{
printf("thread2 was cleaned\n");
}
运行结果
xfliu@ubuntu:线程的创建终止清理$ ./bin/4
this thread1 id is b7567b40
this thread2 id is b6d66b40
thread1 was cleaned
thread2 active
the main over