aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/block
diff options
context:
space:
mode:
authorStephen M. Cameron <scameron@beardog.cce.hp.com>2010-02-26 17:01:37 -0500
committerJens Axboe <jens.axboe@oracle.com>2010-02-28 13:42:32 -0500
commitd45033ef56fa9b09b73a6eb2a0f280fa7c1bab09 (patch)
tree320b92e8b2cee6bcb0b871e96b7e47a331ae5255 /drivers/block
parent2ad6cdc20fbeea1e1744190c00cebb64e4b4c491 (diff)
cciss: factor out scatter gather chain block mapping code
cciss: factor out scatter gather chain block mapping code Rationale is I want to use this code from the scsi half of the driver. Signed-off-by: Stephen M. Cameron <scameron@beardog.cce.hp.com> Signed-off-by: Jens Axboe <jens.axboe@oracle.com>
Diffstat (limited to 'drivers/block')
-rw-r--r--drivers/block/cciss.c63
1 files changed, 34 insertions, 29 deletions
diff --git a/drivers/block/cciss.c b/drivers/block/cciss.c
index c0d794ce69c6..9e3af307aae1 100644
--- a/drivers/block/cciss.c
+++ b/drivers/block/cciss.c
@@ -301,6 +301,35 @@ clean:
301 return NULL; 301 return NULL;
302} 302}
303 303
304static void cciss_unmap_sg_chain_block(ctlr_info_t *h, CommandList_struct *c)
305{
306 SGDescriptor_struct *chain_sg;
307 u64bit temp64;
308
309 if (c->Header.SGTotal <= h->max_cmd_sgentries)
310 return;
311
312 chain_sg = &c->SG[h->max_cmd_sgentries - 1];
313 temp64.val32.lower = chain_sg->Addr.lower;
314 temp64.val32.upper = chain_sg->Addr.upper;
315 pci_unmap_single(h->pdev, temp64.val, chain_sg->Len, PCI_DMA_TODEVICE);
316}
317
318static void cciss_map_sg_chain_block(ctlr_info_t *h, CommandList_struct *c,
319 SGDescriptor_struct *chain_block, int len)
320{
321 SGDescriptor_struct *chain_sg;
322 u64bit temp64;
323
324 chain_sg = &c->SG[h->max_cmd_sgentries - 1];
325 chain_sg->Ext = CCISS_SG_CHAIN;
326 chain_sg->Len = len;
327 temp64.val = pci_map_single(h->pdev, chain_block, len,
328 PCI_DMA_TODEVICE);
329 chain_sg->Addr.lower = temp64.val32.lower;
330 chain_sg->Addr.upper = temp64.val32.upper;
331}
332
304#include "cciss_scsi.c" /* For SCSI tape support */ 333#include "cciss_scsi.c" /* For SCSI tape support */
305 334
306static const char *raid_label[] = { "0", "4", "1(1+0)", "5", "5+1", "ADG", 335static const char *raid_label[] = { "0", "4", "1(1+0)", "5", "5+1", "ADG",
@@ -1715,10 +1744,7 @@ static void cciss_softirq_done(struct request *rq)
1715 /* unmap the DMA mapping for all the scatter gather elements */ 1744 /* unmap the DMA mapping for all the scatter gather elements */
1716 for (i = 0; i < cmd->Header.SGList; i++) { 1745 for (i = 0; i < cmd->Header.SGList; i++) {
1717 if (curr_sg[sg_index].Ext == CCISS_SG_CHAIN) { 1746 if (curr_sg[sg_index].Ext == CCISS_SG_CHAIN) {
1718 temp64.val32.lower = cmd->SG[i].Addr.lower; 1747 cciss_unmap_sg_chain_block(h, cmd);
1719 temp64.val32.upper = cmd->SG[i].Addr.upper;
1720 pci_unmap_single(h->pdev, temp64.val,
1721 cmd->SG[i].Len, PCI_DMA_TODEVICE);
1722 /* Point to the next block */ 1748 /* Point to the next block */
1723 curr_sg = h->cmd_sg_list[cmd->cmdindex]; 1749 curr_sg = h->cmd_sg_list[cmd->cmdindex];
1724 sg_index = 0; 1750 sg_index = 0;
@@ -3122,7 +3148,6 @@ static void do_cciss_request(struct request_queue *q)
3122 SGDescriptor_struct *curr_sg; 3148 SGDescriptor_struct *curr_sg;
3123 drive_info_struct *drv; 3149 drive_info_struct *drv;
3124 int i, dir; 3150 int i, dir;
3125 int nseg = 0;
3126 int sg_index = 0; 3151 int sg_index = 0;
3127 int chained = 0; 3152 int chained = 0;
3128 3153
@@ -3189,11 +3214,6 @@ static void do_cciss_request(struct request_queue *q)
3189 for (i = 0; i < seg; i++) { 3214 for (i = 0; i < seg; i++) {
3190 if (((sg_index+1) == (h->max_cmd_sgentries)) && 3215 if (((sg_index+1) == (h->max_cmd_sgentries)) &&
3191 !chained && ((seg - i) > 1)) { 3216 !chained && ((seg - i) > 1)) {
3192 nseg = seg - i;
3193 curr_sg[sg_index].Len = (nseg) *
3194 sizeof(SGDescriptor_struct);
3195 curr_sg[sg_index].Ext = CCISS_SG_CHAIN;
3196
3197 /* Point to next chain block. */ 3217 /* Point to next chain block. */
3198 curr_sg = h->cmd_sg_list[c->cmdindex]; 3218 curr_sg = h->cmd_sg_list[c->cmdindex];
3199 sg_index = 0; 3219 sg_index = 0;
@@ -3206,27 +3226,12 @@ static void do_cciss_request(struct request_queue *q)
3206 curr_sg[sg_index].Addr.lower = temp64.val32.lower; 3226 curr_sg[sg_index].Addr.lower = temp64.val32.lower;
3207 curr_sg[sg_index].Addr.upper = temp64.val32.upper; 3227 curr_sg[sg_index].Addr.upper = temp64.val32.upper;
3208 curr_sg[sg_index].Ext = 0; /* we are not chaining */ 3228 curr_sg[sg_index].Ext = 0; /* we are not chaining */
3209
3210 ++sg_index; 3229 ++sg_index;
3211 } 3230 }
3212 3231 if (chained)
3213 if (chained) { 3232 cciss_map_sg_chain_block(h, c, h->cmd_sg_list[c->cmdindex],
3214 int len; 3233 (seg - (h->max_cmd_sgentries - 1)) *
3215 dma_addr_t dma_addr; 3234 sizeof(SGDescriptor_struct));
3216 curr_sg = c->SG;
3217 sg_index = h->max_cmd_sgentries - 1;
3218 len = curr_sg[sg_index].Len;
3219 /* Setup pointer to next chain block.
3220 * Fill out last element in current chain
3221 * block with address of next chain block.
3222 */
3223 temp64.val = pci_map_single(h->pdev,
3224 h->cmd_sg_list[c->cmdindex], len,
3225 PCI_DMA_TODEVICE);
3226 dma_addr = temp64.val;
3227 curr_sg[sg_index].Addr.lower = temp64.val32.lower;
3228 curr_sg[sg_index].Addr.upper = temp64.val32.upper;
3229 }
3230 3235
3231 /* track how many SG entries we are using */ 3236 /* track how many SG entries we are using */
3232 if (seg > h->maxSG) 3237 if (seg > h->maxSG)