入職後,我才明白什麼叫Cache
#前言
#事情其實是這樣的,當時領導者交給我一個perf硬體效能監視的任務,在使用perf的過程中,輸入指令perf list,我看到了以下資訊:

我的任務就要讓這些cache事件能夠正常計數,但關鍵是,我根本不知道這些misses
、loads
是什麼意思。
我只知道它們都是cache,但這幾個名字十分類似,又有什麼差別?
出於此,當時我覺得我有必要去學一下cache的知識了,我對cache、效能等的了解也因此開始。
以下是我當時學習cache總結的一些基本概念知識,對於不了解底層或不了解cache的人,相信都會有幫助。
基本上是以問答的方式引導大家,因為我曾經也是一堆疑問走過來的。
1、什麼是Cache?
首先我們要知道,cpu存取內存,不是直接存取的,而是需要先經過Cache,為什麼呢?
原因:cpu內的資料是儲存在暫存器中,存取暫存器的速度很快,但是暫存器容量小。而記憶體容量大,但是速度慢。 為了解決cpu和記憶體之間速度和容量的問題,引進了快取Cache。
Cache位於CPU與主記憶體之間,CPU存取主記憶體時,先去存取Cache,看Cache中有沒有這個數據,如果有,就從Cache中拿資料回傳給CPU;如果Cache裡沒有數據,再去存取主記憶體。
2、多層Cache儲存結構
通常來說,Cache不只一個,而是有多個,也就是多層Cache,為什麼呢?
原因:cpu存取cache速度也是很快的。但是我們做不到速度和容量完全相容,如果cpu存取cache的速度跟cpu存取暫存器的速度差不多,那麼就代表這個cache速度很快,但是容量很小,這麼小的cache容量還不足夠滿足我們的需求,因此引入了多層Cache。
多層Cache將Cache分成多個等級L1、L2、L3等。
依速度快慢,依序為L1>L2>L3。
依照儲存容量大小,依序為L3>L2>L1。

L1最靠近CPU,L3最靠近主記憶體。
通常L1又分成instruction cache(ICache
)和data cache(DCache
),並且L1 cache是cpu私有的,每個cpu都有一個L1 cache。
3、「命中」和「缺失」是什麼意思?
命中:CPU要存取的資料在cache中有緩存,稱為“命中”,即cache hit
缺少:CPU要存取的資料在cache中沒有緩存,稱為“缺失”,即cache miss
4、什麼是cache line?
cache line
:快取行,將cache平均分成相等的許多區塊,每個區塊大小稱為cache line
。
cache line也是cache和主記憶體之間資料傳輸的最小單位.
當CPU試圖load一個位元組資料的時候,如果cache缺失,那麼cache控制器就會從主記憶體中一次性的load cache line大小的資料到cache。例如,cache line大小是8位元組。 CPU即使讀取一個byte,在cache缺失後,cache會從主記憶體load 8位元組填入整個cache line。
CPU存取cache時的位址編碼,通常由tag、index和offset三部分組成:

##tag (標記域):用來判斷cache line快取的資料的位址是否和處理器尋址位址一致。
index(索引網域):用於索引並尋找位址在快取中的哪一行
#offset (偏移量):快取行中的偏移量。可以按字或位元組來尋址高速緩存行的內容
5、cache存取的是虛擬位址還是實體位址?
我們知道,CPU存取記憶體不是直接存取的,而是CPU發出虛擬位址,然後經過MMU轉換為物理位址後,根據物理位址從內存取數據。 那麼cache存取的是虛擬位址還是實體位址?
答:不一定。既可以是虛擬位址,也可以是實體位址,也可以是虛擬位址和實體位址的組合。
因為cache在硬體設計上有多種組織方式:
#VIVT
虛擬快取:虛擬地址的index,虛擬地址的tag。PIPT
物理快取:物理位址的index,物理位址的tag。VIPT
實體標記的虛擬快取:虛擬位址的index,實體位址的tag。
6、什麼是歧義和別名問題?
歧義(homonyms
):相同的虛擬位址對應不同的實體位址
別名(alias
):多個虛擬位址對應到了相同的實體位址(多個虛擬位址稱為別名)。
例如上述VIVT方式就會有別名問題,那VIVT、PIPT和VIPT那個方式比較好呢?
PIPT
其實是比較理想的,因為index和tag都使用了實體位址,軟體層面不需要任何維護就能避免歧義和別名問題。
VIPT
的tag使用了實體位址,所以不存在歧義問題,但index是虛擬位址,所以可能也存在別名問題。
而VIVT
的方式,歧義和別名問題都存在。
實際上,現在硬體中使用的基本是PIPT或VIPT。 VIVT問題太多,已經成為歷史了,不會有人用。另外PIVT的方式是不存在的,因為它只有缺點沒有優點,不只速度慢,歧義和別名問題也都存在。
cache的組織方式,以及歧義和別名問題,是比較大塊的內容。這裡只需要知道cache存取的位址可以是虛擬位址,也可以是實體位址,也可以是虛擬位址和實體位址的組合。而不同的組織方式會有歧義和別名問題。
7、Cache分配策略?
指的是發生cache miss時,cache如何分配。
讀取分配:當CPU
讀取資料時,發生cache
缺失,這種情況會分配一個cache line
緩存從主存讀取的資料。 預設情況下,cache
都支援讀取分配。
寫入分配:當CPU寫入資料發生cache
#缺失時,才會考慮寫入分配策略。當我們不支援寫入分配的情況下,寫指令只會更新主存數據,然後就結束了。當支援寫入分配的時候,我們先從主記憶體載入資料到cache line
中(相當於先做個讀分配動作),然後會更新cache line
中的數據。
8、Cache更新策略?
指的是cache命中時,寫入操作應該如何更新資料。
寫直通:當CPU執行store指令並在cache命中時,我們更新cache中的資料並且更新主記憶體中的資料。 cache和主記憶體的資料總是保持一致。
寫回:當CPU
執行store
指令並在cache
命中時,我們只更新cache
中的數據。而每個cache line
中會有一個bit
位元記錄資料是否被修改過,稱為dirty bit
。我們會將dirty bit
置位。主記憶體中的資料只會在cache line
被取代或顯示的clean
作業時更新。因此,主記憶體中的數據可能是未修改的數據,而修改的數據躺在cache中。 cache和主記憶體的資料可能不一致。
最後
#關於cache的內容,還有TLB、MESI、記憶體一致性模型等等等,是一個需要沉澱和總結才能真正掌握的東西。
但可能很多人都用不上,只有牽涉到效能問題,當你需要提高cache命中率時,才知道這些知識的重要性。
關於本文所講的知識,總結了一份cache基礎知識的心智圖:
以上是入職後,我才明白什麼叫Cache的詳細內容。更多資訊請關注PHP中文網其他相關文章!

熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

AI Hentai Generator
免費產生 AI 無盡。

熱門文章

熱工具

記事本++7.3.1
好用且免費的程式碼編輯器

SublimeText3漢化版
中文版,非常好用

禪工作室 13.0.1
強大的PHP整合開發環境

Dreamweaver CS6
視覺化網頁開發工具

SublimeText3 Mac版
神級程式碼編輯軟體(SublimeText3)

熱門話題

事情其實是這樣的,當時領導者交給我一個perf硬體效能監視的任務,在使用perf的過程中,輸入指令perf list,我看到了以下資訊:我的任務就要讓這些cache事件能夠正常計數,但重點是,我根本不知道這些misses、loads是什麼意思。

使用cache可以提高電腦運行速度這是因為Cache縮短了CPU的等待時間。 Cache是位於CPU和主記憶體DRAM之間,規模較小,但速度很高的記憶體。 Cache的功能是提高CPU資料輸入輸出的速率;Cache容量小但速度快,記憶體速度較低但容量大,透過最佳化調度演算法,系統的效能會大幅提升。

cache叫做高速緩衝記憶體,是介於中央處理器與主記憶體之間的高速小容量記憶體,一般由高速SRAM構成;這種局部記憶體是面向CPU的,引進它是為減少或消除CPU與記憶體之間的速度差異對系統性能帶來的影響。 Cache容量小但速度快,記憶體速度較低但容量大,透過最佳化調度演算法,系統的效能會大幅提升。

以下是nginx反向代理快取的教學:安裝nginx:sudoaptupdatesudoaptinstallnginx設定反向代理:開啟nginx設定檔:sudonano/etc/nginx/nginx.conf在http區塊中加入以下設定來啟用快取:http{...proxy_cache_path /var/cache/nginxlevels=1:2keys_zone=my_cache:10mmax_size=10ginactive=60muse_temp_path=off;proxy_cache

前言快取可以透過將經常存取的資料儲存在記憶體中,減少底層資料來源如資料庫的壓力,從而有效提高系統的效能和穩定性。我想大家的專案中或多或少都有使用過,我們專案也不例外,但是最近在review公司的程式碼的時候寫的很蠢且low,大致寫法如下:publicUsergetById(Stringid){Useruser=cache. getUser();if(user!=null){returnuser;}//從資料庫取得user=loadFromDB(id);cahce.put(id,user);returnu

nginx快取cache的5種方案 1、傳統快取之一(404) 這個辦法是把nginx的404錯誤導向到後端,然後用proxy_store把後端回傳的頁面儲存。設定: location/{ root/home/html/;#主目錄expires1d;#網頁的過期時間error_page404=200/fetch$request_uri;#404定向到/fetch目錄下} location/fetch/{#404定向到/fetch目錄下} location/fetch/{#4044042cation} ;#指明這個目錄不能在外部直接訪

cache的特性:在CPU與主記憶體之間設定的一級或兩級高速小容量記憶體,其資訊是隨著電腦的斷電自然遺失。 ROM的特性:只能從記憶體讀取數據,而不能往裡面寫訊息,電腦斷電後數據仍然存在。 ram的特點:既可以從記憶體讀取數據,也可以到記憶體中寫入資訊;用於存放運行程式所需的命令、程式和資料等;電腦斷電後資訊自然遺失。

具體如下:一、聊聊什麼是硬程式編碼使用快取?在學習SpringCache之前,筆者常會硬編碼的方式使用快取。我們來舉個實際中的例子,為了提升使用者資訊的查詢效率,我們對使用者資訊使用了緩存,範例程式碼如下:@AutowireprivateUserMapperuserMapper;@AutowireprivateRedisCacheredisCache;//查詢使用者publicUsergetUserById(LonguserId){//定義快取keyStringcache= "userId_