Some containers may want the application to run in a special directory.
Add <initdir> element in the domain configuration to handle this case
and use it in the lxc driver.
---
docs/formatdomain.html.in | 5 +++++
docs/schemas/domaincommon.rng | 5 +++++
src/conf/domain_conf.c | 5 +++++
src/conf/domain_conf.h | 1 +
src/lxc/lxc_container.c | 2 ++
tests/lxcxml2xmldata/lxc-initdir.xml | 30 ++++++++++++++++++++++++++++++
tests/lxcxml2xmltest.c | 1 +
7 files changed, 49 insertions(+)
create mode 100644 tests/lxcxml2xmldata/lxc-initdir.xml
diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in
index d2db5a4f9..e79a9d5be 100644
--- a/docs/formatdomain.html.in
+++ b/docs/formatdomain.html.in
@@ -330,6 +330,10 @@
To set environment variables, use the <code>initenv</code> element,
one
for each variable.
</p>
+ <p>
+ To set a custom work directory for the init, use the
<code>initdir</code>
+ element.
+ </p>
<pre>
<os>
@@ -338,6 +342,7 @@
<initarg>--unit</initarg>
<initarg>emergency.service</initarg>
<initenv name='MYENV'>some value</initenv>
+ <initdir>/my/custom/cwd</initdir>
</os>
</pre>
diff --git a/docs/schemas/domaincommon.rng b/docs/schemas/domaincommon.rng
index 1e9fccc9e..06fe62305 100644
--- a/docs/schemas/domaincommon.rng
+++ b/docs/schemas/domaincommon.rng
@@ -395,6 +395,11 @@
<text/>
</element>
</zeroOrMore>
+ <optional>
+ <element name="initdir">
+ <ref name="absFilePath"/>
+ </element>
+ </optional>
</interleave>
</element>
</define>
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 868aa522e..7835852f1 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -2870,6 +2870,7 @@ void virDomainDefFree(virDomainDefPtr def)
VIR_FREE(def->os.initargv);
for (i = 0; def->os.initenv && def->os.initenv[i]; i++)
VIR_FREE(def->os.initenv[i]);
+ VIR_FREE(def->os.initdir);
VIR_FREE(def->os.initenv);
VIR_FREE(def->os.kernel);
VIR_FREE(def->os.initrd);
@@ -17021,6 +17022,7 @@ virDomainDefParseBootOptions(virDomainDefPtr def,
if (def->os.type == VIR_DOMAIN_OSTYPE_EXE) {
def->os.init = virXPathString("string(./os/init[1])", ctxt);
def->os.cmdline = virXPathString("string(./os/cmdline[1])", ctxt);
+ def->os.initdir = virXPathString("string(./os/initdir[1])", ctxt);
if ((n = virXPathNodeSet("./os/initarg", ctxt, &nodes)) < 0)
goto error;
@@ -24902,6 +24904,9 @@ virDomainDefFormatInternal(virDomainDefPtr def,
for (i = 0; def->os.initenv && def->os.initenv[i]; i++)
virBufferAsprintf(buf, "<initenv
name='%s'>%s</initenv>\n",
def->os.initenv[i]->name,
def->os.initenv[i]->value);
+ if (def->os.initdir)
+ virBufferEscapeString(buf, "<initdir>%s</initdir>\n",
+ def->os.initdir);
if (def->os.loader)
virDomainLoaderDefFormat(buf, def->os.loader);
virBufferEscapeString(buf, "<kernel>%s</kernel>\n",
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
index 5e47e2e97..4d41de2a4 100644
--- a/src/conf/domain_conf.h
+++ b/src/conf/domain_conf.h
@@ -1852,6 +1852,7 @@ struct _virDomainOSDef {
char *init;
char **initargv;
virDomainOSEnvPtr *initenv;
+ char *initdir;
char *kernel;
char *initrd;
char *cmdline;
diff --git a/src/lxc/lxc_container.c b/src/lxc/lxc_container.c
index ffafc39d7..8d8e1a735 100644
--- a/src/lxc/lxc_container.c
+++ b/src/lxc/lxc_container.c
@@ -245,6 +245,8 @@ static virCommandPtr lxcContainerBuildInitCmd(virDomainDefPtr vmDef,
virCommandAddEnvPair(cmd, "LIBVIRT_LXC_NAME", vmDef->name);
if (vmDef->os.cmdline)
virCommandAddEnvPair(cmd, "LIBVIRT_LXC_CMDLINE",
vmDef->os.cmdline);
+ if (vmDef->os.initdir)
+ virCommandSetWorkingDirectory(cmd, vmDef->os.initdir);
for (i = 0; vmDef->os.initenv[i]; i++) {
virCommandAddEnvPair(cmd, vmDef->os.initenv[i]->name,
diff --git a/tests/lxcxml2xmldata/lxc-initdir.xml b/tests/lxcxml2xmldata/lxc-initdir.xml
new file mode 100644
index 000000000..2940bda91
--- /dev/null
+++ b/tests/lxcxml2xmldata/lxc-initdir.xml
@@ -0,0 +1,30 @@
+<domain type='lxc'>
+ <name>jessie</name>
+ <uuid>e21987a5-e98e-9c99-0e35-803e4d9ad1fe</uuid>
+ <memory unit='KiB'>1048576</memory>
+ <currentMemory unit='KiB'>1048576</currentMemory>
+ <vcpu placement='static'>1</vcpu>
+ <resource>
+ <partition>/machine</partition>
+ </resource>
+ <os>
+ <type arch='x86_64'>exe</type>
+ <init>/sbin/sh</init>
+ <initdir>/path/to/pwd</initdir>
+ </os>
+ <clock offset='utc'/>
+ <on_poweroff>destroy</on_poweroff>
+ <on_reboot>restart</on_reboot>
+ <on_crash>restart</on_crash>
+ <devices>
+ <emulator>/usr/libexec/libvirt_lxc</emulator>
+ <filesystem type='mount' accessmode='passthrough'>
+ <source dir='/mach/jessie'/>
+ <target dir='/'/>
+ </filesystem>
+ <console type='pty'>
+ <target type='lxc' port='0'/>
+ </console>
+ </devices>
+ <seclabel type='none'/>
+</domain>
diff --git a/tests/lxcxml2xmltest.c b/tests/lxcxml2xmltest.c
index 2a24b60b3..c81b0eace 100644
--- a/tests/lxcxml2xmltest.c
+++ b/tests/lxcxml2xmltest.c
@@ -99,6 +99,7 @@ mymain(void)
DO_TEST_FULL("filesystem-root", 0, false,
VIR_DOMAIN_DEF_PARSE_SKIP_OSTYPE_CHECKS);
DO_TEST("initenv");
+ DO_TEST("initdir");
virObjectUnref(caps);
virObjectUnref(xmlopt);
--
2.12.2