日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

fpga nvme 寄存器

發布時間:2024/3/7 编程问答 51 豆豆
生活随笔 收集整理的這篇文章主要介紹了 fpga nvme 寄存器 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

圖1所示的NVMe多隊列,每個隊列支持64K命令,最多支持64K隊列。這些隊列的設計使得IO命令和對命令的處理不僅可以在同一處理器內核上運行,也可以充分利用多核處理器的并行處理能力。每個應用程序或線程可以有自己的獨立隊列,因此不需要IO鎖定。NVMe還支持MSI-X和中斷控制,避免了CPU中斷處理的瓶頸,實現了系統擴展的可伸縮性。NVMe采用簡化的命令集,相比SAS或SATA,NVMe命令集使用的處理IO請求的指令數量減少了一半,從而在單位CPU指令周期內可以提供更高的IOPS,并且降低主機中IO軟件堆棧的處理延遲。

2 NVMe寄存器

NVMe(Over PCIe)寄存器主要分為兩類,一類是PCIe配置空間寄存器,一類是NVMe控制器相關的寄存器。

a.PCIe配置空間和功能

NVMe PCIe總線寄存器如表1所示,NVMe跟主機CPU的接口主要是基于PCIe總線,使用PCIe的Config和Capability機制。包括PCI/PCIe頭、PCI功能和PCIe擴展功能。

表1 NVMe PCIe配置空間和功能

?

b.NVMe控制器寄存器

NVMe控制器寄存器位于MLBAR/MUBAR寄存器(PCI BAR0和BAR1)中,這些寄存器應映射到支持順序訪問和可變訪問寬度的內存空間。NVMe 1.3d版本的控制器寄存器列表如表2所示。

表2 NVMe 1.3d版本的控制器寄存器列表

起始結束縮寫描述
0h7hCAP控制功能
8hBhVS版本
ChFhINTMS中斷屏蔽設置
10h13hINTMC中斷屏蔽清楚
14h17hCC控制器配置
18h1BhReserved保留
1Ch1FhCSTS控制器狀態
20h23hNSSRNVM子系統重置(可選)
24h27hAQA管理隊列屬性
28h2FhASQ管理提交隊列基地址
30h37hACQ管理完成隊列基地址
38h3BhCMBLOC控制器存儲緩沖位置(可選)
3Ch3FhCMBSZ控制器存儲緩沖大小(可選)
40h43hBPINFO引導分區信息(可選)
44h47hBPRSEL引導分區讀選擇(可選)
48h4FhBPMBL引導分區存儲緩沖位置(可選)
50hEFFhReserved保留
F00hFFFhReserved命令設置具體的寄存器
1000h1003hSQ0TDBL管理SQ0尾Db
1000h + (1 * (4 << CAP.DSTRD))1003h + (1 * (4 << CAP.DSTRD))CQ0HDBL管理CQ0頭Db
1000h + (2 * (4 << CAP.DSTRD))1003h + (2 * (4 << CAP.DSTRD))SQ1TDBLSQ1尾Db
1000h + (3 * (4 << CAP.DSTRD))1003h + (3 * (4 << CAP.DSTRD))CQ1HDBLCQ1頭Db
1000h+ (2y * (4 << CAP.DSTRD))1003h + (2y * (4 << CAP.DSTRD))SQyTDBLSQy尾Db
1000h + ((2y + 1) * (4 << CAP.DSTRD))1003h + ((2y + 1) * (4 << CAP.DSTRD))CQyHDBLCQy頭Db
供應商定制寄存器(可選)
SQ:Submission Queue,提交隊列;CQ:Completion Queue,完成隊列;Db:Doorbell,門鈴。

3 NVMe隊列

NVMe的隊列是經典的環形隊列結構,通過提交/完成隊列對來實現隊列的傳輸交互。

a.隊列概述

NVMe使用的是經典的循環隊列結構來傳遞消息(例如,傳遞命令和命令完成通知)。隊列可以映射到任何PCIe可訪問的內存中,通常是放在主機內存。

如圖2,隊列是固定大小的,通過Tail和Head來分別指向寫入和讀取的指針。像通常的隊列數據結構一樣,隊列實際可使用的大小是隊列大小減1,并且用Head等于Tail指示隊列空,用Head等于(Tail+1)除以隊列大小的余數來指示隊列滿。

