提醒:已領讀者請忽略!
資料中心4件套姊妹篇已全部發布:可購買“架構師技術全店資料打包彙總(全)”,或單獨購買《伺服器基礎知識全解(終極版 第二版)》、《儲存系統基礎知識全解(終極版)》,《SSD快閃記憶體技術基礎知識全解(終極版)》和《資料中心網路基礎知識全解(精編版)》獲取完整版。
之前購買過“架構師技術全店資料打包彙總(全)(已更新至48本)”的讀者免費發放全店更新(請在發貨的彙總連結下載),或請憑藉購買記錄在微店留言獲取(PDF閱讀版本)。


資料中心4件套姊妹篇已全部發布:可購買“架構師技術全店資料打包彙總(全)”,或單獨購買《伺服器基礎知識全解(終極版 第二版)》、《儲存系統基礎知識全解(終極版)》,《SSD快閃記憶體技術基礎知識全解(終極版)》和《資料中心網路基礎知識全解(精編版)》獲取完整版。
之前購買過“架構師技術全店資料打包彙總(全)(已更新至48本)”的讀者免費發放全店更新(請在發貨的彙總連結下載),或請憑藉購買記錄在微店留言獲取(PDF閱讀版本)。
本文以MIPS、PA-RISC、PowerPC、SPARC v9和LoongArch為例,比較不同RISC指令系統的指令格式、定址模式和指令功能,以加深對RISC的瞭解。
推薦閱讀:龍芯3A5000處理器架構分析
1、指令格式比較
五種RISC指令集的指令格式如圖所示。在暫存器類指令中,操作碼都由操作碼(OP)和輔助操作碼(OPX)組成,運算元都包括兩個源運算元(RS)和一個目標運算元(RD);立即數類指令都由操作碼、源運算元、目標運算元和立即數(Const)組成,立即數的位數各有不同;跳轉類指令大同小異,PA-RISC與其他四種差別較大。總的來說,五種RISC指令集的指令編碼主要組成元素基本相同,只是在具體擺放位置上存在差別。

