緩存一致性

緩存

在現(xiàn)代的 CPU(大多數(shù))上赚瘦,所有的內(nèi)存訪問都需要通過層層的緩存來進行悲酷。CPU 的讀 / 寫(以及取指令)單元正常情況下甚至都不能直接訪問內(nèi)存——這是物理結構決定的顿肺;CPU 都沒有管腳直接連到內(nèi)存。相反,CPU 和一級緩存(L1 Cache)通訊凭戴,而一級緩存才能和內(nèi)存通訊档痪。大約二十年前涉枫,一級緩存可以直接和內(nèi)存?zhèn)鬏敂?shù)據(jù)笛坦。如今嫂易,更多級別的緩存加入到設計中,一級緩存已經(jīng)不能直接和內(nèi)存通訊了秩冈,它和二級緩存通訊——而二級緩存才能和內(nèi)存通訊芬失。或者還可能有三級緩存。

緩存是分“段”(line)的消别,一個段對應一塊存儲空間怀读,大小是 32、64或128字節(jié)菜枷,每個緩存段知道自己對應什么范圍的物理內(nèi)存地址苍糠。

當 CPU 看到一條讀內(nèi)存的指令時,它會把內(nèi)存地址傳遞給一級數(shù)據(jù)緩存啤誊。一級數(shù)據(jù)緩存會檢查它是否有這個內(nèi)存地址對應的緩存段岳瞭。如果沒有拥娄,它會把整個緩存段從內(nèi)存(或者從更高一級的緩存,如果有的話)中加載進來瞳筏。是的稚瘾,一次加載整個緩存段,這是基于這樣一個假設:內(nèi)存訪問傾向于本地化(localized)姚炕,如果我們當前需要某個地址的數(shù)據(jù)摊欠,那么很可能我們馬上要訪問它的鄰近地址。一旦緩存段被加載到緩存中柱宦,讀指令就可以正常進行讀取些椒。

如果我們只處理讀操作,那么事情會很簡單掸刊,因為所有級別的緩存都遵守以下規(guī)律——在任意時刻免糕,任意級別緩存中的緩存段的內(nèi)容,等同于它對應的內(nèi)存中的內(nèi)容忧侧。石窑。

一旦我們允許寫操作,事情就變得復雜一點了蚓炬。這里有兩種基本的寫模式:直寫(write-through)和回寫(write-back)松逊。直寫更簡單一點:我們透過本級緩存,直接把數(shù)據(jù)寫到下一級緩存(或直接到內(nèi)存)中试吁,如果對應的段被緩存了棺棵,我們同時更新緩存中的內(nèi)容(甚至直接丟棄),就這么簡單熄捍。這也遵守前面的定律:緩存中的段永遠和它對應的內(nèi)存內(nèi)容匹配烛恤。

回寫模式就有點復雜了。緩存不會立即把寫操作傳遞到下一級余耽,而是僅修改本級緩存中的數(shù)據(jù)缚柏,并且把對應的緩存段標記為“臟”段。臟段會觸發(fā)回寫碟贾,也就是把里面的內(nèi)容寫到對應的內(nèi)存或下一級緩存中币喧。回寫后袱耽,臟段又變“干凈”了杀餐。當一個臟段被丟棄的時候,總是先要進行一次回寫朱巨∈非蹋回寫所遵循的規(guī)律有點不同。當所有的臟段被回寫后,任意級別緩存中的緩存段的內(nèi)容琼讽,等同于它對應的內(nèi)存中的內(nèi)容必峰。

換句話說,回寫模式的定律中钻蹬,我們?nèi)サ袅恕霸谌我鈺r刻”這個修飾語吼蚁,代之以弱化一點的條件:要么緩存段的內(nèi)容和內(nèi)存一致(如果緩存段是干凈的話),要么緩存段中的內(nèi)容最終要回寫到內(nèi)存中(對于臟緩存段來說)问欠。

