2020国产成人精品视频,性做久久久久久久久,亚洲国产成人久久综合一区,亚洲影院天堂中文av色

分享

《深入理解計算機系統(tǒng)》(CSAPP)讀書筆記 —— 第六章 存儲器層次結構

 頭號碼甲 2022-05-16

??在計算機系統(tǒng)模型中,CPU執(zhí)行指令,而存儲器系統(tǒng)為CPU存放指令和數據。實際上,存儲器系統(tǒng)是一個具有不同容量、成本和訪問時間的存儲設備的層次結構。
??如果你的程序需要的數據是存儲在CPU寄存器中,那么在指令的執(zhí)行期間,在0個周期內就能訪問到它們。如果存儲在高速緩存中,需要4~75個周期。如果存儲在主存中,需要上百個周期。而如果存儲在磁盤上,需要大約幾千萬個周期!
??計算機程序的一個基本屬性稱為局部性。具有良好局部性的程序傾向于一次又一次地訪問相同的數據項集合,或是傾向于訪問鄰近的數據項集合。具有良好局部性的程序比局部性差的程序更多地傾向于從存儲器層次結構中較高層次處訪問數據項,因此運行得更快。

存儲技術

隨機訪問存儲器

??隨機訪問存儲器( Random-Access Memory,RAM)分為兩類:靜態(tài)的和動態(tài)的。靜態(tài)RAM(SRAM)比動態(tài)RAM(DRAM)更快,但也貴得多。SRAM用來作為高速緩存存儲器。DRAM用來作為主存以及圖形系統(tǒng)的幀緩沖區(qū)

靜態(tài)RAM

??SRAM將每個位存儲在一個雙穩(wěn)態(tài)的( bistable)存儲器單元里。每個單元是用一個六晶體管電路來實現的。這個電路有這樣一個屬性,它可以無限期地保持在兩個不同的電壓配置( configuration)或狀態(tài)( state)之一。其他任何狀態(tài)都是不穩(wěn)定的,在不穩(wěn)定狀態(tài)時,電路會迅速轉移到兩個穩(wěn)定狀態(tài)的一個。

??由于SRAM存儲器單元的雙穩(wěn)態(tài)特性,只要有電,它就會永遠地保持它的值。即使有干擾(例如電子噪音)來擾亂電壓,當干擾消除時,電路就會恢復到穩(wěn)定值。

動態(tài)RAM

??DRAM將每個位存儲為對一個電容的充電。DRAM存儲器可以制造得非常密集。每個單元由一個電容和一個訪問晶體管組成。但是,與SRAM不同,DRAM存儲器單元對干擾非常敏感。當電容的電壓被擾亂之后,它就永遠不會恢復了。暴露在光線下會導致電容電壓改變。

??下表總結了SRAM和DRAM存儲器的特性。只要有供電,SRAM就會保持不變。與DRAM不同,它不需要刷新。SRAM的存取比DRAM快。SRAM對諸如光和電噪聲這樣的干擾不敏感。代價是SRAM單元比DRAM單元使用更多的晶體管,因而密集度低,而且更貴,功耗更大。

每位晶體管數 相對訪問時間 持續(xù)的 敏感的 相對花費 應用
SRAM 6 1X 1000X 高速緩存存儲器
DRAM 1 10X 1X 主存,幀緩沖區(qū)

傳統(tǒng)的DRAM

??DRAM芯片中的單元(位)被分成d個超單元( supercell),每個超單元都由w個DRAM單元組成。一個\(d \times w\)的DRAM總共存儲了\(dw\)位信息。超單元被組織成一個r行c列的長方形陣列,這里rc=d。每個超單元有形如(i,j)的地址,這里i表示行,而j表示列。

??例如,如下圖所示是一個16×8的DRAM芯片的組織,有d=16個超單元,每個超單元有w=8位,r=4行,c=4列。帶陰影的方框表示地址(2,1)處的超單元。信息通過稱為引腳(pin)的外部連接器流入和流出芯片。每個引腳攜帶一個1位的信號。下圖給出了兩組引腳:8個data引腳,它們能傳送一個字節(jié)到芯片或從芯片傳出一個字節(jié),以及2個addr引腳,它們攜帶2位的行和列超單元地址。其他攜帶控制信息的引腳沒有顯示出來。

image-20201212092653332

