如何基于Debian distroless镜像构建Firecracker可用的ext4 rootfs镜像
故障根因
你遇到的直接退出无输出问题主要由三个原因导致:
- 未添加
console=ttyS0启动参数,内核日志和systemd输出无法打印到Firecracker的串口,且distroless镜像缺systemd运行必需的依赖包、系统配置和设备节点 init=/bin/systemd是软链接,拷贝过程中可能丢失链接属性导致init程序无法找到- 大概率漏了调用Firecracker的块设备挂载API关联rootfs镜像
最小化Debian distroless可启动ext4镜像制作步骤
- 第一步:准备构建环境
启动带特权的Debian 10容器作为构建节点,执行命令安装依赖:docker run -it --privileged debian:10 bash apt update && apt install -y e2fsprogs docker.io --no-install-recommends - 第二步:创建空ext4镜像并挂载
fallocate -l 512M debian-rootfs.ext4 mkfs.ext4 debian-rootfs.ext4 mkdir -p /mnt/rootfs mount debian-rootfs.ext4 /mnt/rootfs - 第三步:定制带systemd的distroless镜像
新建Dockerfile写入以下内容:
执行构建命令:# 基础distroless镜像 FROM gcr.io/distroless/base-debian10 AS base # 构建层安装systemd相关依赖 FROM debian:10 AS builder RUN apt update && apt install -y systemd-sysv libsystemd0 passwd --no-install-recommends RUN rm -rf /var/lib/apt/lists/* /var/cache/apt/* # 写入基础系统配置 RUN echo "root:x:0:0:root:/root:/bin/bash" > /etc/passwd RUN echo "root:*:::::::" > /etc/shadow RUN echo "proc /proc proc defaults 0 0" > /etc/fstab RUN echo "sysfs /sys sysfs defaults 0 0" >> /etc/fstab RUN echo "tmpfs /tmp tmpfs defaults 0 0" >> /etc/fstab RUN systemctl enable serial-getty@ttyS0.service RUN systemctl mask systemd-udevd.service systemd-journald-audit.socket # 合并到distroless镜像 FROM base COPY --from=builder / /docker build -t custom-distroless-debian:10 . - 第四步:将镜像内容同步到ext4分区
docker run --rm custom-distroless-debian:10 tar -cf - / | tar -xf - -C /mnt/rootfs --strip-components=1 - 第五步:补全必需的设备节点和目录权限
mkdir -p /mnt/rootfs/{dev,proc,sys,run,tmp,var/log} chmod 1777 /mnt/rootfs/tmp mknod -m 622 /mnt/rootfs/dev/console c 5 1 mknod -m 666 /mnt/rootfs/dev/null c 1 3 mknod -m 666 /mnt/rootfs/dev/zero c 1 5 mknod -m 666 /mnt/rootfs/dev/tty c 5 0 mknod -m 666 /mnt/rootfs/dev/random c 1 8 mknod -m 666 /mnt/rootfs/dev/urandom c 1 9 - 第六步:卸载镜像,完成制作
umount /mnt/rootfs
Firecracker启动配置修正
- 必须先调用API挂载rootfs镜像:
curl --unix-socket /tmp/firecracker.socket -i \ -X PUT 'http://localhost/drives/rootfs' \ -H 'Accept: application/json' \ -H 'Content-Type: application/json' \ -d "{ \"drive_id\": \"rootfs\", \"path_on_host\": \"debian-rootfs.ext4\", \"is_root_device\": true, \"is_read_only\": false }" - 修正启动参数,添加串口输出配置,使用systemd真实路径:
curl --unix-socket /tmp/firecracker.socket -i \ -X PUT 'http://localhost/boot-source' \ -H 'Accept: application/json' \ -H 'Content-Type: application/json' \ -d "{ \"kernel_image_path\": \"hello-vmlinux.bin\", \"boot_args\": \"init=/lib/systemd/systemd console=ttyS0 reboot=k panic=1 pci=off\" }"
如果使用的官方预编译内核无法启动systemd,需要自行编译内核时开启CONFIG_SYSTEMD相关内核配置项。
内容的提问来源于stack exchange,提问作者t348575
相关产品推荐
相关产品推荐

