[libvirt] [PATCH 1/2] lxc: add support for docker-json Memory and VCPU conversion

Docker Memory and VCPU configuration is converted to fit for LXC container XML configuration --- po/POTFILES.in | 1 + src/Makefile.am | 1 + src/lxc/lxc_driver.c | 13 ++- src/lxc/lxc_native.h | 1 + src/lxc/lxc_native_docker.c | 112 ++++++++++++++++++ src/lxc/lxc_native_docker.h | 30 +++++ tests/Makefile.am | 8 +- .../dockerjson2xmldata-simple.json | 36 ++++++ .../dockerjson2xmldata-simple.xml | 15 +++ tests/dockerjson2xmltest.c | 127 +++++++++++++++++++++ 10 files changed, 338 insertions(+), 6 deletions(-) create mode 100644 src/lxc/lxc_native_docker.c create mode 100644 src/lxc/lxc_native_docker.h create mode 100644 tests/dockerjson2xmldata/dockerjson2xmldata-simple.json create mode 100644 tests/dockerjson2xmldata/dockerjson2xmldata-simple.xml create mode 100644 tests/dockerjson2xmltest.c diff --git a/po/POTFILES.in b/po/POTFILES.in index 275df1f..098be9f 100644 --- a/po/POTFILES.in +++ b/po/POTFILES.in @@ -111,6 +111,7 @@ src/lxc/lxc_driver.c src/lxc/lxc_fuse.c src/lxc/lxc_hostdev.c src/lxc/lxc_native.c +src/lxc/lxc_native_docker.c src/lxc/lxc_process.c src/network/bridge_driver.c src/network/bridge_driver_linux.c diff --git a/src/Makefile.am b/src/Makefile.am index eae32dc..53d1bca 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -839,6 +839,7 @@ LXC_DRIVER_SOURCES = \ lxc/lxc_process.c lxc/lxc_process.h \ lxc/lxc_fuse.c lxc/lxc_fuse.h \ lxc/lxc_native.c lxc/lxc_native.h \ + lxc/lxc_native_docker.c lxc/lxc_native_docker.h \ lxc/lxc_driver.c lxc/lxc_driver.h LXC_CONTROLLER_SOURCES = \ diff --git a/src/lxc/lxc_driver.c b/src/lxc/lxc_driver.c index 22c8b58..0f5a7870 100644 --- a/src/lxc/lxc_driver.c +++ b/src/lxc/lxc_driver.c @@ -53,6 +53,7 @@ #include "lxc_driver.h" #include "lxc_native.h" #include "lxc_process.h" +#include "lxc_native_docker.h" #include "viralloc.h" #include "virnetdevbridge.h" #include "virnetdevveth.h" @@ -1062,15 +1063,17 @@ static char *lxcConnectDomainXMLFromNative(virConnectPtr conn, if (virConnectDomainXMLFromNativeEnsureACL(conn) < 0) goto cleanup; - if (STRNEQ(nativeFormat, LXC_CONFIG_FORMAT)) { + if (STREQ(nativeFormat, DOCKER_CONFIG_FORMAT)) { + if (!(def = dockerParseJSONConfig(caps, driver->xmlopt, nativeConfig))) + goto cleanup; + } else if (STREQ(nativeFormat, LXC_CONFIG_FORMAT)) { + if (!(def = lxcParseConfigString(nativeConfig, caps, driver->xmlopt))) + goto cleanup; + } else { virReportError(VIR_ERR_INVALID_ARG, _("unsupported config type %s"), nativeFormat); goto cleanup; } - - if (!(def = lxcParseConfigString(nativeConfig, caps, driver->xmlopt))) - goto cleanup; - xml = virDomainDefFormat(def, caps, 0); cleanup: diff --git a/src/lxc/lxc_native.h b/src/lxc/lxc_native.h index 15fa0d5..88263ae 100644 --- a/src/lxc/lxc_native.h +++ b/src/lxc/lxc_native.h @@ -26,6 +26,7 @@ # include "domain_conf.h" # define LXC_CONFIG_FORMAT "lxc-tools" +# define DOCKER_CONFIG_FORMAT "docker" virDomainDefPtr lxcParseConfigString(const char *config, virCapsPtr caps, diff --git a/src/lxc/lxc_native_docker.c b/src/lxc/lxc_native_docker.c new file mode 100644 index 0000000..a278309 --- /dev/null +++ b/src/lxc/lxc_native_docker.c @@ -0,0 +1,112 @@ +/* + * lxc_native_docker.c: LXC native docker configuration import + * + * Copyright (C) 2017 Venkat Datta N H + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library. If not, see + * <http://www.gnu.org/licenses/>. + * + * Author: Venkat Datta N H <nhvenkatdatta@gmail.com> + */ +#include <config.h> +#include "util/viralloc.h" +#include "util/virfile.h" +#include "util/virstring.h" +#include "util/virconf.h" +#include "util/virjson.h" +#include "util/virutil.h" +#include "virerror.h" +#include "virlog.h" +#include "conf/domain_conf.h" +#include "lxc_native_docker.h" +#include "secret_conf.h" +#define VIR_FROM_THIS VIR_FROM_LXC +VIR_LOG_INIT("lxc.lxc_native_docker"); + +static int dockerParseVCpus(virDomainDefPtr dom, + virDomainXMLOptionPtr xmlopt, + virJSONValuePtr prop) +{ + int vcpus; + + if (virJSONValueObjectGetNumberInt(prop, "CpuShares", &vcpus) != 0) + return -1; + + if (virDomainDefSetVcpusMax(dom, vcpus, xmlopt) < 0) + return -1; + + if (virDomainDefSetVcpus(dom, vcpus) < 0) + return -1; + + return 0; +} + +static int dockerParseMem(virDomainDefPtr dom, + virJSONValuePtr prop) +{ + unsigned long long mem; + + if (virJSONValueObjectGetNumberUlong(prop, "Memory", &mem) != 0) + return -1; + + virDomainDefSetMemoryTotal(dom, mem / 1024); + dom->mem.cur_balloon = mem / 1024; + + return 0; +} + +virDomainDefPtr dockerParseJSONConfig(virCapsPtr caps ATTRIBUTE_UNUSED, + virDomainXMLOptionPtr xmlopt, + const char *config) +{ + virJSONValuePtr json_obj; + virJSONValuePtr host_config; + + if (!(json_obj = virJSONValueFromString(config))) + return NULL; + + virDomainDefPtr def; + + if (!(def = virDomainDefNew())) + goto error; + + def->id = -1; + def->mem.cur_balloon = 64*1024; + virDomainDefSetMemoryTotal(def, def->mem.cur_balloon); + + if ((host_config = virJSONValueObjectGetObject(json_obj, "HostConfig")) != NULL) { + if (dockerParseVCpus(def, xmlopt, host_config) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("failed to parse VCpu")); + goto error; + } + + if (dockerParseMem(def, host_config) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("failed to parse Memory")); + goto error; + } + } + + def->clock.offset = VIR_DOMAIN_CLOCK_OFFSET_UTC; + def->onReboot = VIR_DOMAIN_LIFECYCLE_RESTART; + def->onCrash = VIR_DOMAIN_LIFECYCLE_CRASH_DESTROY; + def->onPoweroff = VIR_DOMAIN_LIFECYCLE_DESTROY; + def->virtType = VIR_DOMAIN_VIRT_LXC; + def->os.type = VIR_DOMAIN_OSTYPE_EXE; + + return def; + + error: + virDomainDefFree(def); + return NULL; +} diff --git a/src/lxc/lxc_native_docker.h b/src/lxc/lxc_native_docker.h new file mode 100644 index 0000000..40285f9 --- /dev/null +++ b/src/lxc/lxc_native_docker.h @@ -0,0 +1,30 @@ +/* + * lxc_native_docker.h: header file for LXC native docker configuration + * + * Copyright (C) 2017 Venkat Datta N H + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library. If not, see + * <http://www.gnu.org/licenses/>. + * + * Author: Venkat Datta N H <nhvenkatdatta@gmail.com> + */ +#ifndef __LXC_NATIVE_DOCKER_H__ +# define __LXC_NATIVE_DOCKER_H__ +# include "domain_conf.h" + +virDomainDefPtr dockerParseJSONConfig(virCapsPtr caps, + virDomainXMLOptionPtr xmlopt, + const char *config); + +#endif diff --git a/tests/Makefile.am b/tests/Makefile.am index 19986dc..3beb634 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -93,6 +93,7 @@ EXTRA_DIST = \ capabilityschemadata \ commanddata \ cputestdata \ + dockerjson2xmldata \ domaincapsschemadata \ domainconfdata \ domainschemadata \ @@ -295,7 +296,7 @@ test_libraries += libqemumonitortestutils.la \ endif WITH_QEMU if WITH_LXC -test_programs += lxcxml2xmltest lxcconf2xmltest +test_programs += lxcxml2xmltest lxcconf2xmltest dockerjson2xmltest endif WITH_LXC if WITH_OPENVZ @@ -693,6 +694,11 @@ lxcconf2xmltest_SOURCES = \ lxcconf2xmltest.c testutilslxc.c testutilslxc.h \ testutils.c testutils.h lxcconf2xmltest_LDADD = $(lxc_LDADDS) + +dockerjson2xmltest_SOURCES = \ + dockerjson2xmltest.c testutilslxc.c testutilslxc.h \ + testutils.c testutils.h +dockerjson2xmltest_LDADD = $(lxc_LDADDS) else ! WITH_LXC EXTRA_DIST += lxcxml2xmltest.c testutilslxc.c testutilslxc.h endif ! WITH_LXC diff --git a/tests/dockerjson2xmldata/dockerjson2xmldata-simple.json b/tests/dockerjson2xmldata/dockerjson2xmldata-simple.json new file mode 100644 index 0000000..63470be --- /dev/null +++ b/tests/dockerjson2xmldata/dockerjson2xmldata-simple.json @@ -0,0 +1,36 @@ +{ + "Id": "dbb1ae21dac15973d66e6c2b8516d270b32ca766e0cf7551d8b7973513e5f079", + "Created": "2017-05-25T18:55:17.922934825Z", + "Path": "/bin/bash", + "Args": [], + "HostConfig": { + "Binds": null, + "ContainerIDFile": "", + "LogConfig": { + "Type": "json-file", + "Config": {} + }, + "NetworkMode": "default", + "PortBindings": {}, + "ShmSize": 67108864, + "Runtime": "runc", + "Isolation": "", + "CpuShares": 2, + "Memory": 1073741824, + "CgroupParent": "", + "CpuPeriod": 0, + "CpuQuota": 0, + "CpusetCpus": "", + "CpusetMems": "", + "KernelMemory": 0, + "MemoryReservation": 0, + "MemorySwap": -1, + "MemorySwappiness": -1, + "PidsLimit": 0, + "Ulimits": null, + "CpuCount": 0, + "CpuPercent": 0, + "IOMaximumIOps": 0, + "IOMaximumBandwidth": 0 + } +} diff --git a/tests/dockerjson2xmldata/dockerjson2xmldata-simple.xml b/tests/dockerjson2xmldata/dockerjson2xmldata-simple.xml new file mode 100644 index 0000000..8be1ace --- /dev/null +++ b/tests/dockerjson2xmldata/dockerjson2xmldata-simple.xml @@ -0,0 +1,15 @@ +<domain type='lxc'> + <uuid>c7a5fdbd-edaf-9455-926a-d65c16db1809</uuid> + <memory unit='KiB'>1048576</memory> + <currentMemory unit='KiB'>1048576</currentMemory> + <vcpu placement='static'>2</vcpu> + <os> + <type>exe</type> + </os> + <clock offset='utc'/> + <on_poweroff>destroy</on_poweroff> + <on_reboot>restart</on_reboot> + <on_crash>destroy</on_crash> + <devices> + </devices> +</domain> diff --git a/tests/dockerjson2xmltest.c b/tests/dockerjson2xmltest.c new file mode 100644 index 0000000..41c46a1 --- /dev/null +++ b/tests/dockerjson2xmltest.c @@ -0,0 +1,127 @@ +#include <config.h> + +#include "testutils.h" + +#ifdef WITH_LXC + +# include "lxc/lxc_native_docker.h" +# include "lxc/lxc_conf.h" +# include "testutilslxc.h" + +# define VIR_FROM_THIS VIR_FROM_NONE + +static virCapsPtr caps; +static virDomainXMLOptionPtr xmlopt; + +static int testSanitizeDef(virDomainDefPtr vmdef) +{ + /* Remove UUID randomness */ + if (virUUIDParse("c7a5fdbd-edaf-9455-926a-d65c16db1809", vmdef->uuid) < 0) + return -1; + return 0; +} + +static int +testCompareXMLToConfigFiles(const char *xmlfile, + const char *configfile, + bool expectError) +{ + int ret = -1; + char *config = NULL; + char *actualxml = NULL; + virDomainDefPtr vmdef = NULL; + + if (virTestLoadFile(configfile, &config) < 0) + goto fail; + + vmdef = dockerParseJSONConfig(caps, xmlopt, config); + + if (vmdef && expectError) { + if (testSanitizeDef(vmdef) < 0) + goto fail; + + if (!(actualxml = virDomainDefFormat(vmdef, caps, 0))) + goto fail; + + if (virTestCompareToFile(actualxml, xmlfile) < 0) + goto fail; + } + + ret = 0; + + fail: + VIR_FREE(actualxml); + VIR_FREE(config); + virDomainDefFree(vmdef); + return ret; +} + +struct testInfo { + const char *name; + bool expectError; +}; + +static int +testCompareXMLToConfigHelper(const void *data) +{ + int result = -1; + const struct testInfo *info = data; + char *xml = NULL; + char *config = NULL; + + if (virAsprintf(&xml, "%s/dockerjson2xmldata/dockerjson2xmldata-%s.xml", + abs_srcdir, info->name) < 0 || + virAsprintf(&config, "%s/dockerjson2xmldata/dockerjson2xmldata-%s.json", + abs_srcdir, info->name) < 0) + goto cleanup; + + result = testCompareXMLToConfigFiles(xml, config, info->expectError); + + cleanup: + VIR_FREE(xml); + VIR_FREE(config); + return result; +} + +static int +mymain(void) +{ + int ret = EXIT_SUCCESS; + + if (!(caps = testLXCCapsInit())) + return EXIT_FAILURE; + + if (!(xmlopt = lxcDomainXMLConfInit())) { + virObjectUnref(caps); + return EXIT_FAILURE; + } + + +# define DO_TEST(name, expectError) \ + do { \ + const struct testInfo info = { name, expectError }; \ + if (virTestRun("DOCKER JSON-2-XML " name, \ + testCompareXMLToConfigHelper, \ + &info) < 0) \ + ret = EXIT_FAILURE; \ + } while (0) + + DO_TEST("simple", true); + + virObjectUnref(xmlopt); + virObjectUnref(caps); + + return ret; +} + +VIR_TEST_MAIN(mymain) + +#else + +int +main(void) +{ + return EXIT_AM_SKIP; +} + +#endif /* WITH_LXC */ -- 2.7.4

