summaryrefslogtreecommitdiff
path: root/block
diff options
context:
space:
mode:
authorDivyesh Shah <dpshah@google.com>2010-04-09 09:29:57 +0200
committerJens Axboe <jens.axboe@oracle.com>2010-04-09 09:29:57 +0200
commit3440c49f5c5ecb4f29b0544aa87da71888404f8f (patch)
tree62afdbc8eb90393e768d0770c20fc9b2c7e8e042 /block
parent02246c41171097ceab3246f6dc251ac89de6004b (diff)
downloadkernel-common-3440c49f5c5ecb4f29b0544aa87da71888404f8f.tar.gz
kernel-common-3440c49f5c5ecb4f29b0544aa87da71888404f8f.tar.bz2
kernel-common-3440c49f5c5ecb4f29b0544aa87da71888404f8f.zip
cfq-iosched: Fix the incorrect timeslice accounting with forced_dispatch
When CFQ dispatches requests forcefully due to a barrier or changing iosched, it runs through all cfqq's dispatching requests and then expires each queue. However, it does not activate a cfqq before flushing its IOs resulting in using stale values for computing slice_used. This patch fixes it by calling activate queue before flushing reuqests from each queue. This is useful mostly for barrier requests because when the iosched is changing it really doesnt matter if we have incorrect accounting since we're going to break down all structures anyway. We also now expire the current timeslice before moving on with the dispatch to accurately account slice used for that cfqq. Signed-off-by: Divyesh Shah<dpshah@google.com> Signed-off-by: Jens Axboe <jens.axboe@oracle.com>
Diffstat (limited to 'block')
-rw-r--r--block/cfq-iosched.c7
1 files changed, 5 insertions, 2 deletions
diff --git a/block/cfq-iosched.c b/block/cfq-iosched.c
index 7104ac816fb6..b773000f8a06 100644
--- a/block/cfq-iosched.c
+++ b/block/cfq-iosched.c
@@ -2205,10 +2205,13 @@ static int cfq_forced_dispatch(struct cfq_data *cfqd)
struct cfq_queue *cfqq;
int dispatched = 0;
- while ((cfqq = cfq_get_next_queue_forced(cfqd)) != NULL)
+ /* Expire the timeslice of the current active queue first */
+ cfq_slice_expired(cfqd, 0);
+ while ((cfqq = cfq_get_next_queue_forced(cfqd)) != NULL) {
+ __cfq_set_active_queue(cfqd, cfqq);
dispatched += __cfq_forced_dispatch_cfqq(cfqq);
+ }
- cfq_slice_expired(cfqd, 0);
BUG_ON(cfqd->busy_queues);
cfq_log(cfqd, "forced_dispatch=%d", dispatched);