嵌入式Linux:注冊線(xiàn)程清理處理函數
在 Linux 多線(xiàn)程編程中,線(xiàn)程終止時(shí)可以執行特定的清理操作,通過(guò)注冊線(xiàn)程清理函數(thread cleanup handler)來(lái)實(shí)現。
這類(lèi)似于使用 atexit() 注冊進(jìn)程終止處理函數。
線(xiàn)程清理函數用于在線(xiàn)程退出時(shí)執行一些資源釋放或清理工作,例如關(guān)閉文件描述符、釋放內存等。
不同于進(jìn)程,線(xiàn)程可以注冊多個(gè)清理函數,這些清理函數以棧的形式管理,棧是一種先進(jìn)后出的數據結構。
因此,清理函數的執行順序與注冊順序相反。
在 Linux 中,使用 pthread_cleanup_push() 和 pthread_cleanup_pop() 函數分別向線(xiàn)程的清理函數棧添加和移除清理函數。
其原型如下:
void pthread_cleanup_push(void (*routine)(void *); void *arg);void pthread_cleanup_pop(int execute);
參數說(shuō)明:
pthread_cleanup_push():用于將清理函數推入棧中。
routine: 指向清理函數的函數指針,清理函數沒(méi)有返回值,并接受一個(gè) void * 類(lèi)型的參數。
arg: 傳遞給清理函數的參數,當清理函數執行時(shí),該參數作為 routine() 的輸入。
pthread_cleanup_pop():用于從清理函數棧中彈出最近添加的清理函數。
execute: 指定是否執行清理函數。如果為 0,則只移除清理函數而不執行它;如果為非 0,則不僅移除還會(huì )執行清理函數。
線(xiàn)程清理函數執行的場(chǎng)景:
當線(xiàn)程調用 pthread_exit()退出時(shí),清理函數會(huì )自動(dòng)執行。
當線(xiàn)程響應取消請求時(shí)(如通過(guò) pthread_cancel()取消線(xiàn)程),清理函數會(huì )被執行。
當通過(guò)非 0 參數調用 pthread_cleanup_pop() 時(shí),棧頂的清理函數會(huì )被執行。
以下代碼展示了如何使用 pthread_cleanup_push() 和 pthread_cleanup_pop() 注冊和移除清理函數:
void cleanup(void *arg) { printf("Cleaning up: %s\n", (char *)arg); } void *thread_function(void *arg) { pthread_cleanup_push(cleanup, "Resource 1"); pthread_cleanup_push(cleanup, "Resource 2"); // 模擬線(xiàn)程工作 printf("Thread is running...\n"); // 調用pthread_exit()會(huì )觸發(fā)清理函數的執行 pthread_exit(NULL); // 清理函數必須成對使用,因此即使退出后也要調用pthread_cleanup_pop pthread_cleanup_pop(1); pthread_cleanup_pop(1); } int main() { pthread_t thread; // 創(chuàng )建一個(gè)線(xiàn)程 if (pthread_create(&thread, NULL, thread_function, NULL) != 0) { perror("Failed to create thread"); return 1; } // 等待線(xiàn)程結束 pthread_join(thread, NULL); return 0; }
解釋說(shuō)明:
線(xiàn)程中注冊了兩個(gè)清理函數,分別為 "Resource 1" 和 "Resource 2"。
當線(xiàn)程調用 pthread_exit() 時(shí),棧中的清理函數按后進(jìn)先出的順序執行,因此會(huì )先打印 "Cleaning up: Resource 2",再打印 "Cleaning up: Resource 1"。
注意事項:
pthread_cleanup_push() 和 pthread_cleanup_pop() 并不是普通函數,而是宏實(shí)現的,必須在相同的作用域內成對出現,不能在代碼中分開(kāi)使用。
清理函數只會(huì )在線(xiàn)程通過(guò) pthread_exit() 或響應取消請求時(shí)執行。
如果線(xiàn)程通過(guò) return 語(yǔ)句退出,清理函數不會(huì )被執行。
通過(guò)使用 pthread_cleanup_push() 和 pthread_cleanup_pop(),可以確保在線(xiàn)程終止時(shí)執行所需的清理操作,這在資源管理和異常處理中非常有用。
清理函數的自動(dòng)執行使得多線(xiàn)程編程中的資源釋放更加簡(jiǎn)潔、安全。
*博客內容為網(wǎng)友個(gè)人發(fā)布,僅代表博主個(gè)人觀(guān)點(diǎn),如有侵權請聯(lián)系工作人員刪除。