1. 程式人生 > >GlusterFS企業級功能之EC糾刪碼

GlusterFS企業級功能之EC糾刪碼

在這個資料爆炸的時代,很多行業不得不面臨資料快速增長的挑戰,為了應對呈爆炸式增長態勢的資料量,構建大規模的儲存系統成了一種普遍的應用需求。但資料是如此重要,如何保證儲存可靠性、資料可用性成了大規模儲存系統的難點和要點。資料冗餘是保障儲存可靠性、資料可用性的最有效手段,傳統的冗餘機制主要有副本(Replication)和糾刪編碼(Erasure Code,以下簡稱糾刪碼或EC)兩種方式。

副本是將每個原始資料分塊都映象複製到另一儲存介質上,從而保證在原始資料失效後,資料仍然可用並能通過副本資料恢復。在副本機制中,資料的可靠性和副本數是呈正相關,副本數越多,資料可用性越好,可靠性也越高,但也意味著更低的空間利用率以及更高的成本。在大規模儲存系統中,節點出現故障併發生失效是一種大概率事件,這也就意味著雙副本並不能滿足企業對儲存可靠性的需求,但三副本的儲存開銷太大,高達200%,且隨著儲存規模的增大,對儲存系統的開銷(如容量空間成本、運營成本等)都將顯著增加。

相較於副本機制,糾刪碼機制具有更高的儲存效率,在提供相同儲存可靠性的條件下,可以最小化冗餘儲存開銷。糾刪碼機制在網路環境下,其高儲存效率的特性還能能顯著降低網路中的資料流量,也就意味著在大規模儲存系統中使用糾刪碼機制能夠節約網路頻寬和儲存空間。所以在大規模儲存的應用場景中,糾刪碼機制成了保證儲存可靠性、資料可用性的最佳選擇。

一、儲存應用中的糾刪碼

(一)什麼是糾刪碼

糾刪碼本身是一種編碼容錯技術,起源於通訊傳輸領域,用來解決通訊過程中部分資料在傳輸過程中丟失的問題。其基本原理是傳送端把需要傳輸的訊號分段,然後加入一定的校驗並讓各訊號段之間間產生一定的聯絡,最後統一把所有訊號段向接收端傳送;如果在傳輸過程中有部分訊號丟失,接收端仍可以通過演算法把完整的資訊計算出來,從而保證了兩端之間的可靠通訊。其原理如下圖所示:

糾刪碼

圖1:糾刪碼的原理圖

