LLVM 編譯器基礎架構
網站地圖
下載!
搜尋 本站


實用 連結
發布 電子郵件
由以下團隊維護
llvm-admin 團隊
開放 LLVM 專案

LLVM 團隊撰寫

歡迎有潛力的 2025 年 Google 程式碼夏令營學生!本文檔是您尋找 LLVM、Clang 和其他相關子專案中有趣且重要專案的起點。此專案列表不僅為 Google 程式碼夏令營開發,也為真正需要開發人員投入且對 LLVM 社群非常有益的開放專案而開發。

我們鼓勵您瀏覽此列表,看看哪些專案讓您感到興奮,並與您的技能組合非常吻合。我們也歡迎未在此列表中的提案。有關 GSoC 的更多資訊和討論,請參閱 discourse 。如果您對特定專案有疑問,請在 discourse 中找到相關條目,查看先前的討論並提問。如果沒有此類條目,或者您想提出想法,請建立一個新條目。來自社群的回饋是您的提案被考慮並希望被接受的要求。

LLVM 專案已參與 Google 程式碼夏令營多年,並取得了一些非常成功的專案。我們希望今年也不例外,並期待收到您的提案。有關如何提交提案的資訊,請造訪 Google 程式碼夏令營主要網站。

描述

使用來自除錯資訊的變數位置資訊,以來源變數的位置和生命週期註解 LLDB 的反組譯器 (和 `register read`) 輸出。豐富的反組譯器輸出應公開為結構化資料,並透過 LLDB 的腳本 API 提供,以便可以在此基礎上建置更多工具。在終端機中,LLDB 應將註解呈現為文字。

預期成果

例如,我們可以增強以下函數的反組譯
frame #0: 0x0000000100000f80 a.out`main(argc=1, argv=0x00007ff7bfeff1d8) at demo.c:4:10 [opt]
  1   void puts(const char*);
  2   int main(int argc, char **argv) {
  3    for (int i = 0; i < argc; ++i)
→ 4      puts(argv[i]);
  5    return 0;
  6   }
(lldb) disassemble
a.out`main:
...
  0x100000f71 <+17>: movl  %edi, %r14d
  0x100000f74 <+20>: xorl  %r15d, %r15d
  0x100000f77 <+23>: nopw  (%rax,%rax)
→  0x100000f80 <+32>: movq  (%rbx,%r15,8), %rdi
  0x100000f84 <+36>: callq 0x100000f9e ; symbol stub for: puts
  0x100000f89 <+41>: incq  %r15
  0x100000f8c <+44>: cmpq  %r15, %r14
  0x100000f8f <+47>: jne 0x100000f80 ; <+32> at demo.c:4:10
  0x100000f91 <+49>: addq  $0x8, %rsp
  0x100000f95 <+53>: popq  %rbx
...

使用 LLDB 也可存取的除錯資訊 (觀察來源變數 i 如何從 [0x100000f77+slide) 開始在 r15 中)

$ dwarfdump demo.dSYM --name  i
demo.dSYM/Contents/Resources/DWARF/demo: file format Mach-O 64-bit x86-64
0x00000076: DW_TAG_variable
 DW_AT_location (0x00000098:
 [0x0000000100000f60, 0x0000000100000f77): DW_OP_consts +0, DW_OP_stack_value
 [0x0000000100000f77, 0x0000000100000f91): DW_OP_reg15 R15)
 DW_AT_name ("i")
 DW_AT_decl_file ("/tmp/t.c")
 DW_AT_decl_line (3)
 DW_AT_type (0x000000b2 "int")
產生像這樣的輸出,我們在其中註解變數何時有效及其位置
(lldb) disassemble
a.out`main:
...                                                               ; i=0
  0x100000f74 <+20>: xorl  %r15d, %r15d                           ; i=r15
  0x100000f77 <+23>: nopw  (%rax,%rax)                            ; |
→  0x100000f80 <+32>: movq  (%rbx,%r15,8), %rdi                   ; |
  0x100000f84 <+36>: callq 0x100000f9e ; symbol stub for: puts    ; |
  0x100000f89 <+41>: incq  %r15                                   ; |
  0x100000f8c <+44>: cmpq  %r15, %r14                             ; |
  0x100000f8f <+47>: jne 0x100000f80 ; <+32> at t.c:4:10          ; |
  0x100000f91 <+49>: addq  $0x8, %rsp                             ; i=undef
  0x100000f95 <+53>: popq  %rbx

目標是為一組明確的案例產生像這樣的輸出,例如,常數或完全在暫存器中的變數。

已確認的導師及其聯絡方式

  • Adrian Prantl aprantl@apple.com (主要聯絡人)
  • Jonas Devlieghere jdevlieghere@apple.com

所需/期望的技能

必要條件

  • 良好的 C++ 理解能力
  • 熟悉在終端機上使用除錯器
  • 需要熟悉上面範例中提及的所有概念
  • 需要充分理解至少一種機器碼的組合語言 (x86_64 或 AArch64)。

期望條件

  • 編譯器知識,包括資料流和控制流分析,是加分項。
  • 能夠瀏覽除錯資訊 (DWARF) 是加分項。

專案規模

中等 (~175 小時)

專案難度

困難

Discourse: 網址

描述

Bfloat16 是一種最近開發的浮點格式,專為機器學習和 AI 量身定制,並且在最新的 C++23 標準中,它已正式標準化為 std::bfloat16_t。它的支援可以在許多現代硬體中找到,從包括 Intel、AMD、Apple 和 Amazon 在內的所有主要供應商的 CPU,到 GPU (nVidia 和 AMD GPU) 和 Google TPU。在軟體方面,所有主要的加速器程式庫都支援它,例如 CUDA、ROCm、oneAPI、PyTorch 和 Tensorflow。此專案的目標是在 LLVM libc 程式庫中實作 bfloat16 數學函式。

預期結果

  • 正確設定產生的標頭,以便類型和函式可以與各種編譯器 (+版本) 和架構一起使用。
  • 實作通用的基本數學運算,以支援在支援的架構上運作的 bfloat16 資料類型:x86_64、arm (32 + 64)、risc-v (32 + 64) 和 GPU。
  • 盡可能使用編譯器內建函數或特殊硬體指令來實作特化,以提高其效能。
  • 如果時間允許,我們可以開始研究 bfloat16 的更高階數學函式。

技能

基本 C 和 C++ 技能 + 對了解/學習更多關於浮點格式精妙之處的興趣。

專案規模: 大型

難度: 簡單/中等

已確認的導師: Tue LyNicolas Celik

Discourse: 網址

描述

現代 GPU 能夠與主機進行統一尋址。我們目前使用它透過 RPC 介面提供 I/O 支援。但是,這需要在 CPU 上使用專用的使用者執行緒來處理伺服器程式碼。我們希望探索替代方案,以使用 Linux io_uring 介面從 GPU 提供 I/O。

此介面是一個環形緩衝區,旨在加速系統呼叫。但是,它提供了一種 輪詢模式,允許核心刷新環形緩衝區,而無需使用者啟動系統呼叫。我們應該能夠使用 AMDNVIDIA API 呼叫向 GPU 註冊 mmap() 記憶體。此介面應允許我們實作基本的讀/寫介面,該介面可以被認為與 CPU 上的系統呼叫相同。然後,它可以用於實作完整檔案介面。

預期結果

  • 在 GPU 上執行的 pwritepread 的實作。
  • 透過將 snprintf 轉發到 pwrite 來支援 printf
  • 如果時間允許,探索 GPU 檔案 API。

技能

基本 C 和 C++ 技能 + 存取 GPU、Linux 核心知識、GPU 知識。

專案規模: 小型

難度: 困難

已確認的導師: Joseph HuberTian Shilei

Discourse: 網址

描述

LLVM C 程式庫提供了數學函式的實作。我們希望根據現有的實作 (例如 CUDA 的 libdevice、ROCm 的 device libs 和 OpenCL 的 libclc) 來分析這些函式。去年,我們致力於一些介面來支援這些測試,現在需要改進這些介面,並為有趣的函式填寫內容。

此外,我們希望驗證這些函式在 GPU 上執行時的準確性,方法是透過暴力測試。目標是驗證實作是否正確,並且至少符合 OpenCL 標準中的誤差範圍。這將需要一組以 offload/ 專案撰寫的單元測試,理想情況下是使用 @callumfare 正在開發的新 API。

預期結果

  • 最終效能結果類似於 舊結果,但具有更最佳化的函式和更高的準確性。
  • 一個可以進行暴力測試以確認實作符合規範的測試套件。

技能

基本 C 和 C++ 技能 + 存取 GPU、一些數學知識

專案規模: 小型

難度: 簡單/中等

已確認的導師: Joseph HuberTue Ly

Discourse: 網址

描述: ClangIR (CIR) 專案旨在為 Clang 建立新的中間表示法 (IR)。它建立在 MLIR 之上,為 Clang 中基於 C/C++ 的語言提供方言,以及從 Clang AST 發射它所需的基礎架構,以及到 LLVM-IR 方言的降低路徑。ClangIR 上游化目前正在進行中。

為了向社群提供更頻繁的更新,如果我們可以透過衡量在啟用 ClangIR 的管道中現有 Clang 的 CodeGen 測試的覆蓋率來報告 ClangIR 的進度,那就太好了。透過收集有關崩潰、通過或失敗測試的資訊,我們可以提出一個更容易報告和理解的指標,為尋找任務的新手提供切入點,並透過對現有問題進行分類來幫助專案。現有的 Clang CodeGen 測試位於 clang/test/CodeGen* 中,並且在 ClangIR 支援方面可能處於不同的狀態

  • FileCheck 失敗。LLVM IR 建置成功,但 FileCheck 無法比對輸出
    • LLVM IR 不同,因為 ClangIR 管道正在發射不同的 IR (例如,使用了不同的指令、遺失了屬性)。需要建立問題,並且需要修正 ClangIR。
    • LLVM IR 不同,因為 CHECK 行需要更靈活 (LLVM-IR 方言輸出不同、SSA 值名稱、屬性順序等)。像 llvm-canon 這樣的工具在這裡可能很有用。
  • 測試崩潰/錯誤。ClangIR 不支援某些 C/C++ 結構,或者 LLVM 降低尚未實作。
  • 測試通過。太棒了!

為了檢索上述資訊,學生需要變更 Clang 的測試基礎架構 (LIT 設定、腳本、測試、???),以便更容易地重播啟用 ClangIR 的相同調用、與傳統管道結果進行比較或從測試中檢索特殊指示。

目前尚不清楚最佳方法是什麼,但預計希望被認真對待的提交提案應提出關於如何實現此目標的幾個可能想法,鼓勵與社群的其他成員進行事先討論。也希望學生與 ClangIR 社群互動、提交 github 問題、調查和/或變更失敗的 codegen 測試。

預期結果

  1. 建置基礎架構以執行測試並收集結果。
  2. 以可以放置在網頁上的方式呈現結果。
  3. 為上述「FileCheck 失敗」類別的 50% 檔案問題或變更檢查行。目前只需要考慮以下子目錄
        clang/test/CodeGen
        clang/test/CodeGenCXX
        clang/test/CodeGenOpenCL
        clang/test/CodeGenCUDA
        
  • 額外加分:尋找自動化/促進測試變更的方法,提出 PR 以修正 ClangIR 中的問題。

技能: 需要 Python、中級 C++ 程式設計技能和熟悉基本編譯器設計概念。LLVM IR、MLIR、Clang 或 ClangIR 程式設計的先前經驗是一個很大的加分項,但願意學習也是一種可能性。

專案規模: 大型

難度:中等

潛在導師: Bruno Cardoso Lopes Andy Kaylor

Discourse: 網址

描述: ClangIR 是 C 和 C++ 程式碼的新的、基於 MLIR 的中間表示法。它已在 LLVM 孵化器專案中開發,但目前正在進行將程式碼從孵化器遷移到主要 LLVM 儲存庫的工作。在移動程式碼時,必須更新程式碼以符合 LLVM 編碼標準和品質期望。此專案的目標是參與 ClangIR 上游化過程,並幫助改進程式碼和上游化過程。

ClangIR 專案旨在透過新增更緊密地模擬原始碼結構的抽象,保留比標準 LLVM IR 中可用的更多細節,來解鎖 C 和 C++ 程式碼的更好最佳化、分析和診斷的可能性。ClangIR 方言已經在使用 ClangIR 孵化器中可用的實作來解決實際問題,但我們需要將其移至主要 LLVM 儲存庫,以便向更廣泛的受眾提供此功能。

此專案將是一個獲得 MLIR 開發實務經驗的機會,重點是日常軟體工程紀律。參與者將與其他 LLVM 貢獻者並肩工作以實現共同目標,並在此過程中深入了解 ClangIR 方言。

預期結果

  1. 將 ClangIR 對 C 和 C++ 語言功能的支援遷移到主要 LLVM 儲存庫中
  2. 在遷移程式碼時提高程式碼品質
  3. 提出改進遷移過程的方法

技能: 需要精通現代 C++ 程式設計和熟悉基本編譯器設計概念。LLVM IR、MLIR、Clang 或 ClangIR 程式設計的先前經驗是一個很大的加分項,但由於此專案的目標是獲得此類經驗,因此它不是先決條件。

專案規模: 中等到大型

難度:中等

潛在導師: Andy Kaylor Bruno Cardoso Lopes

Discourse: 網址

描述: Clang 靜態分析器 (CSA) 已經可以找到各種時間記憶體錯誤。這些檢查通常具有關於某些 API 行為的硬式編碼知識。例如,cplusplus.InnerPointer 檢查器知道 std::string::data 的語意。Clang 社群引入了一些生命週期註解,包括 [[clang::lifetimebound]][[clang::lifetime_capture_by(X)]],並對 Clang 的預設警告進行了許多改進。不幸的是,編譯器的警告僅執行語句本機分析。CSA 能夠進行進階的跨程序分析。通用化現有的檢查 (如 cplusplus.InnerPointer) 可以使分析器在註解的程式碼中找到更多錯誤。一旦標準程式庫 被註解,這可能會變得更具影響力。

預期結果

  1. 識別可以從 [[clang::lifetimebound]][[clang::lifetime_capture_by(X)]] 註解中受益的檢查。
  2. 擴展這些檢查以支援這些註解。
  3. 確保產生的錯誤報告品質高,診斷正確解釋分析器如何考慮這些註解。
  4. 在真實世界的專案上驗證結果。
  5. 可能會警告錯誤的註解 (延伸目標)。

技能: 需要中級 C++ 程式設計技能和熟悉基本編譯器設計概念。Clang 或 CSA 程式設計的先前經驗是一個很大的加分項,但願意學習也是一種可能性。

專案規模: 大型

難度:困難

潛在導師: Gabor Horvath Balazs Benics Daniel Domjan

Discourse: 網址

描述

目前沒有簡單的方法可以使用 C++20 模組來取得原始碼檔案集合並從中建置可執行檔。這使得難以建立使用 C++20 模組的簡單測試或小型程式,而無需先設定建置系統。此專案的目標是擴展 Clang 驅動程式中極其簡單的建置系統,以處理這些情況。

這可以透過使用 Clang 現有的掃描 C++20 模組的支援來完成,以發現已傳入的原始碼檔案之間的依賴關係,然後按該順序建置它們,在需要的地方傳入正確的 PCM 檔案。這也可以擴展為支援明確建置透過模組地圖檔案發現的 Clang 模組。

預期成果

以類似於以下方式調用 clang

clang -o program -std=c++20 main.cpp A.cppm B.cppm
應成功編譯,其中每個翻譯單元僅匯入在命令列上的其他原始碼檔案或標準程式庫中定義的模組。這不應為未使用模組的情況增加任何額外負擔。

已確認的導師及其聯絡方式

所需技能

中級 C++ 知識;熟悉 C++ 程式碼的建置方式。熟悉 C++20 模組是一個優勢,但不是必需的。

專案規模

中等 (~175 小時)

專案難度

中等

Discourse: 網址

描述

未定義行為偵測器 (UBSan) 是 Clang 中用於尋找未定義行為 (例如,帶號整數溢位) 和有問題的 C/C++ 程式碼 (例如,無號整數溢位) 用途的有用編譯模式。UBSan 的預設版本使用僅在使用者空間中運作的編譯器執行階段 (例如,它在核心或嵌入式應用程式中無法運作),並且被認為不夠安全,無法在生產環境中使用。為了處理這些其他環境,UBSan 提供了一種捕獲模式,該模式發射捕獲指令,立即停止應用程式,而不是調用通常診斷問題然後繼續執行的 UBSan 執行階段。

不幸的是,捕獲 UBSan 存在一些缺陷,使其難以使用。特別是

  • Clang 會靜默忽略-fsanitize-trap=undefined標誌,當它在沒有-fsanitize=undefined的情況下傳遞時。此專案將修正此問題,作為「熱身任務」,以熟悉 Clang 程式碼庫。
  • 當附加除錯器時遇到 UBSan 捕獲時,不方便找出 UBSan 捕獲的原因。對於 x86_64 和 arm64,某些資訊編碼在指令中,但解碼此資訊非常不方便。雖然可以教導 LLDB 查看指令並解碼含義,但這是脆弱的,因為它取決於未記錄的編譯器 ABI。相反,我們可以基於__builtin_verbose_trap工作來編碼除錯資訊內部的捕獲原因 (「捕獲原因」)。如果時間允許,我們也可以研究發射更精確的捕獲原因

預期成果

  • -fsanitize-trap=undefined標誌單獨傳遞時,編譯器會靜默忽略它。目前,Clang 要求也傳遞-fsanitize-trap=標誌。應教導 Clang 警告此問題。
  • 教導 Clang 在 UBSan 捕獲指令上的除錯資訊中發射 UBSan 捕獲原因,類似於__builtin_verbose_trap的工作方式。
  • 確認 LLDB 能夠識別 UBSan 捕獲原因,並為此新增測試。
  • 如果時間允許,我們應研究透過使用編譯器中可用的資訊來發射更精確的捕獲原因。我們可能希望實作類似於「Sema Diagnostic」的方法,在其中可以輕鬆地在編譯器內部建構捕獲原因字串。此任務更開放,並且可能在 UBSan 之外使用 (例如-fbounds-safety).

已確認的導師及其聯絡方式

所需技能

良好的 C++ 理解能力

期望的技能

  • 熟悉 UBSan
  • 熟悉 LLDB

專案規模

小型 (~90 小時)。但如果時間允許,可以擴展

專案難度

簡單。此專案對於 LLVM 初學者來說是不錯的選擇。請注意,「發射更精確的捕獲原因」部分更開放,因此其難度完全取決於申請人選擇的方向。

Discourse: 網址

專案描述: Clang-Doc 是一個 C/C++ 文件產生工具,作為 Doxygen 的替代方案而建立,並建立在 LibTooling 之上。此工作始於 2018 年,關鍵質量已於 2019 年落地,但開發在很大程度上一直停滯不前,主要是由於資源匱乏,直到去年開發作為一個成功的 Google 程式碼夏令營專案重新啟動。

該工具建立在 LibTooling 之上,並利用 Clang 解析器,該解析器支援解析文件註解中的 Doxygen 命令 (此支援也用於實作 Clang 的

-Wdocumentation
,可用於在編譯期間驗證文件註解的內容)。

不幸的是,Clang 的文件解析器不完整,並且存在幾個問題
  • 並非所有 Doxygen 命令都受支援,這限制了 Clang-Doc 的可用性。
  • 並非所有 C/C++ 結構目前都已處理,最值得注意的是 C++20 功能,例如概念。
  • Doxygen 1.8.0 版中引入的文件註解中的 Markdown 支援遺失。

預期結果: 此專案的目標是在 Clang 的文件解析器中實作遺失的功能,以及它們在 Clang-Doc 中的處理方式,以提高產生文件的品質。最終目標是讓 LLVM 專案開始使用 Clang-Doc 來產生其參考文件,但在我們可以做到這一點之前,我們需要確保所有必要的功能都已實作。

成功的提案不僅應側重於解決現有的限制,還應從其他文件工具 (例如 hdocstandardesesubdoccppdocgen) 中汲取其他潛在改進的靈感。

在專案過程中,候選人將有機會獲得 LLVM 和 Clang 內部 (包括詞法分析器和解析器) 以及 C/C++ 語言的豐富經驗。

技能: 中級 C++ 知識;對編譯器和解析器感興趣。Clang/LibTooling 的先前經驗是一個加分項,但不是必需的。

專案規模: 中等或大型。

難度: 中等

已確認的導師: Petr HosekPaul Kirth

Discourse: 網址

專案描述: Clang 編譯器是 LLVM 編譯器基礎架構的一部分,支援多種語言,例如 C、C++、ObjC 和 ObjC++。 LLVM 和 Clang 的設計使其能夠作為函式庫使用,並促成了整個編譯器輔助工具生態系統的創建。 Clang 相對友善的程式碼庫以及 LLVM 中 JIT 基礎架構的進步,進一步推動了對不同 C++ 處理方法的研究,模糊了編譯時間和運行時間之間的界線。 挑戰包括增量編譯以及將編譯/連結時間最佳化融入更動態的環境中。 增量編譯管線透過建構不斷成長的翻譯單元,逐塊處理程式碼。 然後將程式碼降低到 LLVM IR 中,並隨後由 LLVM JIT 執行。 這種管線允許建立高效的直譯器。 直譯器實現了互動式探索,並使 C++ 語言更加使用者友善。 Clang-Repl 就是一個例子。

預期成果: 本專案旨在開發一個穩健的機制,透過動態識別和載入適當的共享物件或靜態封存檔來解決遺失符號的問題。 此外,它將探索基於執行設定檔調整符號的用例,從而顯著提高效能,最佳化即時編譯和動態執行環境的效率。

技能: C++ 中等程度知識,理解 LLVM 和 LLVM JIT,尤其如此

專案規模:中型或大型。

難度: 中等

已確認指導教授: Vassil Vassilev

討論區: 網址

描述

Enzyme 需要關於型別記憶體佈局的良好資訊。 LLVM-IR 是刻意不透明的,例如 `&f32` 和 `&f64` 都具有 LLVM-IR 型別 `ptr`。 Enzyme 通常能夠透過使用情況分析來推斷底層型別(例如 f32 與 f64),但該過程緩慢,並且在某些情況下可能會失敗。 為了使自動微分更加穩健,我們應該將 MIR 或 THIR 型別資訊降低到 LLVM-IR metadata 中。 此分析是遞迴的,例如 `&[T]` 是一個胖指標,因此在 LLVM-IR 中將表示為 (ptr, int) 對。 在這種情況下,演算法也應該遞迴地分析 `T` 並為其產生 metadata。