??每個DRAM芯片被連接到某個稱為內存控制器( memory controller)的電路,這個電路可以一次傳送w位到每個DRAM芯片或一次從每個DRAM芯片傳出w位。為了讀出超單元(i,j)的內容,內存控制器將行地址i發(fā)送到DRAM,然后是列地址j。DRAM把超單元(i,j)的內容發(fā)回給控制器作為響應。行地址i稱為RAS( Row Access strobe,行訪問選通脈沖)請求。列地址j稱為CAS( Column Access strobe,列訪問選通脈沖)請求。注意,RAS和CAS請求共享相同的DRAM地址引腳。

??例如,要從圖6-3中16×8的DRAM中讀出超單元(2,1),內存控制器發(fā)送行地址2,如下圖a所示。DRAM的響應是將行2的整個內容都復制到一個內部行緩沖區(qū)。接下來,內存控制器發(fā)送列地址1,如下圖b所示。DRAM的響應是從行緩沖區(qū)復制出超單元(2,1)中的8位,并把它們發(fā)送到內存控制器。

image-20201212093003882

??電路設計者將DRAM組織成二維陣列而不是線性數組的一個原因是降低芯片上地址引腳的數量。例如,如果示例的128位DRAM被組織成一個16個超單元的線性數組,地址為0~15,那么芯片會需要4個地址引腳而不是2個。二維陣列組織的缺點是必須分兩步發(fā)送地址,這增加了訪問時間。

增強的DRAM

??可以通過以下方式提高訪問基本DRAM的速度。

??快頁模式DRAM( Fast Page Mode dram, FPM DRAM)。傳統(tǒng)的DRAM將超單元的一整行復制到它的內部行緩沖區(qū)中,使用一個,然后丟棄剩余的。FPM DRAM允許對同一行連續(xù)地訪問可以直接從行緩沖區(qū)得到服務。

假如要讀取第4行的3個超單元,傳統(tǒng)DRAM需要發(fā)出3次RAS,CAS。而FPM DRAM只需要發(fā)出一次RAS,CAS,后面跟2個CAS即可。

? 擴展數據輸出DRAM( Extended Data Out Dram, EDO DRAM)。 FPM DRAM的個增強的形式,它允許各個CAS信號在時間上靠得更緊密一點。

??同步DRAM( Synchronous DRaM, SDRAM)。 SDRAM用與驅動內存控制器相同的外部時鐘信號的上升沿來代替許多這樣的控制信號。最終效果就是 SDRAM能夠比那些異步的存儲器更快地輸出它的超單元的內容。

??雙倍數據速率同步DRAM( Double data- Rate SynchronouS DRAm, DDR SDRAM)。DDR SDRAM是對 SDRAM的一種增強,它通過使用兩個時鐘沿作為控制信號,從而使DRAM的速度翻倍。不同類型的 DDR SDRAM是用提高有效帶寬的很小的預取緩沖區(qū)的大小來劃分的:DDR(2位)、DDR2(4位)和DDR(8位)。

??視頻RAM( Video ram,VRAM)。它用在圖形系統(tǒng)的幀緩沖區(qū)中。VRAM的思想與 FPM DRAM類似。兩個主要區(qū)別是:1)VRAM的輸出是通過依次對內部緩沖區(qū)的整個內容進行移位得到的;2)VRAM允許對內存并行地讀和寫。因此,系統(tǒng)可以在寫下一次更新的新值(寫)的同時,用幀緩沖區(qū)中的像素刷屏幕(讀)。

非易失性存儲器

??如果斷電,DRAM和SRAM會丟失它們的信息,從這個意義上說,它們是易失的( volatile)。另一方面,非易失性存儲器( nonvolatile memory)即使是在關電后,仍然保存著它們的信息。

??對EPROM編程是通過使用一種把1寫人 EPROM的特殊設備來完成的。 EPROM能夠被擦除和重編程的次數的數量級可以達到1000次。EEPROM能夠被編程的次數的數量級可以達到10次。

??閃存( flash memory)是一類非易失性存儲器,基于 EEPROM,它已經成為了一種重要的存儲技術。

訪問主存

??數據流通過稱為總線(bus)的共享電子電路在處理器和DRAM主存之間來來回回。每次CPU和主存之間的數據傳送都是通過一系列步驟來完成的,這些步驟稱為總線事務( bus transaction)。讀事務( read transaction)從主存?zhèn)魉蛿祿紺PU。寫事務( write trans-action)從CPU傳送數據到主存。

