]> git.ipfire.org Git - thirdparty/libvirt.git/commitdiff
util: fix virStorageFileGetBackingStoreStr error handling
authorDaniel P. Berrangé <berrange@redhat.com>
Wed, 25 Apr 2018 11:50:27 +0000 (12:50 +0100)
committerDaniel P. Berrangé <berrange@redhat.com>
Thu, 3 May 2018 12:15:51 +0000 (13:15 +0100)
The virStorageFileGetBackingStoreStr method has overloaded the NULL
return value to indicate both no backing available and a fatal
error dealing with it.

The caller is thus not able to correctly propagate the error
messages.

Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
src/qemu/qemu_driver.c
src/util/virstoragefile.c
src/util/virstoragefile.h

index 7484b00e23c3a8b0b7d3742a88116d9f452c00e0..f136ee265ff6208937dec01412b9697a38e1565b 100644 (file)
@@ -11582,8 +11582,16 @@ qemuDomainBlockPeek(virDomainPtr dom,
     if (qemuDomainStorageFileInit(driver, vm, disk->src, NULL) < 0)
         goto cleanup;
 
-    if ((nread = virStorageFileRead(disk->src, offset, size, &tmpbuf)) < 0)
+    if ((nread = virStorageFileRead(disk->src, offset, size, &tmpbuf)) < 0) {
+        if (nread == -2) {
+            virReportError(VIR_ERR_INTERNAL_ERROR,
+                           _("storage file reading is not supported for "
+                             "storage type %s (protocol: %s)"),
+                           virStorageTypeToString(disk->src->type),
+                           virStorageNetProtocolTypeToString(disk->src->protocol));
+        }
         goto cleanup;
+    }
 
     if (nread < size) {
         virReportError(VIR_ERR_INVALID_ARG,
@@ -14608,12 +14616,15 @@ qemuDomainSnapshotDiskDataCollect(virQEMUDriverPtr driver,
 
         /* relative backing store paths need to be updated so that relative
          * block commit still works */
-        if (reuse &&
-            (backingStoreStr = virStorageFileGetBackingStoreStr(dd->src))) {
-            if (virStorageIsRelative(backingStoreStr))
-                VIR_STEAL_PTR(dd->relPath, backingStoreStr);
-            else
-                VIR_FREE(backingStoreStr);
+        if (reuse) {
+            if (virStorageFileGetBackingStoreStr(dd->src, &backingStoreStr) < 0)
+                goto error;
+            if (backingStoreStr != NULL) {
+                if (virStorageIsRelative(backingStoreStr))
+                    VIR_STEAL_PTR(dd->relPath, backingStoreStr);
+                else
+                    VIR_FREE(backingStoreStr);
+            }
         }
 
         /* Note that it's unsafe to assume that the disks in the persistent
index 531540ac91848c57388c68e96ca0279c31bc34c0..f09035cd4a5d027ffed4c1bdd8bf109e197955c5 100644 (file)
@@ -4357,14 +4357,8 @@ virStorageFileRead(virStorageSourcePtr src,
         return -1;
     }
 
-    if (!src->drv->backend->storageFileRead) {
-        virReportError(VIR_ERR_INTERNAL_ERROR,
-                       _("storage file reading is not supported for "
-                         "storage type %s (protocol: %s)"),
-                       virStorageTypeToString(src->type),
-                       virStorageNetProtocolTypeToString(src->protocol));
+    if (!src->drv->backend->storageFileRead)
         return -2;
-    }
 
     ret = src->drv->backend->storageFileRead(src, offset, len, buf);
 
@@ -4551,8 +4545,15 @@ virStorageFileGetMetadataRecurse(virStorageSourcePtr src,
         goto cleanup;
 
     if ((headerLen = virStorageFileRead(src, 0, VIR_STORAGE_MAX_HEADER,
-                                        &buf)) < 0)
+                                        &buf)) < 0) {
+        if (headerLen == -2)
+            virReportError(VIR_ERR_INTERNAL_ERROR,
+                           _("storage file reading is not supported for "
+                             "storage type %s (protocol: %s)"),
+                           virStorageTypeToString(src->type),
+                           virStorageNetProtocolTypeToString(src->protocol));
         goto cleanup;
+    }
 
     if (virStorageFileGetMetadataInternal(src, buf, headerLen,
                                           &backingFormat) < 0)
@@ -4664,24 +4665,36 @@ virStorageFileGetMetadata(virStorageSourcePtr src,
  * In case when the string can't be retrieved or does not exist NULL is
  * returned.
  */
-char *
-virStorageFileGetBackingStoreStr(virStorageSourcePtr src)
+int
+virStorageFileGetBackingStoreStr(virStorageSourcePtr src,
+                                 char **backing)
 {
     virStorageSourcePtr tmp = NULL;
     char *buf = NULL;
     ssize_t headerLen;
-    char *ret = NULL;
+    int ret = -1;
+    int rv;
+
+    *backing = NULL;
 
     /* exit if we can't load information about the current image */
     if (!virStorageFileSupportsBackingChainTraversal(src))
-        return NULL;
+        return 0;
 
-    if (virStorageFileAccess(src, F_OK) < 0)
-        return NULL;
+    rv = virStorageFileAccess(src, F_OK);
+    if (rv == -2)
+        return 0;
+    if (rv < 0) {
+        virStorageFileReportBrokenChain(errno, src, src);
+        return -1;
+    }
 
     if ((headerLen = virStorageFileRead(src, 0, VIR_STORAGE_MAX_HEADER,
-                                        &buf)) < 0)
-        return NULL;
+                                        &buf)) < 0) {
+        if (headerLen == -2)
+            return 0;
+        return -1;
+    }
 
     if (!(tmp = virStorageSourceCopy(src, false)))
         goto cleanup;
@@ -4689,7 +4702,9 @@ virStorageFileGetBackingStoreStr(virStorageSourcePtr src)
     if (virStorageFileGetMetadataInternal(tmp, buf, headerLen, NULL) < 0)
         goto cleanup;
 
-    VIR_STEAL_PTR(ret, tmp->backingStoreRaw);
+    VIR_STEAL_PTR(*backing, tmp->backingStoreRaw);
+
+    ret = 0;
 
  cleanup:
     VIR_FREE(buf);
index d129e819785547b4fa2c62c8d9dd4fe241d7d917..b92c1c47ddb7182303f32aebba6f5957f7d2459b 100644 (file)
@@ -474,8 +474,9 @@ int virStorageFileGetMetadata(virStorageSourcePtr src,
                               bool report_broken)
     ATTRIBUTE_NONNULL(1);
 
-char *virStorageFileGetBackingStoreStr(virStorageSourcePtr src)
-    ATTRIBUTE_NONNULL(1);
+int virStorageFileGetBackingStoreStr(virStorageSourcePtr src,
+                                     char **backing)
+    ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2);
 
 void virStorageFileReportBrokenChain(int errcode,
                                      virStorageSourcePtr src,