此處的 函數 可以擴展為從 rust 的中階 IR (MIR) 產生 metadata。 解析器的原型已在 此處 實作,可用於啟發靈感。 我們想要產生的 metadata 的各種 LLVM-IR 範例可以在 測試資料夾中找到。 尋找 ` {[-1]:Pointer, [-1,0]:Float@float}` 風格的註解。

線上編譯器 Explorer 分支可用於觸發相關錯誤,從「無法推斷 X 的型別」開始。

預期成果

參與者應找到並選擇一些有趣的測試案例,在這些案例中,Enzyme 要么由於型別資訊不足而無法區分範例,要么花費過長的時間(例如,比編譯不含自動微分的程式碼慢 20 倍以上)。 在第二種情況下,應使用效能分析器來驗證 Enzyme 是否由於型別分析而導致編譯時間過長。 然後,參與者應編寫(或稍後擴展)型別解析器以產生正確的 metadata,以便 Enzyme 可以處理新的測試案例。 LIT 測試案例應新增至 rust 編譯器,以避免進一步的迴歸。

目前未正確處理的程式碼範例可以在專案提案階段進行討論。

已確認的導師及其聯絡方式

所需技能

Rust 和 C++ 中等程度知識; 熟悉效能分析器或 LLVM metadata 是一個優勢,但非必要。

專案規模

中等 (~175 小時)

專案難度

中等

討論區: 網址

描述: 目前,每個想要支援呼叫 C 程式碼 (FFI) 的基於 LLVM 的前端都需要重新實作大量複雜的呼叫 ABI 處理。 本專案的目標是引入一個 LLVM ABI 函式庫,該函式庫可以在不同的前端(包括 Clang)之間重複使用。 有關動機的更多詳細資訊以及設計的廣泛概述,請參閱 相應的 RFC

專案的初始階段將是實作一個原型,該原型至少可以處理 x86_64 System V ABI。 這將涉及實作 ABI 型別系統、將 Clang 型別映射到 ABI 型別,以及將至少一部分 X86 ABIInfo 實作從 Clang 移至新的 ABI 函式庫。 這是為了證明一般可行性、找出設計問題並分析編譯時間的影響。

假設原型的結果是正面的,下一步將是透過將其拆分為更小的 PR 來向上游實作。 最後,可以擴展實作以涵蓋其他目標,最終完全刪除 Clang 的 ABI 處理程式碼。

預期成果: 最低限度的成果是 x86_64 ABI 的原型。 最大限度的成果是對所有目標的完全向上游支援。 預期的成果介於兩者之間。

技能: C++ 中等程度知識。 熟悉 LLVM 是一個優勢,但非必要。

專案規模: 大型

難度: 困難

已確認指導教授: Nikita Popov

討論區: 網址

描述: 由於缺乏表示原始記憶體的方式,LLVM IR 無法正確表示 memcpy、memcmp 等的實作。 本專案旨在向 LLVM IR 新增一個新的「byte」型別,以表示原始記憶體。

除了新增新的型別之外,該專案還涉及變更 clang 以將 chars 降級為新的 b8 型別而不是 i8,修復記憶體內建函數的不正確降級,並追蹤效能迴歸。

已經有一個針對舊版本 LLVM 的 byte 型別的 原型 實作。 更多資訊請參閱 此處

預期成果: 最低限度的成果是將現有的原型移植到目前的 LLVM,修復所有已知的錯誤最佳化,新增對 Alive2 的 byte 型別的支援,以及效能分析。

技能: C++ 中等程度知識,熟悉 LLVM、效能分析。

專案規模: 大型

難度: 困難

已確認指導教授: Nuno Lopes

討論區: 網址

描述: LLVM 透過 remarks、效能分析或執行階段偵錯註解(例如,LIBOMPTARGET_INFO=-1)提供不同的資訊。 然而,隨著專案的增加,使用者很難剖析這些資訊。 例如,在建構大型專案時,很難收集所有這些資料、將其視覺化並從中學習。

目前,某些資訊(例如,編譯 remarks)可以 JSON 格式匯出。 我們想要建立一個工具來視覺化、彙總和總結資訊。 為了協助加速器開發,我們將從卸載專案開始作為主要候選專案。

類似的工具(例如 opt-viewer)可以用作參考和起點。

預期成果: 預期的成果是一個工具(例如,以編譯器封裝器(如 ccache)的形式),它將允許以 JSON 格式轉儲所有編譯器產生的資訊,並將其組織在專案結構中。

該工具應產生基於 HTML 的報告,以協助視覺化 remarks。 我們設想一個小型用戶端-伺服器應用程式,使用 Python 生成一個本機伺服器作為視覺化的前端。 伺服器將公開不同的報告,並執行早期分析和彙總。

此外,該工具的設計應使其在未來能夠分析 remarks,從而為開發人員提供通用指南(例如,顯示最常見的 remark、使用 LLM 模型來解釋操作等)。 用戶端(HTML 檢視器)將顯示彙總的資料、內嵌 remarks、效能分析資訊等。 我們不期望該專案在 GSoC 結束時具備所有功能,但可以作為未來成長的基礎。

特別是,本專案的成果應該是

  • 與指導教授一起協助設計編譯器封裝器、資料儲存層和用戶端/伺服器基礎架構。 這包括伺服器 API。 此任務的成果是一份設計文件(類似於 RFC)。
  • 建立一個編譯器封裝器,將不同的資訊以 JSON 格式轉儲到資料儲存層(例如,資料夾)中。
  • 建立一個簡單的伺服器層,向前端公開後端 API。 Python 是正確的方法,但我們歡迎其他與 LLVM 專案一致的建議。 我們希望避免依賴外部專案(例如 Flask),以避免向 LLVM 專案新增更多相依性。
  • 建立一個簡單的用戶端視覺化工具,該工具在未來可以擴展以顯示更多報告。

指導教授: @shiltian@jdoerfert@josemonsalve2

必要/期望的技能

  • 基本理解 LLVM 編譯器,能夠從編譯器產生編譯器 remarks、效能分析資料和其他資訊。
  • 精通 Python 和 C++。
  • 全端網頁開發。

專案規模: 大型

難度: 簡單

討論區連結: [GSoC][Offload]LLVM 卸載編譯器 Remarks 視覺化工具提案

Google Summer of Code 2024 對於 LLVM 專案來說又是成功的一年。 有關已接受和已完成專案的列表,請查看 Google Summer of Code 網站

歡迎有潛力的 Google Summer of Code 2024 學生! 本文件是您尋找 LLVM、Clang 和其他相關子專案中有趣且重要專案的起點。 此專案列表不僅是為 Google Summer of Code 開發的,也是真正需要開發人員參與且對 LLVM 社群非常有益的開放專案。

我們鼓勵您瀏覽此列表,看看哪些專案讓您感到興奮,並與您的技能組合非常吻合。我們也歡迎未在此列表中的提案。有關 GSoC 的更多資訊和討論,請參閱 discourse 。如果您對特定專案有疑問,請在 discourse 中找到相關條目,查看先前的討論並提問。如果沒有此類條目,或者您想提出想法,請建立一個新條目。來自社群的回饋是您的提案被考慮並希望被接受的要求。

LLVM 專案已參與 Google Summer of Code 多年,並取得了一些非常成功的專案。 我們希望今年也不例外,並期待收到您的提案。 有關如何提交提案的資訊,請造訪 Google Summer of Code 主要 網站。

專案描述: LLVM 的許多單元測試都是從較大的測試中自動縮減而來的。 上一代縮減工具到處都使用 undef 和 poison 作為佔位符,並且還引入了未定義行為 (UB)。 具有 UB 的測試是不理想的,因為 1) 它們很脆弱,因為未來編譯器可能會開始更積極地最佳化並破壞測試,以及 2) 它破壞了翻譯驗證工具,例如 Alive2(因為將始終為 UB 的函數翻譯成任何內容都是正確的)。
主要步驟包括

  1. 將已知模式(例如,undef/poison 上的分支、具有無效指標的記憶體存取等)替換為非 UB 模式。
  2. 使用 Alive2 偵測更多模式(透過搜尋始終為 UB 的測試)。
  3. 報告 Alive2 在刪除 UB 時發現的任何 LLVM 錯誤。

預期成果: 大多數 LLVM 的單元測試將沒有 UB。

技能: 需要腳本編寫(Python 或 PHP)經驗。 鼓勵具有正規表示式經驗。

專案規模: 中等或大型。

難度: 中等

已確認指導教授: Nuno Lopes

討論區: 網址

專案描述: LLVM 中描述 SPIR-V 指令集的現有檔案是手動建立的,並且並不總是完整或最新的。 每當需要將新指令新增到 SPIR-V 後端時,都必須修改該檔案。 此外,由於它不是以系統化的方式建立的,因此 SPIR-V 規範中指令的描述方式與 TableGen 檔案中的宣告方式之間通常存在細微的差異。 由於 SPIR-V 後端開發人員在開發新功能時經常使用規範作為參考,因此在規範與 TableGen 記錄之間建立一致的映射將簡化開發。 本專案建議建立一個腳本,該腳本能夠根據 KhronosGroup/SPIRV-Headers 儲存庫中提供的 JSON 文法產生一個完整的 TableGen 檔案,該檔案描述 SPIR-V 指令集,並更新 SPIR-V 後端程式碼以使用新的定義。 將 JSON 文法轉換為 TableGen 的具體方法由申請人自行決定,但是,應將其檢入 LLVM 儲存庫,並附上詳細的文件說明以複製轉換過程,以便未來的維護人員能夠在文法變更時重新產生檔案。 請注意,文法本身應保留在樹狀結構之外,在其現有的獨立儲存庫中。

預期結果

  • TableGen 中 SPIR-V 指令集的定義將替換為自動產生的定義。
  • 編寫了一個腳本和文件,支援根據 SPIR-V 指令集的 JSON 文法,根據需要重新產生定義。
  • SPIR-V 後端中 SPIR-V 指令集的使用已更新為使用新的自動產生定義。

技能: 腳本編寫經驗和 C++ 中等程度知識。 之前具有 LLVM/TableGen 經驗是一個優勢,但非必要。

專案規模: 中型(175 小時)

已確認指導教授: Natalie ChouinardNathan Gauër

討論區: 網址

專案描述: LLVM 位元流檔案格式用於序列化中介編譯器產物,例如 LLVM IR 或 Clang 模組。 在某些情況下,多個位元流檔案儲存相同的資訊,這種重複導致儲存需求增加。

本專案旨在將 LLVM CAS 函式庫整合到 LLVM 位元流檔案格式中。 如果我們將位元流檔案中經常重複的部分分解為單獨的 CAS 物件,我們可以用對規範 CAS 物件的小參考替換所有副本,從而節省儲存空間。

本專案的主要動機用例是依賴性掃描器,它為「隱式發現、顯式建構」的 Clang 模組提供支援。 在實際情況中,即使是區塊層級的粗略去重複也可以將掃描模組快取的大小減半。

預期成果: 有一種方法可以配置 LLVM 位元流寫入器/讀取器以使用 CAS 作為後備儲存。

技能: C++ 中等程度知識,對資料序列化有一定的熟悉度,自我激勵。

專案規模: 中型或大型

已確認指導教授: Jan SvobodaSteven Wu

討論區: 網址

專案描述: 3 向比較 傳回值 -1、0 或 1,具體取決於值比較是較小、相等還是較大。 它們在 C++ 中透過太空船運算子 (operator<=>) 公開,在 Rust 中透過 PartialOrd 和 Ord 特徵公開。 目前,這種比較在某些情況下會產生次佳的程式碼產生和最佳化結果。

本專案的目標是透過實作新的 3 向比較內建函數來解決這些最佳化問題,如 [RFC] 新增 3 向比較內建函數 中所述。 實作步驟大致如下

  1. 將內建函數新增到 LLVM IR。
  2. 在 SelectionDAG 和 GlobalISel 中實作合法化/擴充支援。
  3. 在 ConstantFolding、InstSimplify、InstCombine、CorrelatedValuePropagation、IndVarSimplify、ConstraintElimination、IPSCCP 和其他相關轉換中實作最佳化支援。
  4. 透過 InstCombine 正規化或 clang/rustc 中的直接發射來使用內建函數。
新增目標獨立的內建函數是熟悉 LLVM 廣泛領域的好方法!

預期成果: 後端和最重要的最佳化傳遞中對內建函數的支援。 理想情況下,從前端開始完全整合。

技能: C++ 中等程度知識

專案規模: 中型或大型

難度: 中等

已確認指導教授: Nikita PopovDhruv Chawla

討論區: 網址

專案描述: llvm.org 網站是關於 LLVM 專案資訊的中心樞紐,涵蓋專案詳細資訊、當前事件和相關資源。 隨著時間的推移,網站已經有機地發展,促使需要重新設計以增強其現代性、結構和易於維護性。

本專案的目標是建立一個現代且連貫的靜態網站,以反映 LLVM.org 的本質。 此重新設計旨在改善導航、分類、內容可發現性、行動裝置支援、可存取性和整體可用性。 鑑於該網站在社群中的關鍵作用,將努力與社群成員互動,就擬議的變更尋求共識。

預期成果: 一個現代、外觀連貫的網站,可以吸引新的潛在使用者,並透過更好的導航、分類、內容可發現性和整體可用性來增強現有社群的能力。 由於該網站是一個關鍵基礎架構,並且大多數社群成員都會有意見,因此本專案應嘗試與社群互動,建立社群對所採取步驟的共識。 建議方法

  • 對現有網站進行全面的內容稽核。
  • 選擇適當的技術,最好是 Hugo 或 Jekyll 等靜態網站產生器。
  • 倡導資料和視覺化的分離,利用 YAML 和 Markdown 等格式來促進內容管理,而無需直接進行 HTML 編碼。
  • 展示新網站的三個設計模型,促進公開討論,並允許感興趣的各方提出替代方案的時間。
  • 實作選定的設計,並納入社群的寶貴意見回饋。
  • 與內容建立者協作,以根據需要整合或更新內容。
成功的候選人應承諾定期參與每週會議、進行簡報,並根據要求撰寫部落格文章。 此外,他們應展現出耐心和理解力來駕馭社群流程的能力。

技能: 靜態網站產生器網頁開發領域的知識。 HTML、CSS、Bootstrap 和 Markdown 方面的知識。 耐心和自我激勵。

難度: 困難

專案規模: 大型

已確認指導教授: Tanya LattnerVassil Vassilev

討論區: 網址

專案描述: Clang 編譯器是 LLVM 編譯器基礎架構的一部分,支援多種語言,例如 C、C++、ObjC 和 ObjC++。 LLVM 和 Clang 的設計使其能夠作為函式庫使用,並促成了整個編譯器輔助工具生態系統的創建。 Clang 相對友善的程式碼庫以及 LLVM 中 JIT 基礎架構的進步,進一步推動了對不同 C++ 處理方法的研究,模糊了編譯時間和運行時間之間的界線。 挑戰包括增量編譯以及將編譯/連結時間最佳化融入更動態的環境中。

增量編譯管線透過建構不斷成長的翻譯單元,逐塊處理程式碼。 然後將程式碼降低到 LLVM IR 中,並隨後由 LLVM JIT 執行。 這種管線允許建立高效的直譯器。 直譯器實現了互動式探索,並使 C++ 語言更加使用者友善。 Clang-Repl 就是一個例子。

Clang-Repl 在同一個進程中使用 Orcv2 JIT 基礎架構。 這種設計高效且易於實作,但存在兩個重大缺點。 首先,它不能用於資源不足以託管整個基礎架構的裝置中,例如 arduino due(有關更多詳細資訊,請參閱此 演講)。 其次,使用者程式碼中的崩潰意味著整個進程崩潰,從而妨礙了整體可靠性和易用性。

本專案旨在將 Clang-Repl 移至進程外執行模型,以解決這兩個問題。

預期成果: 實作 Clang-Repl 的語句的進程外執行; 證明 Clang-Repl 可以支援 ez-clang 的一些用例; 研究在崩潰時重新啟動/繼續會話的方法; 作為一個延伸目標,設計一個用於崩潰恢復的多功能可靠性方法;

技能: C++ 中等程度知識,理解 LLVM 和 LLVM JIT,尤其如此

專案規模:中型或大型。

難度: 中等

已確認指導教授: Vassil Vassilev

討論區: 網址

專案描述: Clang 編譯器是 LLVM 編譯器基礎架構的一部分,支援多種語言,例如 C、C++、ObjC 和 ObjC++。 LLVM 和 Clang 的設計允許使用外掛程式 [1] 擴展編譯器。 外掛程式使得在編譯期間運行額外的使用者定義動作成為可能。 由於 Windows 平台的一些特殊性,Unix 和 Darwin 上支援外掛程式,但在 Windows 上不受支援。

本專案將使參與者接觸到 LLVM 程式碼庫的廣泛橫截面。 它涉及探索 API 介面、將介面分類為公共或私有,以及將該資訊註解到 API 宣告中。 它還將使參與者接觸到不同平台的詳細資訊和差異,因為這項工作是跨平台的(Windows、Linux、Darwin、BSD 等)。 由此產生的變更將改善 Linux 和 Windows 上的 LLVM,同時在 Windows 上啟用新功能。

預期成果: 本專案旨在使 clang -fplugin=windows/plugin.dll 工作。 實作方法應擴展工作原型 [3] 並擴展註解工具 [4]。 成功的候選人應準備好參加每週會議、進行簡報並根據要求準備部落格文章。

進一步閱讀
[1] https://clang.llvm.org/docs/ClangPlugins.html
[2] https://discourse.llvm.org/t/clang-plugins-on-windows
[3] https://github.com/llvm/llvm-project/pull/67502
[4] https://github.com/compnerd/ids

技能: C++ 中等程度知識,具有 Windows 及其編譯和連結模型方面的經驗。

專案規模:中型或大型。

難度: 中等

已確認指導教授: Vassil VassilevSaleem Abdulrasool

討論區: 網址

專案描述: Clang 與任何 C++ 編譯器一樣,線性地解析字元序列。 線性字元序列然後在降低為機器碼之前轉換為 token 和 AST。 在許多情況下,終端使用者程式碼僅使用整個翻譯單元中 C++ 實體的一小部分,但使用者仍然要為編譯所有冗餘付出代價。

本專案建議在使用時而不是急切地處理繁重的編譯 C++ 實體。 Clang 的 CodeGen 已經採用了這種方法,它允許 Clang 僅為正在使用的內容產生程式碼。 預計按需編譯將顯著減少編譯峰值記憶體並縮短稀疏使用其內容的翻譯單元的編譯時間。 此外,這將對互動式 C++ 產生重大影響,其中標頭包含本質上變為空操作,並且實體將僅按需解析。

Cling 直譯器實作了一個非常幼稚但高效的跨翻譯單元延遲編譯最佳化,該最佳化在高能物理領域的數百個函式庫中進行擴展。

// A.h
#include <string>
#include <vector>
template <class T, class U = int> struct AStruct {
  void doIt() { /*...*/ }
  const char* data;
  // ...
};

template<class T, class U = AStruct<T>>
inline void freeFunction() { /* ... */ }
inline void doit(unsigned N = 1) { /* ... */ }

// Main.cpp
#include "A.h"
int main() {
  doit();
  return 0;
}
    


這個病態的範例擴展到 37253 行程式碼來處理。 Cling 建構索引(它稱之為自動載入映射),其中僅包含這些 C++ 實體的前向宣告。 它們的大小為 3000 行程式碼。 索引看起來像
// A.h.index
namespace std{inline namespace __1{template <class _Tp, class _Allocator> class __attribute__((annotate("$clingAutoload$vector")))  __attribute__((annotate("$clingAutoload$A.h")))  __vector_base;
  }}
...
template <class T, class U = int> struct __attribute__((annotate("$clingAutoload$A.h"))) AStruct;
    


在需要實體的完整型別時,Cling 會包含相關的標頭檔以獲取它。 有幾種簡單的變通方法可以處理預設引數和預設模板引數,因為它們現在出現在前向宣告和定義中。 您可以在 [1] 中閱讀更多內容。

儘管該實作不能稱為參考實作,但它表明 Clang 的 Parser 和 Preprocessor 相對無狀態,可用於處理本質上非線性的字元序列。 特別是命名空間範圍定義相對容易處理,並且在我們延遲解析某些內容時返回命名空間範圍並非非常困難。 對於其他上下文(例如區域類別),我們將遺失一些基本資訊,例如區域實體的名稱查找表。 但是,這些情況可能不是很令人感興趣,因為延遲解析粒度可能僅適用於頂級實體。

這種實作可以幫助解決標準中已經存在的問題,例如 CWG2335,根據該問題,當類別的延遲部分首次需要時立即解析,前提是第一次使用先於類別的結尾。 這應該為上游所有返回封閉範圍並解析某些內容所需的操作提供良好的動機。

實作方法:在解析期間看到標籤定義時,我們可以建立一個前向宣告,記錄 token 序列並將其標記為延遲定義。 稍後在完整型別請求時,我們可以重新定位解析器以解析定義主體。 我們已經以類似的方式跳過了某些模板特化 [2, 3]。

另一種方法是每個延遲解析的實體都記錄其 token 流,並變更儲存在 LateParsedDeclarations 上的 Toks 以選擇性地引用外部儲存的 token 序列的子序列,而不是儲存其自己的序列(或者可能變更 CachedTokens 以使其可以透明地執行此操作)。 其中一個挑戰是我們目前修改快取 token 列表以附加「eof」token,但應該可以以不同的方式處理它。

在某些情況下,類別定義可能會以幾種方式影響其周圍的上下文,您需要在此處小心

1) 出現在類別內的 `struct X` 可以在封閉上下文中引入名稱 `X`。

2) `static inline` 宣告可以引入具有非恆定初始值設定項的全域變數,這些變數可能具有任意副作用。

對於第 (2) 點,有一個更普遍的問題:解析任何表達式都可能觸發類別模板的模板實例化,該模板具有一個靜態資料成員,其初始值設定項具有副作用。 與上述兩種情況不同,我不認為我們可以透過對 token 流進行一些簡單的分析來正確偵測和處理這種情況; 需要實際的語義分析來偵測這種情況。 但也許如果它們僅發生在本身未使用的程式碼中,那麼 Clang 擁有一種不保證這些實例化實際發生的語言模式並不是一件可怕的事情。

另一種更有效率的實作可能是使查找表基於範圍,但我們甚至沒有原型證明這可能是一種可行的方法。

預期結果

  • 非模板化函數的按需編譯的設計和實作
  • 支援非模板化結構和類別
  • 在相關程式碼庫上運行效能基準測試並準備報告
  • 準備社群 RFC 文件
  • [延伸目標] 支援模板
成功的候選人應承諾定期參與每週會議、進行簡報,並根據要求撰寫部落格文章。 此外,他們應展現出耐心和理解力來駕馭社群流程的能力。

