]> git.karo-electronics.de Git - karo-tx-linux.git/blobdiff - lib/dma-debug.c
dma-debug: fix locking bug in check_unmap()
[karo-tx-linux.git] / lib / dma-debug.c
index 5e396accd3d02a8dce6d06cc2d6020e311b308b0..d3e06a5e981e91eb3b7800c598a79c17dfb44190 100644 (file)
@@ -862,17 +862,21 @@ static void check_unmap(struct dma_debug_entry *ref)
        entry = bucket_find_exact(bucket, ref);
 
        if (!entry) {
+               /* must drop lock before calling dma_mapping_error */
+               put_hash_bucket(bucket, &flags);
+
                if (dma_mapping_error(ref->dev, ref->dev_addr)) {
                        err_printk(ref->dev, NULL,
-                                  "DMA-API: device driver tries "
-                                  "to free an invalid DMA memory address\n");
-                       return;
+                                  "DMA-API: device driver tries to free an "
+                                  "invalid DMA memory address\n");
+               } else {
+                       err_printk(ref->dev, NULL,
+                                  "DMA-API: device driver tries to free DMA "
+                                  "memory it has not allocated [device "
+                                  "address=0x%016llx] [size=%llu bytes]\n",
+                                  ref->dev_addr, ref->size);
                }
-               err_printk(ref->dev, NULL, "DMA-API: device driver tries "
-                          "to free DMA memory it has not allocated "
-                          "[device address=0x%016llx] [size=%llu bytes]\n",
-                          ref->dev_addr, ref->size);
-               goto out;
+               return;
        }
 
        if (ref->size != entry->size) {
@@ -936,7 +940,6 @@ static void check_unmap(struct dma_debug_entry *ref)
        hash_bucket_del(entry);
        dma_entry_free(entry);
 
-out:
        put_hash_bucket(bucket, &flags);
 }