直接模式更簡單肝匆,但是回寫模式有它的優(yōu)勢:它能過濾掉對同一地址的反復寫操作,并且溅潜,如果大多數(shù)緩存段都在回寫模式下工作术唬,那么系統(tǒng)經(jīng)承椒可以一下子寫一大片內(nèi)存滚澜,而不是分成小塊來寫,前者的效率更高设捐。

一致性協(xié)議

只要系統(tǒng)只有一個 CPU 核在工作,一切都沒問題塘淑。如果有多個核萝招,每個核又都有自己的緩存,那么我們就遇到問題了存捺,因為如果一個 CPU 緩存了某塊內(nèi)存槐沼,那么在其他 CPU 修改這塊內(nèi)存的時候,我們希望得到通知捌治。系統(tǒng)的內(nèi)存在各個 CPU 之間無法做到與生俱來的同步岗钩,我們需要一個大家都能遵守的方法來達到同步的目的。

注意肖油,這個問題的根源是我們擁有多組緩存兼吓,而不是多個 CPU 核。我們也可以這樣解決問題森枪,讓多個 CPU 核共用一組緩存:也就是說只有一塊一級緩存视搏,所有處理器都必須共用它。在每一個指令周期县袱,只有一個幸運的 CPU 能通過一級緩存做內(nèi)存操作浑娜,運行它的指令。

這本身沒問題式散。唯一的問題就是太慢了筋遭,因為這下處理器的時間都花在排隊等待使用一級緩存了

我們知道了只有一組緩存也能工作,只是太慢了,接下來最好就是能做到:使用多組緩存宛畦,但使它們的行為看起來就像只有一組緩存那樣瘸洛。緩存一致性協(xié)議就是為了做到這一點而設計的。就像名稱所暗示的那樣次和,這類協(xié)議就是要使多組緩存的內(nèi)容保持一致反肋。

緩存一致性協(xié)議有多種,但是日常處理的大多數(shù)計算機設備使用的都屬于“窺探(snooping)”協(xié)議踏施。

還有一種叫“基于目錄的(directory-based)”協(xié)議石蔗,這種協(xié)議的延遲性較大,但是在擁有很多個處理器的系統(tǒng)中畅形,它有更好的可擴展性养距。

窺探”背后的基本思想是,所有內(nèi)存?zhèn)鬏敹及l(fā)生在一條共享的總線上日熬,而所有的處理器都能看到這條總線:緩存本身是獨立的棍厌,但是內(nèi)存是共享資源,所有的內(nèi)存訪問都要經(jīng)過仲裁(arbitrate):同一個指令周期中竖席,只有一個緩存可以讀寫內(nèi)存耘纱。窺探協(xié)議的思想是,緩存不僅僅在做內(nèi)存?zhèn)鬏數(shù)臅r候才和總線打交道毕荐,而是不停地在窺探總線上發(fā)生的數(shù)據(jù)交換束析,跟蹤其他緩存在做什么。所以當一個緩存代表它所屬的處理器去讀寫內(nèi)存時憎亚,其他處理器都會得到通知员寇,它們以此來使自己的緩存保持同步。只要某個處理器一寫內(nèi)存第美,其他處理器馬上就知道這塊內(nèi)存在它們自己的緩存中對應的段已經(jīng)失效蝶锋。

在直寫模式下,這是很直接的斋日,因為寫操作一旦發(fā)生牲览,它的效果馬上會被“公布”出去。但是如果混著回寫模式恶守,就有問題了第献。因為有可能在寫指令執(zhí)行過后很久,數(shù)據(jù)才會被真正回寫到物理內(nèi)存中——在這段時間內(nèi)兔港,其他處理器的緩存也可能會傻乎乎地去寫同一塊內(nèi)存地址庸毫,導致沖突。在回寫模型中衫樊,簡單把內(nèi)存寫操作的信息廣播給其他處理器是不夠的飒赃,我們需要做的是利花,在修改本地緩存之前,就要告知其他處理器载佳。

MESI以及衍生協(xié)議

