2017-08-16 328 views
-2

我寫使用POSIX pthread庫下面的代碼在pthread_join崩潰:glibc的時候調用在pthread_join()兩次

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

void *thread_function(void *arg) { 
    char *code = "1"; 
} 

int main() { 
int res; 
pthread_t a_thread; 
void *thread_result; 

res = pthread_create(&a_thread, NULL, thread_function, NULL); 
if (res != 0) { 
    perror("Thread creation failed"); 
    exit(EXIT_FAILURE); 
} 

sleep(5); 
printf("\nWaiting for thread to finish...\n"); 
res = pthread_join(a_thread, &thread_result); 
printf("res[%d]\n",res); 
if (res != 0) { 
    perror("Thread join failed"); 
    exit(EXIT_FAILURE); 
} 
res = pthread_join(a_thread, &thread_result); 
printf("res[%d]\n",res); 
exit(EXIT_SUCCESS); 
} 

上執行的代碼,我得到了以下的輸出:

Waiting for thread to finish... 
res[0] 
Segmentation fault (core dumped) 

在代碼,我想測試如果在線程完成後兩次調用pthread_jion()函數 會發生什麼情況。第一次調用函數是正確的,第二次崩潰。回溯:

Core was generated by `./a.out'. 
Program terminated with signal SIGSEGV, Segmentation fault. 
#0 pthread_join (threadid=140150565050112, thread_return=0x7fffa0a2c508) at 
pthread_join.c:47 
47 if (INVALID_NOT_TERMINATED_TD_P (pd)) 
(gdb) bt 
Python Exception exceptions.ImportError No module named gdb.frames: 
#0 pthread_join (threadid=140150565050112, thread_return=0x7fffa0a2c508) at 
pthread_join.c:47 
#1 0x00000000004008d5 in main() 

我檢查pthread_join.c文件:

39 int 
40 pthread_join (threadid, thread_return) 
41  pthread_t threadid; 
42  void **thread_return; 
43 { 
44 struct pthread *pd = (struct pthread *) threadid; 
45 
46 /* Make sure the descriptor is valid. */ 
47 if (INVALID_NOT_TERMINATED_TD_P (pd)) 
48  /* Not a valid thread handle. */ 
49  return ESRCH; 

在第47行,宏定義檢查是否PD是一個有效的線程處理。如果不是,則返回ESRCH(3)。

然而,當我在其他的Linux環境中運行相同的代碼,我得到了以下的輸出:

Waiting for thread to finish... 
res[0] 
res[3] 

是否有任何與環境?這兩個Linux系統具有相同的LDD版本:

ldd (GNU libc) 2.17 

相同GLIBC:

GLIBCXX_3.4 
GLIBCXX_3.4.1 
GLIBCXX_3.4.2 
GLIBCXX_3.4.3 
GLIBCXX_3.4.4 
GLIBCXX_3.4.5 
GLIBCXX_3.4.6 
GLIBCXX_3.4.7 
GLIBCXX_3.4.8 
GLIBCXX_3.4.9 
GLIBCXX_3.4.10 
GLIBCXX_3.4.11 
GLIBCXX_3.4.12 
GLIBCXX_3.4.13 
GLIBCXX_3.4.14 
GLIBCXX_3.4.15 
GLIBCXX_3.4.16 
GLIBCXX_3.4.17 
GLIBCXX_3.4.18 
GLIBCXX_3.4.19 
GLIBCXX_3.4.20 
GLIBC_2.3 
GLIBC_2.2.5 
GLIBC_2.14 
GLIBC_2.17 
GLIBC_2.3.2 
GLIBCXX_FORCE_NEW 
GLIBCXX_DEBUG_MESSAGE_LENGT 

和相同的Linux內核版本:線程終止pthread_detach

Red Hat Enterprise Linux Server release 6.6 (Santiago) 

回答

2

pthread_join電話。 pthread_detach線程終止時釋放所有線程資源。

pthread_detach

試圖脫離在 明確的行爲已經分離的線程結果的文檔。

所以你有沒有明確的行爲,所以你不能保證事後會發生什麼。

至少,threadid指向的內存將被釋放,從而導致訪問釋放的內存。

總之,不要在同一個threadid上兩次調用pthread_join。你爲什麼想要?

編輯:更簡單:爲pthread_join手冊頁說:

與先前已在 不確定的行爲加入結果的線程加入。