summary refs log tree commit diff
path: root/src/main.rs
diff options
context:
space:
mode:
authorChirantan Ekbote <chirantan@chromium.org>2018-05-31 15:31:31 -0700
committerchrome-bot <chrome-bot@chromium.org>2018-06-12 00:36:27 -0700
commit5f787217cc48e526c6244cd39db4f944fadfcd88 (patch)
tree8d3160c83c19c3ef3356502a3b18603b1de05ec3 /src/main.rs
parent92068bca00d7499dc789527b90efdf3daed2e927 (diff)
downloadcrosvm-5f787217cc48e526c6244cd39db4f944fadfcd88.tar
crosvm-5f787217cc48e526c6244cd39db4f944fadfcd88.tar.gz
crosvm-5f787217cc48e526c6244cd39db4f944fadfcd88.tar.bz2
crosvm-5f787217cc48e526c6244cd39db4f944fadfcd88.tar.lz
crosvm-5f787217cc48e526c6244cd39db4f944fadfcd88.tar.xz
crosvm-5f787217cc48e526c6244cd39db4f944fadfcd88.tar.zst
crosvm-5f787217cc48e526c6244cd39db4f944fadfcd88.zip
net: Allow passing in a configured tap fd on the command line
Allow the process that spawned crosvm to pass in a configured tap file
descriptor for networking.  If this option is provided then crosvm will
ignore the other networking related command line flags (like mac
address, netmask, etc).

Passing in a configured tap device allows us to run crosvm without
having to give it CAP_NET_ADMIN.

BUG=none
TEST=Start a container and verify that networking still works

Change-Id: I70b9e6ae030d66c4882e4e48804dc2f29d9874ba
Signed-off-by: Chirantan Ekbote <chirantan@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/1081394
Reviewed-by: Zach Reizner <zachr@chromium.org>
Diffstat (limited to 'src/main.rs')
-rw-r--r--src/main.rs21
1 files changed, 21 insertions, 0 deletions
diff --git a/src/main.rs b/src/main.rs
index 724fc7a..35f4cf0 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -38,6 +38,7 @@ pub mod linux;
 pub mod plugin;
 
 use std::net;
+use std::os::unix::io::RawFd;
 use std::os::unix::net::UnixDatagram;
 use std::path::PathBuf;
 use std::string::String;
@@ -72,6 +73,7 @@ pub struct Config {
     netmask: Option<net::Ipv4Addr>,
     mac_address: Option<net_util::MacAddress>,
     vhost_net: bool,
+    tap_fd: Option<RawFd>,
     wayland_socket_path: Option<PathBuf>,
     wayland_dmabuf: bool,
     socket_path: Option<PathBuf>,
@@ -94,6 +96,7 @@ impl Default for Config {
             netmask: None,
             mac_address: None,
             vhost_net: false,
+            tap_fd: None,
             wayland_socket_path: None,
             wayland_dmabuf: false,
             socket_path: None,
@@ -335,6 +338,17 @@ fn set_argument(cfg: &mut Config, name: &str, value: Option<&str>) -> argument::
         "vhost-net" => {
             cfg.vhost_net = true
         },
+        "tap-fd" => {
+            if cfg.tap_fd.is_some() {
+                return Err(argument::Error::TooManyArguments("`tap-fd` alread given".to_owned()));
+            }
+            cfg.tap_fd = Some(value.unwrap().parse().map_err(|_| {
+                argument::Error::InvalidValue {
+                    value: value.unwrap().to_owned(),
+                    expected: "this value for `tap-fd` must be an unsigned integer",
+                }
+            })?);
+        }
         "help" => return Err(argument::Error::PrintHelp),
         _ => unreachable!(),
     }
@@ -385,6 +399,9 @@ fn run_vm(args: std::env::Args) -> std::result::Result<(), ()> {
           Argument::value("plugin", "PATH", "Absolute path to plugin process to run under crosvm."),
           Argument::value("plugin-root", "PATH", "Absolute path to a directory that will become root filesystem for the plugin process."),
           Argument::flag("vhost-net", "Use vhost for networking."),
+          Argument::value("tap-fd",
+                          "fd",
+                          "File descriptor for configured tap device.  Mutually exclusive with `host_ip`, `netmask`, and `mac`."),
           Argument::short_flag('h', "help", "Print help message.")];
 
     let mut cfg = Config::default();
@@ -406,6 +423,10 @@ fn run_vm(args: std::env::Args) -> std::result::Result<(), ()> {
         if cfg.plugin_root.is_some() && cfg.plugin.is_none() {
             return Err(argument::Error::ExpectedArgument("`plugin-root` requires `plugin`".to_owned()));
         }
+        if cfg.tap_fd.is_some() && (cfg.host_ip.is_some() || cfg.netmask.is_some() || cfg.mac_address.is_some()) {
+            return Err(argument::Error::TooManyArguments(
+                "`tap_fd` and any of `host_ip`, `netmask`, or `mac` are mutually exclusive".to_owned()));
+        }
         Ok(())
     });