POSIX线程清理函数


POSIX清理函数的调用时机:

调用pthread_exit()时,会调用清理函数;通过return返回的线程不会调用。

被别的线程取消的时候,会调用。

pthread_cleanup_pop()参数为非零时,会调用。

  1. #include <stdio.h>   
  2. #include <pthread.h>   
  3. #include <windows.h>  // Sleep   
  4.   
  5. pthread_mutex_t mtx = PTHREAD_MUTEX_INITIALIZER;  
  6. pthread_cond_t cond = PTHREAD_COND_INITIALIZER;  
  7.   
  8. struct Node  
  9. {  
  10.     int         number;  
  11.     struct Node *next;  
  12. } *head = NULL;  
  13.   
  14. // 清理函数   
  15. void cleanup_handler(void *node)  
  16. {  
  17.     printf("Cleanup handler of second thread.\n");  
  18.     free(node);  
  19.     pthread_mutex_unlock(&mtx);  
  20. }  
  21.   
  22. void* thread_func(void *arg)  
  23. {  
  24.     struct Node *p = NULL;  
  25.     // 清理函数入栈,此demo只需一个清理函数   
  26.     pthread_cleanup_push(cleanup_handler, p);  
  27.   
  28.     while (true)  
  29.     {  
  30.         pthread_mutex_lock(&mtx);  
  31.         if (head == NULL)  
  32.         {  
  33.             pthread_cond_wait(&cond, &mtx);  
  34.         }  
  35.         p = head;  
  36.         head = head->next;  
  37.         printf("Got %d from front of queue\n", p->number);  
  38.         free(p);  
  39.         pthread_mutex_unlock(&mtx);  
  40.     }  
  41.     /* 若从此处终止线程,则属于正常退出,无需清理。所以,只需将清理函数出栈。故而用 
  42.     参数零。若是从上面的“取消点”退出,则清理函数出栈时被调用:锁被打开,同时释放资源。*/  
  43.     pthread_cleanup_pop(0);  
  44.     return 0;  
  45. }  
  46.   
  47. int main(int argc, char* argv[])  
  48. {  
  49.     pthread_t tid;  
  50.     pthread_create(&tid, NULL, thread_func, NULL);  
  51.     for (int i = 0; i < 10; i++)  
  52.     {  
  53.         struct Node* p = (Node *)malloc(sizeof(struct Node));  
  54.         p->number = i;  
  55.   
  56.         // <!-- 对head操作属于临界区   
  57.         pthread_mutex_lock(&mtx);  
  58.         p->next = head;  
  59.         head = p;  
  60.         pthread_cond_signal(&cond);  
  61.         pthread_mutex_unlock(&mtx);  
  62.         // 所以要用互斥锁保护起来--!>   
  63.   
  64.         Sleep(1);  
  65.     }  
  66.     printf("Main thread wants to cancel the 2nd thread.\n");  
  67.   
  68.     /* 关于pthread_cancel,有一点额外的说明,它是从外部终止子线程,子线程会在 
  69.     最近的取消点,退出线程。而在我们的代码里,最近的取消点是pthread_cond_wait()了。*/  
  70.     pthread_cancel(tid);  
  71.     pthread_join(tid, NULL);  
  72.     printf("All done -- exiting\n");  
  73.     return 0;  
  74. }  

相关内容

    暂无相关文章