??總線是一組并行的導線,能攜帶地址、數據和控制信號。取決于總線的設計,數據和地址信號可以共享同一組導線,也可以使用不同的。同時,兩個以上的設備也能共享同一總線??刂凭€攜帶的信號會同步事務,并標識出當前正在被執(zhí)行的事務的類型。例如,當前關注的這個事務是到主存的嗎?還是到諸如磁盤控制器這樣的其他I/O設備?這個事務是讀還是寫?總線上的信息是地址還是數據項?

??展示了一個示例計算機系統(tǒng)的配置。主要部件是CPU芯片、我們將稱為IO橋接器(I/ O bridge)的芯片組(其中包括內存控制器),以及組成主存的DRAM內存模塊這些部件由一對總線連接起來,其中一條總線是系統(tǒng)總線( system bus),它連接CPU和I/O橋接器,另一條總線是內存總線( memory bus),它連接I/O橋接器和主存。I/O橋接器將系統(tǒng)總線的電子信號翻譯成內存總線的電子信號。

image-20201212101344668

局部性

??一個編寫良好的計算機程序常常具有良好的局部性( locality)。也就是,它們傾向于引用鄰近于其他最近引用過的數據項的數據項,或者最近引用過的數據項本身。這種傾向性,被稱為局部性原理( principle of locality),是一個持久的概念,對硬件和軟件系統(tǒng)的設計和性能都有著極大的影響。局部性通常有兩種不同的形式:時間局部性( temporal locality)和空間局部性( spatial locality)。在一個具有良好時間局部性的程序中,被引用過一次的內存位置很可能在不遠的將來再被多次引用。在一個具有良好空間局部性的程序中,如果一個內存位置被引用了次,那么程序很可能在不遠的將來引用附近的一個內存位置。一般而言,有良好局部性的程序比局部性差的程序運行得更快。

??如下所示的函數sumvec,它對一個向量的元素求和。在這個例子中,變量sum在每次循環(huán)迭代中被引用一次,因此,對于sum來說,有好的時間局部性。另一方面,因為sun是標量,對于sum來說,沒有空間局部性。

int sumvec(int v[N])
{
    int i,sum = 0;
    for (i = 0; i < N; i++)
        sum += v[i];
    return sum;
}
引用模式:
地址:			0		4		8		12		16
內容:			v0		v1		v2		v3		v4
訪問順序:		1		2		3		4		5

??如上所示,向量v的元素是被順序讀取的,一個接一個,按照它們存儲在內存中的順序(為了方便,我們假設數組是從地址0開始的)。因此,對于變量v,函數有很好的空間局部性,但是時間局部性很差,因為每個向量元素只被訪問一次。

步長為1的引用模式為順序引用模式( sequential reference pattern)。一個連續(xù)向量中,每隔k個元素進行訪問,就稱為步長為k的引用模式( stride-k reference pattern)。步長為1的引用模式是程序中空間局部性常見和重要的來源。一般而言,隨著步長的增加,空間局部性下降。

??如下的函數 sumarrayrows,它對一個二維數組的元素求和。雙重嵌套循環(huán)按照行優(yōu)先順序(row major order)讀數組的元素。也就是,內層循環(huán)讀第一行的元素,然后讀第二行,依此類推。函數 sumarrayrows具有良好的空間局部性,因為它按照數組被存儲的行優(yōu)先順序來訪問這個數組。其結果是得到一個很好的步長為1的引用模式,具有良好的空間局部性。

int sum_array_rows(int a[M][N])
{
    int i, j, sum = 0;

    for (i = 0; i < M; i++)
        for (j = 0; j < N; j++)
            sum += a[i][j];
    return sum;
}
引用模式:
地址:			0		4		8		12		16
內容:			a00		a01		a02		a10		a11
訪問順序:		1		2		3		4		5

存儲器層次結構

??存儲技術和計算機軟件的一些基本的和持久的屬性:
??存儲技術:不同存儲技術的訪問時間差異很大。速度較快的技術每字節(jié)的成本要比速度較慢的技術高,而且容量較小。CPU和主存之間的速度差距在增大。
??計算機軟件:一個編寫良好的程序傾向于展示出良好的局部性。

