X-Git-Url: https://err.no/cgi-bin/gitweb.cgi?a=blobdiff_plain;ds=sidebyside;f=block%2Felevator.c;h=8cd5775acd7a2d4c1111acb0f823a57a46819dc0;hb=64b7d96167977850f4a24e52dd0a76b03c6542cf;hp=f9736fbdab0308f7121694df2faa3ffa68258994;hpb=2ba14a017a4ba8d2266316f481d4ad7400073d18;p=linux-2.6 diff --git a/block/elevator.c b/block/elevator.c index f9736fbdab..8cd5775acd 100644 --- a/block/elevator.c +++ b/block/elevator.c @@ -741,7 +741,21 @@ struct request *elv_next_request(struct request_queue *q) q->boundary_rq = NULL; } - if ((rq->cmd_flags & REQ_DONTPREP) || !q->prep_rq_fn) + if (rq->cmd_flags & REQ_DONTPREP) + break; + + if (q->dma_drain_size && rq->data_len) { + /* + * make sure space for the drain appears we + * know we can do this because max_hw_segments + * has been adjusted to be one fewer than the + * device can handle + */ + rq->nr_phys_segments++; + rq->nr_hw_segments++; + } + + if (!q->prep_rq_fn) break; ret = q->prep_rq_fn(q, rq); @@ -754,6 +768,16 @@ struct request *elv_next_request(struct request_queue *q) * avoid resource deadlock. REQ_STARTED will * prevent other fs requests from passing this one. */ + if (q->dma_drain_size && rq->data_len && + !(rq->cmd_flags & REQ_DONTPREP)) { + /* + * remove the space for the drain we added + * so that we don't add it again + */ + --rq->nr_phys_segments; + --rq->nr_hw_segments; + } + rq = NULL; break; } else if (ret == BLKPREP_KILL) {