初識(shí)互斥量
Case 0 :

運(yùn)行的結(jié)果大概率是字母和數(shù)字混合在一起被打印出來(lái),并不會(huì)先打印完全部數(shù)字再打印字母。這是因?yàn)榫€程的執(zhí)行并沒(méi)有確定的先后順序。
Case 1 :

當(dāng)多個(gè)線程涉及到共享數(shù)據(jù)時(shí),為了防止條件競(jìng)爭(zhēng)和數(shù)據(jù)訪問(wèn)沖突,需要用到互斥量(Mutex)。
訪問(wèn)共享數(shù)據(jù)前,將數(shù)據(jù)鎖住,在訪問(wèn)結(jié)束后,再將數(shù)據(jù)解鎖。當(dāng)一個(gè)線程使用特定互斥量鎖住共享數(shù)據(jù)時(shí),其他的線程想要訪問(wèn)鎖住的數(shù)據(jù),都必須等到之前那個(gè)線程對(duì)數(shù)據(jù)進(jìn)行解鎖后,才能進(jìn)行訪問(wèn)——這就是互斥量的作用。
Case 0的優(yōu)化:

Case 1的優(yōu)化:

使用互斥量來(lái)保護(hù)數(shù)據(jù),并不是僅僅在每一個(gè)成員函數(shù)中都加入一個(gè)std::lock_guard對(duì)象那 么簡(jiǎn)單,一個(gè)指針或引用,也會(huì)讓這種保護(hù)形同虛設(shè)。

在上述代碼中,函數(shù)process_data使用std::lock_guard來(lái)創(chuàng)建一個(gè)互斥量的鎖保護(hù)區(qū)域,確保在同一時(shí)間只有一個(gè)線程可以訪問(wèn)Data對(duì)象的內(nèi)容。但是在boom函數(shù)中調(diào)用process_data函數(shù)時(shí),content的引用被傳遞給了malicious_func函數(shù),從而使得通過(guò)unprotected_content指針可以繞過(guò)互斥量的保護(hù),直接修改Data對(duì)象的內(nèi)容,如果此時(shí)有其他線程在訪問(wèn)和修改Data對(duì)象,又將引發(fā)數(shù)據(jù)競(jìng)爭(zhēng)和未定義的行為。
Warning:切勿將受保護(hù)數(shù)據(jù)的指針或引用傳遞到互斥鎖作用域之外,無(wú)論是函數(shù)返回值,還是存儲(chǔ)在外部可見(jiàn)內(nèi)存,亦或是以參數(shù)的形式傳遞到其他函數(shù)中去。