Docker Json command is split between entrypoint and command properties. Compute a command out of those to fit the LXC container XML configuration. --- src/lxc/lxc_native_docker.c | 65 ++++++++++++++++++++++ .../dockerjson2xmldata-command.json | 50 +++++++++++++++++ .../dockerjson2xmldata-command.xml | 17 ++++++ tests/dockerjson2xmltest.c | 1 + 4 files changed, 133 insertions(+) create mode 100644 tests/dockerjson2xmldata/dockerjson2xmldata-command.json create mode 100644 tests/dockerjson2xmldata/dockerjson2xmldata-command.xml diff --git a/src/lxc/lxc_native_docker.c b/src/lxc/lxc_native_docker.c index a278309..618446d 100644 --- a/src/lxc/lxc_native_docker.c +++ b/src/lxc/lxc_native_docker.c @@ -66,12 +66,70 @@ static int dockerParseMem(virDomainDefPtr dom, return 0; } +struct dockerCmdArgsIteratorArgs { + virDomainDefPtr vmdef; + size_t ninitargs; +}; + +static int dockerCmdArgsIterator(size_t pos ATTRIBUTE_UNUSED, + virJSONValuePtr item, + void *opaque) +{ + struct dockerCmdArgsIteratorArgs *args = opaque; + const char *value = virJSONValueGetString(item); + + if (!args->vmdef->os.init) { + if (VIR_STRDUP(args->vmdef->os.init, value) < 0) + return -1; + else + return 1; + } + + if (VIR_EXPAND_N(args->vmdef->os.initargv, args->ninitargs, 1) < 0) + return -1; + + if (VIR_STRDUP(args->vmdef->os.initargv[args->ninitargs - 1], value) < 0) + return -1; + + return 1; +} + + +static int dockerBuildInitCmd(virDomainDefPtr vmdef, + virJSONValuePtr config) +{ + virJSONValuePtr entry_point = virJSONValueObjectGetArray(config, "Entrypoint"); + virJSONValuePtr command = virJSONValueObjectGetArray(config, "Cmd"); + struct dockerCmdArgsIteratorArgs iterator_args = { vmdef, 0 }; + + if (entry_point && virJSONValueArrayForeachSteal(entry_point, + &dockerCmdArgsIterator, + &iterator_args) < 0) + goto error; + + if (command && virJSONValueArrayForeachSteal(command, + &dockerCmdArgsIterator, + &iterator_args) < 0) + goto error; + + /* Append NULL element at the end */ + if (iterator_args.ninitargs > 0 && + VIR_EXPAND_N(vmdef->os.initargv, iterator_args.ninitargs, 1) < 0) + goto error; + + return 0; + + error: + return -1; +} + virDomainDefPtr dockerParseJSONConfig(virCapsPtr caps ATTRIBUTE_UNUSED, virDomainXMLOptionPtr xmlopt, const char *config) { virJSONValuePtr json_obj; virJSONValuePtr host_config; + virJSONValuePtr docker_config; if (!(json_obj = virJSONValueFromString(config))) return NULL; @@ -97,6 +155,13 @@ virDomainDefPtr dockerParseJSONConfig(virCapsPtr caps ATTRIBUTE_UNUSED, } } + if ((docker_config = virJSONValueObjectGetObject(json_obj, "Config")) != NULL) { + if (dockerBuildInitCmd(def, docker_config) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("failed to parse Command")); + goto error; + } + } + def->clock.offset = VIR_DOMAIN_CLOCK_OFFSET_UTC; def->onReboot = VIR_DOMAIN_LIFECYCLE_RESTART; def->onCrash = VIR_DOMAIN_LIFECYCLE_CRASH_DESTROY; diff --git a/tests/dockerjson2xmldata/dockerjson2xmldata-command.json b/tests/dockerjson2xmldata/dockerjson2xmldata-command.json new file mode 100644 index 0000000..d20419d --- /dev/null +++ b/tests/dockerjson2xmldata/dockerjson2xmldata-command.json @@ -0,0 +1,50 @@ +{ + "Id": "618a2e773b84976ca2736e443a0c98eeeecdcfb2584e3dab1a3cafa313a936da", + "Created": "2017-06-07T00:46:07.149971669Z", + "Path": "/bin/ping", + "Args": [ + "localhost" + ], + "HostConfig": { + "LogConfig": { + "Type": "json-file", + "Config": {} + }, + "NetworkMode": "default", + "PortBindings": {}, + "RestartPolicy": { + "Name": "no", + "MaximumRetryCount": 0 + }, + "ShmSize": 67108864, + "CpuShares": 0, + "Memory": 0, + "MemorySwap": 0, + "MemorySwappiness": -1, + "CpuCount": 0, + "CpuPercent": 0, + "IOMaximumBandwidth": 0 + }, + "GraphDriver": { + "Name": "aufs", + "Data": null + }, + "Mounts": [], + "Config": { + "Hostname": "618a2e773b84", + "Domainname": "", + "User": "", + "Env": [ + "PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin" + ], + "Cmd": [ + "/bin/ping", + "localhost" + ], + "WorkingDir": "", + "Entrypoint": null, + "OnBuild": null, + "Labels": {} + } + +} diff --git a/tests/dockerjson2xmldata/dockerjson2xmldata-command.xml b/tests/dockerjson2xmldata/dockerjson2xmldata-command.xml new file mode 100644 index 0000000..52155d1 --- /dev/null +++ b/tests/dockerjson2xmldata/dockerjson2xmldata-command.xml @@ -0,0 +1,17 @@ +<domain type='lxc'> + <uuid>c7a5fdbd-edaf-9455-926a-d65c16db1809</uuid> + <memory unit='KiB'>0</memory> + <currentMemory unit='KiB'>0</currentMemory> + <vcpu placement='static'>0</vcpu> + <os> + <type>exe</type> + <init>/bin/ping</init> + <initarg>localhost</initarg> + </os> + <clock offset='utc'/> + <on_poweroff>destroy</on_poweroff> + <on_reboot>restart</on_reboot> + <on_crash>destroy</on_crash> + <devices> + </devices> +</domain> diff --git a/tests/dockerjson2xmltest.c b/tests/dockerjson2xmltest.c index 41c46a1..de7f77a 100644 --- a/tests/dockerjson2xmltest.c +++ b/tests/dockerjson2xmltest.c @@ -107,6 +107,7 @@ mymain(void) } while (0) DO_TEST("simple", true); + DO_TEST("command", true); virObjectUnref(xmlopt); virObjectUnref(caps); -- 2.7.4

