将 arch-linux 安装到 USB 移动硬盘并且保留存储空间给 Windows 设备使用
苦于多端环境同步多年,突然想到我仍然有一个 SanDisk 256G Gen3.1 的 U 盘可以使用,因此研究一下如何将 arch linux 安装在 U 盘上
前置准备:
- VMWare Workstation
- Arch Linux 镜像
- 一个快速的大容量 U 盘(推荐 USB 3.0+,并且大小在 50GB 以上)
环境准备
虚拟机
在虚拟机上添加 arch linux 镜像,一切默认即可。开启虚拟机后,把 USB 连接。

分区
使用命令查看设备分区信息
fdisk -l
可以看到,/dev/sdb 就对应了我的 U 盘,因此可以使用下面的命令进入分区操作。
fdisk /dev/sdb通过 m 可以查看每个命令的含义,在这里节约篇幅不再解释。
首先通过 g 创建一个新的 GPT 分区表。之后,通过 n 创建新的分区,分别是 EFI、\以及 reserved_for_usbdisk
# 创建 GPT 分区表Command (m for help): g
# EFI 分区Command (m for help): n # 创建新分区 # 分区号,默认即可 # 扇区,默认即可+300M # 大小,EFI 分区 300MB 即可
# 根目录分区Command (m for help): n # 创建新分区 # 分区号 # 扇区,默认即可+160G # 大小
# USB 保留分区Command (m for help): n # 创建新分区 # 分区号 # 扇区,默认即可 # 大小,直接默认用完之后,设置分区类型,每个对应的类型都可以通过 t 之后 L 查看。
# EFICommand (m for help): t # 修改分区类型1 # 分区号1 # MBR
# RootCommand (m for help): t # 修改分区类型2 # 分区号23 # Linux Root
# USBDiskCommand (m for help): t # 修改分区类型3 # 分区号11 # Microsoft base data使用 p 打印分区表,应该是如下的情况

使用 w 保存退出
设置分区文件系统类型
mkfs.ext4 -O "^has_journal" /dev/sdb2 # rootmkfs.fat -F32 /dev/sdb1 # EFImkfs.fat -F32 /dev/sdb4 # USBDisk,由于我们主要在 Windows 设备之间传输,因此还是使用 FAT32 文件系统。安装
使用 mount 挂在根目录到 /mnt 下
mount /dev/sdb2 /mntmount /dev/sdb1 /mnt/boot/efi --mkdir安装对应的内核以及必要的软件
pacstrap /mnt base linux linux-firmware base-devel vim dhcpcd iwd intel-ucode amd-ucode配置系统
生成 fstab 文件
genfstab -U /mnt >> /mnt/etc/fstab检查文件内容是否正确

设置密码以及配置新用户
不再介绍,自行查询其他教程。
配置 Secure Boot
非常的难配。我们不能使用 sbctl 来签名,因为我们使用的是 removable device,所以必须用 shim 签名。
首先安装依赖
pacman -Sy git sbsigntools(sudoer)$ git clone https://aur.archlinux.org/shim-signed && cd shim-signed && makepkg -si修改 BOOTX64.EFI 为 grubx64.efi
mv /boot/efi/EFI/BOOT/{BOOTX64.EFI,grubx64.efi}复制 shim-singed 的 efi 过来
cp /usr/share/shim-signed/shimx64.efi /boot/efi/EFI/BOOT/BOOTX64.EFIcp /usr/share/shim-signed/mmx64.efi /boot/efi/EFI/BOOT/生成 Mok 密钥,并且签名
cd /boot/efiopenssl req -newkey rsa:4096 -nodes -keyout MOK.key -new -x509 -sha256 -subj "/CN=Machine Owner Key/" -out MOK.crtopenssl x509 -outform DER -in MOK.crt -out MOK.c需要把内核和 grub 都签名
sbsign --key MOK.key --cert MOK.crt --output /boot/vmlinuz-linux /boot/vmlinuz-linuxsbsign --key MOK.key --cert MOK.crt --output /boot/efi/EFI/BOOT/grubx64.efi /boot/efi/EFI/BOOT/grubx64.eficp ./MOK.cer /boot/efi配置引导程序
安装 grub 和 efibootmgr
pacman -Sy grub efibootmgr设置 grub
grub-install --target=x86_64-efi --efi-directory=/boot --removable --modules="normal test efi_gop efi_uga search echo linux all_video gfxmenu gfxterm_background gfxterm_menu gfxterm loadenv configfile tpm" --sbat /usr/share/grub/sbat.csv生成 grub 配置
grub-mkconfig -o /boot/grub/grub.cfgmkinitcpio post hook
vim /etc/initcpio/post/kernel-sbsign#!/usr/bin/env bash
kernel="$1"[[ -n "$kernel" ]] || exit 0
# use already installed kernel if it exists[[ ! -f "$KERNELDESTINATION" ]] || kernel="$KERNELDESTINATION"
keypairs=(/boot/efi/MOK.key /boot/efi/MOK.crt)
for (( i=0; i<${#keypairs[@]}; i+=2 )); do key="${keypairs[$i]}" cert="${keypairs[(( i + 1 ))]}" if ! sbverify --cert "$cert" "$kernel" &>/dev/null; then sbsign --key "$key" --cert "$cert" --output "$kernel" "$kernel" fidonechmod +x /etc/initcpio/post/kernel-sbsign修改区域设置
切换到 /mnt 下进行操作(在未明确标识的情况下,下文都在 arch-chroot /mnt 后的文件系统中进行。
arch-chroot /mnt我们首先设置时区
ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime编辑区域设置,去掉 en_US.UTF-8 和 zh_CN UTF-8 的注释
vim /etc/locale.gen# 去掉注释保存locale-gen
设置 local.conf 到 en_SG.UTF-8
:::info 为什么不设置 zh_CN?或者是用 en_US
主要是兼容性问题。zh_CN 容易导致 tty 输出为方块,且系统 log 使用英文,更容易找到报错的解决。
使用 en_SG 可以使得系统以
- 24 小时制显示时间;
- A4 为默认纸张大小;
- 公制单位为默认;
:::
echo "LANG=en_SG.UTF-8" > /etc/locale.conf设置主机名
echo "MuelNova-Arch" > etc/hostname设置 hosts
hosts 默认也为空,我们进行 localhost 的映射
vim /etc/hosts
# 新增下面两行,保存退出# 127.0.0.1 localhost# ::1 localhost
配置 initramfs
默认的 initramfs 可能存在不同系统块设备和键盘支持的问题
:::info
这是由于 autodetect hook 所导致的。autodetect hook 试图仅包含引导当前系统所必需的模块。这对于大多数内置系统是有效的,因为启动时连接的硬件通常不会改变。然而,对于 USB 驱动器来说,它可能在不同的硬件之间移动,如果依赖 autodetect 来识别硬件,可能无法找到 USB 驱动器上的必要模块,尤其是在不同于安装时的硬件上。
因此,我们把 block 和 keyboard 两个 hook 放到 autodetect 之前,确保它们永远会被加载。
:::
vim /etc/mkinitcpio.conf
# 将 HOOKS 修改为下面的,然后保存。# HOOKS=(base udev block keyboard autodetect modconf filesystems fsck)
mkinitcpio -P # 重新生成 initramfs参考资料
https://carbonateds.com/36.html
Arch Linux USB (安装篇) | Zephyr’s Blog (zephyrheather.github.io)