]> git.ozlabs.org Git - petitboot/blobdiff - discover/devmapper.c
discover/devmapper: Retry dm-device remove if busy
[petitboot] / discover / devmapper.c
index d8445e62e999a7c7e9681fa7f3ce51ccf93b405e..0a4d320ef6a23ebb86978d39b4c91b9517f65b2b 100644 (file)
@@ -138,7 +138,7 @@ static bool snapshot_merge_complete(const char *dm_name)
 
        task = dm_task_create(DM_DEVICE_STATUS);
        if (!task) {
-               pb_log("%s: Error creating task\n", __func__);
+               pb_log_fn("Error creating task\n");
                return result;
        }
 
@@ -198,7 +198,7 @@ static int set_device_active(const char *dm_name, bool active)
                task = dm_task_create(DM_DEVICE_SUSPEND);
 
        if (!task) {
-               pb_log("%s: Could not create dm_task\n", __func__);
+               pb_log_fn("Could not create dm_task\n");
                return rc;
        }
 
@@ -457,24 +457,32 @@ static int destroy_device(const char *dm_name)
 {
        struct dm_task *task;
        uint32_t cookie;
-       int rc = -1;
+       int rc, retries = 0;
 
+retry:
        task = dm_task_create(DM_DEVICE_REMOVE);
        if (!task) {
-               pb_log("%s: could not create dm_task\n", __func__);
+               pb_debug_fn("could not create dm_task\n");
                return -1;
        }
 
        if (!dm_task_set_name(task, dm_name)) {
-               pb_log("No dm device named '%s'\n", dm_name);
+               rc = dm_task_get_errno(task);
+               pb_debug_fn("Couldn't set name for %s, %s (%d)\n",
+                               dm_name, strerror(rc), rc);
                goto out;
        }
 
-       if (!set_cookie(task, &cookie))
+       if (!set_cookie(task, &cookie)) {
+               rc = dm_task_get_errno(task);
+               pb_debug_fn("set_cookie failed, %s (%d)\n", strerror(rc), rc);
                goto out;
+       }
 
        if (!dm_task_run(task)) {
-               pb_log("Unable to remove device '%s'\n", dm_name);
+               rc = dm_task_get_errno(task);
+               pb_debug_fn("Unable to remove device '%s', %s (%d)\n",
+                               dm_name, strerror(rc), rc);
                goto out;
        }
 
@@ -485,6 +493,12 @@ static int destroy_device(const char *dm_name)
 
 out:
        dm_task_destroy(task);
+       if (rc == EBUSY && retries < 5) {
+               pb_log_fn("Device busy, retry %d..\n", retries);
+               usleep(100000);
+               retries++;
+               goto retry;
+       }
        return rc;
 }
 
@@ -543,13 +557,13 @@ static int reload_snapshot(struct discover_device *device, bool merge)
                         device->ramdisk->base);
        }
        if (!target.ttype || !target.params) {
-               pb_log("%s: failed to allocate parameters\n", __func__);
+               pb_log_fn("failed to allocate parameters\n");
                goto err1;
        }
 
        task = dm_task_create(DM_DEVICE_RELOAD);
        if (!task) {
-               pb_log("%s: Error creating task\n", __func__);
+               pb_log_fn("Error creating task\n");
                goto err1;
        }
 
@@ -560,7 +574,7 @@ static int reload_snapshot(struct discover_device *device, bool merge)
 
        if (!dm_task_add_target(task, target.start_sector, target.end_sector,
                                target.ttype, target.params)) {
-               pb_log("%s: Failed to set target\n", __func__);
+               pb_log_fn("Failed to set target\n");
                goto err2;
        }
 
@@ -581,7 +595,7 @@ err1:
 int devmapper_merge_snapshot(struct discover_device *device)
 {
        if (device->mounted) {
-               pb_log("%s: %s still mounted\n", __func__, device->device->id);
+               pb_log_fn("%s still mounted\n", device->device->id);
                return -1;
        }