Blob Blame History Raw
From: NeilBrown <neilb@suse.de>
Subject: Allow a queue to request that timeouts don't get rounded up
Patch-mainline: Not yet, failfast is poorly defined
References: bnc#768084

Rounding a timeout up to the next second, plus a bit for different
CPUs, can add more than a second to a timeout.  But sometimes we
really want the timeout we request.  So allow that possibilty via a flag.

Signed-off-by: Neil Brown <neilb@suse.de>

---
 block/blk-timeout.c    |    9 +++++++--
 include/linux/blkdev.h |    3 +++
 2 files changed, 10 insertions(+), 2 deletions(-)

--- a/block/blk-timeout.c
+++ b/block/blk-timeout.c
@@ -139,8 +139,10 @@ void blk_timeout_work(struct work_struct
 	list_for_each_entry_safe(rq, tmp, &q->timeout_list, timeout_list)
 		blk_rq_check_expired(rq, &next, &next_set);
 
+	if (!test_bit(QUEUE_FLAG_NO_ROUND, &q->queue_flags))
+		next = round_jiffies_up(next);
 	if (next_set)
-		mod_timer(&q->timeout, round_jiffies_up(next));
+		mod_timer(&q->timeout, next);
 
 	spin_unlock_irqrestore(q->queue_lock, flags);
 }
@@ -222,7 +224,10 @@ void blk_add_timer(struct request *req)
 	 * than an existing one, modify the timer. Round up to next nearest
 	 * second.
 	 */
-	expiry = blk_rq_timeout(round_jiffies_up(req->deadline));
+	if (test_bit(QUEUE_FLAG_NO_ROUND, &q->queue_flags))
+		expiry = req->deadline;
+	else
+		expiry = blk_rq_timeout(round_jiffies_up(req->deadline));
 
 	if (!timer_pending(&q->timeout) ||
 	    time_before(expiry, q->timeout.expires)) {
--- a/include/linux/blkdev.h
+++ b/include/linux/blkdev.h
@@ -633,6 +633,9 @@ struct request_queue {
 #define QUEUE_FLAG_REGISTERED  29	/* queue has been registered to a disk */
 #define QUEUE_FLAG_SCSI_PASSTHROUGH 30	/* queue supports SCSI commands */
 #define QUEUE_FLAG_QUIESCED    31	/* queue has been quiesced */
+#define QUEUE_FLAG_NO_ROUND    32	/* Don't round timeout up to next second */
+
+
 
 #define QUEUE_FLAG_DEFAULT	((1 << QUEUE_FLAG_IO_STAT) |		\
 				 (1 << QUEUE_FLAG_STACKABLE)	|	\