進一步閱讀
[1] https://github.com/root-project/root/blob/master/README/README.CXXMODULES.md#header-parsing-in-root
[2] https://github.com/llvm/llvm-project/commit/b9fa99649bc99
[3] https://github.com/llvm/llvm-project/commit/0f192e89405ce

技能: C++ 知識,更深入地了解 Clang 的工作原理,Clang AST 和 Preprocessor 的知識。

專案規模:大型

難度: 困難

已確認指導教授: Vassil VassilevMatheus Izvekov

討論區: 網址

專案描述: Clang-Doc 是一個 C/C++ 文件產生工具,作為 Doxygen 的替代品而建立,並建立在 LibTooling 之上。 這項工作始於 2018 年,關鍵群眾在 2019 年登陸,但此後的開發基本上處於休眠狀態,主要是由於資源匱乏。

該工具目前可以產生 Markdown 和 HTML 格式的文件,但該工具存在一些結構性問題,難以使用,產生的文件存在可用性問題,並且缺少幾個關鍵功能

  • 並非所有 C/C++ 建構目前都由 Markdown 和 HTML 發射器處理,從而限制了該工具的可用性。
  • 產生的 HTML 輸出無法隨著程式碼庫的大小而擴展,這使得它對於較大的 C/C++ 專案不可用。
  • 實作並不總是使用最有效或最合適的資料結構,這會導致正確性和效能問題。
  • 存在許多重複的樣板程式碼,可以使用模板和輔助函數來改進。

預期成果: 本專案的目標是解決現有的缺點並提高 Clang-Doc 的可用性,使其達到可用於為 LLVM 等大型專案產生文件的程度。 理想的結果是 LLVM 專案將使用 Clang-Doc 來產生其 參考文件

成功的提案不僅應關注解決現有的限制,還應從其他類似工具(例如 hdocstandardesesubdoccppdocgen)中汲取其他潛在改進的靈感。

技能: 具有網頁技術(HTML、CSS、JS)的經驗和 C++ 中等程度知識。 之前具有 Clang/LibTooling 經驗是一個優勢,但非必要。

專案規模: 中等或大型。

難度: 中等

已確認的導師: Petr HosekPaul Kirth

討論區: 網址

描述

使用來自除錯資訊的變數位置資訊,以來源變數的位置和生命週期註解 LLDB 的反組譯器 (和 `register read`) 輸出。豐富的反組譯器輸出應公開為結構化資料,並透過 LLDB 的腳本 API 提供,以便可以在此基礎上建置更多工具。在終端機中,LLDB 應將註解呈現為文字。

預期成果

例如,我們可以增強以下函數的反組譯
frame #0: 0x0000000100000f80 a.out`main(argc=1, argv=0x00007ff7bfeff1d8) at demo.c:4:10 [opt]
  1   void puts(const char*);
  2   int main(int argc, char **argv) {
  3    for (int i = 0; i < argc; ++i)
→ 4      puts(argv[i]);
  5    return 0;
  6   }
(lldb) disassemble
a.out`main:
...
  0x100000f71 <+17>: movl  %edi, %r14d
  0x100000f74 <+20>: xorl  %r15d, %r15d
  0x100000f77 <+23>: nopw  (%rax,%rax)
→  0x100000f80 <+32>: movq  (%rbx,%r15,8), %rdi
  0x100000f84 <+36>: callq 0x100000f9e ; symbol stub for: puts
  0x100000f89 <+41>: incq  %r15
  0x100000f8c <+44>: cmpq  %r15, %r14
  0x100000f8f <+47>: jne 0x100000f80 ; <+32> at demo.c:4:10
  0x100000f91 <+49>: addq  $0x8, %rsp
  0x100000f95 <+53>: popq  %rbx
...

使用 LLDB 也可存取的除錯資訊 (觀察來源變數 i 如何從 [0x100000f77+slide) 開始在 r15 中)

$ dwarfdump demo.dSYM --name  i
demo.dSYM/Contents/Resources/DWARF/demo: file format Mach-O 64-bit x86-64
0x00000076: DW_TAG_variable
 DW_AT_location (0x00000098:
 [0x0000000100000f60, 0x0000000100000f77): DW_OP_consts +0, DW_OP_stack_value
 [0x0000000100000f77, 0x0000000100000f91): DW_OP_reg15 R15)
 DW_AT_name ("i")
 DW_AT_decl_file ("/tmp/t.c")
 DW_AT_decl_line (3)
 DW_AT_type (0x000000b2 "int")
產生像這樣的輸出,我們在其中註解變數何時有效及其位置
(lldb) disassemble
a.out`main:
...                                                               ; i=0
  0x100000f74 <+20>: xorl  %r15d, %r15d                           ; i=r15
  0x100000f77 <+23>: nopw  (%rax,%rax)                            ; |
→  0x100000f80 <+32>: movq  (%rbx,%r15,8), %rdi                   ; |
  0x100000f84 <+36>: callq 0x100000f9e ; symbol stub for: puts    ; |
  0x100000f89 <+41>: incq  %r15                                   ; |
  0x100000f8c <+44>: cmpq  %r15, %r14                             ; |
  0x100000f8f <+47>: jne 0x100000f80 ; <+32> at t.c:4:10          ; |
  0x100000f91 <+49>: addq  $0x8, %rsp                             ; i=undef
  0x100000f95 <+53>: popq  %rbx

目標是為一組明確的案例產生像這樣的輸出,例如,常數或完全在暫存器中的變數。

已確認的導師及其聯絡方式

  • Adrian Prantl aprantl@apple.com (主要聯絡人)
  • Jonas Devlieghere jdevlieghere@apple.com

所需/期望的技能

必要條件

  • 良好的 C++ 理解能力
  • 熟悉在終端機上使用除錯器
  • 需要熟悉上面範例中提及的所有概念
  • 需要充分理解至少一種機器碼的組合語言 (x86_64 或 AArch64)。

期望條件

  • 編譯器知識,包括資料流和控制流分析,是加分項。
  • 能夠瀏覽除錯資訊 (DWARF) 是加分項。

專案規模。

中等 (~175 小時)

如果可能,給出簡單、中等或困難的評級

困難

Discourse: 網址

描述

LLVM-reduce 和類似工具執行增量偵錯,但如果存在許多隱式約束,並且違規很容易導致類似於要隔離的原因的錯誤,則它們不太有用。 本專案是關於開發 GPU 感知版本,特別是對於執行時間錯誤,該版本可以與 LLVM/OpenMP GPU 記錄和重播或簡單的 GPU 載入器腳本結合使用,以更有效和高效地最小化 GPU 測試案例。

預期成果

一種減少 GPU 錯誤而不遺失原始錯誤的工具。 或者,其他屬性可以是縮減的重點,而不僅僅是錯誤。

已確認的導師及其聯絡方式

  • Parasyris,Konstantinos parasyris1@llnl.gov
  • Johannes Doerfert jdoerfert@llnl.gov

所需/期望的技能

必要條件

  • 良好的 C++ 理解能力
  • 熟悉 GPU 和 LLVM-IR

期望條件

  • 編譯器知識,包括資料流和控制流分析,是加分項。
  • 具有偵錯和錯誤縮減技術(llvm-reduce)的經驗會有所幫助

專案規模。

中等

如果可能,給出簡單、中等或困難的評級

中等

討論區: 網址

描述

現代 C++ 將並行演算法定義為標準函式庫的一部分,例如 `std::transform_reduce(std::execution::par_unseq, vec.begin(), vec.end(), 0, std::plus, …)`。 在這個專案中,我們希望擴展使用 OpenMP 的實作,包括 GPU 卸載(在合理的情況下)。 雖然某些演算法可能適合透過純粹的(封裝器)運行時解決方案進行 GPU 卸載,但我們知道其他演算法,尤其是那些具有使用者提供的函子的演算法,也將需要靜態程式分析和潛在的轉換以進行額外的資料管理。 該專案的目標是探索不同的演算法以及我們擁有的選項,以在主機以及加速器裝置(尤其是 GPU)上透過 OpenMP 自動執行它們。

預期成果

改進 libcxx 中卸載的原型支援。 針對其他卸載方法進行評估,並記錄遺失的部分和缺點。

已確認的導師及其聯絡方式

  • Johannes Doerfert jdoerfert@llnl.gov
  • Tom Scogland scogland1@llnl.gov
  • Tom Deakin tom.deakin@bristol.ac.uk

所需/期望的技能

必要條件

  • 對 C++ 和 C++ 標準演算法有良好的理解
  • 熟悉 GPU 和(OpenMP)卸載

期望條件

  • 具有 libcxx(開發)經驗。
  • 具有偵錯和效能分析 GPU 程式碼的經驗。

專案規模。

大型

如果可能,給出簡單、中等或困難的評級

中等

討論區: 網址

描述

LLVM 有很多閾值和標誌來避免「成本高昂的情況」。 但是,尚不清楚這些閾值是否有用、它們的值是否合理以及它們的真正影響是什麼。 由於閾值很多,我們無法進行簡單的窮舉搜尋。 在一些原型工作中,我們引入了一個 C++ 類別,它可以替換硬編碼的值並提供對閾值的控制,例如,您可以透過命令列標誌將遞迴限制從硬編碼的「6」增加到不同的數字。 在這個專案中,我們想要探索閾值、它們何時被命中、它們被命中意味著什麼、我們應該如何選擇它們的值,以及我們是否需要不同的「設定檔」。

預期成果

關於 LLVM 程式碼庫內各種閾值影響的統計證據,包括編譯時間變更、對轉換的影響和效能測量。

已確認的導師及其聯絡方式

  • Jan Hueckelheim jhueckelheim@anl.gov
  • Johannes Doerfert jdoerfert@llnl.gov
  • William Moses wmoses@mit.edu

所需/期望的技能

必要條件

  • 統計推理的分析技能與知識

期望條件

  • 良好理解 LLVM 程式碼庫與最佳化流程

專案規模。

中等

如果可能,給出簡單、中等或困難的評級

簡單

討論區: URL

描述

我們已開始著手開發以 GPU 為目標的 libc 函式庫。這將允許使用者在 GPU 上執行時呼叫如 malloc 或 memcpy 等函式。然而,這些實作的功能性與效能至關重要。此專案的目標是針對 GPU 上特定 libc 函式的實作進行基準測試。工作內容將包括編寫基準測試以測試目前的實作,以及編寫更佳化的實作。

預期成果

libc 函式的深入效能分析。GPU 到 CPU 遠端程序呼叫的額外負擔。「libc」函式的更佳化實作。

已確認的導師及其聯絡方式

  • Joseph Huber joseph.huber@amd.com
  • Johannes Doerfert jdoerfert@llnl.gov

所需/期望的技能

必要條件

  • 分析技能與對 GPU 架構的理解

期望條件

  • libc 工具程式的使用經驗

專案規模。

如果可能,給出簡單、中等或困難的評級

簡單

討論區: URL

描述

GPU First 是一種方法論與框架,可使任何現有的主機程式碼在 GPU 上執行整個程式,而無需使用者進行任何修改。此專案的目標有兩個: 1) 將 主機程式碼移植以處理與新外掛程式的 RPC,並使用 GPU LibC 專案中引入的主機 RPC 框架重寫它。 2) 探索在單一 GPU 甚至多個 GPU 上,多個執行緒區塊之間對 MPI 的支援。

預期成果

更有效率的 GPU First 框架,可以支援 NVIDIA 和 AMD GPU。可選擇性地將此框架向上游提交。

已確認的導師及其聯絡方式

  • Shilei Tian i@tianshilei.me
  • Johannes Doerfert jdoerfert@llnl.gov
  • Joseph Huber joseph.huber@amd.com

所需/期望的技能

必要條件

  • 良好理解 C++ 與 GPU 架構
  • 熟悉 GPU 和 LLVM IR

期望條件

  • 良好理解 LLVM 程式碼庫與 OpenMP 目標卸載

專案規模。

中等

如果可能,給出簡單、中等或困難的評級

中等

討論區: URL

專案描述: 諸如 SYCLOpenMPOpenACC 等異質程式設計模型,協助開發人員將計算密集型核心程式卸載到 GPU 和其他加速器。MLIR 有望為下一代異質程式設計模型的編譯器,解鎖新的高階最佳化和更好的程式碼生成。然而,具備穩健的 MLIR 發射 C/C++ 前端是這些努力的先決條件。

ClangIR (CIR) 專案旨在為 Clang 建立新的中介表示法 (IR)。ClangIR 建構於 MLIR 之上,為 Clang 中基於 C/C++ 的語言提供方言,以及從 Clang AST 發射它的必要基礎架構,以及通往 LLVM-IR 方言的降低路徑。在過去一年中,ClangIR 已發展成為成熟的孵化器專案,並且最近關於將其向上游提交到 LLVM monorepo 的 RFC 已獲得正面評論和社群支持。

此 GSoC 專案的總體目標是識別並實作 ClangIR 中缺少的特性,以使其能夠將 OpenCL C 語言中的 GPU 核心程式編譯為 SPIR-V 目標的 LLVM-IR。OpenCL 到 SPIR-V 的流程是此專案的絕佳環境,因為 a) 它在 Clang 中已受到支援,且 b) OpenCL 基於工作項目和工作組的程式設計模型仍然很好地捕捉了現代 GPU 架構。貢獻者將擴展 AST 訪問器、方言和 LLVM-IR 降低,以新增對多個位址空間、向量和自訂浮點類型,以及 spir_kernelspir_func 呼叫慣例的支援。

此項工作的良好起點是 Polybench-GPU 基準測試套件。它包含常見演算法的獨立小型到中型 OpenCL 實作。我們預期只有裝置程式碼 (*.cl 檔案) 會透過 ClangIR 編譯。Clang 中現有的 OpenCL 支援可用於建立具有參考 LLVM-IR 輸出的 lit 測試,以引導開發。或者,Polybench 中的內建結果驗證和時間測量也可用於評估生成程式碼的正確性和品質。

預期成果: Polybench-GPU 的 2DCONVGEMMCORR OpenCL 核心程式可以使用 ClangIR 編譯為 SPIR-V 的 LLVM-IR。

技能: 需要中級 C++ 程式設計技能和對基本編譯器設計概念的熟悉度。具備 LLVM IR、MLIR、Clang 或 GPU 程式設計的先前經驗會是很大的加分,但學習意願也是一種可能性。

專案規模: 大型

難度: 中等

已確認指導老師: Julian OppermannVictor LomüllerBruno Cardoso Lopes

討論區: URL

描述

半精度是一種 IEEE 754 浮點格式,近年來已廣泛使用,尤其是在機器學習和 AI 領域。它已在最新的 C23 標準中標準化為 _Float16,使其支援程度與 float 或 double 資料類型相同。此專案的目標是在 LLVM libc 函式庫中實作 C23 半精度數學函式。

預期結果

  • 正確設定產生的標頭,以便類型和函式可以與各種編譯器 (+版本) 和架構一起使用。
  • 實作支援半精度資料類型的通用基本數學運算,這些運算可在支援的架構上運作:x86_64、arm (32 + 64)、risc-v (32 + 64) 和 GPU。
  • 盡可能使用編譯器內建函數或特殊硬體指令來實作特化,以提高其效能。
  • 如果時間允許,我們可以開始研究用於半精度的更高階數學函式。

技能

需要中級 C++ 程式設計技能和對基本編譯器設計概念的熟悉度。具備 LLVM IR、MLIR、Clang 或 GPU 程式設計的先前經驗會是很大的加分,但學習意願也是一種可能性。

專案規模: 大型

難度: 簡單/中等

已確認指導老師: Tue LyJoseph Huber

討論區: URL

Google Summer of Code 2023 對於 LLVM 專案來說非常成功。如需已接受和已完成專案的清單,請參閱 Google Summer of Code 網站

專案描述: 在即時編譯器中,我們通常選擇較低的最佳化等級,以盡量減少編譯時間並改善啟動時間和延遲,然而,有些函式 (我們稱之為熱門函式) 使用頻率非常高,對於這些函式,更深入的最佳化是值得的。一般而言,熱門函式只能在執行階段識別 (不同的輸入將導致不同的函式變成熱門函式),因此重新最佳化專案的目標是建構基礎架構,以 (1) 在執行階段偵測熱門函式,以及 (2) 以更高的最佳化等級再次編譯它們,因此稱為「重新最佳化」。

對於這個問題的兩個部分,有許多可能的方法。例如,熱門函式可以透過取樣、使用現有的效能分析基礎架構或實作自訂檢測來識別。重新最佳化可以應用於整個函式,或者可以使用外框化來啟用函式部分的最佳化。從 JIT’d 程式碼重新進入 JIT 基礎架構可以在現有的延遲編譯之上實作,或者透過自訂路徑實作。

無論採用何種設計,目標是基礎架構應該是通用的,以便其他 LLVM API 用戶端可以使用它,並且應該支援進程外 JIT 編譯 (因此某些解決方案將在 ORC 執行階段中實作)。

預期結果

  • 改善間接參照的人體工學設計 – 理想情況下,所有形式的間接參照 (用於重新最佳化、延遲編譯和程序連結表) 都應該能夠在執行階段共用單一 stub (和/或二進位重寫中繼資料)。
  • 在整理後的間接參照之上實作基本重新最佳化。
  • (延伸目標) 垃圾回收不再需要的未最佳化程式碼,一旦最佳化版本可用。

理想技能: 中級 C++;理解 LLVM 和 LLVM JIT,尤其重要。

專案規模: 大型。

難度: 中等

已確認指導老師: Vassil VassilevLang Hames

討論區: URL

專案描述: JITLink 是 LLVM 的新 JIT 連結器 API – 低階 API,可將編譯器輸出 (可重定位物件檔案) 轉換為記憶體中可執行的位元組。為此,JITLink 的通用連結器演算法需要專門化,以支援目標物件格式 (COFF、ELF、MachO) 和架構 (arm、arm64、i386、x86-64)。LLVM 已經擁有成熟的 JITLink 實作,適用於 MachO/arm64、MachO/x86-64、ELF/x86-64、ELF/aarch64 和 COFF/x86-64,而 ELF/riscv、ELF/aarch32 和 COFF/i386 的實作仍然相對較新。
您可以處理全新的架構 (如 PowerPC 或 eBPF),或完成最近新增的 JITLink 實作之一。在這兩種情況下,您都可能會重複使用其中一種目標物件格式的現有通用程式碼。您還將處理重定位解析、填充 PLT 和 GOT,並為您選擇的目標連接 ORC 執行階段。

預期成果: 為尚未支援或不完整的格式/架構 (如 PowerPC、AArch32 或 eBPF) 編寫 JITLink 專門化。

理想技能: 中級 C++;理解 LLVM 和 LLVM JIT,尤其重要;熟悉您選擇的格式/架構,以及基本的連結器概念 (例如區段、符號和重定位)。

專案規模: 大型。

難度:中等

已確認指導老師: Vassil VassilevLang Hames

Stefan Gränitz

討論區: URL

專案描述: 雖然編譯器的主要工作是產生快速的程式碼 (良好的執行階段效能),但最佳化不會花費太多時間 (良好的編譯階段效能) 也很重要。此專案的目標是在不損害最佳化品質的情況下,改善編譯時間。
此專案的總體方法是

  1. 選擇要最佳化的工作負載。例如,這可以是從 CTMark 取得的檔案,以特定的建置組態 (例如 -O0 -g-O3 -flto=thin) 編譯。
  2. 收集效能分析資訊。這可能涉及編譯器選項,例如 -ftime-report-ftime-trace 以獲得高階概觀,以及 perf recordvalgrind --tool=callgrind 以獲得詳細的效能分析。
  3. 識別異常緩慢的位置。這在很大程度上取決於工作負載。
  4. 嘗試最佳化已識別的熱點,理想情況下不影響產生的程式碼。編譯時間追蹤器可用於快速評估對 CTMark 的影響。
作為免責聲明,應注意,在病態案例之外,編譯往往沒有方便的熱點,90% 的時間都花費在該熱點上,而是分散在許多遍歷中。因此,個別的改進也往往只對總體編譯時間產生很小的影響。預期進行 10 次每次 0.2% 的改進,而不是一次 2% 的改進。

預期成果: 某些個別檔案的顯著改進 (多個百分點),以及總體幾何平均編譯時間的小幅改進。

理想技能: 中級 C++。熟悉效能分析工具 (如果您不是在 Linux 上,情況尤其如此,在這種情況下我將無法提供協助)。

專案規模: 中等或大型。

難度: 中等

已確認指導老師: Nikita Popov

討論區: URL

專案描述: Rust 程式語言使用 LLVM 進行程式碼生成,並嚴重依賴 LLVM 的最佳化功能。然而,在許多情況下,LLVM 無法最佳化 rustc 發出的典型程式碼模式。此類問題會使用 I-slow 和/或 A-LLVM 標籤回報。
修復這些問題的常用方法是

  1. Godbolt 上檢查 --emit=llvm-ir 輸出。
  2. 建立一個 LLVM IR 測試案例,該案例在透過 opt -O3 執行時未最佳化。
  3. 識別最小的遺失轉換,並使用 alive2 證明其正確性。
  4. 識別哪個或哪些 LLVM pass 可以執行轉換。
  5. 新增必要的測試覆蓋率並實作轉換。
  6. (稍後:檢查在 Rust 中下一個主要 LLVM 版本升級後,問題是否真正解決。)
此專案的目標是解決一些較不困難的最佳化失敗問題。這表示在某些情況下,流程會在步驟 3 或 4 之後停止,而不會繼續進行實作,因為不清楚如何解決該問題,或者這將需要大量的工作。在這種情況下,對問題進行分析仍然很有價值。

預期成果: 修復許多容易到中等的 Rust 最佳化失敗問題。即使未實作任何修復,也針對某些失敗進行初步分析。

理想技能: 用於實作的中級 C++。對 LLVM 的一些熟悉度 (至少能夠理解 LLVM IR) 用於分析。基本的 Rust 知識 (足以閱讀,但不能編寫 Rust)。

專案規模: 中等或大型。

難度: 中等

已確認指導老師: Nikita Popov

討論區: URL

專案描述: Clang 編譯器是 LLVM 編譯器基礎架構的一部分,支援多種語言,例如 C、C++、ObjC 和 ObjC++。 LLVM 和 Clang 的設計使其能夠作為函式庫使用,並促成了整個編譯器輔助工具生態系統的創建。 Clang 相對友善的程式碼庫以及 LLVM 中 JIT 基礎架構的進步,進一步推動了對不同 C++ 處理方法的研究,模糊了編譯時間和運行時間之間的界線。 挑戰包括增量編譯以及將編譯/連結時間最佳化融入更動態的環境中。

