diff options
| -rw-r--r-- | drivers/block/cciss.c | 86 |
1 files changed, 45 insertions, 41 deletions
diff --git a/drivers/block/cciss.c b/drivers/block/cciss.c index 1c4df22dfd2a..7b0eca703a67 100644 --- a/drivers/block/cciss.c +++ b/drivers/block/cciss.c | |||
| @@ -1233,6 +1233,50 @@ static inline void complete_buffers(struct bio *bio, int status) | |||
| 1233 | } | 1233 | } |
| 1234 | } | 1234 | } |
| 1235 | 1235 | ||
| 1236 | static void cciss_check_queues(ctlr_info_t *h) | ||
| 1237 | { | ||
| 1238 | int start_queue = h->next_to_run; | ||
| 1239 | int i; | ||
| 1240 | |||
| 1241 | /* check to see if we have maxed out the number of commands that can | ||
| 1242 | * be placed on the queue. If so then exit. We do this check here | ||
| 1243 | * in case the interrupt we serviced was from an ioctl and did not | ||
| 1244 | * free any new commands. | ||
| 1245 | */ | ||
| 1246 | if ((find_first_zero_bit(h->cmd_pool_bits, NR_CMDS)) == NR_CMDS) | ||
| 1247 | return; | ||
| 1248 | |||
| 1249 | /* We have room on the queue for more commands. Now we need to queue | ||
| 1250 | * them up. We will also keep track of the next queue to run so | ||
| 1251 | * that every queue gets a chance to be started first. | ||
| 1252 | */ | ||
| 1253 | for (i = 0; i < h->highest_lun + 1; i++) { | ||
| 1254 | int curr_queue = (start_queue + i) % (h->highest_lun + 1); | ||
| 1255 | /* make sure the disk has been added and the drive is real | ||
| 1256 | * because this can be called from the middle of init_one. | ||
| 1257 | */ | ||
| 1258 | if (!(h->drv[curr_queue].queue) || !(h->drv[curr_queue].heads)) | ||
| 1259 | continue; | ||
| 1260 | blk_start_queue(h->gendisk[curr_queue]->queue); | ||
| 1261 | |||
| 1262 | /* check to see if we have maxed out the number of commands | ||
| 1263 | * that can be placed on the queue. | ||
| 1264 | */ | ||
| 1265 | if ((find_first_zero_bit(h->cmd_pool_bits, NR_CMDS)) == NR_CMDS) { | ||
| 1266 | if (curr_queue == start_queue) { | ||
| 1267 | h->next_to_run = | ||
| 1268 | (start_queue + 1) % (h->highest_lun + 1); | ||
| 1269 | break; | ||
| 1270 | } else { | ||
| 1271 | h->next_to_run = curr_queue; | ||
| 1272 | break; | ||
| 1273 | } | ||
| 1274 | } else { | ||
| 1275 | curr_queue = (curr_queue + 1) % (h->highest_lun + 1); | ||
| 1276 | } | ||
| 1277 | } | ||
| 1278 | } | ||
| 1279 | |||
| 1236 | static void cciss_softirq_done(struct request *rq) | 1280 | static void cciss_softirq_done(struct request *rq) |
| 1237 | { | 1281 | { |
| 1238 | CommandList_struct *cmd = rq->completion_data; | 1282 | CommandList_struct *cmd = rq->completion_data; |
| @@ -1264,6 +1308,7 @@ static void cciss_softirq_done(struct request *rq) | |||
| 1264 | spin_lock_irqsave(&h->lock, flags); | 1308 | spin_lock_irqsave(&h->lock, flags); |
| 1265 | end_that_request_last(rq, rq->errors); | 1309 | end_that_request_last(rq, rq->errors); |
| 1266 | cmd_free(h, cmd, 1); | 1310 | cmd_free(h, cmd, 1); |
| 1311 | cciss_check_queues(h); | ||
| 1267 | spin_unlock_irqrestore(&h->lock, flags); | 1312 | spin_unlock_irqrestore(&h->lock, flags); |
| 1268 | } | 1313 | } |
| 1269 | 1314 | ||
| @@ -2528,8 +2573,6 @@ static irqreturn_t do_cciss_intr(int irq, void *dev_id, struct pt_regs *regs) | |||
| 2528 | CommandList_struct *c; | 2573 | CommandList_struct *c; |
| 2529 | unsigned long flags; | 2574 | unsigned long flags; |
| 2530 | __u32 a, a1, a2; | 2575 | __u32 a, a1, a2; |
| 2531 | int j; | ||
| 2532 | int start_queue = h->next_to_run; | ||
| 2533 | 2576 | ||
| 2534 | if (interrupt_not_for_us(h)) | 2577 | if (interrupt_not_for_us(h)) |
| 2535 | return IRQ_NONE; | 2578 | return IRQ_NONE; |
| @@ -2588,45 +2631,6 @@ static irqreturn_t do_cciss_intr(int irq, void *dev_id, struct pt_regs *regs) | |||
| 2588 | } | 2631 | } |
| 2589 | } | 2632 | } |
| 2590 | 2633 | ||
| 2591 | /* check to see if we have maxed out the number of commands that can | ||
| 2592 | * be placed on the queue. If so then exit. We do this check here | ||
| 2593 | * in case the interrupt we serviced was from an ioctl and did not | ||
| 2594 | * free any new commands. | ||
| 2595 | */ | ||
| 2596 | if ((find_first_zero_bit(h->cmd_pool_bits, NR_CMDS)) == NR_CMDS) | ||
| 2597 | goto cleanup; | ||
| 2598 | |||
| 2599 | /* We have room on the queue for more commands. Now we need to queue | ||
| 2600 | * them up. We will also keep track of the next queue to run so | ||
| 2601 | * that every queue gets a chance to be started first. | ||
| 2602 | */ | ||
| 2603 | for (j = 0; j < h->highest_lun + 1; j++) { | ||
| 2604 | int curr_queue = (start_queue + j) % (h->highest_lun + 1); | ||
| 2605 | /* make sure the disk has been added and the drive is real | ||
| 2606 | * because this can be called from the middle of init_one. | ||
| 2607 | */ | ||
| 2608 | if (!(h->drv[curr_queue].queue) || !(h->drv[curr_queue].heads)) | ||
| 2609 | continue; | ||
| 2610 | blk_start_queue(h->gendisk[curr_queue]->queue); | ||
| 2611 | |||
| 2612 | /* check to see if we have maxed out the number of commands | ||
| 2613 | * that can be placed on the queue. | ||
| 2614 | */ | ||
| 2615 | if ((find_first_zero_bit(h->cmd_pool_bits, NR_CMDS)) == NR_CMDS) { | ||
| 2616 | if (curr_queue == start_queue) { | ||
| 2617 | h->next_to_run = | ||
| 2618 | (start_queue + 1) % (h->highest_lun + 1); | ||
| 2619 | goto cleanup; | ||
| 2620 | } else { | ||
| 2621 | h->next_to_run = curr_queue; | ||
| 2622 | goto cleanup; | ||
| 2623 | } | ||
| 2624 | } else { | ||
| 2625 | curr_queue = (curr_queue + 1) % (h->highest_lun + 1); | ||
| 2626 | } | ||
| 2627 | } | ||
| 2628 | |||
| 2629 | cleanup: | ||
| 2630 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 2634 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); |
| 2631 | return IRQ_HANDLED; | 2635 | return IRQ_HANDLED; |
| 2632 | } | 2636 | } |