??硬件和軟件的這些基本屬性互相補充得很完美。它們這種相互補充的性質使人想到一種組織存儲器系統(tǒng)的方法,稱為存儲器層次結構( memory hierarchy),下圖展示了一個典型的存儲器層次結構。一般而言,從高層往底層走,存儲設備變得更慢、更便宜和更大。在最高層(L0),是少量快速的CPU寄存器,CPU可以在一個時鐘周期內訪問它們。接下來是一個或多個小型到中型的基于SRAM的高速緩存存儲器,可以在幾個CPU時鐘周期內訪問它們。然后是一個大的基于DRAM的主存,可以在幾十到幾百個時鐘周期內訪問它們。接下來是慢速但是容量很大的本地磁盤。最后,有些系統(tǒng)甚至包括了一層附加的遠程服務器上的磁盤,要通過網絡來訪問它們。

image-20201212112607240

存儲器結構中的緩存

??一般而言,高速緩存( cache,讀作“cash”)是一個小而快速的存儲設備,它作為存儲在更大、也更慢的設備中的數據對象的緩沖區(qū)域。使用高速緩存的過程稱為緩存( caching,讀作“ cashing")。

??存儲器層次結構的中心思想是,對于每個k,位于k層的更快更小的存儲設備作為位于k+1層的更大更慢的存儲設備的緩存。換句話說,層次結構中的每一層都緩存來自較低一層的數據對象。

??數據總是以塊大小為傳送單元( transfer unit)在第k層和第k+1層之間來回復制的。雖然在層次結構中任何一對相鄰的層次之間塊大小是固定的,但是其他的層次對之間可以有不同的塊大小。如上圖所示,L1和L0之間的傳送通常使用的是1個字大小的塊。L2和L1之間(以及L3和I2之間、I4和I3之間)的傳送通常使用的是幾十個字節(jié)的塊。而L5和L4之間的傳送用的是大小為幾百或幾千字節(jié)的塊。一般而言,層次結構中較低層(離CPU較遠)的設備的訪問時間較長,因此為了補償這些較長的訪問時間,傾向于使用較大的塊。

緩存命中

??當程序需要第k+1層的某個數據對象d時,它首先在當前存儲在第k層的一個塊中查找d。如果d剛好緩存在第k層中,那么就是我們所說的緩存命中( cache hit)。

緩存不命中

??另一方面,如果第k層中沒有緩存數據對象d,那么就是我們所說的緩存不命中( cache miss)。當發(fā)生緩存不命中時,第k層的緩存從第k+1層緩存中取出包含d的那個塊,如果第k層的緩存已經滿了,可能就會覆蓋現存的一個塊。(緩存的替換策略:隨機替換替換策略,最少被使用(LRU)替換策略)。

緩存不命中種類

??區(qū)分不同種類的緩存不命中有時候是很有幫助的。如果第k層的緩存是空的,那么對任何數據對象的訪問都會不命中。一個空的緩存有時被稱為冷緩存( cold cache),此類不命中稱為強制性不命中( compulsory miss)或冷不命中( cold miss)。冷不命中很重要,因為它們通常是短暫的事件,不會在反復訪問存儲器使得緩存暖身( warmed up)之后的穩(wěn)定狀態(tài)中出現。

緩存管理

??存儲器層次結構的本質是,每一層存儲設備都是較低一層的緩存。在每一層上,某種形式的邏輯必須管理緩存。這里,我們的意思是指某個東西要將緩存劃分成塊,在不同的層之間傳送塊,判定是命中還是不命中,并處理它們。管理緩存的邏輯可以是硬件、軟件,或是兩者的結合。

高速緩存存儲器

??高速緩存關于讀的操作非常簡單。首先,在高速緩存中查找所需字\(w\)的副本。如果命中,立即返回字\(w\)給CPU。如果不命中,從存儲器層次結構中較低層中取出包含字\(w\)的塊,將這個塊存儲到某個高速緩存行中(可能會驅逐一個有效的行),然后返回字\(w\)

??寫的情況就要復雜一些了。假設我們要寫一個已經緩存了的字\(w\)(寫命中, write hit)。在高速緩存更新了它的\(w\)的副本之后,怎么更新\(w\)在層次結構中緊接著低一層中的副本呢?最簡單的方法,稱為直寫( write-through),就是立即將\(w\)的高速緩存塊寫回到緊接著的低一層中。雖然簡單,但是直寫的缺點是每次寫都會引起總線流量。另一種方法,稱為寫回( write-back),盡可能地推遲更新,只有當替換算法要驅逐這個更新過的塊時,才把它寫到緊接著的低一層中。由于局部性,寫回能顯著地減少總線流量,但是它的缺點是增加了復雜性。高速緩存必須為每個高速緩存行維護一個額外的修改位( dirty bit),表明這個高速緩存塊是否被修改過。

??另一個問題是如何處理寫不命中。一種方法,稱為寫分配( write-allocate),加載相應的低一層中的塊到高速緩存中,然后更新這個高速緩存塊。寫分配試圖利用寫的空間局部性,但是缺點是每次不命中都會導致一個塊從低一層傳送到高速緩存。另一種方法,稱為非寫分配(not- write-allocate),避開高速緩存,直接把這個字寫到低一層中。直寫高速緩存通常是非寫分配的。寫回高速緩存通常是寫分配的。

??高速緩存既保存數據,也保存指令。只保存指令的高速緩存稱為 i-cache。只保存程序數據的高速緩存稱為 d-cache。既保存指令又包括數據的高速緩存稱為統(tǒng)一的高速緩存( unified cache)?,F代處理器包括獨立的 i-cache和d-cache。這樣做有很多原因。有兩個獨立的高速緩存,處理器能夠同時讀一個指令字和一個數據字。 i-cache通常是只讀的,因此比較簡單。通常會針對不同的訪問模式來優(yōu)化這兩個高速緩存,它們可以有不同的塊大小,相聯度和容量。使用不同的高速緩存也確保了數據訪問不會與指令訪問形成沖突不命中,反過來也是一樣,代價就是可能會引起容量不命中增加。

編寫高速緩存友好的代碼

??確保代碼高速緩存友好的基本方法。
??1)讓最常見的情況運行得快。程序通常把大部分時間都花在少量的核心函數上,而這些函數通常把大部分時間都花在了少量循環(huán)上。所以要把注意力集中在核心函數里的循環(huán)上,而忽略其他部分。
??2)盡量減小每個循環(huán)內部的緩存不命中數量。在其他條件(例如加載和存儲的總次數)相同的情況下,不命中率較低的循環(huán)運行得更快。