增量編譯管線透過建置不斷成長的翻譯單元,逐區塊處理程式碼。然後將程式碼降低到 LLVM IR 中,並隨後由 LLVM JIT 執行。此類管線允許建立有效率的直譯器。直譯器啟用互動式探索,並使 C++ 語言更易於使用。增量編譯模式由互動式 C++ 直譯器 Cling 使用,Cling 最初是為了在 C++ 環境中啟用互動式高能物理分析而開發的。

我們的團隊致力於透過一個名為 clang-repl 的新工具,將 Cling 的部分內容納入並可能重新設計到 Clang 主線中。該專案旨在設計和實作穩健的自動完成功能,當使用者在 clang-repl 的提示字元下輸入 C++ 時。例如

      [clang-repl] class MyLongClassName {};
      [clang-repl] My<tab>
      // list of suggestions.
    

預期成果: 有幾個預期的任務

  • 研究 clang 中自動完成的目前方法,例如 clang -code-completion-at=file:col1:col2。
  • 使用 clang 的 libInterpreter 中的部分翻譯單元基礎架構,實作自動完成支援的版本。
  • 研究語意自動完成的要求,這會將程式碼的精確語法位置和語意納入考量。例如
              [clang-repl] struct S {S* operator+(S&) { return nullptr;}};
              [clang-repl] S a, b;
              [clang-repl] v = a + <tab> // shows b as the only acceptable choice here.
            
  • 在相關的會議和研討會上展示這項工作。
  • 專案規模:大型。

    難度: 中等

    已確認指導教授: Vassil Vassilev

    討論區: URL

專案描述: Clang 目前在每個 clang 執行個體中獨立處理模組,使用檔案系統來同步哪個執行個體建置給定的模組。由於為模組重用和檔案系統爭用而做出的權衡,這在健全性和效能方面存在許多問題。

Clang 還有另一種建置模組的方式,即顯式建置模組,目前需要變更建置系統才能採用。在這裡,建置系統決定需要哪些模組,例如透過使用 clang-scan-deps,並確保在執行需要它們的 clang 編譯任務之前,先建置這些模組。

為了允許採用這種新的模組建置方式,而無需進行重大的建置系統工作,我們需要一個模組建置守護程式。透過對命令列進行小幅變更,clang 將連線到此守護程式,並要求它需要的模組。然後,模組建置守護程式會傳回現有的有效模組,或建置然後傳回它。

在 llvm-project 分支中,有一個現有的開放原始碼相依性掃描守護程式。這僅處理檔案相依性,但具有 IPC 機制。此 IPC 系統可以用作模組建置守護程式的基礎,但確實需要擴展到可在 Windows 上運作。

預期成果: 使用 Clang 模組和現有建置系統 (如 Make 或 CMake) 的正常專案,可以僅透過模組建置守護程式,使用顯式建置模組來建置。

理想技能: 中級 C++ 程式設計技能;熟悉編譯器;熟悉 Clang 是一種優勢,但非必要條件。

專案規模: 175 小時或 350 小時,取決於 IPC 的重用情況

難度: 中等

已確認指導老師: Michael SpencerJan Svoboda

討論區: URL

專案描述: Swift-DocC 是 Swift OSS 專案的標準文件編譯器。然而,Swift-DocC 並非 Swift 專用,而是使用 SymbolKit 的語言不可知、基於 JSON 的符號圖格式,來理解程式碼中可用的符號,這樣,只要有符號圖產生器,Swift-DocC 就可以支援任何語言。

Clang 支援 C 和 Objective-C 的符號圖生成,如 [RFC] clang support for API information generation in JSON 中所述。如今,對 Objective-C 類別的支援尚不完整,一方面,如果類別擴展了目前模組中的類型,則類別成員會被假定屬於擴展類型本身。另一方面,如果擴展類型屬於另一個模組,則會忽略該類別。儘管如此,在 Objective-C 中擴展屬於其他模組的類型,作為模組公用 API 的一部分是很常見的。此專案的目標是擴展符號圖格式以容納 Objective-C 類別,並實作支援,以透過 clang 和 libclang 產生此資訊。

預期成果: 在 clang 的符號圖產生器和 libclang 中新增必要的支援,以描述在其他模組中定義的符號類別。這可能涉及對 SymbolKit 的新增內容,需要與該社群討論。

理想技能: 中級 C++ 程式設計技能;熟悉 clang 和 Objective-C 是一種優勢,但非必要條件。

專案規模: 中等

難度: 中等

已確認指導老師: Daniel GrumbergZixu WangJuergen Ributzka

討論區: URL

專案描述: Swift-DocC 是 Swift OSS 專案的標準文件編譯器。然而,Swift-DocC 並非 Swift 專用,而是使用 SymbolKit 的語言不可知、基於 JSON 的符號圖格式,來理解程式碼中可用的符號,這樣,只要有符號圖產生器,Swift-DocC 就可以支援任何語言。

Clang 支援 C 和 Objective-C 的符號圖生成,如 [RFC] clang support for API information generation in JSON 中所述。

目前,發射的符號圖格式不支援各種 C++ 建構,例如範本和例外狀況,且符號圖產生器不完全理解 C++。此專案旨在在符號圖格式中引入對各種 C++ 建構的支援,並實作支援,以在 clang 中產生此資料。

預期成果: 在 clang 的符號圖產生器和 libclang 中新增必要的支援,以描述在其他模組中定義的符號類別。這將涉及對 SymbolKit 的新增內容,需要與該社群討論。

理想技能: 中級 C++ 程式設計技能;熟悉 clang 和 Objective-C 是一種優勢,但非必要條件。

專案規模: 大型

難度: 中等/困難

已確認指導老師: Daniel GrumbergZixu WangJuergen Ributzka

討論區: URL

專案描述: Swift-DocC 是 Swift OSS 專案的標準文件編譯器。然而,Swift-DocC 並非 Swift 專用,而是使用 SymbolKit 的語言不可知、基於 JSON 的符號圖格式,來理解程式碼中可用的符號,這樣,只要有符號圖產生器,Swift-DocC 就可以支援任何語言。

Clang 支援 C 和 Objective-C 的符號圖生成,如 [RFC] clang support for API information generation in JSON 中所述。

目前,使用者可以使用 clang,透過 clang -extract-api 命令列介面產生符號圖檔案,或使用 libclang 介面為特定符號產生符號圖。此專案將需要新增第三種模式,該模式將在常規編譯工作的副作用中產生符號圖輸出。這可以啟用將符號圖格式用作 clang Index 或 clangd 的輕量級替代方案,以用於程式碼智慧服務。

預期成果: 啟用在常規編譯 (或模組建置) 期間產生符號圖檔案;提供一種工具來合併符號圖檔案,其方式與靜態連結器連結個別物件檔案的方式相同;擴展 clang Index 以支援符號圖檔案包含的所有資訊。

理想技能: 中級 C++ 程式設計技能;熟悉 clang 和 Objective-C 是一種優勢,但非必要條件。

專案規模: 中等

難度: 中等/困難

已確認指導老師: Daniel GrumbergZixu WangJuergen Ributzka

討論區: URL

專案描述: clang 發射的診斷訊息最終是其開發人員的介面。雖然診斷訊息通常良好,但仍有一些粗糙的地方需要磨平。有些情況也可以透過在編譯器中特殊處理來改善。

正如人們可以從 Clang 的問題追蹤器中看到的那樣,針對 clang 的診斷訊息,有 許多問題 處於開啟狀態。

此專案的目標不是實作一個大型功能,而是專注於對 Clang 診斷訊息進行較小的增量改進。

可能要解決的範例問題

預期成果:至少三個已修復的較小診斷訊息問題,或一個已實作的較大診斷訊息改進。

已確認指導老師:Timm Bäder

期望的技能

  • 中級 C++ 知識。
  • 最好具備 Clang 程式碼庫的經驗,因為所提及的問題可能在 Clang 程式碼庫的各個部分中都有其根本原因。
  • 最好是已運作的本機 LLVM 建置版本

專案類型: 中等/200 小時

討論區 URL

專案描述: Clang 編譯器是 LLVM 編譯器基礎架構的一部分,支援各種語言,例如 C、C++、ObjC 和 ObjC++。LLVM 和 Clang 的設計使其可以用作函式庫,並促成了整個編譯器輔助工具生態系統的建立。Clang 相對友好的程式碼庫和 LLVM 中 JIT 基礎架構的進展,進一步促成了對處理 C++ 的不同方法的研究,模糊了編譯時間和執行階段之間的界線。挑戰包括增量編譯和將編譯/連結時間最佳化納入更動態的環境中。

增量編譯管線透過建置不斷成長的翻譯單元,逐區塊處理程式碼。然後將程式碼降低到 LLVM IR 中,並隨後由 LLVM JIT 執行。此類管線允許建立有效率的直譯器。直譯器啟用互動式探索,並使 C++ 語言更易於使用。增量編譯模式由互動式 C++ 直譯器 Cling 使用,Cling 最初是為了在 C++ 環境中啟用互動式高能物理分析而開發的。

我們投入精力,透過一個名為 clang-repl 的新工具,將 Cling 的部分內容納入並可能重新設計到 Clang 主線中。該專案旨在實作教學課程,示範專案的功能,並研究在 xeus-clang-repl 原型中採用 clang-repl,以允許在 Jupyter 中編寫 C++。

預期成果: 有幾個預期的任務

  • 編寫幾個教學課程,示範 clang-repl 的目前功能。
  • 研究將 clang-repl 新增為 xeus-cling 後端的必要條件。
  • 改善 clang-repl 的 xeus 核心協定。
  • 準備一篇關於 clang-repl 以及可能的 Jupyter 的部落格文章。在相關的會議和研討會上展示這項工作。
  • 已確認指導老師: Vassil Vassilev David Lange

    理想技能: 中級 C++;理解 Clang 和 Clang API,尤其重要

    專案類型: 中等

    討論區 URL

專案描述: Clang 編譯器是 LLVM 編譯器基礎架構的一部分,支援各種語言,例如 C、C++、ObjC 和 ObjC++。LLVM 和 Clang 的設計使其可以用作函式庫,並促成了整個編譯器輔助工具生態系統的建立。Clang 相對友好的程式碼庫和 LLVM 中 JIT 基礎架構的進展,進一步促成了對處理 C++ 的不同方法的研究,模糊了編譯時間和執行階段之間的界線。挑戰包括增量編譯和將編譯/連結時間最佳化納入更動態的環境中。

增量編譯管線透過建置不斷成長的翻譯單元,逐區塊處理程式碼。然後將程式碼降低到 LLVM IR 中,並隨後由 LLVM JIT 執行。此類管線允許建立有效率的直譯器。直譯器啟用互動式探索,並使 C++ 語言更易於使用。增量編譯模式透過 xeus 核心協定,用於 Jupyter 中的互動式 C++。較新版本的協定允許可能的瀏覽器內執行,為 clang-repl 和 Jupyter 提供更多可能性。

我們投入精力,透過一個名為 clang-repl 的新工具,將 Cling 的部分內容納入並可能重新設計到 Clang 主線中。該專案旨在在 clang-repl 中新增 WebAssembly 支援,並在 xeus-clang-repl 中採用它,以協助基於 Jupyter 的 C++。

預期成果: 有幾個預期的任務

  • 研究以類似於新的 互動式 CUDA 支援的方式產生 WebAssembly 的可行性。
  • 啟用在 clang-repl 中產生 WebAssembly。
  • 在 xeus-clang-repl 中採用該功能。
  • 準備一篇關於 clang-repl 以及可能的 Jupyter 的部落格文章。在相關的會議和研討會上展示這項工作。
  • 已確認指導老師: Vassil Vassilev Alexander Penev

    理想技能: 良好 C++;理解 Clang 和 Clang API 以及 LLVM JIT,尤其重要

    專案類型: 大型

    討論區 URL

專案描述 GNU 工具鏈廣泛用於建置嵌入式目標。Clang/LLVM 社群在改進 Clang 工具鏈以支援嵌入式目標方面具有一定的動力。使用 Clang 工具鏈作為替代方案,可以幫助我們提高程式碼品質、尋找和修復安全性錯誤、改善開發人員體驗,並利用圍繞 Clang/LLVM 社群在支援嵌入式裝置方面的新想法和動力。

可以對 LLD 進行的非詳盡改進清單:

  • --print-memory-usage 支援

    GCC 中的「--print-memory-usage」提供連結器檔案中定義的每個記憶體區域中使用的記憶體細目。嵌入式開發人員使用此旗標來了解對記憶體的影響。嵌入式系統通常定義具有不同空間限制的多個記憶體區域。在 Clang 工具鏈中支援此功能,將有助於希望在其專案中使用 Clang 工具鏈的專案。

  • 連結地圖

    目前,LLD 連結器的連結地圖輸出不如 BFD 連結器輸出豐富。在連結地圖輸出上實現功能對等,對於分析 LLD 連結器建立的二進位檔案非常有用。此外,以不同格式 (目前的 LLD 輸出、BFD 和 JSON) 輸出連結地圖,可以幫助建置自動化工具來調查連結器產生的成品。

  • --print-gc-sections 改進

    當啟用「--print-gc-sections」旗標時,LLD 會列印在連結過程中捨棄的區段。此資訊目前不包含符號與區段群組之間的對應,這對於偵錯很有用。在連結過程中保留此資訊,將需要修改內部連結器資料結構。

專案規模: 中等或大型

難度: 中等/困難

技能: C++

預期結果:

  • 實作「--print-memory-usage」旗標。
  • 支援新的連結地圖輸出格式 1. BFD 和 2. JSON。
  • 改進「--print-gc-sections」輸出,以包含有關倖存符號的資訊。

已確認指導老師: Prabhu Rajasekaran Petr Hosek

討論區: URL