?如上一節的圖1,根據用途,NVMe隊列有兩類:管理隊列和IO隊列;根據傳輸方向有兩類:提交隊列和完成隊列。具體介紹見表3。

表3 NVMe隊列類型

管理IO
提交用于提交管理命令,最大4K項;
用于配置控制器和IO隊列等;
從主機側到控制器側。
用于傳輸IO命令,最大64K項;
用于提交IO操作命令;
從主機側到控制器側。
完成管理命令的完成確認,最大4K項;
從控制器側到主機側;
獨立的MSI-X中斷處理。
IO命令的完成確認,最大64K項;
從控制器側到主機側;
獨立的MSI-X中斷處理。

b.隊列處理流程

NVMe的驅動和設備交互跟Virtio不同:Virtio是在通過一個隊列完成雙向通知交互;而NVMe則采用提交隊列和完成隊列配合完成雙向交互的方式。

如圖3,NVMe隊列處理流程如下(其中主機為軟件驅動,控制器為硬件設備):

(1)主機寫命令到提交隊列項中。

(2)主機寫DB(Doorbell)寄存器,通知控制器有新命令待處理。

(3)控制器從內存中的提交隊列中讀取命令。

(4)控制器執行命令。

(5)控制器更新完成隊列,表示當前的SQ項已經處理。

(6)控制器發MSI-x中斷到主機CPU。

(7)主機處理完成隊列,同步更新提交隊列中的已處理項。

(8)主機寫完成隊列Db到控制器,告知完成隊列項已釋放。

4 NVMe命令結構

我們通過如下一些概念來理解NVMe命令結構:

隊列項的數據格式。NVMe的提交命令固定64字節,完成命令固定16字節。

命令。NVMe命令分為Admin和IO兩類。

NVMe的數據塊組織方式有PRP和SGL兩種。

a.隊列項的數據格式

提交隊列和完成隊列,組成隊列對,協作完成NVMe驅動和設備之間的命令傳輸。提交隊列每一項64字節固定大小,完成隊列每一項16字節固定大小。

提交隊列的數據格式如圖4所示。NVMe提交隊列項的數據格式屬性如下:

Opcode:命令操作碼

FUSE:熔合兩個命令為一條命令

PSDT:PRP或SGL數據傳輸

Command Identifier:命令ID

Namespace Identifier:命名空間ID

Metadata Pointer:元數據指針

PRP entry 1/2:物理區域頁項,對應的由PRP和PRP列表

SGL:散列聚合列表

?完成隊列的數據格式如圖5所示。

圖5 完成隊列項的數據格式

NVMe完成隊列的數據格式屬性如下:

SQ Header pointer:SQ頭指針

SQ Identifier:SQ ID

Command Identifier:命令ID

P:相位標志phase tag,完成隊列沒有head/tail交互,通過相位標志實現完成隊列項的釋放

Status Field:狀態域

b.NVMe命令

NVMe管理類的命令如表4所示。

表4 NVMe管理命令列表

NVMe IO類命令如表5所示。

表5 NVMe IO類命令列表

命令必選或可選類別
創建IO SQ必選隊列管理
刪除IO SQ必選
創建IO CQ必選
刪除IO CQ必選
鑒別必選配置
獲取特征必選
設置特征必選
獲取日志頁必選狀態報告
異步事件請求必選
中止必選中止命令
固件鏡像下載可選固件更新和管理
固件可用可選
IO命令集定制命令可選IO命令集定制
供應商定制命令可選供應商定制

NVMe IO類命令如表5所示。

表5 NVMe IO類命令列表

命令必選或可選類別
必選必選的數據命令
必選
清洗必選
不可改正的寫可選可選的數據命令
寫0可選
比較可選
數據集管理可選數據提示
預約獲取可選預約命令
預約寄存器可選
預約釋放可選
預約報告可選
供應商專用命令可選供應商專用

c.物理區域頁PRP

PRP本質是一個鏈表,鏈表中的每一個指針都指向一個不超過頁大小的數據塊。PRP為8字節(64bits)固定大小,PRPList則最多可以占滿一整個頁。

PRP1和PRP2的格式如圖6(a)所示。如果是首個PRP,則Offset(偏移量)可能是非零的數據,另外,偏移量是32bits對齊的(即末尾兩位為0)。如圖6(b)所示,在PRP列表中的所有PRP項的偏移量都為0,也即是PRP指針指向頁面起始地址。

