Skip to content

[Bug] volume_device_name produces garbage device names past index 23 #175

@andraiming

Description

@andraiming

File: crates/forkd-vmm/src/lib.rs:187-192
Severity: Medium

pub fn volume_device_name(index: usize) -> String {
    let letter = (b'b' + index as u8) as char;
    format!("vd{letter}")
}

The doc comment says "up to 23 → vdy. After that, callers hit virtio-blk's practical drive ceiling; we cap to keep the API simple." But there is no actual cap. index = 24 returns vdz, index = 25 returns vd{, then vd|, vd}, vd~, … through to wrap-around at index = 154 where the addition overflows into the next byte.

BootConfig::with_volume (lines 163-184) calls this every time and pushes whatever it gets into forkd.mounts= on the kernel cmdline, and forkd snapshot --volume accepts the flag repeatedly per the help in crates/forkd-cli/src/main.rs:104-105. Once a user passes a 25th volume, the device name becomes /dev/vd{, which won't exist, and /forkd-init.sh will silently fail to mount — without any error from the host side.

Repro

let cfg = BootConfig::ext4_rw(...);
for _ in 0..30 { cfg = cfg.with_volume(...); }
// boot_args will contain forkd.mounts=vdb:/a,vdc:/b,...,vdz:/x,vd{:/y,vd|:/z,...

Fix

Either return a Result and bail on index >= 24, or have with_volume itself panic/return an error before appending. The test on line 1354 only checks indexes 0/1/22 — add a regression test for >= 24.

Real-world bound is even tighter than 24, but at minimum the API surface should match the documented contract.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions