天天看點

《現代體系結構上的UNIX系統:核心程式員的對稱多處理和緩存技術(修訂版)》——2.10 獨立的指令高速緩存和資料高速緩存

本節書摘來自異步社群《現代體系結構上的unix系統:核心程式員的對稱多處理和緩存技術(修訂版)》一書中的第2章,第2.10節,作者:【美】curt schimmel著,更多章節内容可以通路雲栖社群“異步社群”公衆号檢視

将指令高速緩存和資料高速緩存分開的做法目前在計算機系統中相當常見。這種做法能夠有效地使高速緩存的帶寬加倍,因為它能讓cpu從指令高速緩存預取指令的同時把資料載入或者儲存到資料高速緩存中。圖2-17描繪了這樣的一種組織結構。本章提到的所有處理器,除了intel 80486之外,其片上高速緩存都有獨立的指令高速緩存和資料高速緩存。

因為兩塊高速緩存都可以同時通路主存儲器(缺失處理或者寫操作),是以要由硬體來仲裁高速緩存對主存儲器的通路,這對于軟體來說是透明的。注意,沒有辦法直接把資料儲存到指令高速緩存中。是以,指令高速緩存是隻讀高速緩存。

這種組織結構最重要的方面就是缺乏資料高速緩存和指令高速緩存之間的直接互連。如果在指令高速緩存中沒有命中某個指令,那麼指令高速緩存就無法到資料高速緩存中查找它。指令高速緩存始終都是從主存儲器讀取指令來完成缺失操作。類似地,資料高速緩存中的缺失也要從主存儲器讀取。把資料儲存到資料高速緩存中不會影響指令高速緩存的内容。雖然這是一種最簡單的實作,但是它可能會産生高速緩存的不一緻性,因為主存儲器的内容可能會被緩存在一個以上的地方。如果使用單一的、将指令和資料結合在一起的高速緩存,就不會出現這類不一緻性。

《現代體系結構上的UNIX系統:核心程式員的對稱多處理和緩存技術(修訂版)》——2.10 獨立的指令高速緩存和資料高速緩存

考慮使用自身能夠修改代碼的程式時的情形。這類程式包括諸如lisp解釋器這樣的程式,因為對于它們來說,部分編譯它們正在解釋的程式并非鮮見(編譯後的代碼通常寫入程序的資料區)。如果要執行的指令是在資料區動态生成的,那麼有可能出現兩種不一緻性。第一,如果使用寫回高速緩存機制,那麼最近寫的指令可能尚未寫入主存儲器。這意味着,如果程式試圖執行這些新指令,那麼指令高速緩存可能會從記憶體中取得過時的指令。第二,一旦動态生成的指令被緩存在指令高速緩存中,那麼程式的任何寫操作(以此用新指令來替換那些在指令高速緩存中的老指令)都不會對指令高速緩存造成影響。新指令将寫入資料高速緩存,并且最終寫入主存儲器,但是指令高速緩存不知道要擷取新值。它會繼續執行過時的老指令,直到行替換删除這些指令為止。在這種情況下,對那些指令的下一次引用将會造成一次缺失,并且從主存儲器讀取新指令。

遺憾的是,作業系統不能把高速緩存隐藏起來,進而讓這類程式無視高速緩存的存在,因為作業系統沒有辦法知道程式會在什麼時候試圖執行其資料空間的某個部分。唯一的解決方法是提供特殊的系統調用,以便在程式已經産生了一組它現在想要執行的指令時就通知作業系統。接着,如果在資料高速緩存中使用了寫回高速緩存機制,那麼作業系統就使主存儲器有效,并且使指令高速緩存的内容無效(在提供特殊指令來沖洗高速緩存的體系結構上,如果應用程式能夠直接執行高速緩存沖洗指令,那麼就不一定要有特殊的系統調用)。對指令和資料高速緩存的沖洗通常作為分開的硬體操作來實作。

一般而言,隻要作業系統需要使被緩存的資料無效來保持一緻性,那麼它也必須使被緩存的指令無效。各種特定的執行個體則取決于高速緩存的體系結構,下面的章節将讨論它們。

雖然有可能讓建構的系統中的硬體自動保持指令高速緩存和資料高速緩存的同步,但是卻很少這樣做。這樣的系統會要求每次在資料高速緩存上執行寫操作的時候都檢查指令高速緩存并可能使其無效。這些額外的對指令高速緩存的通路可能會幹擾指令的擷取操作,并使其變慢。那些能夠修改自身的代碼執行個體很少值得為其在硬體上增加複雜性。

繼續閱讀