專案描述: MLIR 的 Presburger 函式庫 FPL (https://grosser.science/FPL) 為多面體編譯和分析提供數學抽象。該函式庫提供的主要抽象是由仿射不等式約束系統定義的整數元組集合。該函式庫支援對此類集合的標準集合運算。結果將是由另一個約束系統定義的集合,可能具有更多約束。當循序執行許多集合運算時,約束系統可能會變得非常大,從而對效能產生負面影響。有幾種潛在的方法可以簡化約束系統;然而,這涉及執行額外的計算。因此,花費更多時間進行更積極的簡化可能會使每個個別運算變慢,但同時,不充分的簡化可能會由於約束系統大小的爆炸性增長而使運算序列變慢。此專案的目標是找到兩者之間的適當平衡點。

此專案的目標

  • 了解函式庫在執行階段和輸出大小方面的效能。
  • 透過找出最佳輸出大小和效能之間的權衡,來最佳化程式庫。

預期成果:

  • 為程式庫的主要操作進行效能基準測試和輸出限制複雜度分析。
  • 實作簡化啟發式演算法。
  • 更深入了解哪些簡化啟發式演算法能充分提升整體效能,使其值得額外的運算成本。

理想技能: 中階 C++、基準測試經驗

專案規模: 大型

難度: 中等

已確認導師: Kunwar Grover

討論區: 網址

專案描述: 此專案旨在為 MLIR 開發一個互動式查詢語言,讓開發人員能夠動態查詢 MLIR IR。此工具將提供 REPL(或命令列)介面,讓使用者能夠查詢 MLIR 程式碼的各種屬性,例如「isConstant」和「resultOf」。此提案工具旨在與 clang-query 類似,後者允許開發人員使用具有自動完成和其他功能的 TUI,在 C++ 程式碼中比對 AST 表達式。

此專案的目標

  • 理解 MLIR IR 表示法以及使用者進行的常見探索。
  • 實作 REPL 以執行 MLIR IR 上的查詢。

預期成果:

  • 可獨立使用,以互動方式探索 IR。
  • 實作此工具可使用的常見比對器。
  • (延伸目標) 啟用將查詢比對到的 IR 部分提取到獨立的 IR 片段中。

理想技能: 中階 C++、編寫/偵錯 peephole 最佳化經驗

專案規模: 中型或大型。

難度: 中等

已確認導師: Jacques Pienaar

討論區: 網址

專案描述 我們正在實際部署中使用機器引導的編譯器最佳化(「MLGO」),以進行暫存器配置逐出和大小內聯。機器學習模型已使用強化學習演算法進行訓練。擴展到更多效能領域目前受到效能估計模型預測品質不佳的阻礙。改善這些模型對於強化學習訓練演算法的有效性至關重要,因此對於系統性地將 MLGO 應用於更多最佳化至關重要。

專案規模: 175 或 350 小時。

難度: 中等

技能: C/C++、一些編譯器經驗、一些 Python。機器學習經驗是加分項。

預期成果:透過包含額外的執行階段/效能分析資訊(例如額外的 PMU 資料、LLC 未命中機率或分支預測錯誤)來更好地建立執行環境模型。這包括 (1) 建立涵蓋額外執行階段資訊的資料收集管線,(2) 修改機器學習模型以允許處理此資料,以及 (3) 修改模型的訓練和推論過程以使用此資料。

如今,這些模型幾乎是純粹的靜態分析;它們會查看指令,但對於程式碼的執行環境和執行階段行為做出一體適用的假設。此專案的目標是從靜態分析轉向更能代表程式碼實際執行方式的動態模型。

導師 Ondrej Sykora、Mircea Trofin、Aiden Grossman

討論區 網址

專案描述: Clang 靜態分析器帶有一個實驗性的汙染分析實作,這是一種以安全性為導向的分析技術,旨在警告使用者受攻擊者控制(「汙染」)的資料流入敏感函數,如果攻擊者能夠偽造正確的輸入,這些函數可能會以意外且危險的方式運作。程式設計師可以透過正確地「清理」受汙染的資料來解決此類警告,以消除這些危險的輸入。以這種方式可以捕獲的常見問題範例是 SQL 注入。一個更簡單的範例,可以說與 Clang 使用者更相關,是由攻擊者控制的數字引起的緩衝區溢位漏洞,這些數字在疊代堆疊或堆積陣列時用作迴圈邊界,或作為引數傳遞給低階緩衝區操作函數,例如memcpy().

作為一個靜態符號執行引擎,靜態分析器透過簡單地維護在符號模擬期間從已知汙染源獲得的「符號」(命名的未知數值)列表來實作汙染分析。然後,這些符號被視為可能採用任意具體值,而不是採用可能值的未知子集的一般情況。例如,除以未檢查的未知值不一定保證除以零警告,因為通常不知道該值是否可能為零。但是,除以未檢查的受汙染值會立即保證除以零警告,因為攻擊者可以自由地傳遞零作為輸入。因此,靜態分析器的汙染基礎結構由幾個部分組成:有一種機制用於追蹤符號程式狀態中的受汙染符號,有一種方法可以定義新的汙染源,並且教導了一些路徑敏感檢查來使用汙染資訊以發出額外的警告(例如除以零檢查器),充當汙染「接收器」並定義檢查器特定的「清理」條件。

整個設施都被標記為實驗性的:它基本上是一個概念驗證實作。它很可能可以做得非常好,但它需要透過在真實世界的原始碼上運行來進行一些品質控制,並且需要解決許多錯誤,尤其是在個別檢查中,然後我們才能宣告它穩定。此外,所有檢查中最吸引人的檢查 – 基於受汙染的迴圈邊界或大小參數的緩衝區溢位偵測 – 從未實作過。還有一個相關的檢查用於使用受汙染的索引進行陣列存取 – 這再次是實驗性的;讓我們看看我們是否也可以宣告這個檢查穩定!

預期結果: 許多與汙染相關的檢查,預設為靜態分析器的所有使用者啟用,或作為選擇加入提供給關心安全性的使用者。它們被確認在真實世界的程式碼上具有低誤報率。希望緩衝區溢位檢查是其中之一。

理想技能: 中階 C++,能夠理解 LLVM 程式碼。我們也將在一些純 C 程式碼上運行我們的分析。編譯器或安全性方面的一些背景知識是受歡迎的,但並非絕對必要。

專案規模: 中等或大型。

難度: 中等

已確認導師: Artem DergachevGábor HorváthZiqing Luo

討論區: 網址

專案描述 這延續了 GSoC 2020 和 2021 的工作。開發人員通常使用標準最佳化管線(如 -O2 和 -O3)來最佳化他們的程式碼。手動製作的啟發式演算法用於確定要選擇哪些最佳化傳遞以及如何排序這些傳遞的執行。但是,此過程並非針對特定程式或程式類型量身定制,因為它旨在對任何輸入執行「相當好」。我們希望改進現有的啟發式演算法或用基於機器學習的模型取代啟發式演算法,以便 LLVM 編譯器可以為每個程式提供卓越的傳遞順序。最後一個里程碑啟用了特徵提取,並開始研究訓練策略以選擇更合適的傳遞管線。

專案規模: 175 或 350 小時。

難度: 中等

技能: C/C++、一些編譯器經驗。機器學習經驗是加分項。

預期成果:預先訓練的模型,選擇最經濟的最佳化管線,且效能沒有損失;在 LLVM 中掛鉤模型;(重新)訓練工具;透過搜尋或學習提出新的最佳化序列。

導師 Tarindu Jayatilaka、Mircea Trofin、Johannes Doerfert

討論區 網址

專案描述
Clang 支援基於原始碼的覆蓋率,顯示已執行的測試涵蓋了哪些程式碼行 [1]。它使用 llvm-profdata [2] 和 llvm-cov [3] 工具來產生覆蓋率報告。 llvm-cov 目前產生單個頂層索引 HTML 檔案。例如,LLVM 儲存庫的單個頂層目錄程式碼覆蓋率報告 [4] 發佈在覆蓋率機器人上。頂層索引會導致大型專案(如 Fuchsia [5])中的渲染可擴展性問題。此專案的目標是在產生的覆蓋率 html 報告中產生階層式目錄結構,以符合目錄結構並解決可擴展性問題。 Chromium 使用其自己的後處理工具來顯示每個目錄的覆蓋率結果階層式結構 [6]。同樣,Lcov(Gcov 的圖形前端 [7])提供單層目錄結構來顯示覆蓋率結果 [8]
[1] 基於原始碼的程式碼覆蓋率
[2] llvm-profdata
[3] llvm-cov
[4] LLVM 覆蓋率報告
[5] Fuchsia
[6] Chromium 的覆蓋率摘要
[7] Gcov
[8] Lcov 覆蓋率報告
[9] Issue #54711:支援 HTML 覆蓋率報告的每個目錄索引檔案

預期成果: 在產生的覆蓋率 html 報告中實作階層式目錄結構的支援,並在 LLVM 儲存庫程式碼覆蓋率報告中顯示此功能的使用方式。

專案規模: 中等或大型

難度: 中等

已確認導師: Gulfem Savrun Yeniceri Petr Hosek

討論區: 網址

專案描述 開發人員經常使用編譯器產生的備註和分析報告來最佳化他們的程式碼。雖然編譯器通常擅長在產生的訊息中包含原始碼位置(即行號和欄號),但如果這些產生的訊息也包含對應的原始碼層級表達式,則會很有用。 LLVM 實作使用的方法是使用一小組內部函數來定義 LLVM 程式物件與原始碼層級表達式之間的對應。此專案的目標是使用包含在這些內部函數中的資訊來產生對應於 LLVM 值的原始碼表達式,或提出和實作解決方案,以便在現有資訊不足的情況下獲得相同的結果。最佳化程式中的記憶體存取對於應用程式效能非常重要。我們特別打算使用編譯器分析訊息,這些訊息報告對應於 LLVM 載入/儲存指令的原始碼層級記憶體存取,這些指令會抑制編譯器最佳化。例如,我們可以使用此資訊來報告抑制向量化的記憶體存取依賴性。

專案規模: 中等

難度: 中等

技能: 中階 C++、熟悉 LLVM 核心或願意學習。

預期成果: 提供一個介面,該介面接受 LLVM 值並傳回對應於等效原始碼層級表達式的字串。我們特別感興趣的是使用此介面將載入/儲存指令中使用的位址對應到等效的原始碼層級記憶體參考。

已確認導師: Satish Guggilla (satish.guggilla@intel.com) Karthik Senthil (karthik.senthil@intel.com)

討論區: 網址

專案描述
Clang codegen 透過使用 AST 訪問器發出 LLVM IR 來運作。在 ClangIR 專案中,我們也從 AST 訪問器(CIRGen)發出 ClangIR (CIR),然後降級為 (a) 直接 LLVM IR,或 (b) MLIR 樹內方言。降級到 LLVM 仍然非常不成熟,並且缺乏許多指令、屬性和元資料支援。 ClangIR 將大大受益於在效能和建置時間方面與 Clang AST → LLVM IR codegen 品質相當的水平。這是逐步橋接正確性和效能測試的關鍵,為未來在 C/C++ 之上進行更高層級的最佳化提供基準。一個好的起點是建置和運行簡單的基準測試,測量產生的程式碼和建置時間效能。 LLVM 的 llvm-test-suite 包含腳本和機制,可以輕鬆檢查正確性並收集效能相關資料,並且其 SingleSource 集合提供了一組更簡單的程式來建置。簡而言之,在從事此專案的同時,學生將彌合 CIR → LLVM 降級的差距,並在某些時候修復任何缺乏的 Clang AST → CIR 支援。這項工作將在 SingleSource 基準測試的基礎上逐步完成,同時測量編譯器建置時間和編譯程式的效能。

技能: 中階 C++ 程式設計技能;熟悉編譯器、LLVM IR、MLIR 或 Clang 是很大的優勢,但願意學習也是一種可能性。

預期成果:從 lvm-test-suite 中的 SingleSource 子目錄建置和運行程式,收集並呈現結果(效能和建置時間),以對抗常規(上游)clang codegen。

專案規模: 大型

難度: 中等

已確認導師: Bruno Cardoso Lopes Nathan Lanza

討論區: 網址

專案描述: Enzyme 對 LLVM 程式執行自動微分(在微積分意義上)。這讓使用者可以使用 Enzyme 對任何降級到 LLVM 的語言的現有程式碼執行各種演算法,例如機器學習中的反向傳播或科學模擬。對越來越多的 LLVM 版本(7-main)、AD 模式(反向、正向、正向向量、反向向量、雅可比行列式)和程式庫(BLAS、OpenMP、MPI、CUDA、ROCm...)的支援導致程式碼庫穩步增長。為了限制複雜性並幫助新的貢獻者,我們希望使用 LLVM Tablegen 來表達我們核心邏輯的更多部分。申請人可以自由決定如何最好地將 Enzyme 中的程式轉換抽象對應到 Tablegen。

預期成果: 1. 擴展 Enzyme 內的 tablegen 規則產生系統,以涵蓋 AdjointGenerator 之外的新組件
2. 將幾個現有規則移至新的自動產生系統(例如 LLVM 指令、LLVM 內部函數、MPI 呼叫...)

已確認導師: Manuel Drehwald William Moses

理想技能: 良好的 C++、微積分和 LLVM 和/或 Clang 和/或 MLIR 內部原理知識。 Tablegen、Enzyme 或自動微分的經驗會很好,但也可以在專案中學習。

專案規模: 大型

難度: 中等

討論區 網址

專案描述 LLVM 中大多數的日常測試都是由 Lit 執行的迴歸測試,結構化為原始碼或 IR 以傳遞給某些二進位檔,而不是直接呼叫要測試的程式碼的測試程式碼。這有很多優點,但很難預測當使用特定測試輸入調用編譯器時會執行哪個程式碼路徑,尤其是對於涉及錯誤處理的邊緣情況。此專案的目標是幫助開發人員為其修補程式建立良好的測試覆蓋率,並使審查人員能夠驗證他們是否已完成此操作。為了實現此目標,我們希望引入一個工具,該工具可以將修補程式作為輸入,為受影響的原始檔新增覆蓋率檢測,運行 Lit 測試,並記錄哪些測試案例導致每個計數器被執行。對於每個計數器,我們可以報告執行計數器的測試案例數量,但更重要的是,我們也可以報告執行計數器的測試案例數量,這些測試案例也以某種方式被修補程式更改,因為修改後的行導致相同的測試結果並未得到正確測試,除非它旨在進行非功能性更改。這可以分為三個獨立的部分實作

  1. 在 llvm-lit 中新增一個選項以發出必要的測試覆蓋率資料,每個測試案例劃分(涉及為每個 RUN 將唯一值設定為 LLVM_PROFILE_FILE
  2. 用於處理產生的覆蓋率資料和相關 git 修補程式的新工具,並以使用者友好的方式呈現結果
  3. 新增一種以非侵入性方式(無需更改建置配置)啟用建置的覆蓋率檢測的方法。透過正常建置專案,觸碰修補程式更改的檔案,並使用設定為 新增覆蓋率CCC_OVERRIDE_OPTIONS 重新建置,我們可以降低產生和處理與修補程式無關的行的覆蓋率的開銷。
步驟 2 和 3 中的工具可以完全與實際的測試執行器無關,從而降低了 Lit 以外的其他測試框架實作相同功能的門檻。如果時間允許,在 CI 中新增此步驟也將對審查人員有所幫助。

專案規模: 小型或中型

難度: 簡單

技能: 用於 Lit、資料處理和 diff 處理的 Python。無需編譯器經驗。

預期成果: 為社群實作一個新工具。開發人員在開發期間獲得幫助以尋找未涵蓋的邊緣情況,同時也避免了為了檢查程式碼是否實際執行而過度散佈斷言或日誌。審查人員可以更輕鬆地檢查每個測試測試了修補程式的哪些部分。

已確認導師: Henrik Olsson

討論區: 網址

Google Summer of Code 2022 對於 LLVM 專案非常成功。如需已接受和已完成專案的列表,請查看 Google Summer of Code 網站

專案描述: 撰寫一個基於共享記憶體的 JITLinkMemoryManager。
LLVM 的 JIT 使用 JITLinkMemoryManager 介面來配置工作記憶體(JIT 在其中修復編譯器產生的可重定位物件)和目標記憶體(JIT 編譯的程式碼將駐留在目標記憶體中)。 JITLinkMemoryManager 實例也負責將修復後的程式碼從工作記憶體傳輸到目標記憶體。 LLVM 有一個現有的跨程序配置器,它使用遠端程序呼叫 (RPC) 來配置位元組並將位元組複製到目標程序,但是更具吸引力的解決方案(當 JIT 和目標程序共享相同的實體記憶體時)是使用共享記憶體頁面以避免程序之間的複製。

預期成果

    實作一個基於共享記憶體的 JITLinkMemoryManager
  • 為共享記憶體配置撰寫通用 LLVM API。
  • 撰寫一個 JITLinkMemoryManager,它使用這些通用 API 來配置共享工作和目標記憶體。
  • 對該方法進行廣泛的效能研究。

已確認指導老師: Vassil VassilevLang Hames

理想技能: 中階 C++;理解 LLVM 和特別是 LLVM JIT;理解虛擬記憶體管理 API。

專案類型: 大型

討論區 網址

專案描述: LLVM 的 BuildingAJIT 教學系列教導讀者使用 LLVM 的 ORC API 從頭開始建置自己的 JIT 類別,但是教學章節尚未跟上最近的 API 改進。讓現有的教學章節與時俱進,撰寫關於延遲編譯的新章節(章節程式碼已可用)或從頭開始撰寫新章節。

預期成果

  • 更新第 1-3 章的章節文字 – 簡單,但提供了快速了解 API 的機會。
  • 為第 4 章撰寫章節文字 – 章節程式碼已可用,但尚未有章節文字。
  • 從頭開始撰寫新章節 – 例如,如何撰寫程序外 JIT,或如何使用 ObjectLinkingLayer::Plugin API 直接操作 JIT 編譯的指令流。

已確認指導老師: Vassil VassilevLang Hames

理想技能: 中階 C++;理解 LLVM 和特別是 LLVM JIT;熟悉 RST(reStructed Text);技術寫作技能。

專案類型: 中等

討論區 網址

專案描述: JITLink 是 LLVM 的新 JIT 連結器 API – 將編譯器輸出(可重定位物件檔案)轉換為記憶體中準備執行的位元組的低階 API。為此,JITLink 的通用連結器演算法需要專門化以支援目標物件格式 (COFF、ELF、MachO) 和架構 (arm、arm64、i386、x86-64)。 LLVM 已經有適用於 MachO/arm64 和 MachO/x86-64 的成熟 JITLink 實作,以及適用於 ELF/x86-64 的相對較新的實作。為您感興趣的遺失目標撰寫 JITLink 實作。如果您選擇使用 ELF 或 MachO 格式實作對新架構的支援,那麼您將能夠重複使用這些格式的現有通用程式碼。如果您想使用 COFF 格式實作對新目標的支援,那麼您將需要為您選擇的架構撰寫通用 COFF 支援程式碼和架構支援程式碼。

預期成果: 為尚未支援的格式/架構撰寫 JITLink 專門化。

已確認導師: Vassil VassilevStefan GränitzLang Hames

理想技能: 中級 C++;理解 LLVM 和 LLVM JIT,尤其重要;熟悉您選擇的格式/架構,以及基本的連結器概念 (例如區段、符號和重定位)。

專案類型: 大型

討論區 網址

專案描述: 每個開發人員在某個時候(通常是在等待他們的程式編譯時)都會問「為什麼要這麼久?」。此專案旨在尋找此問題的答案。 LLVM 以及延伸的 CLANG 內部存在一個計時基礎結構,用於記錄編譯器內部的事件。但是,它的使用不一致且不足。可以透過在整個 LLVM 和 CLANG 中新增更多檢測來改進這一點,但必須小心。過多的檢測或檢測錯誤的事物可能會令人困惑和難以承受,因此使其與資訊不足一樣無用。訣竅是找到正確的位置進行檢測並控制檢測。尋找這些關鍵點將帶您完成整個編譯過程,從預處理到最終程式碼產生,以及介於兩者之間的所有階段。當您檢測程式碼時,您將查看資料,因為您會不斷演進它,這將進一步指導您的搜尋。您將開發新的方法來控制和篩選資訊,以便更好地了解編譯器在哪裡花費時間。您將尋找並開發範例測試輸入,以說明可以改進編譯器的地方,這反過來又有助於指導您的檢測和搜尋。您將考慮並開發控制檢測的方法,以便更好地了解和詳細檢查編譯階段。透過這一切,您將了解編譯器如何運作,從前端處理到 LLVM 最佳化管線,再到程式碼產生。您將看到並了解編譯和最佳化 C/C++ 程式所需的整體情況,特別是 CLANG、LLVM 和 LLC 如何完成這些任務。您的導師擁有約 25 年的編譯器開發和約 8 年的 LLVM 本身經驗,可以幫助您完成您的探索。

預期成果

  • 擴大使用現有的計時基礎結構
  • 識別用於改進編譯時間的合適測試輸入
  • 識別編譯時間熱點
  • 控制計時基礎結構的新的和改進的方法

已確認導師: Jamie Schmeiser、Whitney Tsang

理想技能: C++ 程式設計技能; CLANG/LLVM 知識是資產,但不是必要的;自我激勵;好奇心;學習慾望

專案類型:175 或 350 小時

難度評級:簡單 - 中等

討論區 網址

專案描述 這延續了 GSoC 2020 和 2021 的工作。開發人員通常使用標準最佳化管線(如 -O2 和 -O3)來最佳化他們的程式碼。手動製作的啟發式演算法用於確定要選擇哪些最佳化傳遞以及如何排序這些傳遞的執行。但是,此過程並非針對特定應用程式或應用程式類型量身定制,因為它旨在對任何輸入執行「相當好」。我們希望改進現有的啟發式演算法或用基於機器學習的模型取代啟發式演算法,以便 LLVM 編譯器可以為每個應用程式提供卓越的傳遞順序。最後一個里程碑啟用了特徵提取,並開始研究訓練策略以選擇更合適的傳遞管線。

專案規模: 175 或 350 小時。

難度: 中等

技能: C/C++、一些編譯器經驗。機器學習經驗是加分項。

預期成果:預先訓練的模型,選擇最經濟的最佳化管線,且效能沒有損失;在 LLVM 中掛鉤模型;(重新)訓練工具。

導師 Tarindu Jayatilaka、Mircea Trofin、Johannes Doerfert

討論區 網址

專案描述 此專案是去年 的延續。在 2021 年,該專案實現了第一個里程碑 – 將正確性決策與策略決策分開。這開啟了用機器學習的決策取代後者的可能性。粗略的里程碑:1) 選擇一組初始特徵,並使用現有的 ML Guided Optimizations (MLGO) 基礎結構來產生訓練日誌; 2) 定義一個可以在編譯時計算的獎勵訊號,以引導強化學習訓練迴圈; 3) 疊代訓練並改進獎勵/特徵集

專案規模: 175 或 350 小時,理想情況下為 350 小時

難度: 中等/困難

技能: C/C++、一些編譯器經驗。機器學習經驗是加分項。

預期成果:用於迴圈展開的策略(「顧問」)介面,以當前啟發式演算法作為預設實作;設定用於強化學習訓練的特徵提取;設定獎勵指標;設定訓練演算法,並疊代策略訓練

導師 Johannes Doerfert、Mircea Trofin

討論區 網址

專案描述 LLVM 的內聯器是一個由下而上、強連通組件層級的傳遞。這限制了評估呼叫站點的順序,這會影響內聯的有效性。我們現在有一個功能完善的模組內聯器,這是 GSoC2021 工作的成果。我們想要呼叫站點優先順序方案、成功內聯後運行函數傳遞的有效性/頻率、與 ML 內聯顧問的相互作用,僅舉幾個探索領域。

專案規模: 175 或 350 小時,理想情況下為 350 小時,里程碑允許 175 小時的範圍

難度: 中等/困難

技能: C/C++、一些編譯器經驗。

預期成果:替代遍歷順序的提案和評估;評估「叢集」內聯決策(一次內聯多個呼叫站點);評估內聯後函數最佳化傳遞的有效性/頻率

導師 Kazu Hirata、Liqiang Tao、Mircea Trofin

討論區 網址

專案描述: C 和 C++ 程式通常由各種物件檔案組成,這些物件檔案是從單獨編譯的原始檔產生的,然後連結在一起。在編譯一個原始檔時,通常無法獲得可以從其他原始檔中包含的邏輯推導出的知識。連結時間最佳化(也稱為 LTO)是一種使用來自多個原始檔的資訊來完成最佳化的方法。

在 LLVM 中,LTO 是透過使用 LLVM 位元組碼物件作為「編譯」步驟的輸出,並將這些物件饋送到連結步驟來實現的。 LLVM 的 LTO 與連結器結合運作。連結器由使用者調用,當連結器遇到 LLVM 位元組碼檔案時,連結器又會驅動 LLVM 的 LTO,從 LTO 取得有關位元組碼物件定義或參考哪些符號的資訊。有關物件中定義或參考哪些符號的資訊對於連結器執行符號解析是必要的,並且連結器通常能夠從常規(非位元組碼)物件檔案中提取此類資訊。

LLVM 的 LTO 實作在連結器 GC (linker garbage collection,連結器垃圾回收) 方面有改進的空間,特別是對於激進形式的連結器 GC,其具有物件和區段的延遲包含特性。尤其,LTO 模組中被引用但未定義的符號,對於連結器而言,在模組層級是單體的。同時,常規(非 LTO)物件中被引用但未定義的符號,對於 LTO 而言是單體的。總而言之,這表示將 LTO 模組包含到整體流程中,在連結器的初始符號解析時,可能會導致該模組中的所有未定義符號都被視為已引用;反過來,可能會將額外的產物(例如,封存檔成員)添加到解析中,這進一步導致可能解析為 LTO 模組中定義的符號的引用,以及過早地得出這些符號的定義是需要的結論。這至少意味著可能會為最終將被垃圾回收的函數執行不必要的程式碼生成(浪費電力和時間)。

我們承認理想的實作可能涉及連結器和 LTO 程式碼生成之間類似「協程」的互動,資訊在兩者之間來回流動;然而,這樣的努力對於連結器和 LLVM 而言都是侵入性的。

我們相信透過

  • 讓連結器透過 LTO 的 API 註冊符號引用「節點」,以建模符號與從其連結器選定的定義(包含該定義的物件檔案區段)中依序引用的符號之間的關係,以及
  • 在 LTO 處理中使用該資訊,

LTO 處理將能夠有效地識別一組更準確的 LTO 符號,這些符號在 LTO 單元之外是可見的。連結器僅需識別導出的符號和入口點(例如可執行檔的入口點以及參與初始化和終止的函數)。

讓 LLVM opt/codegen 理解來自「外部世界」的依賴性影響,嚴格來說比另一個方向更好:非 LTO 程式碼中重定位所引用的符號幾乎在編譯時就已固定(而 LTO 程式碼中的某些引用可能會隨著最佳化而消失)。

預期成果

  1. 修改 LLD 使用的 C++ LTO 介面,以實作一個介面來記錄符號引用依賴性資料(包含對區段和 comdat 的感知)。這可能額外包含一種方法來臨時新增 LTO 物件,模擬連結器僅在需要時才新增物件的行為。
  2. 修改 LTO 以在造訪 IR 中的定義(在內部化 pass 之前)時,使用新的符號引用資訊來處理常規物件中的定義,以發現(遞移)符號引用,並記錄如此引用的符號為對常規物件可見。這可能額外包含將臨時新增的 LTO 物件「延遲」併入合併的 LTO 模組中。
  3. 修改 LLD(對於 ELF)以修改初始解析,以使用新的介面來取代設定 VisibleToRegularObj,但入口點函數(包含 C++ 動態初始化和終止)除外。

確認導師: Sean Fertile, Hubert Tong, Wael Yehia

理想技能: 中階 C++;基本連結器概念(例如,符號、區段和重定位)

專案規模: 350 小時

難度: 中等/困難

討論區 URL

專案描述 LLVM 中 undef 值的存在阻礙了幾項最佳化,即使在未使用它的程式中也是如此。因此,我們一直試圖將 undef 的所有用途移至 poison,以便我們最終可以從 LLVM 中移除 undef。
這個專案專注於未初始化的記憶體:目前 LLVM 的語意是,從未初始化的記憶體載入值會產生 undef 值。這阻止了例如 SROA/mem2reg 從最佳化條件載入,因為 phi(undef, %x) 無法替換為 x,因為 %x 可能是 poison。
這個專案包括設計一個針對未初始化的記憶體的一致語意(基於現有的提案)、LLVM 的升級計畫,以及在 LLVM 和 clang 中實作變更。在 clang 中,變更應特定於位元欄位。
如需更多資訊,請參閱以下討論和/或聯繫導師。
延伸閱讀: LLVM 記憶體模型簡介

專案規模: 350 小時

難度: 中等/困難

技能: 中階 C++

預期成果:

  • 記憶體操作的語意,可消除對 undef 值的需求
  • LLVM 和前端的升級計畫
  • 在 LLVM 中實作建議的語意
  • 為舊版 LLVM IR 檔案實作自動升級路徑
  • 在 clang 中實作修正,以使用新的 IR 功能
  • 基準測試以檢查迴歸和/或效能改進

導師: Nuno Lopes

專案描述

目前,LLVM 內的所有函式庫都公開匯出其所有符號。當靜態連結它們時,連結器將移除未使用的符號,這不是問題。

然而,當函式庫建置為共享函式庫時,匯出的符號數量非常龐大,並且原本應為內部的符號會洩漏到共享函式庫 libLLVM.so 的公共 ABI 中。

在這個專案中,我們希望將函式庫符號的預設可見性變更為「隱藏」,為 LLVM 新增一個註解巨集,並使用該巨集逐步將整個函式庫朝這個方向移動。這最終將使在 Windows 上也能建置共享函式庫 libLLVM.so 成為可能。

實際上,這表示將 -fvisibility=hidden 新增到個別函式庫,並使用 LLVM 匯出註解來註解匯出的符號。

我們希望這項工作盡可能不干擾其他開發人員的工作流程,因此從一個小型內部函式庫開始會很有幫助,例如 LLVM 目標或 IR pass 之一。

如需進一步閱讀,有一個 Discourse 討論串可供參考,其中討論了此提案背後的想法:在 Windows 上支援 LLVM_BUILD_LLVM_DYLIB,以及包含實作功能的 patch 的連結 Phabricator 審查:⚙ D109192 [WIP/DNM] Support: introduce public API annotation support。這些工作都尚未提交,但可以作為此提案的起點。

專案規模: 中等

難度: 簡單

技能: 建置系統、CMake、LLVM

預期成果:

  • 實作並提交到 LLVM 的匯出巨集
  • 至少一個內部目標移植到新的匯出方案

導師: Timm Bäder, Tom Stellard

專案描述: 當實例化範本時,範本引數會在替換到範本模式之前進行正規化。當後續存取實例化的成員時,Clang 不會保留類型修飾 (type sugar)。

    std::vector<std::string> vs;
    int n = vs.front(); // bad diagnostic: [...] aka 'std::basic_string<char>' [...]

    template<typename T> struct Id { typedef T type; };
    Id<size_t>::type // just 'unsigned long', 'size_t' sugar has been lost
    
當對類別範本特化執行成員存取時,Clang 應該根據存取的特化的類型修飾來「重新修飾」類型。vs.front() 的類型應該是 std::string,而不是 std::basic_string<char, [...]>。

建議的設計方法:新增一個新的類型節點來表示範本引數修飾,並且每當存取類別範本特化的成員時,隱式建立此節點的實例。當對此節點執行單步去修飾 (desugar) 時,透過將修飾的範本引數傳播到內部類型節點(特別是,用相應的修飾替換 Subst*Parm 節點)來延遲建立去修飾的表示形式。當為了診斷目的列印類型時,使用註解的類型修飾來列印原始寫入的類型。