2、定址方式比較
五種指令集的定址方式如表所示。MIPS、SPARC和LoongArch只支援四種常用的定址方式,PowerPC和PA-RISC支援的定址方式較多。
五種指令集的定址方式比較
定址方式
|
MIPS
|
PowerPC
|
PA-RISC
|
SPARC
|
LoongArch
|
暫存器定址
|
Y
|
Y
|
Y
|
Y
|
Y
|
立即數定址
|
Y
|
Y
|
Y
|
Y
|
Y
|
偏移量定址
|
Y
|
Y
|
Y
|
Y
|
Y
|
變址定址
|
Y(僅浮點)
|
Y
|
Y
|
Y
|
Y
|
比例變址定址
|
Y
|
||||
自增/自減+偏移量定址
|
Y
|
Y
|
|||
自增/自減+變址定址
|
Y
|
Y
|
注:表中Y表示支援該定址方式。
3、共指令功能
RISC指令集都有一些公共指令,如load-store、算術運算、邏輯運算和控制流指令。不同指令集在比較和轉移指令上區別較大。
1)load-store指令。load指令將記憶體中的資料取入通用暫存器,store指令將通用暫存器中的資料存至記憶體中。表2.7給出了LoongArch指令集的load-store指令例項。當從記憶體中取回的資料位寬小於通用暫存器位寬時,字尾沒有U的指令進行有符號擴充套件,即用取回資料的最高位(符號位)填充目標暫存器的高位,否則進行無符號擴充套件,即用數0填充目標暫存器的高位。
LoongArch指令集的load-store指令
指令
|
指令功能
|
LD.B
|
取位元組
|
LD.BU
|
取位元組,無符號擴充套件
|
LD.H
|
取半字
|
LD.HU
|
取半字,無符號擴充套件
|
LD.W
|
取字
|
LD.WU
|
取字,無符號擴充套件
|
LD.D
|
取雙字
|
ST.B
|
存位元組
|
ST.H
|
存半字
|
ST.W
|
存字
|
ST.D
|
存雙字
|
ALU指令。ALU指令都是暫存器型的,常見的ALU指令包括加、減、乘、除、與、或、異或、移位和比較等。表為LoongArch指令集的ALU指令例項。其中帶有“.W”字尾的指令操作的資料位寬為32位(字),帶有“.D”字尾的指令操作的資料位寬為64位(雙字)。
表 2 LoongArch指令集的ALU指令
指令
|
指令功能
|
ADD.W
|
字加
|
ADDI.W
|
字加立即數
|
SUB.W
|
字減
|
ADD.D
|
雙字加
|
ADDI.D
|
雙字加立即數
|
SUB.D
|
雙字減
|
SLT
|
有符號數比較小於置1
|
SLTI
|
有符號數立即數比較小於置1
|
SLTU
|
無符號數比較小於置1
|
SLTUI
|
無符號數立即數比較小於置1
|
AND
|
與
|
OR
|
或
|
XOR
|
異或
|
NOR
|
或非
|
ANDI
|
與立即數
|
ORI
|
或立即數
|
XORI
|
異或立即數
|
LU12I.W
|
載入20位立即數到高位
|
SLL.W
|
字邏輯左移變數位
|
SRL.W
|
字邏輯右移變數位
|
SRA.W
|
字算術右移變數位
|
SLLI.W
|
字邏輯左移常量位
|
SRLI.W
|
字邏輯右移常量位
|
SRAI.W
|
字算術右移常量位
|
SLL.D
|
雙字邏輯左移變數位
|
SRL.D
|
雙字邏輯右移變數位
|
SRA.D
|
雙字算術右移變數位
|
SLLI.D
|
雙字邏輯左移常量位
|
SRLI.D
|
雙字邏輯右移常量位
|
SRAI.D
|
雙字算術右移常量位
|
MUL.W
|
字乘取低半部分
|
MULH.W
|
有符號字乘取高半部分
|
MULH.WU
|
無符號字乘取高半部分
|
MUL.D
|
雙字乘取低半部分
|
MULH.D
|
有符號雙字乘取高半部分
|
MULH.DU
|
無符號雙字乘取高半部分
|
DIV.W
|
有符號字除取商
|
DIV.WU
|
無符號字除取商
|
MOD.W
|
有符號字除取餘
|
MOD.WU
|
無符號字除取餘
|
DIV.D
|
有符號雙字除取商
|
DIV.DU
|
無符號雙字除取商
|
MOD.D
|
有符號雙字除取餘
|
MOD.DU
|
無符號雙字除取餘
|
3)控制流指令。控制流指令分為絕對轉移指令和相對轉移指令。相對轉移的目標地址是當前的PC值加上指令中的偏移量立即數;絕對轉移的目標地址由暫存器或指令中的立即數給出。表為LoongArch指令集中控制流指令的例項。
LoongArch指令集的控制流指令
指令
|
指令功能
|
JIRL
|
相對暫存器偏移跳轉並連結
|
B
|
無條件相對轉移
|
BL
|
無條件相對轉移並連結
|
BEQ
|
等於時相對轉移
|
BNE
|
不等時相對轉移
|
BLT
|
有符號比較小於時相對轉移
|
BGE
|
有符號比較大於等於時相對轉移
|
BLTU
|
無符號比較小於時相對轉移
|
BGEU
|
無符號比較大於等於時相對轉移
|
BEQZ
|
等於0相對轉移
|
BNEZ
|
不等於0時相對轉移
|
在條件轉移指令中,轉移條件的確定有兩種方式:判斷條件碼和比較暫存器的值。SPARC採用條件碼的方式,整數運算指令置條件碼,條件轉移指令使用條件碼進行判斷。MIPS和LoongArch的定點轉移指令使用暫存器比較的方式進行條件判斷,而浮點轉移指令使用條件碼。PowerPC中包含一個條件暫存器,條件轉移指令指定條件暫存器中的特定位作為跳轉條件。PA-RISC有多種選擇,通常透過比較兩個暫存器的值來決定是否跳轉。
RISC指令集中很多條件轉移採用了轉移延遲槽(Delay Slot)技術,程式中條件轉移指令的後一條指令為轉移延遲槽指令。在早期的靜態流水線中,條件轉移指令在譯碼時,後一條指令即進入取指流水級。為避免流水線效率的浪費,有些指令集規定轉移延遲槽指令無論是否跳轉都要執行。MIPS、SPARC和PA-RISC都實現了延遲槽,但對延遲槽指令是否一定執行有不同的規定。對於當今常用的動態流水線和多發射技術而言,延遲槽技術則沒有使用的必要,反而成為指令流水線實現時需要特殊考慮的負擔。Alpha、PowerPC和LoongArch均沒有采用轉移延遲槽技術。
4、不同指令系統的特色
除了上述公共功能外,不同的RISC指令集經過多年的發展形成了各自的特色,下面舉例介紹其各自的主要特色。
1)MIPS部分指令特色。前面介紹過訪存地址的對齊問題,當確實需要使用不對齊資料時,採用對齊訪存指令就需要複雜的地址計算、移位和拼接等操作,這會給大量使用不對齊訪存的程式帶來明顯的代價。MIPS指令集實現了不對齊訪存指令LWL/LWR。LWL指令讀取訪存地址所在的字並將訪存地址到該字中最低位的位元組拼接到目標暫存器的高位,LWR指令讀取訪存地址所在的字並將訪存地址到該字中最高位的位元組拼接到目標暫存器的低位。上述字中的最低位和最高位位元組會根據系統採用的尾端而變化,不同尾端下,LWL和LWR的作用相反。例如,要載入地址1至4的內容到R1暫存器,不同尾端的指令和效果如圖2.9所示。