?如圖7(a)所示,當數據只有一個或兩個頁面的時候,就不需要使用PRP列表數據結構,直接PRP1和PRP2指向內存頁面。當一個命令指向的數據超過兩個內存頁面的時候,就需要使用PRP列表,圖7(b)所顯式的為使用PRP列表的數據結構。

(b) 范例2:PRP列表指針,指向PRP列表,再指向內存頁面

圖7 PRP數據結構范例

d.散列聚合列表SGL

PRP每個鏈表指針最多指向一個頁大小的數據塊,即使若干個頁在內存連續放置,PRP也需要對應的多個PRP項。為了減少元數據規模,SGL不限制指針指向數據塊的大小,這樣連續的若干個頁的數據,只需要一個SGL項就可以標識。

NVMe中SGL的長度為16字節固定長度,其格式如圖8(a)所示,在最高的第15字節SGL描述符類型域和子類型域標識不同類型的SGL描述符,根據不同的描述符,字節14-0的格式各有不同。SGL描述符類型如圖8(b)所示。

如圖9,NVMe SGL的數據結構是鏈表形式,SQ中的首個SGL段只有1項,為指向下一個SGL段的指針。下一個SGL段包含若干SGL數據塊描述符,SGL段的最后的一個SGL描述符為另一個SGL段指針,指向下一個SGL段。根據傳輸數據大小,在最后一個SGL 段中,所有的SGL描述符都是SGL數據塊描述符。

PRP只能指向單個內存頁,這樣,當要傳輸的數據塊非常大的時候,就需要非常多的PRP項。而SGL可以指向不同大小的數據塊,處于連續內存區域的多個數據塊只需要一個SGL描述符就可以標識。因此,一般情況下,SGL比PRP更高效,更節省描述符資源。

NVMe over PCIe協議,定義了NVMe協議的使用范圍、指令集、寄存器配置規范等。

1.1 名詞解釋

1.1.1 Namespace

Namespace是一定數量邏輯塊(LB)的集合,屬性在Identify Controller中的數據結構中定義。

1.1.2 Fused Operations

Fused Operations可以理解為聚合操作,只能聚合兩條命令,并且這兩條命令在隊列中應保持相鄰順序。協議中只有NVM指令才有聚合操作。還需要保證聚合操作的兩條命令讀寫的原子性,參考Compare and Write例子。

1.1.3 指令執行順序

除了聚合操作(Fused Operations),每一條SQ中的命令都是獨立的,不必考慮RAW等數據相關問題,即使考慮,也是host應該解決的問題。

1.1.4 寫單元的原子性

控制器需要支持寫單元的原子性。但有時也能通過host配置Write Atomicity feature,減小原子性單元的大小,提高性能。

1.1.5 元數據

數據的額外信息,相當于提供校驗功能。可選的方式。

1.1.6 仲裁機制

