前言
很久之前发过我关于对UEFI开发的探索。我那个时候的方法是把EFI文件拷进U盘,再直通进虚拟机里,或者插到哪台真机上。这个操作实际上太繁琐了,只有真机运行才是其优势。
正文
其实作为虚拟机,用虚拟磁盘映像才是最便捷的方案。当时我没有快速制作虚拟磁盘映像的这个概念,导致开发EFI程序都得插着U盘,非常折腾。
最近才发现制作一个虚拟磁盘其实挺简单的。
在Linux环境制作映像
先说Linux环境,因为我发现的这个方案是基于Linux的。
方法是安装mtools
包,以Ubuntu/Debian发行版的Linux为例:
sudo apt install mtools
毕竟不涉及内核操作,仅仅是编辑文件什么的。所以这套东西在WSL上(不论WSL1还是WSL2)也是可以用的。
然后是创建空的虚拟磁盘映像,命名为disk.img
。
dd if=/dev/zero of=disk.img bs=1k count=1440
接着将其格式化,并创建EFI需要的目录
mformat -i disk.img -f 1440 ::
mmd -i disk.img ::/EFI
mmd -i disk.img ::/EFI/BOOT
最后是复制粘贴到这个虚拟磁盘了
mcopy -i disk.img bootx64.efi ::/EFI/BOOT
如果需要别的文件,可以追加mcopy
命令。
把这些东西放进Makefile或者啥编译脚本里,就能直接生成一个包含EFI程序的虚拟磁盘映像了。
在Windows环境制作映像
如果你的系统能使用WSL,那可以直接照搬Linux环境里的操作。这里说的是不借助WSL的方案。(比如Windows 7不能使用WSL)
首先是创建空文件,Windows里可以用fsutil
命令创建指定大小的空文件。
fsutil file createNew disk.img 1474560
注意fsutil
只接受字节这个单位。
接着就是mtools
这套东西了。网上没有找到直接发布EXE的,不知道为啥。但是能下载到源码。但是不知道为啥,又找不到mtools的官方git repo,只能下载tar.gz压缩包。
总之只能自己编译了。这里踩了不少坑。我下载到的版本是4.0.43版的。
既然作为GNU的玩意,最省事的解决方案就是通过GCC来编译了。在Windows上安装msys2来获取GCC。
我们使用MinGW64的控制台,首先先更新一下。注意msys2的控制台要用Shift+Ins键来粘贴,不能用Ctrl+V。
pacman -Syu --noconfirm
控制台在更新完毕后关闭。重启它,更新剩余的东西
pacman -Su
我并不知道mtools
具体依赖了哪些包裹。我安装msys2
是为了编译QEMU的,所以安装了以下内容:
pacman -S base-devel mingw-w64-x86_64-toolchain git python ninja
pacman -S mingw-w64-x86_64-glib2 mingw-w64-x86_64-pixman python-setuptools
pacman -S mingw-w64-x86_64-gtk3 mingw-w64-x86_64-SDL2 mingw-w64-x86_64-libslirp
我估计其实安装第一行的base-devel
和mingw-w64-x86_64-toolchain
这两样就够了。
然后用cd
命令切换到mtools
的源码目录里。比方说你把源码放进了D:\mtools-src
目录的话,就用cd /d/mtools-src/
命令。
然后是进行配置。
./configure
配置完成后,别急着编译,mtools源码(4.0.43版)在Windows上编译是有坑的,要先改一下config.h
文件。
找到#define HAVE_ICONV_H 1
这一行,把它注释掉。
找到/* #undef HAVE_LIBICONV */
这一行,取消其注释。
最后编译之。
make -j$(nproc)
最后把生成出来的这些exe文件复制到PATH
环境变量里能找到的地方。
cp *.exe 目标路径
这下就能用mtools
来制作映像了。直接照搬前面在Linux上说的,用mformat
,mmd
和mcopy
这些命令即可。
运行UEFI映像
先说说VMware Workstation上的运行方法。
在VMware里,raw格式的磁盘映像可以视为软盘映像。因此直接向虚拟机添加软盘即可。
然后在固件设置里,直接运行EFI Floppy
选项即可。
可以在固件设置里调整优先级来让虚拟机开机就运行你的EFI程序。
另一种方案是用QEMU。如果用惯了命令行,或许QEMU会更简单。
注意QEMU默认使用SeaBIOS作为固件,它是Legacy的。因此要下载TianoCore的OVMF固件才能运行EFI程序。
在Linux里很简单,直接用安装命令即可一次性安装QEMU和OVMF。
sudo apt install qemu-system ovmf
但在Windows里,还得找别的办法来用OVMF。
Kraxel发布过编译好的OVMF固件,可以直接下载。
虽然不是最新版的(Kraxel不再更新编译好的OVMF了),但是能用就行。如果有所追求,那就直接下载源码自己编译OVMF吧。
Kraxel发布的是RPM包,这个文件可以直接用7z打开。提取出里面的OVMF-pure-efi.fd
文件,这就是我们要用的OVMF固件。为了和Linux使用一样的命令,建议将其重命名为OVMF.fd。
接着就是运行QEMU了,代码很简单,指定一下用哪个固件,以及加上哪个磁盘映像即可。
qemu-system-x86_64 -bios OVMF.fd -drive format=raw,file=disk.img
有什么别的需求可以追加参数。
结语
本文介绍了一种快速测试EFI程序的方案。简单说就是怎么把EFI程序包装成一个虚拟磁盘映像。
这里用到了mtools
包,在Linux里可以直接安装,但在Windows里就需要自己编译了。
最后分别说明了如何用VMware和QEMU运行你的EFI程序。注意QEMU需要额外下载OVMF固件来运行EFI程序。