LWL和LWR指令設計巧妙,兼顧了使用的便利性和硬體實現的簡單性,是MIPS指令集中比較有特色的指令。
2)SPARC部分指令特色。SPARC指令系統有很多特色,這裡挑選暫存器視窗進行介紹。在SPARC指令系統中,一組暫存器(SPARC v9中規定為8~31號暫存器)可用於構成視窗,視窗可有多個,0~7號暫存器作為全域性暫存器。暫存器視窗的好處在於函式呼叫時可不用儲存現場,只需切換暫存器組。
3)PA-RISC部分指令特色。PA-RISC指令集最大的特色就是Nullification指令,除了條件轉移指令,其他指令也可以根據執行結果確定下一條指令是否執行。例如ADDBF(add and branch if false)指令在完成加法後,檢查加法結果是否滿足條件,如果不滿足就進行轉移。一些簡單的條件判斷可以用Nullification指令實現。
4)PowerPC部分指令特色。在RISC結構中,PowerPC的定址方式、指令格式和轉移指令都是最多的,甚至支援十進位制運算,因此又被稱為“RISC中的CISC”。表給出了分別用PowerPC指令和Alpha指令實現的簡單程式示例。實現同樣的迴圈程式,PowerPC只需要6條指令,Alpha則需要10條指令,原因就在於PowerPC的指令功能較強。例如其中的LFU(load with update)和STFU(store with update)指令,除了訪存外還能自動修改基址暫存器的值;FMADD可以在一條指令中完成乘法和加法;轉移指令BC可同時完成計數值減1和條件轉移。
PowerPC和Alpha彙編對比
原始碼:for(k=0;k<512;k++) x[k]=r*x[k]+t*y[k];
|
|
PowerPC程式碼
|
Alpha程式碼
|
r3+8指向xr4+8指向yfp1內容為tfp3內容為rCTR內容為512
|
r1指向xr2指向yr6指向y的結尾fp2內容為tfp4內容為r
|
LOOP: LFU fp0=y(r4=r4+8) FMUL fp0=fp0,fp1 LF fp2=x(r3,8) FMADD fp0=fp0,fp2,fp3 STFU x(r3=r3+8)=fp0 BC LOOP,CTR>0
|
LOOP: LDT fp3=y(r2,0) LDT fp1=x(r1,0) MULT fp3=fp3,fp2 ADDQ r2=r2,8 MULT fp1=fp1,fp4 SUBQ r4=r2,r6 ADDT fp1=fp3,fp1 STT x(r1,0)=fp1 ADDQ r1=r1,8 BNE r4,LOOP
|
5)LoongArch部分指令特色。LoongArch指令集的一個特色是其二進位制翻譯擴充套件。LoongArch的二進位制翻譯擴充套件提供了百餘條指令和一些系統資源來支援軟體實現高效的二進位制翻譯。例如,把X86指令翻譯為RISC類的指令集有個影響翻譯效率的因素:eflags標誌位處理。因為X86指令集中,一個運算指令除了產生運算結果,還會同時產生是否進位、是否溢位等多>個標誌位。完全模擬這樣的一條指令的語義一般需要30條以上常規RISC指令。
LoongArch提供了一系列專門指令用於產生和使用相應的標誌位,在保持RISC指令風格的同時消除了這個瓶頸。目前業界最先進的二進位制翻譯系統可以實現80%左右的翻譯執行效率,LoongArch致力於透過深度的軟硬體協同進一步提升效率,實現多個主流指令集到龍芯指令集幾乎無損的翻譯,最終達到“消滅指令集”或者說軟體定義指令集的目的。
參考來源:https://foxsen.github.io/archbase



溫馨提示:
掃描二維碼關注公眾號,點選閱讀原文連結獲取“架構師技術全店資料打包彙總(全)”電子書資料詳情。