為了獲得良好的結果,範本引數推導也需要能夠推導類型修飾(並調和同一類型被推導兩次但具有不同修飾的情況)。

預期成果: 即使在存取範本特化的成員時,診斷也能保留類型修飾。T<unsigned long> 和 T<size_t> 仍然是相同的類型和相同的範本實例化,但是 T<unsigned long>::type 單步去修飾為 'unsigned long',而 T<size_t>::type 單步去修飾為 'size_t'。

確認導師: Vassil Vassilev, Richard Smith

理想技能: 良好的 clang API 知識、clang 的 AST、中階 C++ 知識。

專案類型: 大型

討論區 URL

專案描述: 儘管 clang AST 在底層完成了所有工作,使得靜態分析器自動支援許多新的 C++ 功能,但 C++17 的「結構化綁定」語法

    auto [x, y] = ...;
需要在靜態分析器端進行一些額外的工作。分析器的轉換函數需要學習新的 AST 節點,BindingDeclDecompositionDecl,以便在標準描述的三種解釋中正確運作。

對結構化綁定的不完整支援是現代 C++ 程式碼中未初始化變數檢查器中誤報的常見來源,例如 #42387

Clang CFG 也可能需要更新。CFG 中的這些變更可能會提高 clang 警告的品質,即使在靜態分析器之外也是如此。

預期成果: 靜態分析器正確地建模結構化綁定和解構宣告。特別是,綁定變數不再對靜態分析器的未初始化變數檢查器顯示為未初始化。

確認導師: Artem Dergachev, Rashmi Mudduluru, Gábor Horváth, Kristóf Umann

理想技能: 中階 C++ 知識。對 Clang AST 的一些熟悉度,和/或一些靜態分析背景。

專案規模: 350 小時

難度: 中等/困難

討論區 URL

描述: Clang 診斷訊息,它向程式設計師發出警告和錯誤,是編譯器的關鍵功能。出色的診斷訊息可以對編譯器的使用者體驗產生重大影響,並提高其生產力。

GCC 最近的改進 [1] [2] 表明在改進診斷訊息(以及一般的使用者互動)方面還有很大的空間。調查並找出 clang 在此主題上的所有可能改進,並開始重新設計下一代診斷訊息,將會是一個非常有影響力的專案。

此外,我們還將對 LLVM Github Issue 頁面上標記為 clang-diagnostics 的問題做出結論,如果需要修復,我們將準備 patch,否則只需關閉它們。

預期成果:診斷訊息將得到改進

  • 改善診斷訊息的美觀性
  • 涵蓋遺失的診斷訊息
  • 降低誤報率
  • 改寫診斷訊息

確認導師: Aaron Ballman, Erich Keane, Shivam Gupta

理想技能: C++ 程式碼撰寫經驗

專案類型: 大型/350 小時

討論區 URL

專案描述: 雖然啟用 Polly 的標準 -O1/-O2/-O3 最佳化 pass 管線在新 Pass 管理器 (New Pass Manager, NPM) 下運作良好,但 Polly 的某些部分仍然僅適用於舊版 pass 管理器。這包括某些 pass,例如 -polly-export-jscop/-polly-export-jscop、迴歸測試、Polly-ACC、命令列選項(例如 -polly-show)、PassInstrumentation 機制(例如 -print-after-all)所使用的機制。LLVM(和 Clang)已轉向 NPM 作為預設值,並且對舊版 pass 管理器的支援已被棄用,逐漸退化,並且功能正在被移除。也就是說,Polly 的所有功能最終也應該適用於 NPM,並為完全移除舊版 pass 管理器做好準備。關於這兩個 pass 管理器的更多詳細資訊,請參閱此處

預期成果: 目標是使 Polly 在僅使用 NPM 的情況下更易於使用。里程碑(不一定所有里程碑都要在這個 GSoC 中達成)是
1. 使 Polly 的所有功能在 NPM 中可用(或決定棄用/移除它)
2. 更好地整合到 NPM 中(例如支援 PassInstrumentation);如果 NPM 變得不足,則僅使用單體函數 pass。
3. 在迴歸測試中取代舊版 pass 管理器。
4. 為完全移除 LLVM 中的舊版 pass 管理器做好準備。

確認導師: Michael Kruse

理想技能: 理解新 pass 管理器使用的 C++ 範本模式(CRTPMixins 等)。熟悉 LLVM 如何被連結(靜態、BUILD_SHARED_LIBS 和 SHLIB/DYLIB)及其外掛程式載入機制(靜態、-load 和 -load-pass-plugin)。理想情況下,已經使用過 LLVM 的新 pass 管理器。

專案規模: 中等

難度: 中等/困難

討論區 URL

專案描述: Enzyme 對 LLVM 程式執行自動微分(在微積分意義上)。這使使用者能夠使用 Enzyme 對於任何降低到 LLVM 的語言的現有程式碼執行各種演算法,例如 ML 中的反向傳播或科學模擬。對越來越多的 LLVM 版本(7-main)、AD 模式(反向、正向、正向向量、反向向量、雅可比矩陣)和函式庫(BLAS、OpenMP、MPI、CUDA、ROCm 等)的支援導致程式碼庫穩步增長。為了限制複雜性並幫助新的貢獻者,我們希望使用 LLVM Tablegen 來表達我們的核心邏輯。申請人可以自由決定如何最好地將 Enzyme 內的程式轉換抽象映射到 Tablegen。

預期成果: 1. Enzyme 內一個可運作的 tablegen 規則產生系統
2. 將幾個現有的規則移至新的自動產生系統(例如 LLVM 指令、LLVM 內建函數、BLAS 呼叫、MPI 呼叫等)

確認導師: William Moses, Valentin Churavy

理想技能: 良好的 C++、微積分和 LLVM 和/或 Clang 和/或 MLIR 內部原理知識。 Tablegen、Enzyme 或自動微分的經驗會很好,但也可以在專案中學習。

專案規模: 大型

難度: 中等

討論區 URL

專案描述: Enzyme 對 LLVM 程式執行自動微分(在微積分意義上)。這使使用者能夠使用 Enzyme 對於任何降低到 LLVM 的語言的現有程式碼執行各種演算法,例如 ML 中的反向傳播或科學模擬。Enzyme 已經實作了正向和反向模式自動微分。Enzyme 還實作了向量正向模式自動微分,這允許 Enzyme 在單次呼叫中批次處理多個物件的導數計算。這個專案的目標是擴展此功能,以執行向量反向模式。這樣做時,可以同時執行多次反向模式自動微分掃描,從而減少記憶體、時間,並在其他方面通常能夠實現進一步的最佳化。

預期成果: 向量化版本的反向模式自動微分

確認導師: William Moses, Tim Gymnich

理想技能: 良好的 C++ 知識和一些 LLVM API 使用經驗。具有 Enzyme 或自動微分的經驗會很好,但也可以在專案中學習。

專案規模: 中等

難度: 中等

討論區 URL

專案描述: Enzyme 是一個用於 LLVM 的編譯器外掛程式,它對 LLVM 程式執行自動微分(在微積分意義上)。這使使用者能夠使用 Enzyme 對於任何降低到 LLVM 的語言的現有程式碼執行各種演算法,例如 ML 中的反向傳播或科學模擬。
Enzyme 透過使用 LLVM 外掛程式整合到前端,該外掛程式可以載入到 Clang、LLVM (opt)、連結器 (lld)、函式庫 (HIPRtc)、直接載入 (Julia) 以及其他 (Flang, Rust 等)。
雖然在內部使用了新 pass 管理器的各種機制,但 Enzyme 目前在使用新 pass 管理器時不會自動註冊其轉換 pass。這為 LLVM 13 或更高版本的使用者帶來了問題,在這些版本中,預設情況下運行新 pass 管理器,並且可能不理解為什麼他們會從未微分的程式碼中收到連結器錯誤(目前他們必須新增一個 flag 來指定舊版 pass 管理器)。
這個專案的目標是使 Enzyme 能夠被 LLVM 中的新 pass 管理器呼叫,並總體上創造一致的使用者體驗。

預期成果: 1. Enzyme 可以被新 pass 管理器呼叫
2. [可選] 使 Enzyme 更易於使用的額外語法糖。

確認導師: William Moses, Valentin Churavy

理想技能: 良好的 C++ 和 LLVM 知識。具有 Enzyme 經驗會很好,但也可以在專案中學習。

專案規模: 小型

難度: 中等

討論區 URL

歡迎有興趣的 2021 年 Google 程式碼夏令營學生!本文檔是您尋找 LLVM、Clang 和其他相關子專案的有趣且重要專案的起點。此專案列表不僅為 Google 程式碼夏令營而開發,也是真正需要開發人員投入工作且對 LLVM 社群非常有益的開放專案。

我們鼓勵您瀏覽此列表,看看哪些專案讓您感到興奮,並且與您的技能組合非常匹配。我們也歡迎未在此列表中的提案。您必須透過我們的開發人員郵件列表 (llvm-dev@lists.llvm.org 或特定的子專案郵件列表) 向 LLVM 社群提出您的想法。來自社群的回饋是您的提案被考慮並有望被接受的要求。

LLVM 專案已參與 Google 程式碼夏令營多年,並取得了一些非常成功的專案。我們希望今年也不例外,並期待聽到您的提案。有關如何提交提案的資訊,請造訪 Google 程式碼夏令營主網站。

專案描述: LLVM lit 測試套件由數千個獨立的小型測試組成。由於測試數量眾多,即使在高規格的電腦上,運行完整的套件也可能需要很長時間。建置已經可以透過使用 distcc 或 icecream 等軟體在同一網路上的多台電腦之間分散,因此在單一機器上運行測試成為潛在的瓶頸。加速運行測試的一種方法可能是將測試執行分散到多台電腦上。Lit 提供了一種測試分片機制,允許多台電腦並行運行同一測試套件的部分,但這目前假設可以存取單一的通用檔案系統,這在所有情況下都可能無法實現,並且需要知道目前可以在哪些機器上運行該套件。這個專案的目標是更新現有的 lit harness(或在其周圍編寫一個 wrapper),以允許以這種方式分散測試,其想法是開發人員可以編寫他們自己的 harness 和他們選擇的分散系統之間的介面。這個 harness 可能需要能夠識別測試依賴項,例如輸入檔案和可執行檔,將測試(可能分批)發送到分散系統,並接收、整理和向使用者報告結果,方式與 lit 已經做的方式類似。

預期成果: 一個如上所述的易於使用的 harness。一些證據表明,在給定分散式系統的情況下,如果使用者正在使用該 harness,他們可以期望看到測試套件執行速度加快。

確認導師: James Henderson

理想技能: 良好的 Python 知識。熟悉 LLVM lit 測試。對分散式系統的一些了解也將有所助益。

專案描述: 這是一個簡短的描述,如果聽起來有趣,請聯繫 Johannes (IRC 上的 jdoerfert) 和 Mircea Trofin。我們成功地為內聯器決策引入了 ML 框架,現在我們希望擴大範圍。在這個專案中,我們將研究迴圈轉換啟發式方法,例如展開因子。作為一個激勵範例,我們可以看看一個小行程計數的 dgemm,我們對它的最佳化非常差。使用 nounroll pragmas,我們做得更好,但仍然遠遠不及 gcc。這個專案是開放式的,我們可以同時研究各種 pass/啟發式方法。

準備資源: LLVM 程式碼庫中的 ML 內聯器框架以及 論文。LLVM 轉換 pass(基於啟發式方法),例如,迴圈展開。

預期成果: 使用學習到的預測器獲得可衡量的更好效能,可能是一組從 ML 模型衍生的「經典」啟發式方法。

確認導師: Johannes Doerfert, Mircea Trofin

理想技能: 中階 ML 知識、C++、自我激勵。

專案描述: 這是一個簡短的描述,如果聽起來有趣,請聯繫 Johannes (IRC 上的 jdoerfert)。Fuzzing 通常會揭示大量錯誤。CSmith(和其他工具)展示了如何使用類似 C 的語言執行此操作,並且我們過去曾成功使用LLVM-IR fuzzing。在這個專案中,我們將 fuzzing 應用於正在開發的新 pass,例如 Attributor pass。我們希望找到並修復崩潰以及其他錯誤,包括編譯時間效能問題。

準備資源: LLVM fuzzer 基礎架構。我們可能想要 fuzz 的 LLVM pass,例如 Attributor pass。先前的 IR-Fuzzing 工作 (https://www.youtube.com/watch?v=UBbQ_s6hNgg)

預期成果: 崩潰、也可能是一種捕捉非崩潰錯誤的方法,包括效能問題。

確認導師: Johannes Doerfert

理想技能: 中階 C++ 知識、自我激勵。

專案描述: 這是一個簡短的描述,如果聽起來有趣,請聯繫 Johannes (IRC 上的 jdoerfert)。llvm.assume是一個保留知識的強大機制。自成立以來,它已經多次改進,但仍有主要的擴展尚未完成,我們希望在這個專案中解決這些擴展。不完整的議題列表包括

  • 基於範圍的假設,RFC 中的設計想法 3)。
  • 概述任意假設/斷言程式碼,RFC 中的設計想法 2)。
  • 無副作用假設,請參閱此審查
  • 更多知識保留用法
  • 減少對最佳化的干擾

準備資源: llvm.assumption 用法、假設快取、「enable-knowledge-retention」選項、RFC此審查

預期成果: 新的 llvm.assume 用例、透過知識保留提高效能、基於斷言的最佳化。

確認導師: Johannes Doerfert

理想技能: 中階 C++ 知識、自我激勵。

專案描述: LLVM 的 IR 存在根本性的、長期存在的問題。許多問題與未定義行為有關。其他問題僅僅是規格不足以及不同的人的不同解釋造成的。Alive2 是一個自動檢測 LLVM 最佳化中錯誤的工具。使用 Alive2,我們追蹤在 儀表板上單元測試暴露的錯誤。

預期成果: 1) 報告並修復 Alive2 檢測到的錯誤。2) 選擇一個基本的 IR 問題,並在解決它方面取得進展,包括為 語意 提出修復方案,透過在 LLVM 單元測試和中型程式上運行 Alive2 來測試語意修復,測試語意修復的效能並修復效能迴歸。

確認導師: Nuno Lopes, Juneyoung Lee

理想技能: 中階 C++;願意學習 LLVM IR 語意;閱讀論文的經驗(首選)。

專案描述: LoopNest pass 的想法是最近新增的,並且沒有現有的 pass 利用它。在沒有 LoopNest pass 之前,如果你想編寫一個適用於迴圈巢狀結構的 pass,你必須從函數 pass 或迴圈 pass 中選擇一個。如果你選擇將其編寫為函數 pass,那麼你將失去將迴圈動態新增回管線的能力。如果你決定將其編寫為迴圈 pass,那麼當給定迴圈不是最外層迴圈時,你將浪費編譯時間來遍歷到你的 pass 並立即返回。在這個專案中,我們希望將最近引入的 LoopNest pass 用於旨在處理迴圈巢狀結構的 pass,並具有與 LoopPass 相同的動態將迴圈新增到管線的能力。此外,在必要時改進 LoopNestPass 的目前實作。

預期成果(可能性): 為某些現有的轉換/分析利用 LoopNest Pass。

確認導師: Whitney Tsang, Ettore Tiotto

理想技能: 中階 C++ 知識、自我激勵。

專案描述: 這是一個簡短的描述,如果聽起來有趣,請聯繫 Johannes (IRC 上的 jdoerfert)。OpenMP GPU 核心通常會降低為原生二進位檔,例如 cubin,並嵌入到主機物件中。在運行時,OpenMP「外掛程式」將與裝置驅動程式(例如 CUDA)連接,以載入和運行此類嵌入式二進位映像。在這個專案中,我們希望開發一個新的外掛程式,該外掛程式接受 LLVM-IR 程式碼,使用僅在運行時才已知的核心參數來最佳化 IR,然後產生 GPU 二進位檔供其他外掛程式使用。與遠端卸載外掛程式類似,我們可以透明地對使用者執行此操作。除了外掛程式中的 JIT 基礎架構設定之外,我們還需要將 IR 嵌入到主機物件中。

準備資源:OpenMP 目標卸載基礎架構、LLVM JIT 基礎架構。

預期成果: 一個具有 JIT 功能的卸載外掛程式,當核心特化啟用最佳化時,可以實現卓越的效能。

確認導師: Johannes Doerfert

理想技能: 中階 C++ 知識、JIT 編譯、自我激勵。

專案描述: Clacc 和 Flacc 是將 OpenACC 支援引入 Clang 和 Flang 的專案。為此,OpenACC 運行時支援正在 LLVM 的 OpenMP 運行時之上開發。然而,LLVM 的 OpenMP 運行時發出的診斷訊息是以 OpenMP 概念表達的,因此這些診斷訊息對於 OpenACC 使用者而言並不總是意義明確。這個專案應分兩個步驟解決這個問題

  1. 開發一種機制,用於選擇由於 OpenACC 相關呼叫進入運行時而發出的 OpenACC 版本診斷訊息。這種機制應該足夠通用,以至於可以應用於 OpenMP 和 OpenACC 之外的程式語言。一種可能的方法是擴展 OpenMP 運行時某些組件中已經存在的國際化機制。
  2. 為現有的 OpenMP 診斷訊息提供 OpenACC 翻譯。此步驟需要理解 OpenACC 和 OpenMP 之間在 Clacc 和 Flacc 中的實作關係。
許多將依賴於這個專案的 OpenACC 支援組件尚未上游化,並且正在開發中。對這些努力的高層次理解對這個專案很有幫助,並且可以由導師提供。儘管如此,這個專案現在可以在上游 LLVM 的 OpenMP 運行時中獨立於這些努力完成。

預期成果: 上游 LLVM 的 OpenMP 運行時的一個版本,可以根據需要發出 OpenACC 診斷訊息。

確認導師: Valentin Clement, Joel E. Denny

理想技能: 中階 C++;OpenACC 或 OpenMP 經驗

專案描述: Polly 使用來自 Integer Set Library (isl) 的演算法,這是一個用 C 語言編寫的函式庫。它使用參考計數進行記憶體管理。在 C++ 中使用 RAII 可以更容易地正確處理參考計數,因此我們為 isl 建立了一個 C++ binding:isl-noexceptions.h。從那時起,isl 也獲得了兩個官方 C++ binding,cpp.hcpp-checked.h。我們希望用上游 binding 取代 Polly 維護的 C++ binding。不幸的是,這不是一個直接替換。差異包括錯誤檢查的方式、方法名稱、哪些函數被視為運算符/建構子重載以及導出的函數集。這將需要變更 Polly 對 C++ binding 的使用,並提交 patch 到 isl 以導出 Polly 所需的額外功能。

預期成果: 減少 Polly 維護的 isl-noexceptions.h binding 與 isl 支援的兩個 C++ binding 之一之間的差異。由於 isl-noexceptions.h 導出的函數和類別比上游 binding 更多,因此完全替換可能無法實現,但即使減少差異也會降低 Polly 的 isl-noexceptions.h 的維護成本。

確認導師: Michael Kruse

理想技能: 深入的 C++ 知識,尤其是 RAII 和移動語意。對 API 設計的興趣。理想情況下,您已經編寫了一些函式庫的標頭檔。具有 isl 函式庫的經驗會很好,但也可以在專案中學習。

專案描述: Enzyme 對 LLVM 程式執行自動微分(在微積分意義上)。這使使用者能夠使用 Enzyme 對於任何降低到 LLVM 的語言的現有程式碼執行各種演算法,例如 ML 中的反向傳播或科學模擬。Enzyme 通過將鏈式法則應用於原始函數要微分的函數所調用的每個函數中的每個指令來實現這一點。雖然功能正常,但對於可能具有代數性質以實現更快導數計算的高階矩陣運算而言,這不一定是最佳的。Enzyme 還有一種機制,用於為給定函數指定自訂梯度。如果自訂導數可用,Enzyme 將使用它,而不是退回到實作自己的導數。許多程式使用 BLAS 函式庫來有效計算矩陣和張量運算。這個專案將通過為其運算指定自訂導數規則,實現 BLAS 和類似函式庫(例如 Eigen)的高效能自動微分。

預期成果: 通過為矩陣和張量運算編寫自訂導數規則,實現 BLAS 和 Eigen 程式碼的高效微分。

確認導師: William Moses, Johannes Doerfert

理想技能: 良好的 C++、微積分和線性代數知識。具有 BLAS、Eigen 或 Enzyme 的經驗會很好,但也可以在專案中學習。

專案描述: Enzyme 對 LLVM 程式執行自動微分(在微積分意義上)。這使使用者能夠使用 Enzyme 對於任何降低到 LLVM 的語言的現有程式碼執行各種演算法,例如 ML 中的反向傳播或科學模擬。雖然這適用於任何發出 LLVM IR 的前端,但為了傳遞額外資訊並創造更好的使用者體驗,可能需要 Enzyme 與前端之間更緊密的整合。Swift 通過在前端指定自訂導數規則來提供自動微分。Enzyme 可以直接與 Swift 整合,微分最終的 LLVM,但它會錯失有關自訂導數的所有額外資訊。此外,天真地調用 Enzyme 將會沒有類型檢查、精細的 AD 特定除錯資訊或 Swift 為 AD 使用者提供的各種其他優良工具。這個專案將尋求整合 Enzyme 和 Swift 前端,以便為想要使用 Enzyme 來實現高效能自動微分的 swift 程式設計師提供良好的使用者體驗,並允許 Enzyme 利用 Swift 中已有的導數特定元數據。

預期成果: 在 Swift 中建立用於調用 Enzyme 的自訂類型檢查語言結構。用於傳遞 Swift 的微分特定元數據以供 Enzyme 使用的機制。

確認導師: William Moses, Vassil Vassilev

理想技能: 良好的 C++ 和 Swift 知識。具有 Enzyme 或自動微分的經驗會很好,但也可以在專案中學習。

專案描述: Enzyme 對 LLVM 程式執行自動微分(微積分意義上的)。這讓使用者能夠使用 Enzyme 在任何可降低為 LLVM 的語言的現有程式碼上,執行各種演算法,例如 ML 中的反向傳播或科學模擬。在許多領域中,期望在定點值(例如整數)而不是浮點值上進行計算。這避免了可能對特定應用程式至關重要的某些截斷誤差。此外,特定的硬體可能在定點值上比在浮點值上更有效率。此專案將尋求擴展 Enzyme,使其不僅支援浮點基本值的微分,還支援定點基本值的微分。

預期成果: 實作 LLVM 定點內建函數的伴隨函數、必要的類型分析規則,以及整合到前端以進行端對端測試。

已確認指導教授: William Moses

理想技能: 良好的 C++、微積分和 LLVM 內部知識。 具備 Enzyme 或自動微分的經驗會更好,但也可以在專案中學習。

專案描述: Enzyme 對 LLVM 程式執行自動微分(微積分意義上的)。這讓使用者能夠使用 Enzyme 在任何可降低為 LLVM 的語言的前端程式碼上,執行各種演算法,例如 ML 中的反向傳播或科學模擬。雖然這適用於任何發射 LLVM IR 的前端,但為了傳遞額外資訊並創造更好的使用者體驗,可能需要 Enzyme 和前端之間更緊密的整合。此專案將尋求整合 Enzyme 和 Rust 前端,為想要使用 Enzyme 啟用高效能自動微分的 Rust 程式設計師提供良好的使用者體驗。這也可能涉及將 LLVM 外掛程式支援/自訂程式碼生成整合到 rustc 中。

預期成果: 在 Rust 中建立用於呼叫 Enzyme 的自訂類型檢查語言結構。 將 Rust 類型資訊(表示為偵錯 LLVM 偵錯資訊)直接解析到類型分析的機制。

已確認指導教授: William Moses

理想技能: 良好的 C++ 和 Rust 知識。 具備 Enzyme 或自動微分的經驗會更好,但也可以在專案中學習。

專案描述

  • 繪製時間在傳輸函數中花費多少的圖表 – 包括(但不限於!)檢查器回呼。
  • 新增 llvm 統計資料和計時器,以便快速取得精確簡潔的傾印,而無需外部效能分析器。 關於狀態分割的統計資料可能特別有趣!
  • 測量分析特定堆疊框架所花費的時間。 例如,我們在內聯中花費多少時間std::string方法? 如果我們為這些方法新增自訂模型,則可以節省這些時間。

已確認指導教授: Artem Dergachev

專案描述: CSA 有一個小型內部約束求解器,它非常簡單,但速度超快。 目標是支援某些符號運算子的基於範圍的邏輯,同時保持線性。 此外,可以專門為測試約束求解器設計單元測試框架(目前它的測試相當笨拙)。 這個專案有幾個有趣的屬性。 它可以分割成小塊,並且每個小塊都有一個重要的解決方案。 它可能會帶您進入求解器的世界(最好使用一些重量級求解器(例如 z3)來檢查您的想法)。 並且由於現有的求解器很簡單,因此可以嘗試進行無數可能的擴展。

已確認指導教授: Valeriy Savchenko

專案描述

  • 設計和整合新的診斷抽象(類似於 clang::Diagnostic),以結構化的方式報告錯誤、警告和注意事項。
  • 讓我們區分錯誤(意外錯誤)和偵錯器根本不知道的事物(預期錯誤)。 聰明地只列印一次全域錯誤。 能夠詳細,並具有額外的元數據(來源位置、DWARF 單元、物件檔案等,取決於錯誤類型及其來源)。
  • 應與現有類別(例如 Status 和 CommandReturnObject)相容並緊密整合。

已確認指導教授: Jonas Devlieghere 和 Raphael Isemann

LLVM 參與 2020 年 Google Summer of Code 非常成功,並促成了許多有趣的專案貢獻給 LLVM。 有關已接受和已完成專案的列表,請查看 Google Summer of Code 網站。

專案描述: 這是一個簡短的描述,如果聽起來有趣,請聯繫 Johannes (IRC 上的 jdoerfert)。 在 GSoC'19 期間,我們建立了 Attributor 框架,以提高 LLVM 的跨程序功能。 這本身很有用,尤其是在內聯不可能或不理想的情況下。 在這個 GSoC 專案中,我們將研究 Attributor 中尚未提供的功能,以及將 Attributor 與現有的內部程序和跨程序最佳化連接的可能性。 在這個專案中,有很多自由來決定實際任務,但我們將提供一個小型和中型任務池,可以從中選擇。

準備資源: 來自 2019 年 LLVM 開發者會議的 Attributor YouTube 影片和來自同次會議的 IPO 小組錄音。 Attributor 框架以及 LLVM 中的其他現有跨程序分析和最佳化。

預期成果: 可衡量的更好的 IPO,尤其是在內聯不是選項或不理想的情況下可見。

確認導師: Johannes Doerfert

理想技能: 中級 C++ 知識、自我激勵。

專案描述: 這是一個簡短的描述,如果聽起來有趣,請聯繫 Johannes (IRC 上的 jdoerfert)。 透過 OpenMPOpt pass (正在審查中),我們開始教導 LLVM 最佳化管道關於編碼為 OpenMP 執行階段呼叫的 OpenMP 並行性。 在這個 GSoC 專案中,我們將研究 OpenMPOpt pass 中尚未提供的功能,以及連接現有的內部程序和跨程序最佳化(例如 Attributor)的可能性。 在這個專案中,有很多自由來決定實際任務,但我們將提供一個小型和中型任務池,可以從中選擇。

準備資源: 來自 2018 年 LLVM 開發者會議的 YouTube 影片 "Optimizing Indirections, using abstractions without remorse"。 論文 "Compiler Optimizations for OpenMP" 和 "Compiler Optimizations For Parallel Programs" 均由 J. Doerfert 和 H. Finkel 撰寫(這些的投影片可能更有用)。

預期成果: 針對並行程式(重點是 OpenMP)的可衡量的更好的效能或程式分析結果。

確認導師: Johannes Doerfert

理想技能: 中級 C++ 知識、自我激勵。

專案描述: 產生偵錯資訊是編譯器通常執行的基本任務之一。 很明顯,可執行的產生程式碼不應取決於偵錯資訊的存在。

不幸的是,在 LLVM 中存在已知案例,其中程式碼產生會因是否啟用偵錯資訊 (`-g`) 而異。 這些類型的錯誤可能會導致糟糕的偵錯體驗,範圍從意外的執行行為到程式在偵錯模式下執行良好,但在沒有偵錯資訊的情況下崩潰。

這個問題可能不是單一原因造成的,而是在不同架構上的不同 pass 期間觸發的。 其中一個原因是編譯器後端在框架降低和其他後續 pass 期間插入呼叫框架資訊 (CFI)。 CFI 指令的存在似乎會改變指令排程,因此導致產生不同的程式碼。

準備資源

  • PR37728 是一個元錯誤,收集了幾個相關的不同程式碼產生的問題。
  • PR37240 是一個討論上述 CFI 問題的錯誤。
  • 以下 RFC 討論了一些可能的緩解策略,並提供了有關 CFI 問題的一些背景資訊。

預期成果

  • 編寫一些基於現有腳本的工具,以自動產生不同程式碼產生的範例。 這旨在作為一個入門任務,以了解現有的 LLVM 工具、學習閱讀 LLVM 的內部輸出等。
  • 選擇一個或多個(取決於難度)導致程式碼產生差異的錯誤,並嘗試提供修補程式來修復它們。 我們特別感興趣的是提到的 CFI 問題,但處理其他一些相關錯誤也絕對可以。

已確認指導教授: Paul Robinson 和 David Tellenbach

理想技能: 中級 C++ 知識、對一般電腦架構的一些熟悉度、對 x86 或 Arm/AArch64 指令集的一些熟悉度。

專案描述: MergeSimilarFunctions pass 不僅能夠合併相同的函數,還能夠合併指令略有不同的函數,以減少程式碼大小。 它透過在合併的函數中插入控制流和額外參數來解決差異來做到這一點。 這項工作在 2013 年 LLVM 開發者會議 上發表。 更詳細的描述發表在 LCTES 2014 的一篇論文中。 程式碼當時已發佈給社群。 同時,該 pass 在 QuIC 的生產環境中使用了過去幾年,並且在內部得到了積極維護。 為了擴大 MergeSimilarFunctions 的影響,它已被移植到 ThinLTO,並且修補程式已上游化(請參見下面提到的 5 個修補程式的堆疊)。 但是社群建議我們使用 MergeSimilarFunctions 的想法來改進現有的 MergeFunctions pass,而不是在 LLVM 上游取代現有的 MergeFunctions pass。 然後利用 ThinLTO 在此基礎上。 在 ThinLTO 中使用的 MergeSimilarFunction 在廣泛的工作負載中提供了令人印象深刻的程式碼大小縮減,這項工作在 LLVM-dev 2018 上發表。 LLVM 專案將從這種程式碼大小最佳化中受益匪淺,因為大多數嵌入式系統(想想智慧型手機)應用程式都受到程式碼大小的限制。

準備資源

預期成果

  • 改進 MergeFunctions 以使其具有與 MergeSimilarFunctions 相同的功能。
  • 啟用 MergeFunctions 以用於 ThinLTO。

已確認指導教授:Aditya Kumar (IRC 和 phabricator 上的 hiraditya)、JF Bastien (phabricator 上的 jfb)

理想技能: 編譯器設計課程、SSA 表示法、中級 C++ 知識、熟悉 LLVM Core。

專案描述: LLVM 提供了一個名為 yaml2obj 的工具,它可以將 YAML 文件轉換為物件檔案,適用於各種不同的檔案格式,例如 ELF、COFF 和 Mach-O,以及執行相反操作的 obj2yaml。 該工具通常用於測試 LLVM 的各個部分,因為 YAML 通常比原始組合語言更容易描述物件檔案,並且比預先建置的二進位檔案更易於維護。 DWARF 是一種偵錯檔案格式,通常由 LLVM 使用。 許多 LLVM 的 DWARF 發射測試都是用組合語言編寫的,但用 YAML 編寫它們會更好。 但是,yaml2obj 不完全支援 DWARF 區段的發射。 這個專案是向 yaml2obj 新增功能,以簡化 DWARF 測試的測試輸入的編寫,尤其是對於 ELF 物件。

準備資源: 閱讀 DWARF 檔案格式將很有用,特別是 http://dwarfstd.org/Download.php 上提供的標準。 此外,熟悉 ELF 檔案格式的基礎知識(如此處所述 https://www.sco.com/developers/gabi/latest/contents.html)可能會有所幫助。

預期成果: 能夠使用 yaml2obj 為物件檔案產生 DWARF 區段。 特別重要的是確保輸入 YAML 比等效的組合語言更容易理解。

已確認指導教授: James Henderson

理想技能: 中級 C++ 知識。

專案描述: LLVM 中的熱區塊冷區塊分割是一種 IR 層級的函數分割轉換。 熱區塊/冷區塊分割的目標是提高程式碼的記憶體區域性,並有助於減少啟動工作集。 分割 pass 透過識別冷區塊並將它們移動到單獨的函數中來做到這一點。 因為它是在 IR 層級實作的,所以所有後端目標都從中受益。 這是一個相對較新的最佳化,最近在 2019 年 LLVM 開發者會議 上發表,投影片 在此。 因為大多數好處來自於概述小區塊,例如 __assert_rtn。 這個專案的目標是透過靜態分析(例如,例外處理程式碼、最佳化個性化函數)來識別潛在的區塊。 使用成本模型來確保概述減少呼叫者的程式碼大小,並在適當的時候使用尾部呼叫來節省指令。

準備資源

預期成果

  • 改進熱區塊冷區塊分割,以透過靜態分析或效能分析資訊來檢測和概述程式中的冷區塊。 使用適當的成本模型來衡量 HCS 的好處。 如果編譯時間開銷變成二次方,請提出一種成本模型來檢測何時觸發二次方行為,並根據編譯器標誌退出。

已確認指導教授:Aditya Kumar (IRC 和 phabricator 上的 hiraditya)

理想技能: 編譯器設計課程、SSA 表示法、中級 C++ 知識、熟悉 LLVM Core。

專案描述: 為給定應用程式選擇最佳化 pass 非常重要,但由於編譯器轉換空間(包括 pass 順序)的巨大規模,這是一個非平凡的問題。 雖然現有的啟發式方法可以為某些應用程式提供高效能程式碼,但它們無法輕易地使廣泛的應用程式程式碼受益。 這個專案的目標是學習 LLVM 轉換 pass 和程式碼結構之間的相互作用,然後改進現有的啟發式方法(或用基於機器學習的模型取代啟發式方法),以便 LLVM 編譯器可以為每個應用程式提供卓越的 pass 順序。

預期成果(可能性)

  • 關於現有 pass 之間的(隱含)依賴關係的見解。
  • 新的 pass 管道(想想 -O3a、-O3b、...),使用者可以選擇這些管道,這些管道在某些種類的程式上往往表現得更好。
  • 改進的 LLVM pass 啟發式方法或新的基於機器學習的模型,可以根據程式碼結構選擇 LLVM 轉換 pass 的最佳順序。

準備資源

  • HERCULES:邁向更智慧預測建模的強模式,Eunjung Park; Christos Kartsaklis; John Cavazos,IEEE ICPP’14 https://ieeexplore.ieee.org/abstract/document/6957226
  • 多面體最佳化空間中的預測建模,Eunjung Park、John Cavazos、Louis-Noël Pouchet、Cédric Bastoul、Albert Cohen & P. Sadayappan,IJPP’13 https://link.springer.com/article/10.1007/s10766-013-0241-1
  • 編譯器最佳化中的機器學習,Zheng Wang 和 Michael O’Boyle,IEEE Magazine 2018。 https://ieeexplore.ieee.org/document/8357388

已確認指導教授:EJ Park、Giorgis Georgakoudis、Johannes Doerfert

理想技能: C++、Python、最好具有 LLVM 和基於學習的預測經驗。

專案描述: 用於編譯器最佳化的當前機器學習模型根據隔離的每個函數分析來選擇函數的最佳最佳化策略。 在這種方法中,建構的模型不知道與其周圍的其他函數(呼叫者或被呼叫者)的任何關係,這可能有助於確定每個函數的最佳最佳化策略。 在這個專案中,我們想要探索 SCC(強連通元件)呼叫圖,以在建構基於機器學習的模型中新增跨程序功能,以找到每個函數的最佳最佳化策略。 此外,我們想要探索將強相關函數組合在一起並作為一個組進行最佳化,而不是每個函數進行最佳化,這是否有所幫助。

預期成果(可能性)

  • 改進現有(跨程序)pass 的啟發式方法,例如,根據程式碼功能權衡內聯與函數複製。
  • 使用程式碼功能和跨程序分析來選擇最佳最佳化的機器學習模型。 這個模型可以用於隔離的函數或函數組,例如 CGSCC。

準備資源

  • HERCULES:邁向更智慧預測建模的強模式,Eunjung Park; Christos Kartsaklis; John Cavazos,IEEE ICPP’14 https://ieeexplore.ieee.org/abstract/document/6957226
  • 多面體最佳化空間中的預測建模,Eunjung Park、John Cavazos、Louis-Noël Pouchet、Cédric Bastoul、Albert Cohen & P. Sadayappan,IJPP’13 https://link.springer.com/article/10.1007/s10766-013-0241-1
  • 編譯器最佳化中的機器學習,Zheng Wang 和 Michael O’Boyle,IEEE Magazine 2018。 https://ieeexplore.ieee.org/document/8357388

已確認指導教授:EJ Park、Giorgis Georgakoudis、Johannes Doerfert

理想技能: C++、Python、最好具有 LLVM 和基於學習的預測經驗。

專案描述: 目前沒有簡單的方法可以在迴圈 pass 中使用 PostDominatorTreeAnalysis 的結果,因為 PostDominatorTreeAnalysis 是一個函數分析,並且它不包含在 LoopStandardAnalysisResults 中。 如果在 LoopStandardAnalysisResults 中新增 PostDominatorTreeAnalysis,那麼所有迴圈 pass 都需要保留它,這意味著所有迴圈 pass 都需要確保結果是最新的。 在這個專案中,我們想要修改一些常用的實用程式來產生更新列表,這些更新列表可以被不同的更新器使用,例如 DomTreeUpdater 來更新 DominatorTree 和 PostDominatorTree,以及 MSSAU 來更新 MemorySSA 等,而不是僅更新 DominatorTree。 此外,我們想要更改現有的迴圈 pass 以保留 PostDominatorTree。 最後,在 LoopStandardAnalysisResults 中新增 PostDominatorTree。

預期成果(可能性): PostDominatorTree 新增到 LoopStandardAnalysisResults 中,並且可以被迴圈 pass 使用。 更多通用實用程式變更為產生更新列表,以便不同的更新器可以輕鬆取得。

已確認指導教授: Whitney Tsang、Ettore Tiotto、Bardia Mahjour

理想技能: 中階 C++ 知識、自我激勵。

準備資源:

專案描述: 目前,如果您想編寫一個適用於迴圈巢狀結構的 pass,您必須從函數 pass 或迴圈 pass 中選擇一個。 如果您選擇將其編寫為函數 pass,那麼您將失去將迴圈動態新增回管道的能力。 如果您決定將其編寫為迴圈 pass,那麼當給定的迴圈不是最外層迴圈時,您將浪費編譯時間來遍歷您的 pass 並立即返回。 在這個專案中,我們想要建立一個 LoopNestPass,其中用於迴圈巢狀結構的轉換可以從它繼承,並具有與 LoopPass 相同的動態將迴圈新增到管道的能力。 此外,建立在 pass 建構器的不同點新增迴圈巢狀結構 pass 所需的所有適配器。

預期成果(可能性): 轉換/分析可以編寫為 LoopNestPass,而不會損害編譯時間或可用性。

確認導師: Whitney Tsang, Ettore Tiotto

理想技能: 中階 C++ 知識、自我激勵。

準備資源:

專案描述: TableGen 非常靈活,並允許最終使用者定義和設定記錄(指令)的通用屬性。 每個目標都有數十個或數百個這樣的指令屬性。 隨著目標程式碼的發展,td 檔案變得越來越複雜,越來越難以看出某些屬性的設定是否必要,甚至是否正確。 例如:hasSideEffects 屬性是否在所有指令上都正確設定? 可以手動搜尋 TableGen 產生的檔案; 或編寫一些腳本來執行 TableGen 並比對某些特定屬性的輸出,但是從建置流程管理的角度來看,可以系統地傾印和檢查指令屬性的獨立實用程式(例如:也允許目標定義一些驗證規則)可能會更好。 這有助於找到許多隱藏的錯誤,從而提高整體程式碼產生程式碼品質。 此外,該實用程式可用於編寫指令屬性的迴歸測試,這將提高 LLVM 迴歸測試的品質和精確度。

預期成果(可能性): 一個可以系統地傾印和檢查指令屬性的獨立 llvm 工具或實用程式

已確認指導教授: Hal Finkel、Jinsong Ji、Qingshan Zhang

理想技能: 中階 C++ 知識、自我激勵。

專案描述: 確定移動程式碼是否安全已在 LLVM 的多個轉換中實作(例如 LICM 中的 canSinkOrHoistInst 或 Loop 中的 makeLoopInvariant)。 對於給定的查詢,這些實作中的每一個都可能返回不同的結果,從而導致程式碼移動安全檢查不一致且重複。 另一方面,在每個轉換中執行實際程式碼移動的機制也不同。 程式碼重複會導致維護問題,並增加編寫新轉換所需的時間。 在這個專案中,我們想要首先識別迴圈轉換(可能是函數或迴圈 pass)中檢查程式碼移動是否安全以及移動程式碼的所有現有方法,並建立一種標準化的方法來執行此操作。

預期成果(可能性): 迴圈轉換中檢查程式碼移動是否安全和移動 的所有現有方法的標準化/超集

已確認指導教授: Whitney Tsang、Ettore Tiotto、Bardia Mahjour

理想技能: 中階 C++ 知識、自我激勵。

準備資源:

開放專案列表中的所有項目 都向 GSOC 開放。 隨時在 Discourse 上提出您自己的想法。

專案描述: Clang 靜態分析器已經知道如何防止由任意程式碼中的空指標取消引用引起的崩潰,但是當程式碼太複雜時,它通常會「放棄」。 特別是,C++ 標準類別(即使是簡單的類別,例如智慧型指標或 optionals)的實作細節可能對於分析器來說太過複雜而無法完全理解。 此外,確切的行為取決於使用的標準函式庫的哪個實作(例如,GNU libstdc++ 或 LLVM 自己的 libc++)。

我們可以透過明確地教導分析器關於 C++ 標準類別的行為,從而跳過分析器嘗試自行理解所有實作細節的整個過程,來使分析器在現代 C++ 程式碼中找到更多錯誤。 例如,我們可以教導它預設建構的智慧型指標為空,並且任何嘗試取消引用它都會導致崩潰。 因此,該專案將包括手動為標準類別的各種方法提供實作。

預期成果: 我們希望靜態分析器在程式碼中發生空智慧型指標取消引用時發出警告。 例如

    #include <memory>

    int foo(bool flag) {
      std::unique_ptr<int> x;  // note: Default constructor produces a null unique pointer;

      if (flag)                // note: Assuming 'flag' is false;
        return 0;              // note: Taking false branch

      return *x;               // warning: Dereferenced smart pointer 'x' is null.
    }
    
我們應該能夠完全涵蓋至少一個類別,例如,std::unique_ptr,然後看看我們是否可以將我們的結果推廣到其他類別,例如std::shared_ptr或 C++17std::optional.

已確認指導教授: Artem Dergachev、Gábor Horváth

理想技能: 中級 C++ 知識。

專案描述: LLDB 的命令列提供了幾個受 UNIX shell 功能啟發的便利功能,例如 Tab 鍵完成或命令歷史記錄。 一個尚未實作的功能是「自動建議」。 這些是對使用者可能想要鍵入的可能命令的建議,但與 Tab 鍵完成不同,它們直接顯示在使用者鍵入命令時游標的後面。 一個關於這看起來如何的良好示範是 fish shell 中實作的自動建議。

這個專案是關於在 LLDB 基於 editline 的命令 shell 中實作自動建議。

已確認指導教授: Jonas Devlieghere 和 Raphael Isemann

理想技能: 中級 C++ 知識。

專案描述: LLDB 的命令列提供了幾個受 UNIX shell 功能啟發的便利功能,例如命令的 Tab 鍵完成。 這些 Tab 鍵完成由一個完成引擎實作,該引擎不僅被 LLDB 的命令列介面使用,而且也被 LLDB 的圖形介面(例如 IDE)使用。 雖然 LLDB 中的 Tab 鍵完成非常有用,但目前並非所有命令及其各自的參數都實作了它們。 這個專案是關於為 LLDB 中的命令實作剩餘的完成,這將大大改善 LLDB 的使用者體驗。 改進現有的完成也是專案的一部分。 請注意,完成不是字串的靜態列表,而是通常需要檢查和理解 LLDB 的內部狀態。 由於 LLDB 命令及其 Tab 鍵完成涵蓋了 LLDB 的所有方面,因此這個專案提供了一個全面了解 LLDB 中所有功能的絕佳方式。

已確認指導教授:Raphael Isemann

理想技能: 中級 C++ 知識。

