Merge tag 'for-5.3-rc2-tag' of git://git.kernel.org/pub/scm/linux/kernel/git/kdave...
[sfrench/cifs-2.6.git] / block / blk-mq.h
index f4bf5161333e3b2078800511f09c5c66fd16534c..32c62c64e6c2b86356621d5535fdacc21269652a 100644 (file)
@@ -233,4 +233,36 @@ static inline void blk_mq_clear_mq_map(struct blk_mq_queue_map *qmap)
                qmap->mq_map[cpu] = 0;
 }
 
+/*
+ * blk_mq_plug() - Get caller context plug
+ * @q: request queue
+ * @bio : the bio being submitted by the caller context
+ *
+ * Plugging, by design, may delay the insertion of BIOs into the elevator in
+ * order to increase BIO merging opportunities. This however can cause BIO
+ * insertion order to change from the order in which submit_bio() is being
+ * executed in the case of multiple contexts concurrently issuing BIOs to a
+ * device, even if these context are synchronized to tightly control BIO issuing
+ * order. While this is not a problem with regular block devices, this ordering
+ * change can cause write BIO failures with zoned block devices as these
+ * require sequential write patterns to zones. Prevent this from happening by
+ * ignoring the plug state of a BIO issuing context if the target request queue
+ * is for a zoned block device and the BIO to plug is a write operation.
+ *
+ * Return current->plug if the bio can be plugged and NULL otherwise
+ */
+static inline struct blk_plug *blk_mq_plug(struct request_queue *q,
+                                          struct bio *bio)
+{
+       /*
+        * For regular block devices or read operations, use the context plug
+        * which may be NULL if blk_start_plug() was not executed.
+        */
+       if (!blk_queue_is_zoned(q) || !op_is_write(bio_op(bio)))
+               return current->plug;
+
+       /* Zoned block device write operation case: do not plug the BIO */
+       return NULL;
+}
+
 #endif