??考慮如下的函數

int sumvec(int v[N])
{
	int i,sum = 0;
    
	for(i = 0;i<N;i++)
		sum +=v[i];
	return sum;
}

??首先,注意對于局部變量i和sum,循環(huán)體有良好的時間局部性?,F在考慮一下對向量v的步長為1的引用。一般而言,如果一個高速緩存的塊大小為B字節(jié),那么一個步長為k的引用模式(這里k是以字為單位的)平均每次循環(huán)迭代會有\(\min (1,(wordsize \times k)/B)\)次緩存不命中。當k=1時,它取最小值,所以對v的步長為1的引用確實是高速緩存友好的。

??例如,假設v是塊對齊的,字為4個字節(jié),高速緩存塊為4個字,而高速緩存初始為空(冷高速緩存)。在這個例子中,對v[0]的引用會不命中,而相應的包含v[0] ~v[3]的塊會被從內存加載到高速緩存中。因此,接下來三個引用都會命中。對v[4]的引用會導致不命中,而個新的塊被加載到高速緩存中,接下來的三個引用都命中,依此類推。總的來說,四個引用中,三個會命中,在這種冷緩存的情況下,這是我們所能做到的最好的情況了。

??總之,簡單的 sumvec示例說明了兩個關于編寫高速緩存友好的代碼的重要問題:第一,對局部變量的反復引用是好的,因為編譯器能夠將它們緩存在寄存器文件中(時間局部性)。第二,步長為1的引用模式是好的,因為存儲器層次結構中所有層次上的緩存都是將數據存儲為連續(xù)的塊(空間局部性)。

總結

??本章主要介紹了各種各樣的存儲系統(tǒng)及其原理,一般來說,較小、較快的設備在頂部,較大、較慢的設備在底部。因為編寫良好的程序有好的局部性,大多數數據都可以從較高層得到服務,結果就是存儲系統(tǒng)能以較高層的速度運行,但卻有較低層的成本和容量。我們可以通過編寫有良好空間和時間局部性的程序來顯著地改進程序的運行時間。例如,可以利用基于SRAM的高速緩存存儲器。主要原因是從高速緩存取數據的程序比主要從內存取數據的程序運行得快得多。

?

    本站是提供個人知識管理的網絡存儲空間,所有內容均由用戶發(fā)布,不代表本站觀點。請注意甄別內容中的聯系方式、誘導購買等信息,謹防詐騙。如發(fā)現有害或侵權內容,請點擊一鍵舉報。
    轉藏 分享 獻花(0

    0條評論

    發(fā)表

    請遵守用戶 評論公約

    類似文章 更多