- 深入理解LLVM:代碼生成
- 彭成寒 李靈 戴賢澤 王志磊 俞佳嘉
- 1273字
- 2024-12-18 16:44:26
1.1 LLVM設計思路分析
LLVM項目起源于伊利諾伊大學香檳分校的研究型項目,在2000年由Chris Lattner和其導師Vikram Adve發起,并于2003年正式開源并發布1.0版本。2002年,Lattner在其碩士論文“LLVM: AN INFRASTRUCTURE FOR MULTI-STAGE OPTIMIZATION”中詳細介紹了LLVM的設計思路,本節將簡單總結這一思路。
LLVM的愿景是實現一個編譯器的基礎設施,能適配現代編程語言、硬件架構發展,它有3個目標。
1)具備多階段優化能力(如過程內優化、過程間優化、配置文件驅動的優化),保證程序執行性能足夠高。
2)提供基礎機制,方便進行編譯器研發。
3)兼容標準系統編譯器的行為。
為了達到這些目標,LLVM設計了一套虛擬指令集,稱為LLVM IR。雖然LLVM IR是低級的中間表示,但是它攜帶了程序的類型信息,這樣的IR設計既方便了靜態編譯優化,又允許在鏈接時進行優化。Lattner設想在鏈接優化完成后生成的二進制文件中,既可以包含可執行代碼,又可以包含IR,其中IR可以用于后續的JIT優化[1]。Lattner還設想在LLVM中提供運行時優化,通過監控程序的執行過程來收集反饋信息(profile information)并用于指導程序優化[2]。
LLVM編譯器整體架構圖如圖1-1所示。

圖1-1 LLVM編譯器整體架構圖
從圖1-1中可以看到,LLVM編譯優化策略和程序的“編譯-鏈接-執行”模式完全匹配,在編譯期、鏈接期、執行期都可以進行優化。和其他編譯器不同的是:LLVM借助了LLVM IR,大量的優化工作都是圍繞LLVM IR展開的,不同的優化都由獨立的模塊完成。
1)編譯時優化:各個語言的編譯器前端將代碼翻譯成LLVM IR,LLVM優化器針對LLVM IR做盡可能多的優化。編譯期優化大多數屬于局部優化(少量優化是過程間優化),通常包含架構無關優化和架構相關優化。
2)鏈接時優化:編譯器在編譯時為函數提供過程間摘要信息,并附加到LLVM IR中,在連接時使用這些信息完成優化。
3)運行時和離線優化:基于收集的程序執行信息,再次對應用進行優化。
在這些優化工作中,LLVM IR是整個編譯系統設計的關鍵,具有如下特點。
1)LLVM使用LLVM IR描述一個虛擬架構并捕獲常規處理器的關鍵操作,同時消除了特定機器架構限制,如物理寄存器、流水線、調用約定、陷阱等方面的限制。
2)LLVM IR提供無限數量的類型化虛擬寄存器,并用這些寄存器來存儲基礎類型(如整型、浮點型、指針類型)的值。LLVM IR采用SSA形式,從而更便于進行編譯優化。
3)在LLVM IR中提供了特有的指令,顯式描述異常控制流信息。
4)LLVM IR約定虛擬寄存器和內存之間,僅靠load和store指令進行數據交換,交換數據時需要約定數據類型。內存被劃分為全局區域、棧、堆(過程被視為全局對象),其中棧、堆上的對象分別使用alloca指令[3]和malloc指令操作分配空間,并通過這兩個函數返回的指針值來訪問相應的空間,棧對象在當前函數的棧幀中分配,控制流(線程)離開函數時自動釋放棧對象,堆對象必須使用free指令進行顯式釋放。
5)LLVM IR集成了運行時和系統函數,如I/O、內存管理、信號量等的相關函數,這些函數由運行時庫提供,可以被程序鏈接使用。同時LLVM IR提供文本、二進制、內存3種文件格式,以方便開發、存儲和運行。
LLVM IR提供了各種分析和變換的Pass(Pass是指對編譯對象進行一次處理,詳細內容可以參考附錄C),以及配套的工具集,如匯編、反匯編、解釋器、優化器、編譯器、測試套等相關工具,能幫助開發者快速入門和使用LLVM。
- Maven Build Customization
- Java Web程序設計
- Spring實戰(第5版)
- Python數據可視化之Matplotlib與Pyecharts實戰
- 名師講壇:Spring實戰開發(Redis+SpringDataJPA+SpringMVC+SpringSecurity)
- 網站構建技術
- Spring Boot+Vue全棧開發實戰
- Spring+Spring MVC+MyBatis從零開始學
- UML2面向對象分析與設計(第2版)
- Illustrator CS6設計與應用任務教程
- 編程改變生活:用Python提升你的能力(進階篇·微課視頻版)
- 從零開始:C語言快速入門教程
- ROS機器人編程實戰
- Scratch編程從入門到精通
- ASP.NET本質論