]> git.ipfire.org Git - thirdparty/libvirt.git/commitdiff
qemuDomainCreateDevice: Don't loop endlessly
authorMichal Privoznik <mprivozn@redhat.com>
Thu, 19 Jan 2017 07:30:09 +0000 (08:30 +0100)
committerMichal Privoznik <mprivozn@redhat.com>
Tue, 7 Feb 2017 12:18:32 +0000 (13:18 +0100)
When working with symlinks it is fairly easy to get into a loop.
Don't.

Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
src/qemu/qemu_domain.c

index 7d84e6f5c767ca60903ac1d3934d2bba7357c5e2..e909395ca63d2a235cdb083606a09adeaeb54c5e 100644 (file)
@@ -6999,9 +6999,10 @@ qemuDomainGetPreservedMounts(virQEMUDriverPtr driver,
 
 
 static int
-qemuDomainCreateDevice(const char *device,
-                       const char *path,
-                       bool allow_noent)
+qemuDomainCreateDeviceRecursive(const char *device,
+                                const char *path,
+                                bool allow_noent,
+                                unsigned int ttl)
 {
     char *devicePath = NULL;
     char *target = NULL;
@@ -7013,6 +7014,13 @@ qemuDomainCreateDevice(const char *device,
     char *tcon = NULL;
 #endif
 
+    if (!ttl) {
+        virReportSystemError(ELOOP,
+                             _("Too many levels of symbolic links: %s"),
+                             device);
+        return ret;
+    }
+
     if (lstat(device, &sb) < 0) {
         if (errno == ENOENT && allow_noent) {
             /* Ignore non-existent device. */
@@ -7102,7 +7110,8 @@ qemuDomainCreateDevice(const char *device,
             tmp = NULL;
         }
 
-        if (qemuDomainCreateDevice(target, path, allow_noent) < 0)
+        if (qemuDomainCreateDeviceRecursive(target, path,
+                                            allow_noent, ttl - 1) < 0)
             goto cleanup;
     } else {
         if (create &&
@@ -7173,6 +7182,17 @@ qemuDomainCreateDevice(const char *device,
 }
 
 
+static int
+qemuDomainCreateDevice(const char *device,
+                       const char *path,
+                       bool allow_noent)
+{
+    long symloop_max = sysconf(_SC_SYMLOOP_MAX);
+
+    return qemuDomainCreateDeviceRecursive(device, path,
+                                           allow_noent, symloop_max);
+}
+
 
 static int
 qemuDomainPopulateDevices(virQEMUDriverPtr driver,