用來選擇下一次執行的命令的SQ的機制,三種仲裁方式:

  • RR(每個隊列優先級相同,輪轉調度)

  • 帶權重的RR(隊列有4種優先級,根據優先級調度)

  • 自定義實現

  • 1.1.8 Queue Pair

    由SQ(提交隊列)與CQ(完成隊列)組成,host通過SQ提交命令,NVMe Controller通過CQ提交完成命令。

    1.1.9 NVM 子系統

    NVM子系統包括控制器、NVM存儲介質以及控制器與NVM之間的接口。

    1.2 NVMe SSD

    1.2.1基本架構

    整體來看,NVMe SSD可以分為三部分,host端的驅動(NVMe官網以及linux、Windows已經集成了相應的驅動)、PCIe+NVMe實現的控制器以及FTL+NAND Flash的存儲介質。

  • ?

    1.2.2 NVMe控制器

    NVMe控制器實質上為DMA + multi Queue,DMA負責數據搬運(指令+用戶數據),多隊列負責發揮閃存的并行能力。

  • ?

    2. PCIe寄存器配置

    NVMe over PCIe,通過利用PCIe總線實現數據交互的功能,實現對物理層的抽象功能。

    2.1 PCIe總線的基本結構

    PCIe總線分為三層,物理層,數據鏈路層,處理層(類似于計算機網絡的分層結構),通過包來轉發數據。NVMe協議定義的內容相當于PCIe的上一層應用層,處于應用層。PCIe給NVMe提供了底層的抽象。

    NVMe SSD相當于一個PCIe的端設備(EP)。

  • ?

    2.2 寄存器配置

    在協議中主要定義了PC header、PCI Capabilities和PCI Express Extended Capabilities三部分內容。

    具體在host內存中會占有4KB,結構如下:

  • ?

    2.2.1 PCI header

    PCI header有兩種類型,type0表示設備,type1表示橋。NVMe 控制器屬于EP,所以定義為type0的類型。共64KB,如下圖:

  • ?

    2.2.2 PCI Capabilities

    這里配置了PCI Capbilities,包括電源管理、中斷管理(MSI、MSI-X)、PCIe Capbilities。

    2.2.3 PCI Express Extended Capabilities

    這里配置有關錯誤恢復等高級功能。

    3. NVMe寄存器配置

    3.1 寄存器定義

    NVMe寄存器主要分為兩部分,一部分定義了Controller整體屬性,一部分用來存放每組隊列的頭尾DB寄存器。

  • CAP——控制器能力,定義了內存頁大小的最大最小值、支持的I/O指令集、DB寄存器步長、等待時間界限、仲裁機制、隊列是否物理上連續、隊列大小;

  • VS——版本號,定義了控制器實現NVMe協議的版本號;

  • INTMS——中斷掩碼,每個bit對應一個中斷向量,使用MSI-X中斷時,此寄存器無效;

  • INTMC——中斷有效,每個bit對應一個中斷向量,使用MSI-X中斷時,此寄存器無效;

  • CC——控制器配置,定義了I/O SQ和CQ隊列元素大小、關機狀態提醒、仲裁機制、內存頁大小、支持的I/O指令集、使能;

  • CSTS——控制器狀態,包括關機狀態、控制器致命錯誤、就緒狀態;

  • AQA——Admin 隊列屬性,包括SQ大小和CQ大小;

  • ASQ——Admin SQ基地址;

  • ACQ——Admin CQ基地址;

  • 1000h之后的寄存器定義了隊列的頭、尾DB寄存器。


  • ?

    3.2 寄存器理解

  • CAP寄存器標識的是Controller具有多少能力,而CC寄存器則是指當前Controller選擇了哪些能力,可以理解為CC是CAP的一個子集;如果重啟(reset)的話,可以更換CC配置;

  • CC.EN置一,表示Controller已經可以開始處理NVM命令,從1到0表示Controller重啟;

  • CC.EN與CSTS.RDY關系密切,CSTS.RDY總是在CC.EN之后由Controller改變,其他不符合執行順序的操作都將產生未定義的行為;

  • Admin隊列有host直接創建,AQA、ASQ、ACQ三個寄存器標識了Admin隊列,而其他I/O隊列則有Admin命令創建(eg,創建I/O CQ命令);

  • Admin隊列的頭、尾DB寄存器標識為0,其他I/O隊列標識由host按照一定規則分配;只有16bit的有效位,是因為隊列深度最大64K。
    ?

    4. 內存數據結構

    4.1 SQ與CQ的詳細定義

    4.1.1 空隊列

?

4.1.2 滿隊列

判斷隊列滿可以有多種方法,協議中規定的是頭指針比尾指針大一,所以隊列滿時,空余一個元素。

?

4.1.3 隊列性質

1. 隊列大小有16bit,最小隊列大小為2個元素(因為滿隊列的定義方式,所以最小為2個元素),對于I/O隊列,最大隊列大小為64k;對于Admin隊列,最大隊列為4k;

2. QID來標識唯一ID,16bit,由host分配;

3. host可以修改隊列優先級(如果支持的話),共四級,U、H、M、L;

4.2 仲裁機制

4.2.1 RR

RR仲裁,Admin SQ與I/O SQ優先級相同,控制器每次可以選擇一個隊列中的多個命令(Arbitration Burst setting)。

?

4.2.2 帶有優先權的RR

有3個嚴格的優先權,Priority1 > Priority2 > Priority3,在這三個優先級隊列中,高優先級的隊列中如果有命令,則優先執行(非搶占式)。

?

4.2.3 其他仲裁方式

Vendor Specific。

4.3 數據尋址方式(PRP和SGL)

4.3.1 PRP

NVMe把Host的內存分為頁的集合,頁的大小在CC寄存器中配置,PRP是一個64位的內存物理地址指針,結構如下:

