qemu_command_builder/
virtfs.rs

1use crate::fsdev::SecurityModel;
2use crate::to_command::{ToArg, ToCommand};
3use bon::Builder;
4use std::path::PathBuf;
5
6pub enum RemapForbidWarn {
7    Remap,
8    Forbid,
9    Warn,
10}
11
12impl ToArg for RemapForbidWarn {
13    fn to_arg(&self) -> &str {
14        match self {
15            RemapForbidWarn::Remap => "remap",
16            RemapForbidWarn::Forbid => "forbid",
17            RemapForbidWarn::Warn => "warn",
18        }
19    }
20}
21
22#[derive(Builder)]
23pub struct Local {
24    path: PathBuf,
25    mount_tag: String,
26    security_mode: SecurityModel,
27    id: Option<String>,
28    writeout: Option<()>,
29    readonly: Option<bool>,
30    fmode: Option<String>,
31    dmode: Option<String>,
32    multidevs: Option<RemapForbidWarn>,
33}
34
35#[derive(Builder)]
36pub struct Synth {
37    mount_tag: String,
38}
39
40pub enum Virtfs {
41    Local(Local),
42    Synth(Synth),
43}
44impl ToCommand for Virtfs {
45    fn to_command(&self) -> Vec<String> {
46        let mut cmd = vec!["-add-fd".to_string()];
47
48        let mut args = vec![];
49
50        match self {
51            Virtfs::Local(local) => {
52                args.push("local".to_string());
53                args.push(format!("path={}", local.path.display()));
54                args.push(format!("mount_tag={}", local.mount_tag));
55                args.push(format!("security_mode={}", local.security_mode.to_arg()));
56                if let Some(id) = &local.id {
57                    args.push(format!("id={}", id));
58                }
59                if local.writeout.is_some() {
60                    args.push("writeout=immediate".to_string());
61                }
62                if let Some(readonly) = &local.readonly
63                    && *readonly
64                {
65                    args.push("readonly=on".to_string());
66                }
67                if let Some(fmode) = &local.fmode {
68                    args.push(format!("fmode={}", fmode));
69                }
70                if let Some(dmode) = &local.dmode {
71                    args.push(format!("dmode={}", dmode));
72                }
73                if let Some(multidevs) = &local.multidevs {
74                    args.push(format!("multidevs={}", multidevs.to_arg()));
75                }
76            }
77            Virtfs::Synth(synth) => {
78                args.push("synth".to_string());
79                args.push(format!("mount_tag={}", synth.mount_tag));
80            }
81        }
82
83        cmd.push(args.join(","));
84        cmd
85    }
86}