EDK2環(huan)境(jing)搭建以及HelloWorld編譯實現
EDK2環境搭建以及HelloWorld編譯實現
一、TianoCore的官方介紹
Welcome to TianoCore, the community supporting an open source implementation of the Unified Extensible Firmware Interface (). is a modern, feature-rich, cross-platform firmware development environment for the UEFI and UEFI Platform Initialization () specifications. We hope that you’ll review our documentation, use TianoCore for platform firmware, you find, and contribute to the community.
TianoCore 致力(li)于支持 UEFI(統一(yi)可(ke)擴展固(gu)件接口)的(de)開源實現。EDK II 是一(yi)個現代化、功(gong)能強大(da)且跨平臺(tai)的(de)固(gu)件開發環境,完全遵循 UEFI 及 UEFI PI(平臺(tai)初始化)規范。
二、UEFI & EDKII & OVMF
- UEFI是一種標準或者規范手冊。它定義了系統的啟動流程,實現從硬件到操作系統的引導過程,定義了固件與操作系統之間的接口。比方說要蓋房子,規范就規定了房子要有承重墻,電路布線規則,門窗大小等。
- EDK2的全稱是EFI Development Kit II,是由Intel主導的開源UEFI開發框架。開發者可以基于EDK2編寫自己的UEFI固件。
- OVMF全稱是Open Virtual Machine Firmware,是EDK2的一個子項目,專門針對QEMU虛擬機環境提供UEFI支持。輸出的文件通常是
OVMF.fd或者OVMF_CODE.fd/OVMF_VARS.fd。
三、EDK2環境搭建
-
安裝依賴
sudo apt update sudo apt install -y build-essential uuid-dev iasl git nasm\ python3-distutils python2-pip python3-setuptools python3-venv python3-dev\ flex bison openssl libssl-dev libpython3-dev -
獲取源碼
# edk2的GitHub官網 //github.com/tianocore/edk2/tree/master # 獲取穩定版本 git clone //github.com/tianocore/edk2.git -b stable/202011mkdir -p ~/src cd ~/src git clone //github.com/tianocore/edk2.git -b stable/202011 cd edk2 git submodule update --init -
編譯
BaseToolscd ~/src/edk2 make -C BaseTools # 完成后期望看到 GenFv GenFw GenFfs VolInfo 等工具 ls -l BaseTools/Source/C/bin -
初始化構建環境
cd ~/src/edk2 source edksetup.sh這一步會在
Conf/下生成targart.txt、tool_def.txt。如果(guo)以(yi)后每次打開新shell要構建,可(ke)以(yi)把這句加入(ru)到~/.bashrc。 -
編輯
Conf/targart.txt# 適用于本地x86_64的最小配置 ACTIVE_PLATFORM = OvmfPkg/OvmfPkgX64.dsc TARGET = DEBUG TARGET_ARCH = X64 TOOL_CHAIN_TAG = GCC5 BUILD_RULE_CONF = Conf/build_rule.txtACTIVE_PLATFORM指向要構建的Platform.dsc(這里是OVMF x64)。
TOOL_CHAIN_TAG = GCC5這里的GCC5是默認選項,不用改成GCC。
TARGET有兩個常用的選項,分別是DEBUG和RELEASE。二者分(fen)別表(biao)示編(bian)譯的(de)固件版(ban)本為調試(shi)版(ban)本和(he)發布版(ban)本。調試(shi)版(ban)本幾乎不會編(bian)譯優化(hua),保留完(wan)整的(de)調試(shi)符號,鏡(jing)像(xiang)較大,啟(qi)動速度略慢,用(yong)于固件的(de)開(kai)發、調試(shi)、驗證階段。 -
構建
OVME(x64固件)cd ~/src/edk2 source edksetup.sh # 需要注意的是,在編輯過Conf/targart.txt之后可以直接build build -a X64 -t GCC5 -p OvmfPkg/OvmfPkgX64.dsc -b DEBUG # 構建成功后,固件文件位于 ~/src/edk2/Build/OvmfX64/DEBUG_GCC5/FV/ # 重要文件示例:OVMF_CODE.fd OVMF_VARS.fd OVMF.fd此時其實固件已經生成完(wan)畢了。
-
生成直接可用的
bios.bin(可選)cd ~/src/edk2/Build/OvmfX64/DEBUG_GCC5/FV cat OVMF_CODE.fd OVMF_VARS.fd > ~/run-ovmf/bios.bin # 校驗大小接近 OVMF_CODE + OVMF_VARS ls -lh ~/run-ovmf/bios.bin -
創(chuang)建測試用(yong)的(de)FAT磁盤目錄(lu)
mkdir -p ~/run-ovmf/hda-contents/EFI/BOOT把一個
64-bit的EFI程序放進去,下面編譯HelloWorld。 -
HelloWorld編譯# 默認HelloWorld的位置在:MdeModulePkg/Application/HelloWorld/HelloWorld.inf build -a X64 -t GCC5 -p MdeModulePkg/MdeModulePkg.dsc -m MdeModulePkg/Application/HelloWorld/HelloWorld.inf # 生成的文件路徑:Build/MdeModule/DEBUG_GCC5/X64/HelloWorld.efi cp ~/src/edk2/Build/MdeModule/DEBUG_GCC5/X64/HelloWorld.efi hda-contents/EFI/BOOT/BOOTX64.EFI -
運行
QEMUqemu-system-x86_64 -bios /home/ayuan/run-ovmf/OVMF.fd -drive format=raw,file=fat:rw:/home/ayuan/run-ovmf/hda-contents -m 512M cat OVMF_CODE.fd OVMF_VARS.fd > ~/run-ovmf/bios.bin qemu-system-x86_64 \ -bios /home/ayuan/run-ovmf/bios.bin \ -drive format=raw,file=fat:rw:/home/ayuan/run-ovmf/hda-contents \ -m 1024M以上兩個命令有所區別。
OVMF.fd的固件結構是單文件,是CODE和VARS在一起的。其中CODE是UEFI的代碼段,VARS是內嵌的變量存儲區,這種情況下啟動后修改的UEFI變量不會持久保存,下次啟動會恢復初始狀態(tai)。與之相反的(de)是(shi)第二條命(ming)令,其可以持久保(bao)存UEFI的(de)設置。
在Ubuntu20.04上運行QUMU遇到的問題以及解決方法
一、執行QEMU界面卡住,無法進入shell
-
直接使用命令
sudo apt install qemu-system-x86_64安裝的版本在執行時會卡到Guest has not initialized the display (yet)界面,無法(fa)進入下一步,如圖(tu)1所示(shi)。
圖1:錯誤頁面示意圖 - 考慮是
QEMU虛擬機版本的問題,所以接下來嘗試兩種解決方法,一種是使用Windows安裝QEMU虛擬機運行自Linux編譯出的OVMF固件鏡像。另一種是在Ubuntu上利用源碼編譯出更高版本的QEMU虛擬機。
- 考慮是
二、Windows上安裝QEMU執行OVMF.fd
安裝步驟(只講關鍵步驟)
-
下載地址:
-
下載版本如圖二。
圖2:win下qemu下載版本 -
正常步驟安裝即可。
-
將安裝路徑
D:\Program Files\qemu添加至環境變量path,直接搜索環境變量即可。
圖3:添加環境變量 -
安裝完畢確認。
qemu-system-x86_64 -version -
執行。
qemu-system-x86_64 -bios D:\users\wsy\Desktop\EDK2\edk2\run-ovmf\bios.bin -drive format=raw,file=fat:rw:D:\users\wsy\Desktop\EDK2\edk2\run-ovmf\hda-contents -m 512M -
進入
shell。
Boot Manager->EFI Interal Shell進入到shell。進入對應的目錄執行
HelloWorld。
圖4:執行HelloWorld
-
三、Ubuntu上編譯出更高版本的QEMU
3.1 使用apt命令安裝qemu
# 安裝基礎的QEMU包
sudo apt update
sudo apt install qemu-kvm qemu-utils
# 常用的組件有
# qemu-kvm: KVM加速支持
# qemu-utils: QEMU工具集(qemu-img等)
# qemu-system: 完整的系統模擬器(可替換為特定架構)
# virt-manager: 圖形化管理工具(可選)
# 可以安裝完整的QEMU套件,也可以安裝特定架構的QEMU
sudo apt install qemu-system qemu-utils virt-manager
# 或者
sudo apt install qemu-system-x86
# 驗證安裝
qemu-system-x86_64 --version
# 此時安裝上的版本是6.0,上面我們提到默認的版本太低了,可能導致問題。所以接下來的命令是獲取更高版本的源碼,編譯安裝。
3.2 舊版本qemu卸載
卸載方式與安裝方式有關,我用到的安裝方式有兩種,一種是通過apt命令直接下載,另一種是git clone源(yuan)碼編譯,兩種(zhong)安裝方式對應著兩種(zhong)卸載方式。
如果是通過apt安裝的:
sudo apt remove --purge qemu qemu-system qemu-utils qemu-kvm
sudo apt autoremove --purge
sudo apt clean
# 查看是否殘留,如果還有相關殘留,繼續remove即可
dpkg -l | grep qemu
如果(guo)是通(tong)過源碼編譯安裝的:
cd /home/name/src/qemu
sudo make uninstall
# 如果沒有uninstall目標,可以手動刪除QEMU的安裝文件
sudo rm -f /usr/local/bin/qemu-system-* \
/usr/local/bin/qemu-img \
/usr/local/bin/qemu-nbd \
/usr/local/bin/qemu-pr-helper
sudo rm -rf /usr/local/share/qemu
sudo rm -rf /usr/local/libexec/qemu
sudo rm -rf /usr/local/include/qemu
# 清理舊的配置或者殘留
sudo ldconfig
# 驗證
which qemu-system-x86_64
ls /usr/local/bin | grep qemu
3.3 qemu源碼克隆編譯
-
qemu項目的git地址(zhi)為(wei)//github.com/qemu/qemu/tree/master。 -
克隆和編譯步驟。
# 如果不加-b stable-9.0則克隆下來的是最新版本,但不是最新穩定版,這里我們選擇9.0的穩定版本。 git clone //github.com/qemu/qemu.git -b stable-9.0 # 安裝常用的依賴 sudo apt update sudo apt install -y \ git libglib2.0-dev libfdt-dev libpixman-1-dev zlib1g-dev \ libaio-dev libbluetooth-dev libbrlapi-dev libcap-dev libcurl4-gnutls-dev \ libgtk-3-dev libibverbs-dev libjpeg8-dev libncurses5-dev libnuma-dev \ librbd-dev librdmacm-dev libsasl2-dev libsdl2-dev libseccomp-dev \ libsnappy-dev libssh-dev libvde-dev libvte-2.91-dev libxen-dev \ liblzo2-dev python3 python3-pip pkg-config ninja-build上面列出的依賴介紹(這里我自己好奇用
ChatGPT搜了一下,大家可(ke)以直接安裝即可(ke))。?? 一、基礎構建工具(編譯器和構建系統) 包名 作用說明 git 用來克隆 QEMU 源碼倉庫。 pkg-config 用來在編譯時查找庫的頭文件和鏈接參數(自動生成 -I、-L 選項)。 python3 QEMU 的構建腳本使用 Python 編寫。 python3-pip 用于安裝額外的 Python 構建模塊(如 meson、ninja)。 ninja-build QEMU 使用的現代化構建系統(比 make 更快)。 ?? 二、核心依賴(QEMU 模擬和設備框架) 包名 作用說明 libglib2.0-dev QEMU 使用的核心工具庫,提供事件循環、線程、數據結構(必須)。 libfdt-dev 支持設備樹(Flattened Device Tree),在 ARM 平臺或嵌入式模擬中使用。 libpixman-1-dev 圖像像素操作庫,QEMU 的圖形輸出(SDL/VNC)依賴它。 zlib1g-dev 壓縮庫,QEMU 用它來支持壓縮磁盤鏡像(qcow2 等)。 ?? 三、I/O 與虛擬化設備支持 包名 作用說明 libaio-dev 異步 I/O 支持(提升磁盤讀寫性能)。 libnuma-dev 支持 NUMA(多CPU內存架構),在多核模擬時使用。 libseccomp-dev 啟用沙盒隔離,提升安全性(防止主機被虛擬機訪問)。 libcap-dev 支持 Linux capability 權限控制。 libxen-dev 支持 Xen 虛擬化環境的接口。 libvde-dev 支持虛擬分布式以太網(Virtual Distributed Ethernet)實現虛擬機間互聯。 ?? 四、網絡與遠程訪問支持 包名 作用說明 libcurl4-gnutls-dev 讓 QEMU 能通過 HTTP/HTTPS 下載鏡像或遠程訪問資源。 libsasl2-dev 用于遠程認證(SMTP、VNC 登錄等)。 libssh-dev 支持通過 SSH 協議訪問磁盤鏡像或遠程遷移虛擬機。 librdmacm-dev / libibverbs-dev 支持 RDMA(遠程直接內存訪問),加速虛擬機之間通信。 librbd-dev 提供對 Ceph RADOS 塊設備(分布式存儲)的支持。 ??? 五、圖形界面與輸入輸出支持 包名 作用說明 libsdl2-dev SDL 圖形庫,提供基本的 GUI 窗口(QEMU 的顯示輸出)。 libgtk-3-dev GTK 圖形界面庫,使 QEMU 的 GUI 更現代(帶菜單欄、控制按鈕)。 libvte-2.91-dev 終端控件支持(用于 QEMU 的 GTK 版內置終端)。 libjpeg8-dev JPEG 圖像支持(VNC 輸出截圖、視頻編碼)。 liblzo2-dev 壓縮支持庫(用于 qcow2 壓縮鏡像)。 libsnappy-dev Google Snappy 壓縮支持,提高磁盤鏡像 I/O 性能。安裝過程中如遇依賴問題,可以使用
aptitude命令(ling)獲(huo)取(qu)解決方案后繼續安裝,舉例如下。# 以libgtk-3-dev為例,安裝時遇到如下問題 ayuan@ayuan-virtual-machine:~/src/qemu$ sudo apt install libgtk-3-dev ... 下列軟件包有未滿足的依賴關系: libpango1.0-dev : 依賴: gir1.2-pango-1.0 (= 1.50.6+ds-2) 但是 1.50.6+ds-2ubuntu1 正要被安裝 ...... E: 無法修正錯誤,因為您要求某些軟件包保持現狀,就是它們破壞了軟件包間的依賴關系。 ayuan@ayuan-virtual-machine:~/src/qemu$ # 解決方法 sudo aptitude install libgtk-3-dev # 然后出現如下字樣 保持 下列軟件包于其當前版本: 1) libgtk-3-dev [未安裝的] 是否接受該解決方案?[Y/n/q/?] # 如果選擇Y,那么該依賴仍然不會被安裝,所以這里選擇n,此時: 安裝 下列軟件包: 1) icu-devtools [70.1-2 (jammy)] 2) libdatrie-dev [0.2.13-2 (jammy)] 3) libgraphite2-dev [1.3.14-1build2 (jammy)] 4) libharfbuzz-dev [2.7.4-1ubuntu3.2 (jammy-security)] 5) libharfbuzz-gobject0 [2.7.4-1ubuntu3.2 (jammy-security)] 6) libicu-dev [70.1-2 (jammy)] 7) libpango1.0-dev [1.50.6+ds-2 (jammy)] 8) libthai-dev [0.1.29-1build1 (jammy)] 9) libxft-dev [2.3.4-1 (jammy)] 10) pango1.0-tools [1.50.6+ds-2 (jammy)] 降級 下列軟件包: 11) gir1.2-pango-1.0 [1.50.6+ds-2ubuntu1 (now) -> 1.50.6+ds-2 (jammy)] 12) libpango-1.0-0 [1.50.6+ds-2ubuntu1 (now) -> 1.50.6+ds-2 (jammy)] 13) libpangocairo-1.0-0 [1.50.6+ds-2ubuntu1 (now) -> 1.50.6+ds-2 (jammy)] 14) libpangoft2-1.0-0 [1.50.6+ds-2ubuntu1 (now) -> 1.50.6+ds-2 (jammy)] 15) libpangoxft-1.0-0 [1.50.6+ds-2ubuntu1 (now) -> 1.50.6+ds-2 (jammy)] 是否接受該解決方案?[Y/n/q/?] # 這時候就可以選擇Y,進行安裝了。接下來是主要的安裝(zhuang)流程,安裝(zhuang)過(guo)(guo)程中也會遇到一些(xie)依賴問題,可以用(yong)AI搜(sou)索解決(jue)這里不過(guo)(guo)多贅(zhui)述。
注:如果遇到類似缺少某個頭文件
.h,通常可以按以下規(gui)律解(jie)決:缺失頭文件 對應開發包(Ubuntu) libusb.h / libusb-1.0/libusb.h libusb-1.0-0-dev glib.h libglib2.0-dev pixman.h libpixman-1-dev snappy-c.h libsnappy-dev gnutls/gnutls.h libgnutls28-dev nettle/nettle.h libnettle-devcd qemu/ mkdir build && cd build ../configure \ --prefix=/usr/local/qemu \ --target-list=x86_64-softmmu,aarch64-softmmu \ --enable-kvm \ --enable-sdl \ --enable-gtk \ --enable-vnc \ --enable-curses \ --enable-debug \ --enable-libusb \ --enable-nettle \ --enable-snappy \ --enable-gnutls \ --enable-opengl ninja # 或者更快的ninja -j$(nproc) sudo ninja install # 安裝完成后會有 prefix : /usr/local/qemu在終端顯示,這就是安裝位置。 # 驗證安裝是否成功 /usr/local/qemu/bin/qemu-system-x86_64 --version # 為了在任何路徑都能調用該命令,添加環境變量 echo 'export PATH=/usr/local/qemu/bin:$PATH' >> ~/.bashrc -
經過以上步驟安裝新版本的
qemu之后,再(zai)次(ci)執行我們編譯好(hao)的固件,問題得到(dao)了解決。
參考文章
【1】ChatGPT
【2】

本文簡單介紹了Linux環境下搭建EDK2開發環境的關鍵步驟和命令。