[英]Close a thread based on a variable value from calling thread
我在C中使用posix線程。我的程序中有兩個線程,thread1和thread2。 線程1啟動線程2。
線程1維護一個變量var1,基於該變量必須安全退出線程2。
thread2調用了許多冗長的函數(其運行時間最多為5秒)。 在thread2中有許多使用malloc的內存分配。 一旦var1變為true,我需要關閉thread2,但僅在取消分配所有已分配的內存之后。 如何做到這一點?
代碼如下:
void * func1(void *arg)
{
pthread_create(&thread2, &attr, func2, NULL);
while(1)
{
// ...
var1 = func3();
if(var1 == true)
{
// Cancel thread2
}
// ...
}
}
void * func2(void *arg)
{
// ...
func4(); // runs for 2 sec
char* var2 = malloc(10);
func5(); // runs for 5 sec
char* var3 = malloc(20);
// ...
cleanup:
free(var2);
free(var3);
return (void*) 0;
}
有幾種方法可以做到這一點。 這是一個:
從線程1的角度來看,您可以在時間到時在線程2上簡單地使用pthread_cancel
。 但是您需要相應地重組thread2,以確保它在安全的地方具有取消點。 您還需要重新構造數據的存儲方式,以允許為線程2調用取消回調:
struct func2_data {
char *var2;
char *var3;
};
void func2_cleanup(void *vdata) {
struct func2_data *data = vdata;
free(data->var2);
free(data->var3);
}
void * func2(void *arg)
{
struct func2_data data = {
NULL, NULL
};
pthread_cleanup_push(func2_cleanup, &data);
// ....
func4();
data.var2 = malloc(10);
pthread_testcancel();
func5();
data.var3 = malloc(10);
pthread_testcancel();
// ....
pthread_cleanup_pop(1);
return NULL;
}
那么這里發生了什么?
所有需要釋放的指針都捆綁在一起並初始化為NULL。 如果在分配任何單個變量之前調用了清除函數,則允許以free
操作的方式對其進行操作。
注冊了一個回調以釋放指針。 該回調將在任何取消點被調用。 包括線程何時從其處理函數返回。 因此,除了調用pop之外,您無需在其中明確地處理它。
取消點通過pthread_testcancel
添加到各個“安全”位置。 因此,允許線程在計算之間過早結束。 根據需要添加它們。
即使您的問題無法正確理解,在下面的代碼中,我還是給出了一個想法來處理這些問題。 使用ptread_join
安全退出線程
void * func1(void *arg)
{
pthread_create(&thread2, &attr, func2, (void*)&var1); /* Pass addr of var1 as argument to thread*/
while(1)
{
...
var1 = func3();
if(var1 == TRUE){
int *ret;
pthread_join(thread2,&ret);
}
...
}
}
void * func2(void *arg)
{
bool *check = (bool*)arg;
...
func4(); // runs for 2 sec
if(*check == TRUE)
goto end;
char* var2 = malloc(10);
func5(); // runs for 5 sec
if(*check == TRUE)
goto clean_var2;
char* var3 = malloc(20);
...
cleanup:
free(var3);
clean_var2:
free(var2);
end:
return (void*) 0;
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.