Quick note: next time you send a patch series, add a cover letter to it. You can get git to automatically ask you about one by running git config add format.coverletter auto Having reviewed them off-list first, ACK from me to those changes. Daniel, do you want to double-review them? -- Cedric On Fri, 2017-06-16 at 19:59 +0530, Venkat Datta N H wrote:
Docker Memory and VCPU configuration is converted to fit for LXC container XML configuration --- po/POTFILES.in | 1 + src/Makefile.am | 1 + src/lxc/lxc_driver.c | 13 ++- src/lxc/lxc_native.h | 1 + src/lxc/lxc_native_docker.c | 112 ++++++++++++++++++ src/lxc/lxc_native_docker.h | 30 +++++ tests/Makefile.am | 8 +- .../dockerjson2xmldata-simple.json | 36 ++++++ .../dockerjson2xmldata-simple.xml | 15 +++ tests/dockerjson2xmltest.c | 127 +++++++++++++++++++++ 10 files changed, 338 insertions(+), 6 deletions(-) create mode 100644 src/lxc/lxc_native_docker.c create mode 100644 src/lxc/lxc_native_docker.h create mode 100644 tests/dockerjson2xmldata/dockerjson2xmldata-simple.json create mode 100644 tests/dockerjson2xmldata/dockerjson2xmldata-simple.xml create mode 100644 tests/dockerjson2xmltest.c
diff --git a/po/POTFILES.in b/po/POTFILES.in index 275df1f..098be9f 100644 --- a/po/POTFILES.in +++ b/po/POTFILES.in @@ -111,6 +111,7 @@ src/lxc/lxc_driver.c src/lxc/lxc_fuse.c src/lxc/lxc_hostdev.c src/lxc/lxc_native.c +src/lxc/lxc_native_docker.c src/lxc/lxc_process.c src/network/bridge_driver.c src/network/bridge_driver_linux.c diff --git a/src/Makefile.am b/src/Makefile.am index eae32dc..53d1bca 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -839,6 +839,7 @@ LXC_DRIVER_SOURCES = \ lxc/lxc_process.c lxc/lxc_process.h \ lxc/lxc_fuse.c lxc/lxc_fuse.h \ lxc/lxc_native.c lxc/lxc_native.h \ + lxc/lxc_native_docker.c lxc/lxc_native_docker.h \ lxc/lxc_driver.c lxc/lxc_driver.h LXC_CONTROLLER_SOURCES = \ diff --git a/src/lxc/lxc_driver.c b/src/lxc/lxc_driver.c index 22c8b58..0f5a7870 100644 --- a/src/lxc/lxc_driver.c +++ b/src/lxc/lxc_driver.c @@ -53,6 +53,7 @@ #include "lxc_driver.h" #include "lxc_native.h" #include "lxc_process.h" +#include "lxc_native_docker.h" #include "viralloc.h" #include "virnetdevbridge.h" #include "virnetdevveth.h" @@ -1062,15 +1063,17 @@ static char *lxcConnectDomainXMLFromNative(virConnectPtr conn, if (virConnectDomainXMLFromNativeEnsureACL(conn) < 0) goto cleanup; - if (STRNEQ(nativeFormat, LXC_CONFIG_FORMAT)) { + if (STREQ(nativeFormat, DOCKER_CONFIG_FORMAT)) { + if (!(def = dockerParseJSONConfig(caps, driver->xmlopt, nativeConfig))) + goto cleanup; + } else if (STREQ(nativeFormat, LXC_CONFIG_FORMAT)) { + if (!(def = lxcParseConfigString(nativeConfig, caps, driver->xmlopt))) + goto cleanup; + } else { virReportError(VIR_ERR_INVALID_ARG, _("unsupported config type %s"), nativeFormat); goto cleanup; } - - if (!(def = lxcParseConfigString(nativeConfig, caps, driver->xmlopt))) - goto cleanup; - xml = virDomainDefFormat(def, caps, 0); cleanup: diff --git a/src/lxc/lxc_native.h b/src/lxc/lxc_native.h index 15fa0d5..88263ae 100644 --- a/src/lxc/lxc_native.h +++ b/src/lxc/lxc_native.h @@ -26,6 +26,7 @@ # include "domain_conf.h" # define LXC_CONFIG_FORMAT "lxc-tools" +# define DOCKER_CONFIG_FORMAT "docker" virDomainDefPtr lxcParseConfigString(const char *config, virCapsPtr caps, diff --git a/src/lxc/lxc_native_docker.c b/src/lxc/lxc_native_docker.c new file mode 100644 index 0000000..a278309 --- /dev/null +++ b/src/lxc/lxc_native_docker.c @@ -0,0 +1,112 @@ +/* + * lxc_native_docker.c: LXC native docker configuration import + * + * Copyright (C) 2017 Venkat Datta N H + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library. If not, see + * <http://www.gnu.org/licenses/>. + * + * Author: Venkat Datta N H <nhvenkatdatta@gmail.com> + */ +#include <config.h> +#include "util/viralloc.h" +#include "util/virfile.h" +#include "util/virstring.h" +#include "util/virconf.h" +#include "util/virjson.h" +#include "util/virutil.h" +#include "virerror.h" +#include "virlog.h" +#include "conf/domain_conf.h" +#include "lxc_native_docker.h" +#include "secret_conf.h" +#define VIR_FROM_THIS VIR_FROM_LXC +VIR_LOG_INIT("lxc.lxc_native_docker"); + +static int dockerParseVCpus(virDomainDefPtr dom, + virDomainXMLOptionPtr xmlopt, + virJSONValuePtr prop) +{ + int vcpus; + + if (virJSONValueObjectGetNumberInt(prop, "CpuShares", &vcpus) != 0) + return -1; + + if (virDomainDefSetVcpusMax(dom, vcpus, xmlopt) < 0) + return -1; + + if (virDomainDefSetVcpus(dom, vcpus) < 0) + return -1; + + return 0; +} + +static int dockerParseMem(virDomainDefPtr dom, + virJSONValuePtr prop) +{ + unsigned long long mem; + + if (virJSONValueObjectGetNumberUlong(prop, "Memory", &mem) != 0) + return -1; + + virDomainDefSetMemoryTotal(dom, mem / 1024); + dom->mem.cur_balloon = mem / 1024; + + return 0; +} + +virDomainDefPtr dockerParseJSONConfig(virCapsPtr caps ATTRIBUTE_UNUSED, + virDomainXMLOptionPtr xmlopt, + const char *config) +{ + virJSONValuePtr json_obj; + virJSONValuePtr host_config; + + if (!(json_obj = virJSONValueFromString(config))) + return NULL; + + virDomainDefPtr def; + + if (!(def = virDomainDefNew())) + goto error; + + def->id = -1; + def->mem.cur_balloon = 64*1024; + virDomainDefSetMemoryTotal(def, def->mem.cur_balloon); + + if ((host_config = virJSONValueObjectGetObject(json_obj, "HostConfig")) != NULL) { + if (dockerParseVCpus(def, xmlopt, host_config) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("failed to parse VCpu")); + goto error; + } + + if (dockerParseMem(def, host_config) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("failed to parse Memory")); + goto error; + } + } + + def->clock.offset = VIR_DOMAIN_CLOCK_OFFSET_UTC; + def->onReboot = VIR_DOMAIN_LIFECYCLE_RESTART; + def->onCrash = VIR_DOMAIN_LIFECYCLE_CRASH_DESTROY; + def->onPoweroff = VIR_DOMAIN_LIFECYCLE_DESTROY; + def->virtType = VIR_DOMAIN_VIRT_LXC; + def->os.type = VIR_DOMAIN_OSTYPE_EXE; + + return def; + + error: + virDomainDefFree(def); + return NULL; +} diff --git a/src/lxc/lxc_native_docker.h b/src/lxc/lxc_native_docker.h new file mode 100644 index 0000000..40285f9 --- /dev/null +++ b/src/lxc/lxc_native_docker.h @@ -0,0 +1,30 @@ +/* + * lxc_native_docker.h: header file for LXC native docker configuration + * + * Copyright (C) 2017 Venkat Datta N H + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library. If not, see + * <http://www.gnu.org/licenses/>. + * + * Author: Venkat Datta N H <nhvenkatdatta@gmail.com> + */ +#ifndef __LXC_NATIVE_DOCKER_H__ +# define __LXC_NATIVE_DOCKER_H__ +# include "domain_conf.h" + +virDomainDefPtr dockerParseJSONConfig(virCapsPtr caps, + virDomainXMLOptionPtr xmlopt, + const char *config); + +#endif diff --git a/tests/Makefile.am b/tests/Makefile.am index 19986dc..3beb634 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -93,6 +93,7 @@ EXTRA_DIST = \ capabilityschemadata \ commanddata \ cputestdata \ + dockerjson2xmldata \ domaincapsschemadata \ domainconfdata \ domainschemadata \ @@ -295,7 +296,7 @@ test_libraries += libqemumonitortestutils.la \ endif WITH_QEMU if WITH_LXC -test_programs += lxcxml2xmltest lxcconf2xmltest +test_programs += lxcxml2xmltest lxcconf2xmltest dockerjson2xmltest endif WITH_LXC if WITH_OPENVZ @@ -693,6 +694,11 @@ lxcconf2xmltest_SOURCES = \ lxcconf2xmltest.c testutilslxc.c testutilslxc.h \ testutils.c testutils.h lxcconf2xmltest_LDADD = $(lxc_LDADDS) + +dockerjson2xmltest_SOURCES = \ + dockerjson2xmltest.c testutilslxc.c testutilslxc.h \ + testutils.c testutils.h +dockerjson2xmltest_LDADD = $(lxc_LDADDS) else ! WITH_LXC EXTRA_DIST += lxcxml2xmltest.c testutilslxc.c testutilslxc.h endif ! WITH_LXC diff --git a/tests/dockerjson2xmldata/dockerjson2xmldata-simple.json b/tests/dockerjson2xmldata/dockerjson2xmldata- simple.json new file mode 100644 index 0000000..63470be --- /dev/null +++ b/tests/dockerjson2xmldata/dockerjson2xmldata-simple.json @@ -0,0 +1,36 @@ +{ + "Id": "dbb1ae21dac15973d66e6c2b8516d270b32ca766e0cf7551d8b7973513e5f079", + "Created": "2017-05-25T18:55:17.922934825Z", + "Path": "/bin/bash", + "Args": [], + "HostConfig": { + "Binds": null, + "ContainerIDFile": "", + "LogConfig": { + "Type": "json-file", + "Config": {} + }, + "NetworkMode": "default", + "PortBindings": {}, + "ShmSize": 67108864, + "Runtime": "runc", + "Isolation": "", + "CpuShares": 2, + "Memory": 1073741824, + "CgroupParent": "", + "CpuPeriod": 0, + "CpuQuota": 0, + "CpusetCpus": "", + "CpusetMems": "", + "KernelMemory": 0, + "MemoryReservation": 0, + "MemorySwap": -1, + "MemorySwappiness": -1, + "PidsLimit": 0, + "Ulimits": null, + "CpuCount": 0, + "CpuPercent": 0, + "IOMaximumIOps": 0, + "IOMaximumBandwidth": 0 + } +} diff --git a/tests/dockerjson2xmldata/dockerjson2xmldata-simple.xml b/tests/dockerjson2xmldata/dockerjson2xmldata- simple.xml new file mode 100644 index 0000000..8be1ace --- /dev/null +++ b/tests/dockerjson2xmldata/dockerjson2xmldata-simple.xml @@ -0,0 +1,15 @@ +<domain type='lxc'> + <uuid>c7a5fdbd-edaf-9455-926a-d65c16db1809</uuid> + <memory unit='KiB'>1048576</memory> + <currentMemory unit='KiB'>1048576</currentMemory> + <vcpu placement='static'>2</vcpu> + <os> + <type>exe</type> + </os> + <clock offset='utc'/> + <on_poweroff>destroy</on_poweroff> + <on_reboot>restart</on_reboot> + <on_crash>destroy</on_crash> + <devices> + </devices> +</domain> diff --git a/tests/dockerjson2xmltest.c b/tests/dockerjson2xmltest.c new file mode 100644 index 0000000..41c46a1 --- /dev/null +++ b/tests/dockerjson2xmltest.c @@ -0,0 +1,127 @@ +#include <config.h> + +#include "testutils.h" + +#ifdef WITH_LXC + +# include "lxc/lxc_native_docker.h" +# include "lxc/lxc_conf.h" +# include "testutilslxc.h" + +# define VIR_FROM_THIS VIR_FROM_NONE + +static virCapsPtr caps; +static virDomainXMLOptionPtr xmlopt; + +static int testSanitizeDef(virDomainDefPtr vmdef) +{ + /* Remove UUID randomness */ + if (virUUIDParse("c7a5fdbd-edaf-9455-926a-d65c16db1809", vmdef->uuid) < 0) + return -1; + return 0; +} + +static int +testCompareXMLToConfigFiles(const char *xmlfile, + const char *configfile, + bool expectError) +{ + int ret = -1; + char *config = NULL; + char *actualxml = NULL; + virDomainDefPtr vmdef = NULL; + + if (virTestLoadFile(configfile, &config) < 0) + goto fail; + + vmdef = dockerParseJSONConfig(caps, xmlopt, config); + + if (vmdef && expectError) { + if (testSanitizeDef(vmdef) < 0) + goto fail; + + if (!(actualxml = virDomainDefFormat(vmdef, caps, 0))) + goto fail; + + if (virTestCompareToFile(actualxml, xmlfile) < 0) + goto fail; + } + + ret = 0; + + fail: + VIR_FREE(actualxml); + VIR_FREE(config); + virDomainDefFree(vmdef); + return ret; +} + +struct testInfo { + const char *name; + bool expectError; +}; + +static int +testCompareXMLToConfigHelper(const void *data) +{ + int result = -1; + const struct testInfo *info = data; + char *xml = NULL; + char *config = NULL; + + if (virAsprintf(&xml, "%s/dockerjson2xmldata/dockerjson2xmldata-%s.xml", + abs_srcdir, info->name) < 0 || + virAsprintf(&config, "%s/dockerjson2xmldata/dockerjson2xmldata-%s.json", + abs_srcdir, info->name) < 0) + goto cleanup; + + result = testCompareXMLToConfigFiles(xml, config, info->expectError); + + cleanup: + VIR_FREE(xml); + VIR_FREE(config); + return result; +} + +static int +mymain(void) +{ + int ret = EXIT_SUCCESS; + + if (!(caps = testLXCCapsInit())) + return EXIT_FAILURE; + + if (!(xmlopt = lxcDomainXMLConfInit())) { + virObjectUnref(caps); + return EXIT_FAILURE; + } + + +# define DO_TEST(name, expectError) \ + do { \ + const struct testInfo info = { name, expectError }; \ + if (virTestRun("DOCKER JSON-2-XML " name, \ + testCompareXMLToConfigHelper, \ + &info) < 0) \ + ret = EXIT_FAILURE; \ + } while (0) + + DO_TEST("simple", true); + + virObjectUnref(xmlopt); + virObjectUnref(caps); + + return ret; +} + +VIR_TEST_MAIN(mymain) + +#else + +int +main(void) +{ + return EXIT_AM_SKIP; +} + +#endif /* WITH_LXC */