MESI 是四種緩存段狀態(tài)的首字母縮寫炒事,任何多核系統(tǒng)中的緩存段都處于這四種狀態(tài)之一。

狀態(tài) 說明 監(jiān)聽任務
Invalid 失效緩存段蔫慧,要么已經(jīng)不在緩存中挠乳,要么它的內(nèi)容已經(jīng)過時。為了達到緩存的目的姑躲,這種狀態(tài)的段將會被忽略睡扬。一旦緩存段被標記為失效,那效果就等同于它從來沒被加載到緩存中黍析。 緩存行必須時刻監(jiān)聽所有試圖讀該緩存行相對就主存的操作卖怜,這種操作必須在緩存將該緩存行寫回主存并將狀態(tài)變成S(共享)狀態(tài)之前被延遲執(zhí)行。
Shared 共享緩存段阐枣,它是和主內(nèi)存內(nèi)容保持一致的一份拷貝马靠,在這種狀態(tài)下的緩存段只能被讀取,不能被寫入侮繁。多組緩存可以同時擁有針對同一內(nèi)存地址的共享緩存段,這就是名稱的由來锁孟。 緩存行也必須監(jiān)聽其它緩存讀主存中該緩存行的操作,一旦有這種操作圆恤,該緩存行需要變成S(共享)狀態(tài)。
Exclusive 獨占緩存段腔稀,和 S 狀態(tài)一樣,也是和主內(nèi)存內(nèi)容保持一致的一份拷貝淡喜。區(qū)別在于炼团,如果一個處理器持有了某個 E 狀態(tài)的緩存段瘟芝,那其他處理器就不能同時持有它颈抚,所以叫“獨占”贩汉。這意味著,如果其他處理器原本也持有同一緩存段锚赤,那么它會馬上變成“失效”狀態(tài)。 緩存行也必須監(jiān)聽其它緩存使該緩存行無效或者獨享該緩存行的請求,并將該緩存行變成無效(Invalid)。
Modified 已修改緩存段,屬于臟段构资,它們已經(jīng)被所屬的處理器修改了。如果一個段處于已修改狀態(tài)葵姥,那么它在其他處理器緩存中的拷貝馬上會變成失效狀態(tài),這個規(guī)律和 E 狀態(tài)一樣允乐。此外,已修改緩存段如果被丟棄或標記為失效厦滤,那么先要把它的內(nèi)容回寫到內(nèi)存中——這和回寫模式下常規(guī)的臟段處理方式一樣趟咆。

從CPU讀寫角度來說:

  • CPU讀請求:緩存處于M、E值纱、S狀態(tài)都可以被讀取鳞贷,I狀態(tài)CPU只能從主存中讀取數(shù)據(jù)
  • CPU寫請求:緩存處于M、E狀態(tài)才可以被寫虐唠。對于S狀態(tài)的寫搀愧,需要將其他CPU中緩存行置為無效才可寫

上圖的切換解釋:


MESI優(yōu)化和他們引入的問題

緩存的一致性消息傳遞是要時間的,這就使其切換時會產(chǎn)生延遲凿滤。當一個緩存被切換狀態(tài)時其他緩存收到消息完成各自的切換并且發(fā)出回應消息這么一長串的時間中CPU都會等待所有緩存響應完成妈橄。可能出現(xiàn)的阻塞都會導致各種各樣的性能問題和穩(wěn)定性問題翁脆。

比如你需要修改本地緩存中的一條信息,那么你必須將I(無效)狀態(tài)通知到其他擁有該緩存數(shù)據(jù)的CPU緩存中鼻种,并且等待確認反番。等待確認的過程會阻塞處理器,這會降低處理器的性能叉钥。因為這個等待遠遠比一個指令的執(zhí)行時間長的多罢缸。

為了避免這種CPU運算能力的浪費,Store Bufferes被引入使用投队。處理器把它想要寫入到主存的值寫到緩存枫疆,然后繼續(xù)去處理其他事情。當所有失效確認(Invalidate Acknowledge)都接收到時敷鸦,數(shù)據(jù)才會最終被提交息楔。

