[PATCH 5/5] kvm tools: Add 'kvm sandbox'

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



This patch adds 'kvm sandbox' which is a wrapper on top of 'kvm run' which
allows the user to easily specify sandboxed command to run in a custom
rootfs guest.

Example usage:

	kvm sandbox -d test_guest -k some_kernel -- do_something_in_guest

Suggested-by: Pekka Enberg <penberg@xxxxxxxxxxxxxx>
Signed-off-by: Sasha Levin <levinsasha928@xxxxxxxxx>
---
 tools/kvm/Documentation/kvm-sandbox.txt |   16 ++++++++++
 tools/kvm/Makefile                      |    1 +
 tools/kvm/builtin-run.c                 |   49 +++++++++++++++++++++++++++++-
 tools/kvm/builtin-sandbox.c             |    9 ++++++
 tools/kvm/command-list.txt              |    1 +
 tools/kvm/include/kvm/builtin-run.h     |    2 +
 tools/kvm/include/kvm/builtin-sandbox.h |    6 ++++
 tools/kvm/kvm-cmd.c                     |    2 +
 8 files changed, 84 insertions(+), 2 deletions(-)
 create mode 100644 tools/kvm/Documentation/kvm-sandbox.txt
 create mode 100644 tools/kvm/builtin-sandbox.c
 create mode 100644 tools/kvm/include/kvm/builtin-sandbox.h

diff --git a/tools/kvm/Documentation/kvm-sandbox.txt b/tools/kvm/Documentation/kvm-sandbox.txt
new file mode 100644
index 0000000..8f24fc7
--- /dev/null
+++ b/tools/kvm/Documentation/kvm-sandbox.txt
@@ -0,0 +1,16 @@
+kvm-sandbox(1)
+================
+
+NAME
+----
+kvm-sandbox - Run a command in a sandboxed guest
+
+SYNOPSIS
+--------
+[verse]
+'kvm sandbox ['kvm run' arguments] -- [sandboxed command]'
+
+DESCRIPTION
+-----------
+The sandboxed command will run in a guest as part of it's init
+command.
diff --git a/tools/kvm/Makefile b/tools/kvm/Makefile
index ece3306..24af1d0 100644
--- a/tools/kvm/Makefile
+++ b/tools/kvm/Makefile
@@ -85,6 +85,7 @@ OBJS	+= hw/vesa.o
 OBJS	+= hw/i8042.o
 OBJS	+= hw/pci-shmem.o
 OBJS	+= kvm-ipc.o
+OBJS	+= builtin-sandbox.o
 
 FLAGS_BFD := $(CFLAGS) -lbfd
 has_bfd := $(call try-cc,$(SOURCE_BFD),$(FLAGS_BFD))
diff --git a/tools/kvm/builtin-run.c b/tools/kvm/builtin-run.c
index 5db6995..7a57b5c 100644
--- a/tools/kvm/builtin-run.c
+++ b/tools/kvm/builtin-run.c
@@ -53,6 +53,7 @@
 #define DEFAULT_GUEST_MAC	"02:15:15:15:15:15"
 #define DEFAULT_HOST_MAC	"02:01:01:01:01:01"
 #define DEFAULT_SCRIPT		"none"
+const char *DEFAULT_SANDBOX_FILENAME = "guest/sandbox.sh";
 
 #define MB_SHIFT		(20)
 #define KB_SHIFT		(10)
@@ -94,6 +95,7 @@ static bool custom_rootfs;
 static bool no_net;
 static bool no_dhcp;
 extern bool ioport_debug;
+static int  kvm_run_wrapper;
 extern int  active_console;
 extern int  debug_iodelay;
 
@@ -107,6 +109,15 @@ static const char * const run_usage[] = {
 	NULL
 };
 
+enum {
+	KVM_RUN_SANDBOX,
+};
+
+void kvm_run_set_wrapper_sandbox(void)
+{
+	kvm_run_wrapper = KVM_RUN_SANDBOX;
+}
+
 static int img_name_parser(const struct option *opt, const char *arg, int unset)
 {
 	char *sep;
@@ -755,6 +766,35 @@ static int kvm_run_set_sandbox(void)
 	return symlink(script, path);
 }
 
