Re: block: del_gendisk() vs blk_queue_enter() race condition

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On (24/10/04 05:20), Christoph Hellwig wrote:
> This needs to check for a NULL disk.  And now that I'm looking at the
> code a bit more this makes me worried that checking for q->disk here
> sounds like a good way to hit a race with clearing it.  So I fear we
> need the other hack variant that sets QUEUE_FLAG_DYING unconditionally
> in __blk_mark_disk_dead and then clears it again (for GD_OWNS_QUEUE
> only) toward the end of del_gendisk.

Something like this?

---

diff --git a/block/genhd.c b/block/genhd.c
index 1c05dd4c6980..aca43c8fa4ed 100644
--- a/block/genhd.c
+++ b/block/genhd.c
@@ -589,9 +589,6 @@ static void __blk_mark_disk_dead(struct gendisk *disk)
 	if (test_and_set_bit(GD_DEAD, &disk->state))
 		return;
 
-	if (test_bit(GD_OWNS_QUEUE, &disk->state))
-		blk_queue_flag_set(QUEUE_FLAG_DYING, disk->queue);
-
 	/*
 	 * Stop buffered writers from dirtying pages that can't be written out.
 	 */
@@ -649,6 +646,9 @@ void del_gendisk(struct gendisk *disk)
 
 	disk_del_events(disk);
 
+	blk_queue_flag_set(QUEUE_FLAG_DYING, disk->queue);
+	wake_up_all(&disk->queue->mq_freeze_wq);
+
 	/*
 	 * Prevent new openers by unlinked the bdev inode.
 	 */
@@ -725,6 +725,9 @@ void del_gendisk(struct gendisk *disk)
 		if (queue_is_mq(q))
 			blk_mq_exit_queue(q);
 	}
+
+	if (!test_bit(GD_OWNS_QUEUE, &disk->state))
+		blk_queue_flag_clear(QUEUE_FLAG_DYING, disk->queue);
 }
 EXPORT_SYMBOL(del_gendisk);
 




[Index of Archives]     [Linux RAID]     [Linux SCSI]     [Linux ATA RAID]     [IDE]     [Linux Wireless]     [Linux Kernel]     [ATH6KL]     [Linux Bluetooth]     [Linux Netdev]     [Kernel Newbies]     [Security]     [Git]     [Netfilter]     [Bugtraq]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Device Mapper]

  Powered by Linux