?

最后兩位為0,指四字節對齊;(n:2)位表示頁內內偏移。

舉個例子,內存頁大小位4KB,則(11:2)表示頁內偏移。

PRP尋址有兩種方式,直接用PRP指針尋址,通過PRP List尋址。當使用PRP List尋址時,偏移必須為0h,每一個PRP條目表示一個內存頁,如下:

?

?

Admin命令的數據地址只能采取PRP的方式,I/O命令的數據地址既可以采取PRP的方式,又可以采取SGL的方式。Host在命令中會告訴Controller采用何種方式。具體來說,如果命令當中DW0[15:14]是0,就是PRP的方式,否則就是SGL的方式。

命令的Dword6~Dword9只定義了PRP1、PRP2兩個數據指針,通過PRP條目可以指向PRP List。如下圖:

?

?

在上面的例子中,PRP1直接指向內存頁,PRP2指向PRP List存在的地址,在PRP List中存有數據的真正的地址。

更詳細的說:

協議中PRP Entry是一個指向物理內存頁的指針。PRP被用作NVMe Controller和PC內存之間進行數據傳輸。PRPEntry是固定大小的(8B)。

首先,明確兩個概念,PRP Entry 為PRP指針,PRP List為PRP列表指針,示意圖如下:

?

?

根據每次傳輸數據的大小,以及PRP指針的偏移(offset)可以分為以下五種情況:

?

?

?

4.3.2 SGL

SGL是另外一種索引內存的數據結構。SGL由若干個SGL段組成,SGL段又由若干個SGL描述符組成,所以SGL描述符是SGL數據結構的基本單位。

目前定義的SGL描述符有6種:

5.4 NVM指令

NVMe控制器讀寫的最小單元是LB,層次圖如下:

