Skip to content

Commit 8afa205

Browse files
committed
mount: enable bind mounting folders from initrd
1 parent 607dfad commit 8afa205

File tree

3 files changed

+41
-1
lines changed

3 files changed

+41
-1
lines changed

src/cmdline.rs

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ pub struct CmdlineOptions {
1414
pub nfsroot: Option<String>,
1515
pub init: String,
1616
pub cleanup: bool,
17+
pub bind_mount: Vec<String>,
1718
}
1819

1920
const SBIN_INIT: &str = "/sbin/init";
@@ -28,6 +29,7 @@ impl Default for CmdlineOptions {
2829
nfsroot: None,
2930
init: SBIN_INIT.into(),
3031
cleanup: true,
32+
bind_mount: Vec::new(),
3133
}
3234
}
3335
}
@@ -45,6 +47,9 @@ fn parse_option(key: &str, value: Option<&str>, options: &mut CmdlineOptions) ->
4547
"rw" => options.rootfsflags.remove(MsFlags::MS_RDONLY),
4648
"nfsroot" => options.nfsroot = Some(ensure_value(key, value)?.to_string()),
4749
"init" => options.init = ensure_value(key, value)?.into(),
50+
"rsinit.bind" => options
51+
.bind_mount
52+
.push(ensure_value(key, value)?.to_string()),
4853
_ => (),
4954
}
5055
Ok(())
@@ -236,4 +241,19 @@ mod tests {
236241

237242
assert_eq!(options, expected);
238243
}
244+
245+
#[test]
246+
fn test_rsinit_bind() {
247+
let cmdline = "root=/dev/root rsinit.bind=/lib/modules rsinit.bind=/usr/lib/modules\n";
248+
249+
let expected = CmdlineOptions {
250+
root: Some("/dev/root".into()),
251+
bind_mount: vec!["/lib/modules".into(), "/usr/lib/modules".into()],
252+
..Default::default()
253+
};
254+
255+
let options = parse_cmdline(cmdline).expect("failed");
256+
257+
assert_eq!(options, expected);
258+
}
239259
}

src/main.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,8 @@ use systemd::{mount_systemd, shutdown};
3030
#[cfg(feature = "usb9pfs")]
3131
use usbg_9pfs::prepare_9pfs_gadget;
3232

33+
use crate::mount::mount_binds;
34+
3335
mod cmdline;
3436
#[cfg(feature = "dmverity")]
3537
mod dmverity;
@@ -96,6 +98,7 @@ fn start_root(options: &mut CmdlineOptions) -> Result<()> {
9698
unlink(exe.as_path())?;
9799
}
98100

101+
mount_binds(options)?;
99102
mount_move_special(options)?;
100103

101104
chdir("/root")?;

src/mount.rs

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
use std::fs::remove_dir;
55
use std::path::Path;
66

7-
use log::debug;
7+
use log::{debug, error};
88
use nix::mount::{mount, MsFlags};
99

1010
use crate::cmdline::CmdlineOptions;
@@ -105,3 +105,20 @@ pub fn mount_move_special(options: &CmdlineOptions) -> Result<()> {
105105
mount_move("/proc", "/root/proc", options.cleanup)?;
106106
Ok(())
107107
}
108+
109+
pub fn mount_binds(options: &CmdlineOptions) -> Result<()> {
110+
for src in &options.bind_mount {
111+
if !Path::new(src).exists() {
112+
error!("Can't bind mount {} as it doesn't exist", src);
113+
continue;
114+
}
115+
116+
let dst = format!("/root{src}");
117+
118+
debug!("Bind mounting {src} to {dst}");
119+
120+
do_mount(Some(src), &dst, None, MsFlags::MS_BIND, None)?;
121+
}
122+
123+
Ok(())
124+
}

0 commit comments

Comments
 (0)