技術文章:編譯器的寄存器分配

2022年07月04日18:36:25 科技 1923

因為存儲速度成本之間的問題,電腦的整個存儲系統按照CPU從近到遠可以分為4級:寄存器、cache緩存、主內存、硬盤。

離CPU最近的寄存器,讀寫速度最快

離CPU最遠的硬盤,讀寫速度最慢。

包括C語言在內的大多數語言,是不需要關注寄存器怎麼分配的。這部分的工作被編譯器處理了。

當然,彙編語言是需要手動分配寄存器的。

程序員在寫彙編時,會按照自己的直覺給出一個寄存器分配方案。

例如 5 / 3 = 1;彙編是這麼寫的:

mov 5, eax

xor edx, edx

mov 3, ecx

div ecx

這時,在eax里,餘數在edx里。英特爾的CPU就是這麼設計除法指令的。

除法使用固定的寄存器eax和edx,是CISC架構的缺點,讓寄存器的分配變得麻煩。

如果是int a = 5, b = 3, c = a / b;

那麼就要盡量給c分配寄存器eax,因為除法的商默認就在eax里,這樣可以提高生成的彙編碼的效率

如果是c = a % b,那麼就要盡量給c分配寄存器edx,因為餘數默認就在edx里。

因為寄存器只有16個,在程序規模較大的時候,是沒法這麼理想的分配寄存器的。

編譯器里,寄存器的分配是根據變量之間的活躍度來的:同時活躍變量不能使用同一個寄存器,否則數據就互相覆蓋了。

c = a / b這行代碼的被除數a和除數b肯定是同時活躍的,在除法指令運行的那一刻它們必須同時有效(而且互相覆蓋)。

c與a、b並不是同時活躍的,它是在除法運行之後開始活躍。

如果變量a在這行代碼之後不再使用,那麼c和a是可以共用eax的。

如果後續還要使用a,那麼就不能共用eax。例如:

int a = 5, b = 3;

int c = a / b;

c += a; // a在這裡還是活躍的,不能在第二行c = a / b時被覆蓋。

這時就只能給c分配eax,同時edx除法指令佔用,所以a和b只能使用ecx和ebx

以上代碼翻譯成彙編:

mov 5, ecx // a使用ecx

mov 3, ebx // b使用ebx

mov ebx, eax // 加載被除數的最低32位到eax

xor edx, edx // 被除數的高32位清零

div ebx // 真正的除法運算只是這一條

add ecx, eax // c += a

技術文章:編譯器的寄存器分配 - 天天要聞

上面2行代碼c = a / b, c += a的寄存器衝突圖,如上。

給這個圖的3個頂點a、b、c着色,被衝突線連接兩個頂點不能是同一個顏色,即不能分配同一個寄存器

因為CISC的除法使用edx,我們把它也作為一個約束條件添加到這個圖裡:變量a是不能使用它的,因為它會被除法運算的餘數覆蓋,而a在c += a這行代碼還要使用。

c可以使用它,但c作為除法運算的商應該優先分配eax,否則就還需要多1條mov eax, edx的彙編碼。

技術文章:編譯器的寄存器分配 - 天天要聞

64位寄存器的位元組分配

實際CPU的寄存器是個64位的寄存器組,它的最低8位AL、次低8位AH、最低16位AX、最低32位EAX、整個寄存器RAX的關係如圖。

al和rax是衝突的:

char buf[8] = {0};

char c = 'A';

char* p = buf;

*p += c;

如果指針p使用了rax,那麼char類型的變量c就不能再使用al,反之也一樣。

代碼 *p += c里,指針變量p和字符變量c是同時活躍的。

這種情況可以通過掩碼來判斷,可以用1個二進制表示寄存器的1個位元組

1,RAX是8位元組的寄存器,掩碼就是0xff。

2,al是1位元組的寄存器,掩碼就是0x1。