+static void kvm_run_write_sandbox_cmd(const char **argv, int argc)
+{
+	const char script_hdr[] = "#! /bin/bash\n\n";
+	int fd;
+
+	remove(sandbox);
+
+	fd = open(sandbox, O_RDWR | O_CREAT, 0777);
+	if (fd < 0)
+		die("Failed creating sandbox script");
+
+	if (write(fd, script_hdr, sizeof(script_hdr) - 1) <= 0)
+		die("Failed writing sandbox script");
+
+	while (argc) {
+		if (write(fd, argv[0], strlen(argv[0])) <= 0)
+			die("Failed writing sandbox script");
+		if (argc - 1)
+			if (write(fd, " ", 1) <= 0)
+				die("Failed writing sandbox script");
+		argv++;
+		argc--;
+	}
+	if (write(fd, "\n", 1) <= 0)
+		die("Failed writing sandbox script");
+
+	close(fd);
+}
+
 int kvm_cmd_run(int argc, const char **argv, const char *prefix)
 {
 	static char real_cmdline[2048], default_name[20];
@@ -780,8 +820,13 @@ int kvm_cmd_run(int argc, const char **argv, const char *prefix)
 				PARSE_OPT_KEEP_DASHDASH);
 		if (argc != 0) {
 			/* Cusrom options, should have been handled elsewhere */
-			if (strcmp(argv[0], "--") == 0)
-				break;
+			if (strcmp(argv[0], "--") == 0) {
+				if (kvm_run_wrapper == KVM_RUN_SANDBOX) {
+					sandbox = DEFAULT_SANDBOX_FILENAME;
+					kvm_run_write_sandbox_cmd(argv+1, argc-1);
+					break;
+				}
+			}
 
 			if (kernel_filename) {
 				fprintf(stderr, "Cannot handle parameter: "
diff --git a/tools/kvm/builtin-sandbox.c b/tools/kvm/builtin-sandbox.c
new file mode 100644
index 0000000..433f536
--- /dev/null
+++ b/tools/kvm/builtin-sandbox.c
@@ -0,0 +1,9 @@
+#include "kvm/builtin-sandbox.h"
+#include "kvm/builtin-run.h"
+
+int kvm_cmd_sandbox(int argc, const char **argv, const char *prefix)
+{
+	kvm_run_set_wrapper_sandbox();
+
+	return kvm_cmd_run(argc, argv, prefix);
+}
diff --git a/tools/kvm/command-list.txt b/tools/kvm/command-list.txt
index 0d16c62..53469ab 100644
--- a/tools/kvm/command-list.txt
+++ b/tools/kvm/command-list.txt
@@ -12,3 +12,4 @@ kvm-debug			common
 kvm-balloon			common
 kvm-stop			common
 kvm-stat			common
+kvm-sandbox			common
diff --git a/tools/kvm/include/kvm/builtin-run.h b/tools/kvm/include/kvm/builtin-run.h
index d056ad4..c4b8ccb 100644
--- a/tools/kvm/include/kvm/builtin-run.h
+++ b/tools/kvm/include/kvm/builtin-run.h
@@ -4,4 +4,6 @@
 int kvm_cmd_run(int argc, const char **argv, const char *prefix);
 void kvm_run_help(void);
 
+void kvm_run_set_wrapper_sandbox(void);
+
 #endif
diff --git a/tools/kvm/include/kvm/builtin-sandbox.h b/tools/kvm/include/kvm/builtin-sandbox.h
new file mode 100644
index 0000000..98cd6be
--- /dev/null
+++ b/tools/kvm/include/kvm/builtin-sandbox.h
@@ -0,0 +1,6 @@
+#ifndef KVM__SANDBOX_H
+#define KVM__SANDBOX_H
+
+int kvm_cmd_sandbox(int argc, const char **argv, const char *prefix);
+
+#endif
diff --git a/tools/kvm/kvm-cmd.c b/tools/kvm/kvm-cmd.c
index 96108a8..604dce4 100644
--- a/tools/kvm/kvm-cmd.c
+++ b/tools/kvm/kvm-cmd.c
@@ -15,6 +15,7 @@
 #include "kvm/builtin-stop.h"
 #include "kvm/builtin-stat.h"
 #include "kvm/builtin-help.h"
+#include "kvm/builtin-sandbox.h"
 #include "kvm/kvm-cmd.h"
 #include "kvm/builtin-run.h"
 #include "kvm/util.h"
@@ -32,6 +33,7 @@ struct cmd_struct kvm_commands[] = {
 	{ "help",	kvm_cmd_help,		NULL,			0 },
 	{ "setup",	kvm_cmd_setup,		kvm_setup_help,		0 },
 	{ "run",	kvm_cmd_run,		kvm_run_help,		0 },
+	{ "sandbox",	kvm_cmd_sandbox,	kvm_run_help,		0 },
 	{ NULL,		NULL,			NULL,			0 },
 };
 
-- 
1.7.8

--
To unsubscribe from this list: send the line "unsubscribe kvm" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[Index of Archives]     [KVM ARM]     [KVM ia64]     [KVM ppc]     [Virtualization Tools]     [Spice Development]     [Libvirt]     [Libvirt Users]     [Linux USB Devel]     [Linux Audio Users]     [Yosemite Questions]     [Linux Kernel]     [Linux SCSI]     [XFree86]
  Powered by Linux