[CRIU] [PATCH 3/6] unshare: Preparations and CLI option
Pavel Emelyanov
xemul at parallels.com
Wed Dec 9 03:59:46 PST 2015
On restore one may say --unshare <what>. The <what> can be namespace
name for ns unshare or 'proc' to mount new proc in mntns. Several
<what>-s are to be comma-separated.
With this the restored tree will get born into the desired set of
namespaces. As different namespaces have their peculiarities, the
ability to unshare each will come with next patches.
Signed-off-by: Pavel Emelyanov <xemul at parallels.com>
---
crtools.c | 49 +++++++++++++++++++++++++++++++++++++++++++++++++
include/cr_options.h | 1 +
pstree.c | 21 +++++++++++++++++++++
3 files changed, 71 insertions(+)
diff --git a/crtools.c b/crtools.c
index 68756a0..bca7471 100644
--- a/crtools.c
+++ b/crtools.c
@@ -95,6 +95,49 @@ bad_ns:
return -1;
}
+static int parse_unshare_arg(char *opt)
+{
+ while (1) {
+ char *aux;
+
+ aux = strchr(opt, ',');
+ if (aux)
+ *aux = '\0';
+
+ if (!strcmp(opt, "uts"))
+ opts.unshare_flags |= CLONE_NEWUTS;
+ else if (!strcmp(opt, "ipc"))
+ opts.unshare_flags |= CLONE_NEWIPC;
+ else if (!strcmp(opt, "mnt"))
+ opts.unshare_flags |= CLONE_NEWNS;
+ else if (!strcmp(opt, "pid"))
+ opts.unshare_flags |= CLONE_NEWPID;
+ else if (!strcmp(opt, "net"))
+ opts.unshare_flags |= CLONE_NEWNET;
+ else if (!strcmp(opt, "user"))
+ opts.unshare_flags |= CLONE_NEWUSER;
+ else if (!strcmp(opt, "proc"))
+ opts.unshare_flags |= 0x1; /* mount new proc */
+ else {
+ pr_msg("Error: unknown unshare flag %s\n", opt);
+ return -1;
+ }
+
+ if (!aux)
+ break;
+
+ opt = aux + 1;
+ }
+
+ /* Only pid, mnt and user for now */
+ if (opts.unshare_flags) {
+ pr_err("Unsharing this namespace(s) is not supported yet\n");
+ return -1;
+ }
+
+ return 0;
+}
+
static int parse_cpu_cap(struct cr_options *opts, const char *optarg)
{
bool inverse = false;
@@ -255,6 +298,7 @@ int main(int argc, char *argv[], char *envp[])
{ "ghost-limit", required_argument, 0, 1069 },
{ "irmap-scan-path", required_argument, 0, 1070 },
{ "lsm-profile", required_argument, 0, 1071 },
+ { "unshare", required_argument, 0, 1072 },
{ },
};
@@ -504,6 +548,10 @@ int main(int argc, char *argv[], char *envp[])
if (parse_lsm_arg(optarg) < 0)
return -1;
break;
+ case 1072:
+ if (parse_unshare_arg(optarg))
+ return -1;
+ break;
case 'M':
{
char *aux;
@@ -714,6 +762,7 @@ usage:
" 'cpu','fpu','all','ins','none'. To disable capability, prefix it with '^'.\n"
" --exec-cmd execute the command specified after '--' on successful\n"
" restore making it the parent of the restored process\n"
+" --unshare FLAGS what namespaces to unshare when restoring\n"
" --freeze-cgroup\n"
" use cgroup freezer to collect processes\n"
"\n"
diff --git a/include/cr_options.h b/include/cr_options.h
index d0c74fe..20e4180 100644
--- a/include/cr_options.h
+++ b/include/cr_options.h
@@ -64,6 +64,7 @@ struct cr_options {
bool evasive_devices;
bool link_remap_ok;
unsigned int rst_namespaces_flags;
+ unsigned long unshare_flags;
bool log_file_per_pid;
bool swrk_restore;
char *output;
diff --git a/pstree.c b/pstree.c
index 116b5e7..ba547c1 100644
--- a/pstree.c
+++ b/pstree.c
@@ -741,6 +741,25 @@ set_mask:
return 0;
}
+static int prepare_pstree_for_unshare(void)
+{
+ {
+ unsigned long aux;
+
+ /*
+ * Move root into desired set of namespaces, but keep
+ * in opts.unshare_flags those that were deliberately
+ * enforced for further reference.
+ */
+ aux = rsti(root_item)->clone_flags;
+ rsti(root_item)->clone_flags |= opts.unshare_flags;
+ opts.unshare_flags &= ~aux;
+ }
+
+ root_ns_mask |= opts.unshare_flags;
+ return 0;
+}
+
int prepare_pstree(void)
{
int ret;
@@ -759,6 +778,8 @@ int prepare_pstree(void)
*/
ret = prepare_pstree_kobj_ids();
if (!ret)
+ ret = prepare_pstree_for_unshare();
+ if (!ret)
/*
* Session/Group leaders might be dead. Need to fix
* pstree with properly injected helper tasks.
--
1.9.3
More information about the CRIU
mailing list