?NVM指令與Admin指令結構完全相同,也是通過Dword0中的8位操作碼來定義不同指令。

  • SGL 數據描述符,用來索引數據塊地址,host內存;

  • SGL 垃圾數據描述符,用來索引無用數據;

  • SGL 段描述符,用來索引下一個SGL段;

  • SGL 最后一個段描述符,用來索引最后一個SGL段;

  • keyed SGL 數據描述符;

  • Transport SGL 數據描述符;

    ?

    在上面SGL例子中,共有3個SGL段,用到了4種SGL描述符。Host需要往SSD中讀取13KB的數據,其中真正只需要11KB數據,這11KB的數據需要放到3個大小不同的內存中,分別是:3KB,4KB和4KB。

    4.3.3 比較PRP與SGL

    無論是PRP還是SGL,本質都是描述內存中的一段數據空間,這段數據空間在物理上可能連續的,也可能是不連續的。Host在命令中設置好PRP或者SGL,告訴Controller數據源在內存的什么位置,或者從閃存上讀取的數據應該放到內存的什么位置。

    SGL和PRP本質的區別在于,一段數據空間,對PRP來說,它只能映射到一個個物理頁,而對SGL來說,它可以映射到任意大小的連續物理空間,具有更大的靈活性,也能夠描述更大的數據空間。如下圖:

    ?

    5. NVMe協議定義的命令

    5.0 命令執行過程

    命令由host提交到內存中的SQ隊列中,更新TDBxSQ后,NVMe控制器通過DMA的方式將SQ中的命令(怎么取,如何取,取多少,因設計而異)取到控制器緩沖區,執行命令;執行完成后,根據執行狀態,組裝完成命令,仍然通過DMA的方式將完成命令寫入內存CQ的隊列中;NVMe控制器通過MSI-X中斷方式通知host已完成命令;最后,host處理CQ命令,更新控制器中HDBxCQ,標識著命令真正完成。

    5.1 命令分類

    命令分為Admin指令與NVM指令(I/O指令)。

    Admin指令只能提交到Admin Controller中,主要負責管理NVMe控制器,也包含對NVM的一些控制指令。

    NVM 指令只能提交到I/O Controller中,主要負責完成數據的傳輸。

    在1.0e版本中,Admin指令有15條(3條與NVM相關),NVM指令有6條;在1.3d版本中,Admin指令有15條(3條與NVM相關),NVM指令有11條。

    5.2 命令通用格式

    命令均為64字節,具有相同的格式,某些字段根據命令的不同有不同的定義。

    完成命令同樣具有相同的格式,某些字段根據命令的不同有不同的定義。

    5.3 Admin 指令

    Admin指令與NVM指令根據放置的的隊列組(Queue Pair)來區分,Admin指令在Admin CQ與SQ里,NVM指令在I/O CQ與SQ里。

    通過Dword0中的8位操作碼定義不同指令,注意并不是絕對的順序增加(eg,沒有03h)。每一種指令都對應有其完成命令,通過SQID(提交隊列ID)+CID(命令ID)唯一標識完成的命令。

    Note:

  • Admin隊列是通過配置ASQ等寄存器創建的

  • 先創建CQ再創建SQ

  • 6 控制器結構

    控制器從功能上可以分為三類,I/O、Admin和Discovery

    ?

    在實現過程中,Admin 控制器只有一個,負責管理控制器及其他控制功能。控制器只是抽象的概念,應用于具體的實現中,可能是一個具體的模塊,也可能多個模塊。

    控制器主要的作用是實現對NVMe定義命令的翻譯,從而實現數據傳輸、狀態控制等功能。

    6.1 命令執行過程

    1. host將命令(1條或者多條)寫入提前分配好的SQ中;

    2. 更新對應SQ的DB寄存器;

    3. NVMe控制器取SQ中命令(通過HDB和TDB可以判斷是否有未完成命令);

    4. NVMe控制器執行命令;

    5. NVMe 控制器在命令完成后,將完成命令(可能執行成功,也可能失敗,但都會返回完成命令)寫入host內存SQ對應的CQ中;

    6. NVMe 控制器根據實現的中斷方式,提醒host命令已完成;

    7. host響應中斷,處理完成命令;

    8. host 更新對應CQ的DB寄存器。

    ?

    6.2 重啟(Reset)

    6.2.1 Controller level

    Controller重啟可能發生在PCIe總線重啟、PCI重啟、控制器CC.EN從1到0重啟。當重啟發生時:

  • 所有的I/O SQ和CQ都被刪除;

  • 所有未完成的指令(Admin和I/O)應該執行撤銷操作;

  • Controller處于idele狀態,CSTS.RDY清0;

  • AQA、ASQ、ACQ不受影響。

  • 重啟后,host操作:

  • 更新寄存器狀態;

  • 將CC.EN置1;

  • 等待CSTS.RDY置1;

  • 使用Admin命令配置Controller;

  • 創建I/O CQ和SQ;

  • 執行正常的I/O指令。

  • 6.2.2 Queue level

    隊列水平的重啟,即,刪除該隊列,再重新創建一個新隊列。刪除隊列的時候,host應該保證隊列處于idle狀態(所有命令均已完成——接收到了完成命令),否則的話,可能會導致CQ接收不到提交命令的完成命令。

    6.3 中斷

    在Controller完成SQ命令后,根據執行狀態,將結果組裝成完成命令寫入CQ中,Controller通過中斷機制通知Host處理完成命令。

    NVMe協議中支持的中斷方式有4種,pin-based、Single MSI、Multi-message MSI和MSI-X,協議推薦采用MSI-X中斷方式,能夠支持更多的中斷向量(2K)。

    MSI-X允許每一個CQ發送自己的中斷信息(相比于發一條中斷信息提醒全部CQ隊列有很大的優勢)。在產生MSI-X中斷信息前,需要檢查該中斷在相應寄存器種不被屏蔽。

    6.4 Controller初始化

    Controller的初始化過程:

  • 設置PCI和PCIe寄存器;

  • 等待CSTS.RDY變為;

  • 配置AQA、ASQ、ACQ寄存器;

  • 配置CC寄存器;

  • 將CC.EN置1;

  • 等待CSTS.RDY置1

  • Host通過Identify命令,確定Controller的數據結構、確定Namespace的數據結構;

  • Host通過get features(協議中是set features,待研究)獲取I/O SQ和CQ信息,然后配置中斷機制;

  • Host分配適當的I/O CQ、SQ隊列;

  • 如果Host希望獲取Controller的錯誤或健康信息,可以添加異步事件請求命令。

  • Controller 關機

    正常關機:

  • Host停止提交新的I/O命令,但允許未完成的命令繼續完成;

  • Host刪除所有I/O SQ,刪除所有SQ隊列后,所有未完成的命令將被撤銷;

  • Host刪除所有I/O CQ;

  • Host將CC.SHN置01b,表示正常關機;關機程序完成時,將CSTS.SHST置10b。

  • 突然關機:

  • Host停止提交新的I/O命令;

  • Host將CC.SHN置10b,表示突然關機;關機程序完成時,將CSTS.SHST置10b

  • 6.5 host端命令實例

    6.5.1 創建命令

    ?6.5.2 處理完成命令

    ?

    6.6 NVMe與PCIe交互實例(分析包結構)

    以Host發出read命令為例。

  • Host準備了一個Read命令給SSD:

    ?

    分析該包,Host需要從起始LBA 0x20E0448(SLBA)上讀取128個DWORD (512字節)的數據,讀到哪里去呢?PRP1給出內存地址是0x14ACCB000。這個命令放在編號為3的SQ里 (SQID = 3),CQ編號也是3 (CQID = 3)

  • Host通過寫SQ的Tail DB,通知Controller來取命令:

    ?上圖中,上層是NVMe層,下層是PCIe傳輸層的TLP。Host想往SQ Tail DB中寫入的值是5。PCIe是通過一個Memory Write TLP來實現Host寫CQ的Tail DB的。該Tail DB寄存器映射在Host的內存地址為F7C11018,由于NVMe 的寄存器映射到了Host內存中,所以可以根據這個地址寫入寄存器值
    SSD收到通知,去Host端的SQ中取指

    ?

    PCIe是通過發一個Memory Read TLP到Host的SQ中取指的。可以看到,PCIe需要往Host內存中讀取16個DWORD的數據(一個NVMe指令大小),

  • SSD執行讀命令,把數據從閃存中讀到緩存中,然后把數據傳給Host:

    ?

    SSD是通過Memory write TLP 把Host命令所需的128個DWORD數據寫入到Host命令所要求的內存中去。SSD每次寫入32個DWORD,一共寫了4次。

  • SSD往Host的CQ中返回狀態:

    ?

    SSD是通過Memory write TLP 把16個字節的命令完成狀態信息寫入到Host的CQ中。

  • SSD采用中斷的方式告訴Host去處理CQ

    ?

  • 上圖使用的是MSI-X中斷方式。這種方式將中斷信息和正常的數據信息一樣,PCIe打包把中斷信息告知Host。SSD還是通過Memory Write TLP把中斷信息告知Host,這個中斷信息長度是1DWORD。

  • Host處理相應的CQ

  • Host處理完相應的CQ后,需要更新SSD端的CQ Head DB告知SSD處理

  • 完成:

    ?

    Host還是通過Memory Write TLP更新SSD端的CQ Head DB。

    該過程完整的包流程如下:

    ?

    7. NVMe features

    7.1 固件(Firmware)更新過程

    1. 將固件下載到Controller中(使用 Firmware Image Download命令);

    2. Host提交Firmware Activate命令(也可以激活之前版本的Controller鏡像);

    3. Controller reset;

    4. reset完成后,Host重新初始化Controller,包括Host重新分配I/O隊列,與reset步驟相同。

    7.2 元數據(Metadata)傳輸

    元數據的使用并沒有強制規定,最經常的使用方法是用做端到端數據的保護信息。有兩種傳輸元數據的方式,一種可以作為LB數據塊的一部分,如下圖:

    ?

    7.3 端到端的數據保護

    端到端,一端指主機的內存空間,一端指閃存空間(NVM)。數據傳輸的兩個環節如下圖:

    ?

    ?

    數據在PCIe上傳輸的時候,由于信道噪聲的存在(說白了就是存在干擾),可能導致數據出錯;另外,Controller閃存之間,數據也可能發生錯誤。采用元數據進行數據的保護是最常用的一種手段。

    充當保護數據角色的元數據結構如下:

    ?其中,Guard為16bit的CRC校驗碼,Application Tag與LBAT相關,Reference Tag將用戶數據和地址(LBA)相關聯。下圖為以512bytes的數據塊為例:

    ?

    那么按照排列組合,共有四種保護情況(1帶2帶、1不帶2不帶、1帶2不帶、1不帶2帶)。但由于協議中控制保護信息的只有兩個字段(1. 是否采用保護 2. PRACT位),只有三種情況,如下圖(是以寫命令為例,讀命令相同):

    ?

    ?

    總結

    以上是生活随笔為你收集整理的fpga nvme 寄存器的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。