執(zhí)行失效也不是一個簡單的操作寝贡,它需要處理器去處理。另外值依,存儲緩存(Store Buffers)并不是無窮大的圃泡,所以處理器有時需要等待失效確認的返回。這兩個操作都會使得性能大幅降低愿险。為了應付這種情況颇蜡,引入了失效隊列——對于所有的收到的Invalidate請求,Invalidate Acknowlege消息必須立刻發(fā)送辆亏,Invalidate并不真正執(zhí)行风秤,而是被放在一個特殊的隊列中,在方便的時候才會去執(zhí)行扮叨,處理器不會發(fā)送任何消息給所處理的緩存條目缤弦,直到它處理Invalidate。


?著作權歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末甫匹,一起剝皮案震驚了整個濱河市甸鸟,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌兵迅,老刑警劉巖抢韭,帶你破解...
    沈念sama閱讀 206,311評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異恍箭,居然都是意外死亡刻恭,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,339評論 2 382
  • 文/潘曉璐 我一進店門扯夭,熙熙樓的掌柜王于貴愁眉苦臉地迎上來鳍贾,“玉大人,你說我怎么就攤上這事交洗∑锟疲” “怎么了?”我有些...
    開封第一講書人閱讀 152,671評論 0 342
  • 文/不壞的土叔 我叫張陵构拳,是天一觀的道長咆爽。 經(jīng)常有香客問我,道長置森,這世上最難降的妖魔是什么斗埂? 我笑而不...
    開封第一講書人閱讀 55,252評論 1 279
  • 正文 為了忘掉前任,我火速辦了婚禮凫海,結果婚禮上呛凶,老公的妹妹穿的比我還像新娘。我一直安慰自己行贪,他們只是感情好漾稀,可當我...
    茶點故事閱讀 64,253評論 5 371
  • 文/花漫 我一把揭開白布模闲。 她就那樣靜靜地躺著,像睡著了一般县好。 火紅的嫁衣襯著肌膚如雪围橡。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 49,031評論 1 285
  • 那天缕贡,我揣著相機與錄音翁授,去河邊找鬼。 笑死晾咪,一個胖子當著我的面吹牛收擦,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播谍倦,決...
    沈念sama閱讀 38,340評論 3 399
  • 文/蒼蘭香墨 我猛地睜開眼塞赂,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了昼蛀?” 一聲冷哼從身側(cè)響起宴猾,我...
    開封第一講書人閱讀 36,973評論 0 259
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎叼旋,沒想到半個月后仇哆,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 43,466評論 1 300
  • 正文 獨居荒郊野嶺守林人離奇死亡夫植,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 35,937評論 2 323
  • 正文 我和宋清朗相戀三年讹剔,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片详民。...
    茶點故事閱讀 38,039評論 1 333
  • 序言:一個原本活蹦亂跳的男人離奇死亡延欠,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出沈跨,到底是詐尸還是另有隱情由捎,我是刑警寧澤,帶...
    沈念sama閱讀 33,701評論 4 323
  • 正文 年R本政府宣布饿凛,位于F島的核電站隅俘,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏笤喳。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 39,254評論 3 307
  • 文/蒙蒙 一碌宴、第九天 我趴在偏房一處隱蔽的房頂上張望杀狡。 院中可真熱鬧,春花似錦贰镣、人聲如沸呜象。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,259評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽恭陡。三九已至蹬音,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間休玩,已是汗流浹背著淆。 一陣腳步聲響...
    開封第一講書人閱讀 31,485評論 1 262
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留拴疤,地道東北人永部。 一個月前我還...
    沈念sama閱讀 45,497評論 2 354
  • 正文 我出身青樓,卻偏偏與公主長得像呐矾,于是被迫代替她去往敵國和親苔埋。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 42,786評論 2 345

推薦閱讀更多精彩內(nèi)容