客戶端,把原始資料資訊切分為k塊source data,然後通過糾刪碼Encoder生成n塊encoded data,最後統一向服務端傳輸;服務端,只要能夠接收到k` >= k塊的encoded data,就能夠通過糾刪碼decoder出所有的source data。

(二)糾刪碼的分類

按照誤碼控制的不同功能,可分為檢錯、糾錯和糾刪三種類型。檢錯碼僅具備識別錯碼功能而無糾正錯碼功能;糾錯碼不僅具備識別錯碼功能,同時還具備糾正錯碼功能;糾刪碼則不僅具備識別錯碼和糾正錯碼的功能,而且當錯碼超過糾正範圍時,還可把無法糾錯的資訊刪除。

按照儲存單元連線方式的不同,可分為基於高速匯流排方式的磁碟陣列、基於LAN方式的叢集儲存和基於WAN/Internet方式的廣域網路儲存系統。陣列碼是一種特殊化的糾刪碼,其採用高效率的異或運算(XOR),如RAID5、RAID6等。叢集儲存系統中,如HDFS的HDFS-RAID、PanFS支援RAID-5容錯編碼、Google的GFSⅡ、微軟的WAS等;廣域網下,如RACS、DepSky等;開源的叢集儲存系統中,如GlusterFS的EC卷、ceph糾刪碼等。

糾刪碼常見的有裡德-所羅門碼Reed-Solomen(簡稱RS)、級聯低密度糾刪碼和數字噴泉碼三類。目前在儲存行業內的應用中,主要使用的是RS類糾刪碼,比如光碟儲存中使用 RS 碼進行容錯,防止光碟上的劃痕導致資料不可讀;生活中經常使用的二維碼就利用了RS碼來提高識別的成功率。主要原因就是,RS類碼是唯一可以滿足任意磁碟數目N和校驗資料M中丟失M塊後能恢復的Maximum Distance Separable(簡稱MDS)編碼,所以下文中主要以RS類碼來介紹糾刪碼在儲存應用中的使用原理。

(三)糾刪碼在儲存應用中的使用原理

在大規模儲存應用場景中,節點故障、資料失效是一種常態,使用糾刪碼來保證儲存可靠性、資料可用性是目前的最有效方式之一。其原理是將檔案資料分割成N個大小相同的原始資料塊,然後編碼生成M個大小相同的校驗資料塊(注:原始資料塊和校驗資料塊大小相同),最後將原始資料塊和校驗資料塊分別儲存在不同的位置,如不同的磁碟、不同的儲存節點等。糾刪碼的容錯能力正是來源於這些校驗資料塊,在1~M個數據塊(注:原始資料或校驗都行)損壞的情況下,整體資料仍然可以通過剩餘的資料塊計算得出,確保了資料仍的高可用性。

糾刪碼儲存的存取過程包含編碼、修改、解碼三種基本操作。以(6,2)RS碼為例,檔案劃分為4個原始資料塊{D1,D2,D3,D4},經過編碼得到{P1,P2}2個校驗資料塊;當原始資料塊D4被更新為D4’時,校驗資料塊{P1,P2 }也要重新編碼更新為{P1’,P2’ };藉助解碼函式,可根據任意4個數據塊(如{D1,D2,D3,P1’})重構出所有的資料塊。

糾刪碼操作

圖2:糾刪碼的三種基本操作

糾刪碼儲存的資料恢復過程主要利用編碼、解碼來恢復丟失的資料。同樣以(6,2)RS碼為例,檔案劃分為4個原始資料塊{D1,D2,D3,D4},經過編碼得到{P1,P2}2個校驗資料塊,然後把所有資料塊統一儲存。

當原始資料分塊D4丟失時,可根據{D1,D2,D3,P1,P2}中任意4個數據塊解碼計算出原始資料塊D4。

糾刪碼資料恢復

圖3:糾刪碼儲存的資料分塊恢復

當校驗資料塊P2丟失時,可根據{D1,D2,D3,D4,P1 }中任意4個數據塊編碼計算出校驗資料塊P2。

糾刪碼校驗恢復

圖4:糾刪碼儲存的校驗分塊恢復

在(6,2)RS碼為例的糾刪碼儲存中,其冗餘度為2,即最多可以同時丟失2塊資料塊,當丟失的資料塊個數大於2時,丟失資料塊就不可恢復了。

二、基於EC的開源實現技術

現今,基於糾刪碼的開源實現技術主要有Intel ISA-L、Jerasure等庫,以下就來簡單介紹一下這兩種庫:

(一)Intel ISA-L

Intel ISA-L(Intelligent Storage Acceleration Library),即英特爾智慧儲存加速庫,是英特爾公司開發的一套專門用來加速和優化基於英特爾架構(IntelArchitecture,IA)儲存的lib庫,可在多種英特爾處理器上執行,能夠最大程度提高儲存吞吐量,安全性和靈活性,並減少空間使用量。該庫還可加速RS碼的計算速度,通過使用AES-NI、SSE、AVX、AVX2等指令集來提高計算速度,從而提高編解碼效能。同時還可在儲存資料可恢復性、資料完整性性、資料安全性以及加速資料壓縮等方面提供幫助,並提供了一組高度優化的功能函式,主要有:RAID函式、糾刪碼函式、CRC(迴圈冗餘檢查)函式、緩衝雜湊(MbH)函式、加密函式壓縮函式等。

(二)Jerasure

Jerasure是美國田納西大學Plank教授開發的C/C++糾刪碼函式庫,提供Reed-Solomon和Cauchy Reed-Solomon兩種編碼演算法的實現。Jerasure有1.2和 2.0兩個常用版本,Jerasure 2.0為目前的最新版本,可藉助intel sse指令集來加速編解碼,相比1.2版本有較大的提升。Jerasure庫分為5個模組,每個模組包括一個頭檔案和實現檔案。
(1)galois.h/galois.c:提供了伽羅華域算術運算。
(2)jerasure.j/jerasure.c:為絕大部分糾刪碼提供的核心函式,它只依賴galois模組。這些核心函式支援基於矩陣的編碼與解碼、基於位矩陣的編碼與解碼、位矩陣變換、矩陣轉置和位矩陣轉置。
(3)reedsol.h/reedsol.c:支援RS編/解碼和優化後的RS編碼。
(4)cauchy.h/Cauchy.c:支援柯西RS編解碼和最優柯西RS編碼。
(5)liberation.h/liberation.c:支援Liberation RAID-6編碼啊、Blaum-Roth編碼和Liberation RAID-6編碼。其中,Liberation是一種最低密度的MDS編碼。這三種編碼採用位矩陣來實現,其效能優於現在有RS碼和EVENODD,在某種情況下也優於RDP編碼。

(三)Intel ISA VS Jerasure

Intel ISA-L庫和Jerasure庫都能加速RS碼的計算速度。其中,ISA-L 庫對於加速RS碼的計算速度效果更好,是目前業界最佳。ISA-L 之所以速度快,主要有兩點,一是由於Intel 諳熟彙編優化之道,ISA-L直接使用匯編程式碼;二是因為它將整體矩陣運算搬遷到彙編中進行。但這導致了彙編程式碼的急劇膨脹,令人望而生畏。另外,ISA-L 未對 vandermonde 矩陣做特殊處理,而是直接拼接單位矩陣作為其編碼矩陣,因此在某些引數下會出現編碼矩陣線性相關的問題。

雖然Jerasure2.0庫相較ISA-L 庫對於加速RS碼的計算速度效果略差,但是Jerasure2.0庫在儲存應用中仍具有一些ISA-L 庫所沒有的優勢,如Jerasure2.0使用 C 語言封裝後的指令,讓程式碼更加的友好。另外Jerasure2.0 不僅僅支援 GF(2^8) 有限域的計算,其還可以進行 GF(2^4) – GF(2^128) 之間的有限域。並且除了 RS 碼,還提供了 Cauchy Reed-Solomon code(CRS碼)等其他編碼方法的支援。且在工業應用之外,其學術價值也非常高,是目前使用最為廣泛的編碼庫之一,開源的Ceph分散式儲存系統就是使用Jerasure庫作為預設的糾刪碼庫。

三、GlusterFS糾刪碼卷

2011年,Linux系統廠商RedHat紅帽以1.36億美元收購了網紅Gluster,然後基於紅帽企業的Linux作業系統構建了企業級的RedHat Gluster Storage儲存,並在過去的幾年裡,為其添加了一系列的企業級新功能,如EC(Erasure Code)糾刪碼卷、SSD Tier分層、Geo-Replication遠端複製等,顯著增強了GlusterFS儲存的效能、可靠性、靈活性與安全性。

在早期版本的GlusterFS儲存中,其中有兩種基本卷,Striped卷和Replicated卷。其中Striped卷提供了較高的物理磁碟空間利用率機制,但不提供容錯機制,即可靠性較差;Replicated卷提供了容錯機制,但對物理磁碟空間利用率較低。那麼可不可以結合Striped卷、Replicated卷兩者的優點,開發一種具有即能提供容錯機制、又能提高物理磁碟空間利用率的卷呢?於是有了EC糾刪碼卷的出現。在GlusterFS 3.6版本中釋出了一種基於Erasure Code所開發的新型別卷Dispersed卷和Distributed Dispersed卷,簡稱EC卷,類似於RAID5/6。

(一)EC卷的架構

在GlusterFS儲存中,EC卷是通過使用系統記憶體儲的資訊來重建丟失或損壞的資料,從而進一步加強對資料的保護。下面就簡單介紹EC卷的自修復過程:首先客戶端檢查元資料是否一致;如果不一致,則向服務端發出資料修復請求;服務端接收到請求後則會呼叫entrylk()和inodelk()兩個函式,先是和客戶端通訊確認,確認後,如果修復準備就緒,就開始對元資料進行修復;元資料修復成功後,下一步就是對資料塊的修復了,資料塊在修復期間是沒有鎖的;資料塊修復成功後會再次呼叫inodelk()函式,用於同步元資料(如擴充套件屬性),同步成功後,自修復也就完成了。其架構如下圖所示:

架構圖

圖5:架構圖

在GlusterFS儲存中,有兩種卷是基於erasure codes的,分別是Dispersed卷和Distributed Dispersed卷。其核心思想是以計算換容量,和RAID類似,同樣突破了單盤容量的限制,且能夠通過配置Redundancy(冗餘)級別來提高資料的可靠性,也就是說儲存系統底層不做RAID,使用EC卷就能提供大容量的儲存空間,還能保證較高的儲存可靠性。

Dispersed卷可以有任意多個bricks(B),且可配置冗餘度redunancy(R),R最小值為1,最大值為(B-1)/2。R的最小值不能為0的原因在於,如果當R的值為0時,卷就不提供容錯機制了,其效能還不如直接使用雜湊卷,所以限定R最小值為1;R的最大值為(B-1)/2的原因在於,當R的值為B/2時,其儲存利用率和replica-2複製卷相同,但其效能就遠遠不如replica-2複製捲了,所以限定其最大值為(B-1)/2。R最小值、最大值的確定使得B的最小值被確定為3,也就是說建立EC卷至少需要3個brick,才能建立成功。

Dispersed卷提高了儲存空間的利用率,其儲存利用率計算公式為(B-R)/B,有效儲存空間為(B-R)*Brick_size,在理論上儲存空間利用率可以達到99.9%。也就是說,能夠保證在提供一定容錯機制的情況下,最大限度的提高儲存利用率。

Dispersed卷提高了儲存的可靠性,只要任意大於等於B-R個brick能夠正常則資料可正常讀寫,就能夠保證資料是可用的、可恢復的;同時還優化了頻寬的使用,且部分檔案資料的分片失效引起的降級讀寫不影響其他檔案資料的讀寫。

Distributed Dispersed 卷可以通過擴充套件Dispersed 卷生成,即擴充套件一倍或n倍的bricks(B)。對比於Dispersed卷,其原理相同,但在相同的erasure codeing配置下,具有更好的I/O效能。所以下文中將主要以Dispersed捲來介紹EC卷的原理。

(二)EC卷的原理

1. Disperse卷的機制

Disperse卷中,會把每個讀寫請求切分為大小相同的Chunk塊,而每個Chunk塊又被分割成(B-R)個大小為512bytes的Fragment資料分片;然後使用演算法Rabin IDA計算生成R個大小為512bytes的Fragment校驗分片;最後把(B-R)個數據分片和R個校驗分片以條帶的方式儲存在一起,即分別儲存於每個Brick上,從而降低訪問熱點;其中R個校驗分片會以輪詢輪的方式儲存於卷的每個brick上,用以提高卷的可靠性。(注:Fragment的大小在GlusterFS的原始碼中是一個巨集定義,其大小等於EC_METHOD_WORD_SIZE* EC_GF_BITS = 64*8 = 512 bytes)

Disperse卷中,Chunk的大小可配置,其大小與具體的Redundancy配置有關,其大小等於512*(B-R) bytes。可通過調整Redundancy的配置(注:Redundancy的配置在Disperse卷建立之後就確定,不可修改),來修改Chunk的大小。那麼以官方經典的配置B=6,R=2的Disperse卷為例,得出Chunk的大小為(6-2)*512 = 2048 bytes。

Chunk的大小與效能有關,而效能又與訪問模式以及檔案大小有關。其效能會隨著Chunk的大小改變而改變,使用者可以根據具體的應用場景,通過調整Chunk的大小,在儲存利用和可靠性之間做均衡選擇,從而獲得更好的效能。

Dispersed

圖6:Dispersed卷的儲存機制

2. Disperse卷的編碼
Disperse卷使用演算法Rabin IDA(Information Dispersal Algorithm)進行編碼,其中R(redundancy)個校驗資料由(B-R)個原始資料計算得出。

Dispersed卷的編碼

圖7:Dispersed卷的編碼

3. Disperse卷的失效資料恢復
任意資料/校驗塊的失效都可用(B-R)個數據/校驗塊通過解碼/編碼恢復,資料塊通過解碼方式恢復,校驗塊通過編碼方式恢復。

Dispersed資料恢復

圖8:Dispersed卷的失效資料恢復

4. Disperse卷的讀操作
讀操作,每個Chunk都必須從B-R個brick中成功讀取B-R個數據/校驗分片;儘量讀資料塊而不是校驗塊;校驗塊輪詢分佈在各個brick上,達到更好的平衡負載。

Dispersed讀操作

圖9:Dispersed卷的讀操作

5. Disperse卷的寫操作
(1)普通的寫操作
根據(B-R)個原始資料塊使用演算法IDA計算得出R(redundancy)個校驗塊,然後再把資料塊和校驗塊以條帶的方式一起寫入底層所有brick中。

Dispersed寫操作

圖10:Dispersed卷的寫操作

(2)部分寫
部分寫分為兩種情況,一是沒有失效的資料塊分片,首先將不完整的Chunk將讀出來,然後結合新寫入資料重新計算校驗塊,最後再把資料塊、校驗塊統一寫入底層brick中;二是有失效的資料塊分片,首先利用該Chunk中其他的分片通過編碼/解碼計算恢復,然後結合新寫入資料重新計算校驗塊,最後再把資料塊、校驗塊統一寫入底層brick中。

(三)EC卷的引數介紹

在Gluster3.7版本中,EC卷有disperse.eager-lock、cluster.disperse-self-heal-daemon、cluster.heal-timeout、disperse.background-heals、disperse.heal-wait-qlength以及disperse.read-policy等幾個引數,下面就對幾個重要的引數進行簡單介紹:
disperse.eager-lock:預設值為on,建議把這個引數設定為off。設定為off時,雖然會降低讀效能,但當對於檔案的操作完成後檔案鎖能夠立即得到釋放,從而提升一些操作(如寫操作、修復等操作)的效能。
disperse.background-heals:預設值為8,用來控制平行修復時的個數。
disperse.heal-wait-qlength:預設值為128,用來控制等待修復的個數。
disperse.read-policy:預設值為round-robin,用來設定讀的策略。
cluster.heal-timeout:預設值為600,用來設定自修復程序檢查需要自修覆文件的時間間隔。

在Gluster 3.9版本中,EC卷又增加了disperse.shd-max-threads、disperse.shd-wait-qlength、disperse.cpu-extensions等三個引數,由於篇幅有限在這裡就不做介紹了。

四、EC糾刪碼卷實踐 

(一)EC實踐總結

1、Disperse卷的建立
Disperse卷的建立與節點個數無關(節點個數大於等於1),只與bricks(B)、冗餘度redunancy(R)相關;其中bricks(B)必須大於等於3,disperse-data 的個數必須要大於等於2,redunancy(R)的值最小為1,最大為(B-1)/2、必須小於bricks(B)的一半且值是不能改變的。

2、Disperse卷的資料儲存
disperse卷的單個底層brick中不具有完整資料,需整合多個brick上的資料片段才能看到完整的檔案資料;底層brick中儲存的不是原始資料;資料塊和校驗塊是儲存在一起的。

3、Disperse卷的資料恢復
在配置bricks(B)為3,冗餘度redunancy(R)為1的disperse卷中,任意掛掉一個brick後,資料都能夠恢復,且不影響正常訪問;在修復大檔案資料時,需要同步訪問來觸發才能修復資料;修復小檔案資料,則不需要;手動刪除底層brick中的資料,也能夠實現修復。

4、Disperse卷的擴充套件
三個brick的disperse卷不能同時擴充套件一個或兩個brick,只能同時擴充套件3n(n>=1)個brick,即disperse卷不能任意擴展卷,只能同時擴充套件n*B(n>=1)個brick;Distributed Dispersed 卷可以通過擴充套件Dispersed 卷生成;Dispersed 卷可在線上擴充套件,且擴充套件過程中不影響資料的訪問。

5、chunk的大小是否與效能有關
disperse卷的效能會隨著chunk的大小改變而改變,使用者可以根據需求改變chunk的大小來調整disperse卷的效能。可通過調整EC配置,來修改Chunk的大小。(注:冗餘度Redundancy在Disperse卷建立之後就確定,且不可修改。)

6、Disperse卷的均衡
disperse卷在擴展卷時不會自動均衡卷,需要手動均衡卷;均衡時,小檔案直接進行遷移均衡,大檔案則是先建立黏著位連結,然後再進行資料遷移均衡。

7、Disperse卷的收縮
disperse卷在收縮卷時,不能任意收縮,只能同時收縮n*B(n>=1)個brick;必須先遷移資料然後才能刪除相應的brick。

8、Disperse卷的替換
disperse卷在替換brick時,替換的brick不能是卷內部的brick,也不能是其他卷裡面的brick;目錄也能夠替換;替換正常執行的brick是通過計算所有節點中brick的資料來進行替換的;替換過不正常執行的brick是通過計算其他節點中正常執行的brick中資料來進行替換的;且替換過程中不影響卷的正常訪問。

9、Distributed Disperse卷的資料恢復
在配置B為6、R為2的Distributed Disperse卷中,最多隻能同時掛掉不同組中的2個brick;寫檔案時,檔案的資料塊和校驗塊都只會儲存在一個組中,不會交叉儲存;同時具有Distributed卷和Disperse卷的特性,其中Disperse卷作為Distributed卷的子卷。

10、EC卷的效能總結
相同EC配置下Distributed-Disperse卷比Disperse卷具有更好的IO效能;相同disperse-data個數的Disperse卷的效能相近;相同冗餘配置的EC卷比複製卷具有更大的空間利用率,但讀寫效能均比複製卷略差;相對於分散式複製卷,Distributed-Disperse卷的優點是具有較高的磁碟利用率和容錯性,但是其IOPS效能下降較多。
在配置為1 x (2+1)的disperse卷中任意掛掉一個brick後,不影響資料的正常訪問;資料的修復是通過計算其他兩個節點中的brick來修復的;在修復100G資料時,替換brick用時約2.2秒,但是發現替換成功後新的brick中並沒有資料,需要同步訪問來觸發才能修復資料;修復100M 資料,則不需要同步訪問來觸發修復;EC卷的穩定性良好,測試過程無報警。

(二)EC效能測試

1、測試環境

2、測試工具

IOzone,檔案系統測試基準工具,可以測試不同作業系統中檔案系統的讀寫效能。主要測試檔案系統的write、re-write、read、re-read、random read、random write等效能。注意:在單程序的測試中,測試檔案的大小一定要大過記憶體的大小(最佳值為記憶體大小的兩倍),否則linux會給讀寫的資料進行快取,從而造成測試數值不準確。

3、測試方法
搭建3個節點的glusterfs叢集,建立6x(2+1)的Distributed Dispersed卷,啟動卷。在每個節點使用Gluster原生協議本地掛載卷,然後分別在每個節點中使用測試工具iozone,測試程序數為4、塊大小為512KB、檔案大小為16GB時,EC卷的讀寫效能,測試命令為:

# ./iozone -s 16g -r 512k -i 0 -i 1 –t 4。

4、測試結果

5、測試總結
在配置為6x(2+1)的Distributed-Disperse卷測試中,無論是寫效能,還是讀效能,都達到了1GB/s,特別是寫效能更是高達1.5GB/s。由此得出,EC卷是可以滿足企業對於效能的一般需求的,是可以在實際環境中使用的。

(三)EC配置推薦

基於Glusterfs搭建的叢集中,建立EC卷推薦以下幾種配置:
a. 冗餘度為1,推薦建立配置為(2+1) EC卷;
b. 冗餘度為2,推薦建立配置為(4 +2) EC卷;
c. 冗餘度為3,推薦建立配置為(8 +3) EC卷;
d. 冗餘度為4,推薦建立配置為(8 + 4) EC卷。
由於在相同的EC配置下,Distributed Disperse卷比Disperse卷具有更好的IO效能,所以推薦在硬碟數量足夠的情況下建立Distributed Disperse卷。

在底層的配置中,推薦邏輯盤(如/dev/sda)不分割槽直接格式化為塊大小512B的XFS檔案系統,且邏輯盤與brick是一一對應的關係;推薦有n個節點,B就等於n,即同一組的Disperse卷配置中,一個brick對應一個節點。比如,三個節點的gluster叢集就推薦建立配為(B=3,R=1)的EC卷,每組Disperse卷配置中,一個brick對應一個節點。

五、EC卷的優化方向

對於如何優化EC卷的效能主要在於以下幾點:一是如何提高編/解碼的速度;二是如何提高編碼速度的穩定性;三是EC卷引數的可配置;四是如何降低修復的開銷。

其中如何提高編/解碼的速度是最重要,也是最基礎的一點。編/解碼的運算速度主要依賴於分散式系統的計算能力以及網路速度,那麼可以從三個方面來提高。第一,伺服器硬體效能的升級;第二,網路環境的升級;第三,則是使用成熟的庫來加速RS碼的計算速度,如Intel ISA-L庫、Jerasure庫等。雖然從這三個方面都能夠提高糾刪碼的編/解碼的速度,但其中伺服器硬體效能的升級以及網路環境的升級都會增大企業的成本,所以推薦使用第三中方式,即使用成熟的庫來提高編/解碼的運算速度。其中Jerasure庫早已成為開源Ceph分散式儲存系統的預設糾刪碼庫,相對於ISA-L庫,Jerasure庫在這一點上具有一定的先天優勢,所以在Gluster儲存中推薦使用Jerasure庫來加速EC卷的編/解碼速度。除了以上幾點外,還可以從分散式叢集這一特性入手,分散式叢集儲存中單一節點的計算能力不算很好,但如果能讓叢集中每個節點協同完成編/解碼的計算,就能夠擁有足夠的計算能力,叢集中節點越多,叢集的計算能力越強,編/解碼的運算速度也就越快,相應的EC卷效能也就越好。

編碼策略在理論範圍內可隨意切換,即引數可配置,可以大大降低了後續的開發和維護所需要的精力。在Gluster儲存中,EC卷的效能會隨著chunk的大小改變而改變,那麼實現chunk大小的引數可配置就顯得尤為必要了。實踐中,得知chunk的大小等於Fragment_size*(B-R),但其中R的大小在Disperse卷建立之後就確定,且不可修改;而Fragment_size在GlusterFS的原始碼中又是一個巨集定義,其大小等於EC_METHOD_WORD_SIZE * EC_GF_BITS = 64*8 = 512 bytes,這也就是說chunk的大小在disperse卷建立成功後就不可修改,而這極大降低了EC卷在實際應用中的靈活度,例如根據資料的冷熱程度和資料重要程度選擇不同冗餘配置、根據儲存檔案的大小調整底層塊大小從而提高效能等。

EC卷具有很大的修復開銷,這主要是由於RS碼本身的特性所導致的,在配置為(D+R)的RS碼中修復任何一個數據塊時,都需要從磁碟上讀取D塊的其他資料塊,然後在網路上傳輸,最後使用演算法計算恢復。比如在4+2的配置中,丟失任何一個數據塊都將必須讀取至少4個數據塊來修復,在整個修復過程中會佔用大量磁碟I/O以及網路流量,並且會使得系統暴露在一種降級的不穩定狀態。那麼使用較小的D值就能在很大程度上降低修復的開銷,還能提高儲存的可靠性,但這會降低儲存利用率,這就需要在效能和儲存空間利用率之間做權衡了。

在EC卷中,無論是讀操作、寫操作,還是修改操作都需要做大量的計算、通訊、下發檔案鎖等操作。就拿寫操作來說,以在配置為(4+2)的EC卷中寫一個chunk資料塊為例,a.把這個chunk塊切分為4個fragment原始資料塊;b.讀4個原始資料塊;c.計算得出2個校驗資料塊;d.對每個資料塊下發檔案鎖,並新增擴充套件屬性;e.把6個數據塊統一寫入底層brick中;f.寫入成功後,擦除擴充套件屬性。當然,這僅僅只是大概流程,在這其中至少包含10個檔案鎖、20次通訊、5個狀態機等等操作。那麼是否可以考慮從優化Gluster中關於EC卷的原始碼這方面來提升EC卷的效能,例如把其中的一些重複操作合併,去除一些不必要的操作,優化演算法,從根本上去解決問題,當然這屬於對Gluster做二次研發了,還需做具體的調研,在這裡就不細說了。

EC卷的的核心是以計算換容量,其效能較複製卷略差,但具有更高的儲存利用率。那麼從實際應用的角度出發,可以這樣使用EC卷:建立Tier分層來儲存資料,熱卷使用複製卷,冷卷使用EC卷。在實際應用中熱資料就直接存入複製卷中,當熱資料變為冷資料後再把資料遷移到EC卷中,這樣就既提供了較高的效能,又保證了較高的儲存利用率。

文章來 自微信公眾號:運維幫