專案描述: 正如 LLVM 是一個用於建置編譯器的函式庫一樣,LLDB 是一個用於建置偵錯器的函式庫。 LLDB 銷售一個穩定、公開的 SB API。 由於歷史原因,LLDB 命令列介面目前是在 LLDB 私有 API 之上實作的,並且它重複了很多已經在公開 API 中實作的功能。 在公開 API 之上重寫 LLDB 的命令列介面將簡化實作、消除重複程式碼,並且最重要的是減少測試表面。

這項工作也將提供一個機會來清理 SB API 中隨著時間的推移累積了太多重載的命令,並轉換它們以利用選項類別來收集所有變體並使 API 具有未來性。

已確認指導教授:Adrian Prantl 和 Jim Ingham

理想技能: 中級 C++ 知識。

專案描述: 測試套件中的一個緊張關係是,啟動一個進程並使其到達某個點並不是一個廉價的操作,因此您希望到達那裡時執行一堆測試。 但是當前測試套件在第一次失敗時就會中止,因此您不想執行太多測試,因為一個測試的失敗會導致所有其他測試都失敗。 另一方面,在某些個別測試斷言中,斷言的失敗應該導致整個測試失敗。 例如,如果您未能停在您想要檢查某些變數值的斷點處,那麼整個測試都應該失敗。 但是,如果您的測試然後想要檢查五個獨立局部變數的值,它應該能夠執行所有五個,然後報告五個變數斷言中有多少個失敗。 我們可以透過為一批測試新增開始結束標記來做到這一點,執行批次中的所有測試而不會使整個測試失敗,然後報告錯誤,並在適當時使整個測試失敗。 也許還有一種在 Python 中使用範圍物件來進行測試區段的好方法。

已確認指導教授: Jim Ingham

理想技能: 中級 Python 知識。

2019 年 Google Summer of Code 為 LLVM 專案做出了很大貢獻。 有關已接受和已完成專案的列表,請查看 Google Summer of Code 網站。

專案描述: 新增偵錯資訊(使用 `clang -g` 編譯)不應更改產生的程式碼。 不幸的是,我們有錯誤。 這些錯誤通常不太難修復,並且是發現程式碼庫新部分的好方法! 我們建議以兩種方式建置物件檔案並反組譯文字區段,這將比比較 .s 檔案產生更乾淨的差異。

預期成果: 縮減的測試案例、包含分析的錯誤報告(例如,哪個 pass 負責)、可能的修補程式。

已確認指導教授: Paul Robinson

理想技能: 中級 C++ 知識、對 x86 或 ARM 指令集的一些熟悉度。

專案描述: Clang 包含一個 ASTImporter,它允許將宣告和語句從一個 Clang AST 移動到另一個。 例如,這用於跨翻譯單元的靜態分析和 LLDB 的表達式評估器中。

當將簡單的 C 程式碼從一個 AST 移動到另一個 AST 時,目前的 ASTImporter 可以按預期工作。 但是,更複雜的宣告(例如 C++ 的 OOP 功能和範本)尚未完全實作,並且可能導致崩潰或無效的 AST 節點。 與這些崩潰相關的錯誤報告通常針對 LLDB 的表達式評估器提出,並且很少以最小的重現器提交。 這使得改進 ASTImporter 成為一項耗時且乏味的任務。

這個專案是關於編寫一個模糊測試器,以主動發現這些 ASTImporter 錯誤並提供最小的重現器,這使得理解和修復底層錯誤更容易。

這種模糊測試器和驅動程式的可能實作可能如下所示

  • 產生一些可以匯入的原始碼(完全隨機或基於來自使用者給定的程式碼語料庫的現有原始碼)。
  • 從這個 AST 隨機匯入一些宣告。 可以使用宣告預先填充要將它們匯入的 AST。
  • 在我們匯入的 AST 上執行 Clang 的程式碼產生器。
  • 如果我們在匯入或 CodeGen 步驟中遇到斷言,我們可能找到了 ASTImporter 錯誤。
  • 模糊測試器驅動程式現在應該縮小原始碼的大小,直到它盡可能小並且仍然重現崩潰(例如,透過使用自動產生的測試腳本執行 Creduce)。
  • 重現器現在應該以一種格式儲存,以便它可以直接複製到 Clang 的 ASTImporter 迴歸測試套件中(請參閱 clang/test/Import/ 目錄)。 當作為測試套件的一部分執行時,重現器必須仍然重現找到的錯誤。
這只是一種可能的方法,歡迎學生提交他們自己關於模糊測試器應如何運作的想法。 鼓勵允許自動驗證匯入的 AST 的更多方面(例如,AST 節點的來源位置、RecordDecl 的大小)的方法。 模糊測試器和驅動程式應以 C++ 和/或 Python 實作。

已確認指導教授: Raphael Isemann、Shafik Yaghmour

理想技能: 中級 C++ 知識。

專案描述: Clang 有一個新實作的自動完成功能,其詳細資訊可以在 LLVM 部落格 中找到。 我們希望透過向自動完成新增更多標誌、支援更多 shell(目前僅支援 bash)並將此功能匯出到其他專案(例如 llvm-opt)來改進它。 接受的學生將致力於 Clang Driver、LLVM Options 和 shell 腳本。

預期成果: 自動完成在 bash 和 zsh 上工作,支援 llvm-opt 選項。

已確認指導教授: Yuka Takahashi 和 Vassil Vassilev

理想技能: 中級 C++ 和 shell 腳本編寫知識

2018 年 Google Summer of Code 為 LLVM 專案做出了很大貢獻。 有關已接受和已完成專案的列表,請查看 Google Summer of Code 網站。

2017 年 Google Summer of Code 為 LLVM 專案做出了很大貢獻。 有關已接受和已完成專案的列表,請查看 Google Summer of Code 網站。

本文檔旨在作為 LLVM 的一種「大型 TODO 列表」。 本文檔中的每個專案都是對 LLVM 有用的東西,並且也是熟悉該系統的好方法。 其中一些專案很小且獨立,可能在幾天內實作,其他專案則較大。 其中幾個專案可能會引發其自身有趣的研

如果您正在考慮著手進行其中一個專案,請發送郵件至 LLVM 開發者郵件列表,以便我們知道該專案正在進行中。此外,這也是獲取關於特定專案更多資訊,或建議將其他專案添加到此頁面的好方法。

此頁面中的專案是開放式的。更具體的專案已在 LLVM 錯誤追蹤器中作為未分配的增強功能提交。如果您希望幫助改進 LLVM,請參閱目前待處理問題列表

除了在主要的 LLVM 專案上進行開發之外,LLVM 還有幾個子專案,包括 Clang 和其他專案。如果您有興趣參與這些專案,請參閱他們的「開放專案」頁面

對當前基礎架構的改進總是受到非常歡迎的,並且通常相當容易實施。以下是一些可以改進的關鍵領域...

目前,Clang 和 LLVM 都具有獨立的目標描述基礎架構,其中一些功能是重複的,另一些功能是「共享」的(就 Clang 必須建立完整的 LLVM 目標描述以查詢特定資訊而言)。

這種分離是並行發展的,因為最初它們非常不同,並且服務於不同的目的。但是隨著編譯器的發展,越來越多的功能必須在兩者之間共享,以便編譯器能夠正常運作。一個例子是當目標在沒有標誌的特定配置上具有預設功能時。如果後端具有與前端不同的「預設」行為,而後者無法強制執行行為,則它將無法工作。

另一種選擇是為所有小的怪癖建立標誌,但首先,Clang 不是唯一使用 LLVM 中間/後端的前端或工具,其次,這就是「預設行為」的目的,因此我們將會錯失重點。

已經有一些關於修復 Clang 驅動程式 WRT 識別架構、功能等的想法(table-gen 它,使用者特定的設定檔等等),但它們都沒有觸及關鍵問題:與後端共享該資訊。

最近,將目標描述基礎架構從 Clang 和 LLVM 中分離出來,放入它們都使用的獨立函式庫中的想法一直在流傳。這將確保所有預設值、標誌和行為都是共享的,同時也將大大降低複雜性(以及維護成本)。這也將允許所有工具(lli、llc、lld、lldb 等)在各方面都具有相同的行為。

主要的挑戰是

  • 確保過渡不會破壞任何目標上的微妙平衡,因為某些預設值是隱含的,有時甚至是未知的。
  • 能夠一次遷移一個目標、一次遷移一個工具,並且仍然保持舊的基礎架構完整。
  • 使前端和後端的功能都能夠輕鬆檢測目標的功能,並將兩者合併為一組連貫的屬性。
  • 為尚未遷移的工具(尤其是樹外的工具)提供通往新系統的橋樑,這些工具將需要一些時間(至少一個版本)來遷移。

LLVM 錯誤追蹤器偶爾會有提交 「程式碼清理」錯誤。 處理其中一個並修復它,是讓您初步了解 LLVM 程式碼並發現其某些組件如何運作的好方法。 其中一些包括一些主要的 IR 重新設計工作,這是影響深遠的,因為它可以簡化最佳化器中的許多事情。

一些特定的項目會很棒

此外,LLVM 中還存在效能改進,需要修復。這些都標記為slow-compile關鍵字。使用 此 LLVM 錯誤追蹤器查詢來找到它們。

llvm-test 測試套件是我們用於夜間測試產生程式碼效能、編譯時間、正確性等等的大型程式集合。擁有大型測試套件為我們提供了廣泛的程式覆蓋率,並使我們能夠發現和改進編譯器中的任何問題區域。

一個非常有用的任務,不需要深入了解編譯器,就是擴展我們的測試套件,以包含 新的程式和基準測試。特別是,我們對 CPU 密集型程式感興趣,這些程式的函式庫依賴性很少,產生一些可用於正確性測試的輸出,並且可以以原始碼形式重新發佈。許多不同的程式都適用,例如,請參閱 此列表以了解一些潛在的候選者。

我們一直在尋找新的測試案例和基準測試,以用於 LLVM。特別是,嘗試使用 LLVM 編譯您最喜歡的 C 原始碼會很有用。如果它無法編譯,請嘗試找出原因或將其報告給 llvm-bugs 列表。如果您讓程式編譯成功,將建置系統轉換為與 LLVM Programs 測試套件相容將非常有用,以便我們可以將其簽入 SVN,並且自動測試器可以使用它來追蹤編譯器的進度。

在測試程式碼時,請嘗試使用各種最佳化以及所有後端:CBE、llc 和 lli 執行它。

使用我們的 測試結果 或您自己的基準測試,找到 LLVM 程式碼產生器未產生最佳程式碼,或另一個編譯器產生更好程式碼的地方。嘗試最小化展示問題的測試案例。然後,提交包含您的測試案例和 LLVM 產生的程式碼與它應該產生的程式碼的錯誤報告,或者更好的是,看看您是否可以改進程式碼產生器並提交修補程式。基本想法是,如果我們知道效能問題,通常很容易修復它們,但我們通常沒有資源去找出為什麼效能很差。

LNT 效能資料庫具有一些不錯的功能,例如偵測移動平均值、標準差、變異等等。但是報告頁面過於強調個別變異(其中雜訊可能高於訊號),例如 這個案例

專案的第一部分是建立一個分析工具,該工具將追蹤移動平均值並報告

  • 如果目前的結果高於/低於先前的移動平均值超過(可設定的)S 個標準差
  • 如果目前的移動平均值大於基準運行的 S 個標準差
  • 如果最後 A 個移動平均值持續增加/減少超過 P 個百分比

第二部分是建立一個網頁,該網頁將顯示所有相關的基準測試(可能是可設定的,例如儀表板),並顯示基本統計資訊,並使用紅色/黃色/綠色代碼來顯示狀態以及指向每個基準測試更詳細分析的連結。

可能的第三部分是能夠自動交叉引用不同的建置版本,這樣如果您按架構/編譯器/CPU 數量對它們進行分組,這個自動化工具將會理解這些變更在一個特定的群組中更為常見。

LLVM 覆蓋率報告有一個很好的介面來顯示哪些原始碼行被測試覆蓋,但它沒有提及哪些測試、哪個修訂版本和哪個架構被覆蓋。

改造 LCOV 的專案將涉及

  • 使其在建置機器人上運行,以便我們知道哪些提交/架構被覆蓋
  • 更新網頁以顯示該資訊
  • 開發一個系統,將每個建置機器人建置版本報告到可搜尋的資料庫網頁中,例如 LNT

另一個想法是使測試套件能夠運行所有建置的後端,而不僅僅是主機架構,以便可以在快速機器中建立覆蓋率報告,並且每個提交都有一個報告,而無需更新建置機器人。

  1. 完全重寫 bugpoint。除了混亂之外,bugpoint 還存在許多問題,在縮減時會「遺失」錯誤。應該從頭開始重寫它,以解決這些問題和其他問題。
  2. 為 PassManager 新增事務支援,以改進 bugpoint。
  3. 改進 bugpoint 以支援在 MP 機器上並行運行測試.
  4. 為 SPARC 連接埠新增 MC 組譯器/反組譯器和 JIT 支援。
  5. 將更多最佳化移出-instcombinepass 並移入 InstructionSimplify。應該移動的最佳化是不會建立新指令的最佳化,例如將sub i32 %x, 0變成%x。許多 pass 使用 InstructionSimplify 來清理程式碼,因此使其更智慧可以帶來各方面的改進。

有時創造新事物比改進現有事物更有趣。這些專案往往更複雜,可能需要更多工作,但也可能非常有回報。

許多建議的 LLVM 核心的擴展和改進正在等待設計和實施。

  1. 偵錯資訊產生的改進
  2. 對非呼叫例外情況的 EH 支援
  3. 許多功能請求的想法都儲存在 LLVM bugzilla 中。搜尋 帶有「new-feature」關鍵字的錯誤

我們擁有開發基於指標分析的最佳化以及指標分析本身的 堅實基礎。我們希望利用這一點

  1. 全域變數 mod/ref pass 執行低成本的自下而上上下文相關別名分析。我們可以做一些低成本的事情來更好地捕捉存取指標引數的函式的效果。這對於 C++ 方法來說非常重要,它們花費大量時間存取 'this' 的指標。
  2. 別名分析 API 支援 getModRefBehavior 方法,該方法允許實作提供函式的詳細分析。例如,我們可以實作 完全了解 printf/scanf 的副作用,這將很有用。此功能已到位,但目前未用於任何用途。
  3. 我們需要某種方法來推論 errno。考慮像這樣的迴圈
        for ()
          x += sqrt(loopinvariant);
    

    我們希望將其轉換為

        t = sqrt(loopinvariant);
        for ()
          x += t;
    

    此轉換是安全的,因為 errno 的值在迴圈中沒有其他變更,並且迴圈的 errno 退出值是相同的。我們目前無法做到這一點,因為 sqrt 會破壞 errno,因此它不是「readonly」或「readnone」,並且我們沒有好的方法來建模它。

    這個專案的重要部分是弄清楚如何在最佳化器中描述 errno:每個 libc #defines errno 似乎都不同。也許解決方案是擁有一個 __builtin_errno_addr() 或類似的東西,並更改 sys 標頭以使用它。

  4. 有很多方法可以最佳化和 改進 memcpy/memset 的處理

我們現在擁有一個統一的基礎架構,用於編寫以設定檔引導的轉換,它可以在離線編譯時或在 JIT 中工作,但我們沒有很多轉換。我們歡迎新的以設定檔引導的轉換,以及對目前設定檔系統的改進。

以設定檔引導的轉換的想法

  1. 超區塊形成(具有許多最佳化)
  2. 迴圈展開/剝離
  3. 以設定檔引導的內聯
  4. 程式碼佈局
  5. ...

對現有支援的改進

  1. 目前插入的區塊和邊緣設定檔程式碼非常簡單且效率低下。透過使用控制依賴性資訊,可以將更少的計數器插入程式碼中。此外,如果已知迴圈的執行計數是編譯時或運行時常數,則可以避免迴圈中的所有計數器。
  2. 您可以實作其中一種「靜態設定檔」演算法,該演算法分析一段程式碼,並對程式碼各個部分的相對執行頻率做出有根據的猜測。
  3. 您可以新增路徑設定檔支援,或調整現有的 LLVM 路徑設定檔程式碼以與通用設定檔介面一起使用。

LLVM 積極地針對效能進行最佳化,但尚未針對程式碼大小進行最佳化。隨著新的 ARM 後端出現,人們越來越有興趣在程式碼大小更重要的嵌入式系統中使用 LLVM。

有興趣在 LLVM 中實作程式碼壓縮的人員可能想閱讀 這篇 文章,其中描述了使用連結時間最佳化來進行程式碼大小最佳化。

  1. 實作迴圈依賴性分析基礎架構
    - 設計某種方式來表示和查詢依賴性分析
  2. 值域傳播 pass
  3. 更多關於迴圈的樂趣:預測性共同化
  4. 類型推斷(又名:去虛擬化)
  5. 值斷言(另請參閱 PR810)。
  1. 透過新增必要的目標掛鉤並確保正確處理所有 IR/MI 功能(例如暫存器遮罩和述詞指令),來通用化可以獨立於目標的特定目標後端 pass。在其他目標上啟用這些功能,如果這樣做顯然是有益的。例如
    1. lib/Target/Hexagon/RDF*
    2. lib/Target/AArch64/AArch64AddressTypePromotion.cpp
  2. 將重複的延遲槽填充邏輯合併到(至少)Sparc 和 Mips 後端中,形成單個獨立於目標的 pass。同樣,幾個目標中的分支縮短邏輯應合併到一個 pass 中。
  3. 實作「堆疊槽著色」,如果兩個框架索引的存活範圍不重疊,則將它們分配給相同的堆疊偏移量。這可以重複使用來自 LiveIntervals 的大量分析機制。縮小堆疊對於快取使用很有好處,並且在負載位移有限的目標(如 ppc、thumb、mips、sparc 等)上非常重要。這應該在序言/結語插入之前作為一個 pass 完成。這現在已針對暫存器分配器臨時變數完成,但不適用於 allocas。
  4. 實作「收縮包裝」,這是對被呼叫者儲存暫存器儲存/還原的智慧放置。現在 PrologEpilogInsertion 總是將序言中每個(修改過的)被呼叫者儲存暫存器儲存起來,並在結語中還原它,但是,函數中的某些路徑(例如,提前退出)可能不會使用所有暫存器。將儲存下沉到 CFG 中可以避免在這些路徑上進行無用的工作。這方面的工作已經開始,請在 llvm-dev 上詢問。
  5. 實作跨程序暫存器分配。CallGraphSCCPass 可用於實作自下而上的分析,該分析將確定函數實際破壞的實際暫存器。使用 pass 根據被呼叫者使用的實際暫存器來微調呼叫者中的暫存器使用情況。
  6. 為組譯器和反組譯器新增對 16 位元 x86 組譯碼和真實模式的支援,以供 BIOS 程式碼使用。這包括 16 位元指令編碼以及特權指令(lgdt、lldt、ltr、lmsw、clts、invd、invlpg、wbinvd、hlt、rdmsr、wrmsr、rdpmc、rdtsc)以及控制和偵錯暫存器。
  1. 將 Manuel Serrano 在 INRIA Sophia-Antipolis 開發的 Bigloo Scheme 編譯器移植到輸出 LLVM 位元組碼。它似乎已經可以輸出 .NET 位元組碼、JVM 位元組碼和 C,因此 LLVM 表面上將是另一個好的候選者。
  2. 為其他一些語言編寫新的前端(Java?OCaml?Forth?)
  3. 隨機測試向量產生器:使用 C 文法產生隨機 C 程式碼,例如 quest;透過 llvm-gcc 運行它,然後使用 opt 在其上運行一組隨機的 pass。嘗試崩潰opt。當opt崩潰時,使用bugpoint來縮減測試案例並將其發佈到網站或郵件列表。無限重複。
  4. 為 Interpreter 新增沙箱功能:捕獲無效的記憶體存取、潛在的不安全操作(透過任意記憶體指標存取)等。
  5. 移植 Valgrind 以使用 LLVM 程式碼產生和最佳化 pass,而不是它自己的。
  6. 編寫 LLVM IR 級別偵錯器(擴展 Interpreter?)
  7. 編寫 LLVM 超級最佳化器。將以下 x86 超級最佳化器的想法應用於 LLVM 程式碼將會很有趣:論文 #1論文 #2 並使其適應在 LLVM 程式碼上運行。

    在 LLVM 程式碼上運作似乎可以節省大量時間,因為它的語義比 x86 簡單得多。在 LLVM 上運作的代價是會錯過特定於目標的技巧。

    結果將是一個新的 LLVM pass,它至少包含指令組合器,可能還包含一些其他 pass。好處包括不會遺漏目前組合器遺漏的案例,並且更容易適應 LLVM IR 的變更。

    以前的所有超級最佳化器都在線性程式碼序列上工作。在程式依賴圖的小型子圖上運作似乎會更好。

除了增強現有 LLVM 基礎架構的專案外,還有一些專案可以改進使用 LLVM 編譯器基礎架構的軟體,但這些軟體不包含在 LLVM 編譯器基礎架構中。這些專案包括使用 LLVM 的開源軟體專案和研究專案。與增強核心 LLVM 基礎架構的專案一樣,這些專案通常也具有挑戰性且回報豐厚。

至少有一個專案(可能更多)需要在 MachineFunctionPass 中使用分析資訊(例如呼叫圖分析),但是,大多數分析 pass 在 LLVM IR 級別運作。在某些情況下,值(例如,函數指標)無法從 MachineInstr 級別可靠地映射回 LLVM IR 級別,這使得從 MachineFunctionPass 中使用現有的 LLVM 分析 pass 變得不可能(或至少是脆弱的)。

這個專案是在產生 MachineInstr IR 時,將來自 LLVM IR 級別的分析資訊編碼到 MachineInstr IR 中,以便 MachineFunctionPass 可以使用它。範例是呼叫圖分析(對於控制流程完整性檢測、程式碼重用防禦分析和小工具編譯器很有用);但是,其他 LLVM 分析可能也很有用。

在 LLVM JIT 中實作隨需函數重定位器。這可以幫助使用運行時設定檔資訊來改善程式碼局部性。這個想法是對每個函數使用重定位表。每次函數重定位時都需要更新重定位條目(請查看 這篇文章)。(每個函數的)基本區塊重新排序將是一個有用的擴展。

這個專案的目標是使用參考親緣性模型來實作更好的資料佈局最佳化。這篇 論文 提供了一些背景資訊。

Slimmer 是一個原型工具,使用 LLVM 建置,它使用動態分析來查找程式中潛在的效能錯誤。Slimmer 的開發始於 2015 年的 Google Summer of Code,並產生了一個初始原型,但仍需要對原型進行評估和改進,以使其可移植且穩健。這個專案將讓學生接手並完成 Slimmer 的工作。Slimmer 的原始碼及其目前的文檔可以在其 Github 網頁上找到。