On Fri, Jun 16, 2017 at 05:49:54PM +0200, Cedric Bosdonnat wrote:
Quick note: next time you send a patch series, add a cover letter to it. You can get git to automatically ask you about one by running
git config add format.coverletter auto
Having reviewed them off-list first, ACK from me to those changes. Daniel, do you want to double-review them?
Functionally it looks fine - just had some comments about style / layout and naming conventions. Regards, Daniel -- |: https://berrange.com -o- https://www.flickr.com/photos/dberrange :| |: https://libvirt.org -o- https://fstop138.berrange.com :| |: https://entangle-photo.org -o- https://www.instagram.com/dberrange :|

On Fri, Jun 16, 2017 at 07:59:44PM +0530, Venkat Datta N H wrote:
Docker Memory and VCPU configuration is converted to fit for LXC container XML configuration --- po/POTFILES.in | 1 + src/Makefile.am | 1 + src/lxc/lxc_driver.c | 13 ++- src/lxc/lxc_native.h | 1 + src/lxc/lxc_native_docker.c | 112 ++++++++++++++++++ src/lxc/lxc_native_docker.h | 30 +++++ tests/Makefile.am | 8 +- .../dockerjson2xmldata-simple.json | 36 ++++++ .../dockerjson2xmldata-simple.xml | 15 +++ tests/dockerjson2xmltest.c | 127 +++++++++++++++++++++ 10 files changed, 338 insertions(+), 6 deletions(-) create mode 100644 src/lxc/lxc_native_docker.c create mode 100644 src/lxc/lxc_native_docker.h create mode 100644 tests/dockerjson2xmldata/dockerjson2xmldata-simple.json create mode 100644 tests/dockerjson2xmldata/dockerjson2xmldata-simple.xml create mode 100644 tests/dockerjson2xmltest.c
diff --git a/src/lxc/lxc_native_docker.c b/src/lxc/lxc_native_docker.c new file mode 100644 index 0000000..a278309 --- /dev/null +++ b/src/lxc/lxc_native_docker.c @@ -0,0 +1,112 @@ +/* + * lxc_native_docker.c: LXC native docker configuration import + * + * Copyright (C) 2017 Venkat Datta N H + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library. If not, see + * <http://www.gnu.org/licenses/>. + * + * Author: Venkat Datta N H <nhvenkatdatta@gmail.com> + */
Add blank line
+#include <config.h>
Add blank line
+#include "util/viralloc.h" +#include "util/virfile.h" +#include "util/virstring.h" +#include "util/virconf.h" +#include "util/virjson.h" +#include "util/virutil.h" +#include "virerror.h" +#include "virlog.h" +#include "conf/domain_conf.h" +#include "lxc_native_docker.h" +#include "secret_conf.h"
Add blank line
+#define VIR_FROM_THIS VIR_FROM_LXC
Add blank line
+VIR_LOG_INIT("lxc.lxc_native_docker"); + +static int dockerParseVCpus(virDomainDefPtr dom, + virDomainXMLOptionPtr xmlopt, + virJSONValuePtr prop)
Generally all functions should have a name prefix matching the driver and file name. eg I'd expect all these methods to be named something like virLXCNativeDockerXXXX, or would accept just virLXCDockerXXXX For that matter the filename could just be lxc_docker.{c,h} too if we pick the latter.
+{ + int vcpus; + + if (virJSONValueObjectGetNumberInt(prop, "CpuShares", &vcpus) != 0) + return -1; + + if (virDomainDefSetVcpusMax(dom, vcpus, xmlopt) < 0) + return -1; + + if (virDomainDefSetVcpus(dom, vcpus) < 0) + return -1; + + return 0; +} + +static int dockerParseMem(virDomainDefPtr dom, + virJSONValuePtr prop) +{ + unsigned long long mem; + + if (virJSONValueObjectGetNumberUlong(prop, "Memory", &mem) != 0) + return -1; + + virDomainDefSetMemoryTotal(dom, mem / 1024); + dom->mem.cur_balloon = mem / 1024; + + return 0; +} + +virDomainDefPtr dockerParseJSONConfig(virCapsPtr caps ATTRIBUTE_UNUSED, + virDomainXMLOptionPtr xmlopt, + const char *config) +{ + virJSONValuePtr json_obj; + virJSONValuePtr host_config; + + if (!(json_obj = virJSONValueFromString(config))) + return NULL; + + virDomainDefPtr def; + + if (!(def = virDomainDefNew())) + goto error; + + def->id = -1; + def->mem.cur_balloon = 64*1024; + virDomainDefSetMemoryTotal(def, def->mem.cur_balloon); + + if ((host_config = virJSONValueObjectGetObject(json_obj, "HostConfig")) != NULL) { + if (dockerParseVCpus(def, xmlopt, host_config) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("failed to parse VCpu")); + goto error; + } + + if (dockerParseMem(def, host_config) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("failed to parse Memory")); + goto error; + } + } + + def->clock.offset = VIR_DOMAIN_CLOCK_OFFSET_UTC; + def->onReboot = VIR_DOMAIN_LIFECYCLE_RESTART; + def->onCrash = VIR_DOMAIN_LIFECYCLE_CRASH_DESTROY; + def->onPoweroff = VIR_DOMAIN_LIFECYCLE_DESTROY; + def->virtType = VIR_DOMAIN_VIRT_LXC; + def->os.type = VIR_DOMAIN_OSTYPE_EXE; + + return def; + + error: + virDomainDefFree(def); + return NULL; +}
diff --git a/src/lxc/lxc_native_docker.h b/src/lxc/lxc_native_docker.h new file mode 100644 index 0000000..40285f9 --- /dev/null +++ b/src/lxc/lxc_native_docker.h @@ -0,0 +1,30 @@ +/* + * lxc_native_docker.h: header file for LXC native docker configuration + * + * Copyright (C) 2017 Venkat Datta N H + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library. If not, see + * <http://www.gnu.org/licenses/>. + * + * Author: Venkat Datta N H <nhvenkatdatta@gmail.com> + */
Add blank line
+#ifndef __LXC_NATIVE_DOCKER_H__ +# define __LXC_NATIVE_DOCKER_H__
Add blank line
+# include "domain_conf.h" + +virDomainDefPtr dockerParseJSONConfig(virCapsPtr caps, + virDomainXMLOptionPtr xmlopt, + const char *config); + +#endif
Usually expect a /* ! __LXC_NATIVE_DOCKER_H__ */ comment after #endif
diff --git a/tests/Makefile.am b/tests/Makefile.am index 19986dc..3beb634 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -93,6 +93,7 @@ EXTRA_DIST = \ capabilityschemadata \ commanddata \ cputestdata \ + dockerjson2xmldata \
Lets name it lxcdocker2xmldata
domaincapsschemadata \ domainconfdata \ domainschemadata \ @@ -295,7 +296,7 @@ test_libraries += libqemumonitortestutils.la \ endif WITH_QEMU
if WITH_LXC -test_programs += lxcxml2xmltest lxcconf2xmltest +test_programs += lxcxml2xmltest lxcconf2xmltest dockerjson2xmltest
And lxcdocker2xmltest
diff --git a/tests/dockerjson2xmltest.c b/tests/dockerjson2xmltest.c new file mode 100644 index 0000000..41c46a1 --- /dev/null +++ b/tests/dockerjson2xmltest.c @@ -0,0 +1,127 @@
Needs the license header boilerplate
+#include <config.h> + +#include "testutils.h" + +#ifdef WITH_LXC + +# include "lxc/lxc_native_docker.h" +# include "lxc/lxc_conf.h" +# include "testutilslxc.h" + +# define VIR_FROM_THIS VIR_FROM_NONE + +static virCapsPtr caps; +static virDomainXMLOptionPtr xmlopt; + +static int testSanitizeDef(virDomainDefPtr vmdef) +{ + /* Remove UUID randomness */ + if (virUUIDParse("c7a5fdbd-edaf-9455-926a-d65c16db1809", vmdef->uuid) < 0) + return -1; + return 0; +} + +static int +testCompareXMLToConfigFiles(const char *xmlfile, + const char *configfile, + bool expectError) +{ + int ret = -1; + char *config = NULL; + char *actualxml = NULL; + virDomainDefPtr vmdef = NULL; + + if (virTestLoadFile(configfile, &config) < 0) + goto fail; + + vmdef = dockerParseJSONConfig(caps, xmlopt, config); + + if (vmdef && expectError) { + if (testSanitizeDef(vmdef) < 0) + goto fail; + + if (!(actualxml = virDomainDefFormat(vmdef, caps, 0))) + goto fail; + + if (virTestCompareToFile(actualxml, xmlfile) < 0) + goto fail; + } + + ret = 0; + + fail: + VIR_FREE(actualxml); + VIR_FREE(config); + virDomainDefFree(vmdef); + return ret; +} + +struct testInfo { + const char *name; + bool expectError; +}; + +static int +testCompareXMLToConfigHelper(const void *data) +{ + int result = -1; + const struct testInfo *info = data; + char *xml = NULL; + char *config = NULL; + + if (virAsprintf(&xml, "%s/dockerjson2xmldata/dockerjson2xmldata-%s.xml", + abs_srcdir, info->name) < 0 || + virAsprintf(&config, "%s/dockerjson2xmldata/dockerjson2xmldata-%s.json", + abs_srcdir, info->name) < 0) + goto cleanup; + + result = testCompareXMLToConfigFiles(xml, config, info->expectError); + + cleanup: + VIR_FREE(xml); + VIR_FREE(config); + return result; +} + +static int +mymain(void) +{ + int ret = EXIT_SUCCESS; + + if (!(caps = testLXCCapsInit())) + return EXIT_FAILURE; + + if (!(xmlopt = lxcDomainXMLConfInit())) { + virObjectUnref(caps); + return EXIT_FAILURE; + } + + +# define DO_TEST(name, expectError) \ + do { \ + const struct testInfo info = { name, expectError }; \ + if (virTestRun("DOCKER JSON-2-XML " name, \ + testCompareXMLToConfigHelper, \ + &info) < 0) \ + ret = EXIT_FAILURE; \ + } while (0) + + DO_TEST("simple", true); + + virObjectUnref(xmlopt); + virObjectUnref(caps); + + return ret; +} + +VIR_TEST_MAIN(mymain) + +#else + +int +main(void) +{ + return EXIT_AM_SKIP; +} + +#endif /* WITH_LXC */
Regards, Daniel -- |: https://berrange.com -o- https://www.flickr.com/photos/dberrange :| |: https://libvirt.org -o- https://fstop138.berrange.com :| |: https://entangle-photo.org -o- https://www.instagram.com/dberrange :|
participants (3)
-
Cedric Bosdonnat
-
Daniel P. Berrange
-
Venkat Datta N H