3,ah的掩碼是0x2,因為它使用的是第2個位元組。

4,ax的掩碼是0x3,2個位元組。

5,eax的掩碼是0xf,4個位元組。

如果掩碼的與運算不為0,就是互相衝突的寄存器,不能用於同一個變量。

當然不是同一個寄存器組的寄存器,肯定是不衝突的。

ah和al是不衝突的,因為0x2 & 0x1 == 0。

ah和ax是衝突的,因為0x2 & 0x3 != 0。

技術文章:編譯器的寄存器分配 - 天天要聞

科技分類資訊推薦

地平線總裁陳黎明:高階智能輔助駕駛的拐點已經到來,將會快速增長 - 天天要聞

地平線總裁陳黎明:高階智能輔助駕駛的拐點已經到來,將會快速增長

紅星資本局7月11日消息,今日,地平線(09660.HK)總裁陳黎明在2025中國汽車論壇上表示,高階智能輔助駕駛的拐點已經到來,後面會有比較快速的增長。對此,他表示依據有三:第一,智能駕駛是我國智能網聯新能源汽車發展戰略的一個重要組成部分,政府工作報告對智能汽車的發展做出了規劃和行動方向。在電動化上,地平線可以...
洛斐發佈Flow2矮軸三模無線機械鍵盤 - 天天要聞

洛斐發佈Flow2矮軸三模無線機械鍵盤

沒想到,洛斐Flow系列這麼快就進入迭代了,發佈全新Flow2。引入了全新的設計語言,依然是全鋁金屬外殼機身,邊框像蘋果手機那樣的直板機身。其中,右側部分加長,側面則是增加了Touch Bar觸控滑動條,支持調節燈光亮度或系統音量。另一方面,鍵盤背面增加了同樣極具辨識度的撐腳模塊,支持兩種角度調節。 同時還全新升級了...
大爺寫《我的母親》火爆全網!視頻發佈者最新發聲 - 天天要聞

大爺寫《我的母親》火爆全網!視頻發佈者最新發聲

連日來,一段關於大爺挑戰寫作1957年高考同題作文《我的母親》的視頻火爆全網。不少網民表示,文字質樸,催人淚下,深深被打動。7月11日,大皖新聞記者聯繫上了視頻發佈者連文傑。對方表示,視頻中展示的作文內容由大爺獨立寫作,產生的版權收入也全給大爺。大爺寫作文視頻走紅網絡。大爺寫的作文在網上爆火大皖新聞記者注...
10.38萬元起,吉利銀河A7發佈預售價 - 天天要聞

10.38萬元起,吉利銀河A7發佈預售價

7月11日,吉利銀河發佈了預售價,預售價格範圍為10.38-13.38萬元,在發佈預售價格的同時,官方也帶來了多項權益,包括500元訂金抵扣1500元,贈送價值8800元的Flyme Sound音響等。
「中欣卡」突然停擺,超150萬用戶退款難 - 天天要聞

「中欣卡」突然停擺,超150萬用戶退款難

覆蓋北京2000多家門店、擁有超150萬持卡用戶的預付卡「中欣卡」近日停擺,線上線下消費渠道均被暫停,恢復時間未知。大量持卡用戶面臨資金凍結困境。消費渠道全面「癱瘓」近日,中欣卡發佈公告稱「因業務調整,全面暫停所有門店合作,無法消費」。中國新聞網《民生調查局》記者發現,其官網合作商戶名錄已清空,線上提貨渠...
突發,聊聊Manus「刪博跑路」 - 天天要聞

突發,聊聊Manus「刪博跑路」

摘要:「如果最後有不錯的結果,證明作為中國出生的創始人,也能在新的環境下做好全球化的產品,那就太好了」鳳凰網科技 出品作者|董雨晴7月11日,AI Agent產品Manus官方賬號清空了發佈在微博、小紅書的內容。兩天前,Manus剛剛陷入裁