[Pkg-libvirt-commits] [libvirt] 01/02: Cherry-pick cgroup related fixes from upstream trunk
Guido Guenther
agx at alioth.debian.org
Thu Sep 12 14:43:16 UTC 2013
This is an automated email from the git hooks/post-receive script.
agx pushed a commit to annotated tag debian/1.1.2-3
in repository libvirt.
commit d7b6d7a5aedb372e9c3fbf24acf3e1d1db4a15ee
Author: Guido Günther <agx at sigxcpu.org>
Date: Thu Sep 12 16:12:17 2013 +0200
Cherry-pick cgroup related fixes from upstream trunk
Namely a48838ad2e36c124229b6faaf6e24284810e3802 and
f0b6d8d472de3c1bf3ade24e07df7c6d02075b77.
Thanks: Laurent Biognville for chasing this and Daniel P. Berrange for the acutual fixes.
Closes: #721979
---
...ups-when-all-are-mounted-on-sys-fs-cgroup.patch | 207 ++++++++++++++++++
...ng-of-VMs-on-when-only-logind-part-of-sys.patch | 230 ++++++++++++++++++++
debian/patches/series | 2 +
3 files changed, 439 insertions(+)
diff --git a/debian/patches/Fix-cgroups-when-all-are-mounted-on-sys-fs-cgroup.patch b/debian/patches/Fix-cgroups-when-all-are-mounted-on-sys-fs-cgroup.patch
new file mode 100644
index 0000000..4e21155
--- /dev/null
+++ b/debian/patches/Fix-cgroups-when-all-are-mounted-on-sys-fs-cgroup.patch
@@ -0,0 +1,207 @@
+From: "Daniel P. Berrange" <berrange at redhat.com>
+Date: Tue, 10 Sep 2013 14:31:53 +0100
+Subject: Fix cgroups when all are mounted on /sys/fs/cgroup
+
+Some users in Ubuntu/Debian seem to have a setup where all the
+cgroup controllers are mounted on /sys/fs/cgroup rather than
+any /sys/fs/cgroup/<controller> name. In the loop which detects
+which controllers are present for a mount point we were modifying
+'mnt_dir' field in the 'struct mntent' var, but not always restoring
+the original value. This caused detection to break in the all-in-one
+mount setup.
+
+Fix that logic bug and add test case coverage for this mount
+setup.
+
+Signed-off-by: Daniel P. Berrange <berrange at redhat.com>
+---
+ src/util/vircgroup.c | 3 ++-
+ tests/vircgroupmock.c | 45 ++++++++++++++++++++++++++++++++++++++---
+ tests/vircgrouptest.c | 55 +++++++++++++++++++++++++++++++++++++++++++++++++++
+ 3 files changed, 99 insertions(+), 4 deletions(-)
+
+diff --git a/src/util/vircgroup.c b/src/util/vircgroup.c
+index 16458a3..a260356 100644
+--- a/src/util/vircgroup.c
++++ b/src/util/vircgroup.c
+@@ -342,10 +342,11 @@ virCgroupDetectMounts(virCgroupPtr group)
+ entry.mnt_dir);
+ goto error;
+ }
+- *tmp2 = '\0';
++
+ /* If it is a co-mount it has a filename like "cpu,cpuacct"
+ * and we must identify the symlink path */
+ if (strchr(tmp2 + 1, ',')) {
++ *tmp2 = '\0';
+ if (virAsprintf(&linksrc, "%s/%s",
+ entry.mnt_dir, typestr) < 0)
+ goto error;
+diff --git a/tests/vircgroupmock.c b/tests/vircgroupmock.c
+index f1a5700..d83496c 100644
+--- a/tests/vircgroupmock.c
++++ b/tests/vircgroupmock.c
+@@ -103,6 +103,27 @@ const char *proccgroups =
+ "blkio 8 4 1\n";
+
+
++const char *procmountsallinone =
++ "rootfs / rootfs rw 0 0\n"
++ "sysfs /sys sysfs rw,nosuid,nodev,noexec,relatime 0 0\n"
++ "proc /proc proc rw,nosuid,nodev,noexec,relatime 0 0\n"
++ "udev /dev devtmpfs rw,relatime,size=16458560k,nr_inodes=4114640,mode=755 0 0\n"
++ "devpts /dev/pts devpts rw,nosuid,noexec,relatime,gid=5,mode=620,ptmxmode=000 0 0\n"
++ "nfsd /proc/fs/nfsd nfsd rw,relatime 0 0\n"
++ "cgroup /not/really/sys/fs/cgroup cgroup rw,relatime,blkio,devices,memory,cpuacct,cpu,cpuset 0 0\n";
++
++const char *procselfcgroupsallinone =
++ "6:blkio,devices,memory,cpuacct,cpu,cpuset:/";
++
++const char *proccgroupsallinone =
++ "#subsys_name hierarchy num_cgroups enabled\n"
++ "cpuset 6 1 1\n"
++ "cpu 6 1 1\n"
++ "cpuacct 6 1 1\n"
++ "memory 6 1 1\n"
++ "devices 6 1 1\n"
++ "blkio 6 1 1\n";
++
+ static int make_file(const char *path,
+ const char *name,
+ const char *value)
+@@ -378,11 +399,21 @@ static void init_sysfs(void)
+
+ FILE *fopen(const char *path, const char *mode)
+ {
++ const char *mock;
++ bool allinone = false;
+ init_syms();
+
++ mock = getenv("VIR_CGROUP_MOCK_MODE");
++ if (mock && STREQ(mock, "allinone"))
++ allinone = true;
++
+ if (STREQ(path, "/proc/mounts")) {
+ if (STREQ(mode, "r")) {
+- return fmemopen((void *)procmounts, strlen(procmounts), mode);
++ if (allinone)
++ return fmemopen((void *)procmountsallinone,
++ strlen(procmountsallinone), mode);
++ else
++ return fmemopen((void *)procmounts, strlen(procmounts), mode);
+ } else {
+ errno = EACCES;
+ return NULL;
+@@ -390,7 +421,11 @@ FILE *fopen(const char *path, const char *mode)
+ }
+ if (STREQ(path, "/proc/cgroups")) {
+ if (STREQ(mode, "r")) {
+- return fmemopen((void *)proccgroups, strlen(proccgroups), mode);
++ if (allinone)
++ return fmemopen((void *)proccgroupsallinone,
++ strlen(proccgroupsallinone), mode);
++ else
++ return fmemopen((void *)proccgroups, strlen(proccgroups), mode);
+ } else {
+ errno = EACCES;
+ return NULL;
+@@ -398,7 +433,11 @@ FILE *fopen(const char *path, const char *mode)
+ }
+ if (STREQ(path, "/proc/self/cgroup")) {
+ if (STREQ(mode, "r")) {
+- return fmemopen((void *)procselfcgroups, strlen(procselfcgroups), mode);
++ if (allinone)
++ return fmemopen((void *)procselfcgroupsallinone,
++ strlen(procselfcgroupsallinone), mode);
++ else
++ return fmemopen((void *)procselfcgroups, strlen(procselfcgroups), mode);
+ } else {
+ errno = EACCES;
+ return NULL;
+diff --git a/tests/vircgrouptest.c b/tests/vircgrouptest.c
+index 4bdd4c9..f12587c 100644
+--- a/tests/vircgrouptest.c
++++ b/tests/vircgrouptest.c
+@@ -99,6 +99,16 @@ const char *mountsFull[VIR_CGROUP_CONTROLLER_LAST] = {
+ [VIR_CGROUP_CONTROLLER_BLKIO] = "/not/really/sys/fs/cgroup/blkio",
+ [VIR_CGROUP_CONTROLLER_SYSTEMD] = "/not/really/sys/fs/cgroup/systemd",
+ };
++const char *mountsAllInOne[VIR_CGROUP_CONTROLLER_LAST] = {
++ [VIR_CGROUP_CONTROLLER_CPU] = "/not/really/sys/fs/cgroup",
++ [VIR_CGROUP_CONTROLLER_CPUACCT] = "/not/really/sys/fs/cgroup",
++ [VIR_CGROUP_CONTROLLER_CPUSET] = "/not/really/sys/fs/cgroup",
++ [VIR_CGROUP_CONTROLLER_MEMORY] = "/not/really/sys/fs/cgroup",
++ [VIR_CGROUP_CONTROLLER_DEVICES] = "/not/really/sys/fs/cgroup",
++ [VIR_CGROUP_CONTROLLER_FREEZER] = NULL,
++ [VIR_CGROUP_CONTROLLER_BLKIO] = "/not/really/sys/fs/cgroup",
++ [VIR_CGROUP_CONTROLLER_SYSTEMD] = NULL,
++};
+
+ const char *links[VIR_CGROUP_CONTROLLER_LAST] = {
+ [VIR_CGROUP_CONTROLLER_CPU] = "/not/really/sys/fs/cgroup/cpu",
+@@ -108,6 +118,18 @@ const char *links[VIR_CGROUP_CONTROLLER_LAST] = {
+ [VIR_CGROUP_CONTROLLER_DEVICES] = NULL,
+ [VIR_CGROUP_CONTROLLER_FREEZER] = NULL,
+ [VIR_CGROUP_CONTROLLER_BLKIO] = NULL,
++ [VIR_CGROUP_CONTROLLER_SYSTEMD] = NULL,
++};
++
++const char *linksAllInOne[VIR_CGROUP_CONTROLLER_LAST] = {
++ [VIR_CGROUP_CONTROLLER_CPU] = NULL,
++ [VIR_CGROUP_CONTROLLER_CPUACCT] = NULL,
++ [VIR_CGROUP_CONTROLLER_CPUSET] = NULL,
++ [VIR_CGROUP_CONTROLLER_MEMORY] = NULL,
++ [VIR_CGROUP_CONTROLLER_DEVICES] = NULL,
++ [VIR_CGROUP_CONTROLLER_FREEZER] = NULL,
++ [VIR_CGROUP_CONTROLLER_BLKIO] = NULL,
++ [VIR_CGROUP_CONTROLLER_SYSTEMD] = NULL,
+ };
+
+
+@@ -417,6 +439,34 @@ cleanup:
+ return ret;
+ }
+
++static int testCgroupNewForSelfAllInOne(const void *args ATTRIBUTE_UNUSED)
++{
++ virCgroupPtr cgroup = NULL;
++ int ret = -1;
++ const char *placement[VIR_CGROUP_CONTROLLER_LAST] = {
++ [VIR_CGROUP_CONTROLLER_CPU] = "/",
++ [VIR_CGROUP_CONTROLLER_CPUACCT] = "/",
++ [VIR_CGROUP_CONTROLLER_CPUSET] = "/",
++ [VIR_CGROUP_CONTROLLER_MEMORY] = "/",
++ [VIR_CGROUP_CONTROLLER_DEVICES] = "/",
++ [VIR_CGROUP_CONTROLLER_FREEZER] = NULL,
++ [VIR_CGROUP_CONTROLLER_BLKIO] = "/",
++ };
++
++ if (virCgroupNewSelf(&cgroup) < 0) {
++ fprintf(stderr, "Cannot create cgroup for self\n");
++ goto cleanup;
++ }
++
++ ret = validateCgroup(cgroup, "", mountsAllInOne, linksAllInOne, placement);
++
++cleanup:
++ virCgroupFree(&cgroup);
++ return ret;
++}
++
++
++
+ # define FAKESYSFSDIRTEMPLATE abs_builddir "/fakesysfsdir-XXXXXX"
+
+ static int
+@@ -455,6 +505,11 @@ mymain(void)
+ if (virtTestRun("New cgroup for domain partition escaped", 1, testCgroupNewForPartitionDomainEscaped, NULL) < 0)
+ ret = -1;
+
++ setenv("VIR_CGROUP_MOCK_MODE", "allinone", 1);
++ if (virtTestRun("New cgroup for self (allinone)", 1, testCgroupNewForSelfAllInOne, NULL) < 0)
++ ret = -1;
++ unsetenv("VIR_CGROUP_MOCK_MODE");
++
+ if (getenv("LIBVIRT_SKIP_CLEANUP") == NULL)
+ virFileDeleteTree(fakesysfsdir);
+
diff --git a/debian/patches/Fix-launching-of-VMs-on-when-only-logind-part-of-sys.patch b/debian/patches/Fix-launching-of-VMs-on-when-only-logind-part-of-sys.patch
new file mode 100644
index 0000000..b575255
--- /dev/null
+++ b/debian/patches/Fix-launching-of-VMs-on-when-only-logind-part-of-sys.patch
@@ -0,0 +1,230 @@
+From: "Daniel P. Berrange" <berrange at redhat.com>
+Date: Wed, 11 Sep 2013 19:15:52 +0100
+Subject: Fix launching of VMs on when only logind part of systemd is present
+
+Debian systems may run the 'systemd-logind' daemon, which causes the
+/sys/fs/cgroup/systemd mount to be setup, but no other cgroup
+controllers are created. While the LXC driver considers cgroups to
+be mandatory, the QEMU driver is supposed to accept them as optional.
+
+We detect whether they are present by looking in /proc/mounts for
+any mounts of type 'cgroups', but this is not sufficient. We need to
+skip any named mounts (as seen by a name=XXX string in the mount
+options), so that we only detect actual resource controllers.
+
+http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=721979
+
+Signed-off-by: Daniel P. Berrange <berrange at redhat.com>
+---
+ src/util/vircgroup.c | 5 +++-
+ tests/vircgroupmock.c | 40 ++++++++++++++++++++++++---
+ tests/vircgrouptest.c | 75 +++++++++++++++++++++++++++++++++++++++++++++++++++
+ 3 files changed, 116 insertions(+), 4 deletions(-)
+
+diff --git a/src/util/vircgroup.c b/src/util/vircgroup.c
+index a260356..626bbc6 100644
+--- a/src/util/vircgroup.c
++++ b/src/util/vircgroup.c
+@@ -91,7 +91,10 @@ virCgroupAvailable(void)
+ return false;
+
+ while (getmntent_r(mounts, &entry, buf, sizeof(buf)) != NULL) {
+- if (STREQ(entry.mnt_type, "cgroup")) {
++ /* We're looking for at least one 'cgroup' fs mount,
++ * which is *not* a named mount. */
++ if (STREQ(entry.mnt_type, "cgroup") &&
++ !strstr(entry.mnt_opts, "name=")) {
+ ret = true;
+ break;
+ }
+diff --git a/tests/vircgroupmock.c b/tests/vircgroupmock.c
+index d83496c..adc1718 100644
+--- a/tests/vircgroupmock.c
++++ b/tests/vircgroupmock.c
+@@ -124,6 +124,27 @@ const char *proccgroupsallinone =
+ "devices 6 1 1\n"
+ "blkio 6 1 1\n";
+
++const char *procmountslogind =
++ "none /not/really/sys/fs/cgroup tmpfs rw,rootcontext=system_u:object_r:sysfs_t:s0,seclabel,relatime,size=4k,mode=755 0 0\n"
++ "systemd /not/really/sys/fs/cgroup/systemd cgroup rw,nosuid,nodev,noexec,relatime,name=systemd 0 0\n";
++
++const char *procselfcgroupslogind =
++ "1:name=systemd:/\n";
++
++const char *proccgroupslogind =
++ "#subsys_name hierarchy num_cgroups enabled\n"
++ "cpuset 0 1 1\n"
++ "cpu 0 1 1\n"
++ "cpuacct 0 1 1\n"
++ "memory 0 1 0\n"
++ "devices 0 1 1\n"
++ "freezer 0 1 1\n"
++ "net_cls 0 1 1\n"
++ "blkio 0 1 1\n"
++ "perf_event 0 1 1\n";
++
++
++
+ static int make_file(const char *path,
+ const char *name,
+ const char *value)
+@@ -400,18 +421,25 @@ static void init_sysfs(void)
+ FILE *fopen(const char *path, const char *mode)
+ {
+ const char *mock;
+- bool allinone = false;
++ bool allinone = false, logind = false;
+ init_syms();
+
+ mock = getenv("VIR_CGROUP_MOCK_MODE");
+- if (mock && STREQ(mock, "allinone"))
+- allinone = true;
++ if (mock) {
++ if (STREQ(mock, "allinone"))
++ allinone = true;
++ else if (STREQ(mock, "logind"))
++ logind = true;
++ }
+
+ if (STREQ(path, "/proc/mounts")) {
+ if (STREQ(mode, "r")) {
+ if (allinone)
+ return fmemopen((void *)procmountsallinone,
+ strlen(procmountsallinone), mode);
++ else if (logind)
++ return fmemopen((void *)procmountslogind,
++ strlen(procmountslogind), mode);
+ else
+ return fmemopen((void *)procmounts, strlen(procmounts), mode);
+ } else {
+@@ -424,6 +452,9 @@ FILE *fopen(const char *path, const char *mode)
+ if (allinone)
+ return fmemopen((void *)proccgroupsallinone,
+ strlen(proccgroupsallinone), mode);
++ else if (logind)
++ return fmemopen((void *)proccgroupslogind,
++ strlen(proccgroupslogind), mode);
+ else
+ return fmemopen((void *)proccgroups, strlen(proccgroups), mode);
+ } else {
+@@ -436,6 +467,9 @@ FILE *fopen(const char *path, const char *mode)
+ if (allinone)
+ return fmemopen((void *)procselfcgroupsallinone,
+ strlen(procselfcgroupsallinone), mode);
++ else if (logind)
++ return fmemopen((void *)procselfcgroupslogind,
++ strlen(procselfcgroupslogind), mode);
+ else
+ return fmemopen((void *)procselfcgroups, strlen(procselfcgroups), mode);
+ } else {
+diff --git a/tests/vircgrouptest.c b/tests/vircgrouptest.c
+index f12587c..570e061 100644
+--- a/tests/vircgrouptest.c
++++ b/tests/vircgrouptest.c
+@@ -109,6 +109,16 @@ const char *mountsAllInOne[VIR_CGROUP_CONTROLLER_LAST] = {
+ [VIR_CGROUP_CONTROLLER_BLKIO] = "/not/really/sys/fs/cgroup",
+ [VIR_CGROUP_CONTROLLER_SYSTEMD] = NULL,
+ };
++const char *mountsLogind[VIR_CGROUP_CONTROLLER_LAST] = {
++ [VIR_CGROUP_CONTROLLER_CPU] = NULL,
++ [VIR_CGROUP_CONTROLLER_CPUACCT] = NULL,
++ [VIR_CGROUP_CONTROLLER_CPUSET] = NULL,
++ [VIR_CGROUP_CONTROLLER_MEMORY] = NULL,
++ [VIR_CGROUP_CONTROLLER_DEVICES] = NULL,
++ [VIR_CGROUP_CONTROLLER_FREEZER] = NULL,
++ [VIR_CGROUP_CONTROLLER_BLKIO] = NULL,
++ [VIR_CGROUP_CONTROLLER_SYSTEMD] = "/not/really/sys/fs/cgroup/systemd",
++};
+
+ const char *links[VIR_CGROUP_CONTROLLER_LAST] = {
+ [VIR_CGROUP_CONTROLLER_CPU] = "/not/really/sys/fs/cgroup/cpu",
+@@ -132,6 +142,17 @@ const char *linksAllInOne[VIR_CGROUP_CONTROLLER_LAST] = {
+ [VIR_CGROUP_CONTROLLER_SYSTEMD] = NULL,
+ };
+
++const char *linksLogind[VIR_CGROUP_CONTROLLER_LAST] = {
++ [VIR_CGROUP_CONTROLLER_CPU] = NULL,
++ [VIR_CGROUP_CONTROLLER_CPUACCT] = NULL,
++ [VIR_CGROUP_CONTROLLER_CPUSET] = NULL,
++ [VIR_CGROUP_CONTROLLER_MEMORY] = NULL,
++ [VIR_CGROUP_CONTROLLER_DEVICES] = NULL,
++ [VIR_CGROUP_CONTROLLER_FREEZER] = NULL,
++ [VIR_CGROUP_CONTROLLER_BLKIO] = NULL,
++ [VIR_CGROUP_CONTROLLER_SYSTEMD] = NULL,
++};
++
+
+ static int testCgroupNewForSelf(const void *args ATTRIBUTE_UNUSED)
+ {
+@@ -466,6 +487,48 @@ cleanup:
+ }
+
+
++static int testCgroupNewForSelfLogind(const void *args ATTRIBUTE_UNUSED)
++{
++ virCgroupPtr cgroup = NULL;
++ int ret = -1;
++ const char *placement[VIR_CGROUP_CONTROLLER_LAST] = {
++ [VIR_CGROUP_CONTROLLER_CPU] = NULL,
++ [VIR_CGROUP_CONTROLLER_CPUACCT] = NULL,
++ [VIR_CGROUP_CONTROLLER_CPUSET] = NULL,
++ [VIR_CGROUP_CONTROLLER_MEMORY] = NULL,
++ [VIR_CGROUP_CONTROLLER_DEVICES] = NULL,
++ [VIR_CGROUP_CONTROLLER_FREEZER] = NULL,
++ [VIR_CGROUP_CONTROLLER_BLKIO] = NULL,
++ [VIR_CGROUP_CONTROLLER_SYSTEMD] = "/",
++ };
++
++ if (virCgroupNewSelf(&cgroup) < 0) {
++ fprintf(stderr, "Cannot create cgroup for self\n");
++ goto cleanup;
++ }
++
++ ret = validateCgroup(cgroup, "", mountsLogind, linksLogind, placement);
++
++cleanup:
++ virCgroupFree(&cgroup);
++ return ret;
++}
++
++
++static int testCgroupAvailable(const void *args)
++{
++ bool got = virCgroupAvailable();
++ bool want = args == (void*)0x1;
++
++ if (got != want) {
++ fprintf(stderr, "Expected cgroup %savailable, but state was wrong\n",
++ want ? "" : "not ");
++ return -1;
++ }
++
++ return 0;
++}
++
+
+ # define FAKESYSFSDIRTEMPLATE abs_builddir "/fakesysfsdir-XXXXXX"
+
+@@ -505,9 +568,21 @@ mymain(void)
+ if (virtTestRun("New cgroup for domain partition escaped", 1, testCgroupNewForPartitionDomainEscaped, NULL) < 0)
+ ret = -1;
+
++ if (virtTestRun("Cgroup available", 1, testCgroupAvailable, (void*)0x1) < 0)
++ ret = -1;
++
+ setenv("VIR_CGROUP_MOCK_MODE", "allinone", 1);
+ if (virtTestRun("New cgroup for self (allinone)", 1, testCgroupNewForSelfAllInOne, NULL) < 0)
+ ret = -1;
++ if (virtTestRun("Cgroup available", 1, testCgroupAvailable, (void*)0x1) < 0)
++ ret = -1;
++ unsetenv("VIR_CGROUP_MOCK_MODE");
++
++ setenv("VIR_CGROUP_MOCK_MODE", "logind", 1);
++ if (virtTestRun("New cgroup for self (logind)", 1, testCgroupNewForSelfLogind, NULL) < 0)
++ ret = -1;
++ if (virtTestRun("Cgroup available", 1, testCgroupAvailable, (void*)0x0) < 0)
++ ret = -1;
+ unsetenv("VIR_CGROUP_MOCK_MODE");
+
+ if (getenv("LIBVIRT_SKIP_CLEANUP") == NULL)
diff --git a/debian/patches/series b/debian/patches/series
index 328e080..56bb5c8 100644
--- a/debian/patches/series
+++ b/debian/patches/series
@@ -13,3 +13,5 @@ Allow-xen-toolstack-to-find-it-s-binaries.patch
Fix-make-check-not-finding-finding-the-libvirtd-lens.patch
Parse-AM_LDFLAGS-to-driver-modules-too.patch
virFileNBDDeviceAssociate-Avoid-use-of-uninitialized.patch
+Fix-cgroups-when-all-are-mounted-on-sys-fs-cgroup.patch
+Fix-launching-of-VMs-on-when-only-logind-part-of-sys.patch
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-libvirt/libvirt.git
More information about the Pkg-libvirt-commits
mailing list