aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMatthew Wilcox <matthew@wil.cx>2007-10-02 21:55:41 -0400
committerJames Bottomley <jejb@mulgrave.localdomain>2007-10-12 14:54:05 -0400
commitd10fb2c7b5ce1b475df50cde9262d2c3fe3d296e (patch)
treefd037eb44ff9ac58cf8f207efc11cb6612d851cf
parentb249c7fda2ca8efcbe37ace1e20a3fffac08bccb (diff)
[SCSI] advansys: Use dma mapping for overrun buffer
Convert the call to virt_to_bus() into a call to dma_map_single(). Some architectures may require different DMA addresses for different devices, so allocate one overrun buffer per host rather than one for all cards. Signed-off-by: Matthew Wilcox <willy@linux.intel.com> Signed-off-by: James Bottomley <James.Bottomley@SteelEye.com>
-rw-r--r--drivers/scsi/advansys.c42
1 files changed, 24 insertions, 18 deletions
diff --git a/drivers/scsi/advansys.c b/drivers/scsi/advansys.c
index 88e7fef18a29..07507a7e9c50 100644
--- a/drivers/scsi/advansys.c
+++ b/drivers/scsi/advansys.c
@@ -529,7 +529,6 @@ typedef struct asc_dvc_cfg {
529 ushort mcode_date; 529 ushort mcode_date;
530 ushort mcode_version; 530 ushort mcode_version;
531 uchar max_tag_qng[ASC_MAX_TID + 1]; 531 uchar max_tag_qng[ASC_MAX_TID + 1];
532 uchar *overrun_buf;
533 uchar sdtr_period_offset[ASC_MAX_TID + 1]; 532 uchar sdtr_period_offset[ASC_MAX_TID + 1];
534 uchar adapter_info[6]; 533 uchar adapter_info[6];
535} ASC_DVC_CFG; 534} ASC_DVC_CFG;
@@ -551,6 +550,7 @@ typedef struct asc_dvc_cfg {
551#define ASC_BUG_FIX_ASYN_USE_SYN 0x0002 550#define ASC_BUG_FIX_ASYN_USE_SYN 0x0002
552#define ASC_MIN_TAGGED_CMD 7 551#define ASC_MIN_TAGGED_CMD 7
553#define ASC_MAX_SCSI_RESET_WAIT 30 552#define ASC_MAX_SCSI_RESET_WAIT 30
553#define ASC_OVERRUN_BSIZE 64
554 554
555struct asc_dvc_var; /* Forward Declaration. */ 555struct asc_dvc_var; /* Forward Declaration. */
556 556
@@ -566,6 +566,8 @@ typedef struct asc_dvc_var {
566 ASC_SCSI_BIT_ID_TYPE unit_not_ready; 566 ASC_SCSI_BIT_ID_TYPE unit_not_ready;
567 ASC_SCSI_BIT_ID_TYPE queue_full_or_busy; 567 ASC_SCSI_BIT_ID_TYPE queue_full_or_busy;
568 ASC_SCSI_BIT_ID_TYPE start_motor; 568 ASC_SCSI_BIT_ID_TYPE start_motor;
569 uchar overrun_buf[ASC_OVERRUN_BSIZE] __aligned(8);
570 dma_addr_t overrun_dma;
569 uchar scsi_reset_wait; 571 uchar scsi_reset_wait;
570 uchar chip_no; 572 uchar chip_no;
571 char is_in_int; 573 char is_in_int;
@@ -668,7 +670,6 @@ typedef struct asceep_config {
668#define ASC_EEP_CMD_WRITE 0x40 670#define ASC_EEP_CMD_WRITE 0x40
669#define ASC_EEP_CMD_WRITE_ABLE 0x30 671#define ASC_EEP_CMD_WRITE_ABLE 0x30
670#define ASC_EEP_CMD_WRITE_DISABLE 0x00 672#define ASC_EEP_CMD_WRITE_DISABLE 0x00
671#define ASC_OVERRUN_BSIZE 0x00000048UL
672#define ASCV_MSGOUT_BEG 0x0000 673#define ASCV_MSGOUT_BEG 0x0000
673#define ASCV_MSGOUT_SDTR_PERIOD (ASCV_MSGOUT_BEG+3) 674#define ASCV_MSGOUT_SDTR_PERIOD (ASCV_MSGOUT_BEG+3)
674#define ASCV_MSGOUT_SDTR_OFFSET (ASCV_MSGOUT_BEG+4) 675#define ASCV_MSGOUT_SDTR_OFFSET (ASCV_MSGOUT_BEG+4)
@@ -2404,13 +2405,12 @@ struct asc_board {
2404 ushort bios_codelen; /* BIOS Code Segment Length. */ 2405 ushort bios_codelen; /* BIOS Code Segment Length. */
2405}; 2406};
2406 2407
2408#define asc_dvc_to_board(asc_dvc) container_of(asc_dvc, struct asc_board, \
2409 dvc_var.asc_dvc_var)
2407#define adv_dvc_to_board(adv_dvc) container_of(adv_dvc, struct asc_board, \ 2410#define adv_dvc_to_board(adv_dvc) container_of(adv_dvc, struct asc_board, \
2408 dvc_var.adv_dvc_var) 2411 dvc_var.adv_dvc_var)
2409#define adv_dvc_to_pdev(adv_dvc) to_pci_dev(adv_dvc_to_board(adv_dvc)->dev) 2412#define adv_dvc_to_pdev(adv_dvc) to_pci_dev(adv_dvc_to_board(adv_dvc)->dev)
2410 2413
2411/* Overrun buffer used by all narrow boards. */
2412static uchar overrun_buf[ASC_OVERRUN_BSIZE] = { 0 };
2413
2414#ifdef ADVANSYS_DEBUG 2414#ifdef ADVANSYS_DEBUG
2415static int asc_dbglvl = 3; 2415static int asc_dbglvl = 3;
2416 2416
@@ -2465,8 +2465,8 @@ static void asc_prt_asc_dvc_cfg(ASC_DVC_CFG *h)
2465 "chip_version %d,\n", h->chip_scsi_id, h->isa_dma_speed, 2465 "chip_version %d,\n", h->chip_scsi_id, h->isa_dma_speed,
2466 h->isa_dma_channel, h->chip_version); 2466 h->isa_dma_channel, h->chip_version);
2467 2467
2468 printk(" mcode_date 0x%x, mcode_version %d, overrun_buf 0x%p\n", 2468 printk(" mcode_date 0x%x, mcode_version %d\n",
2469 h->mcode_date, h->mcode_version, h->overrun_buf); 2469 h->mcode_date, h->mcode_version);
2470} 2470}
2471 2471
2472/* 2472/*
@@ -6316,6 +6316,7 @@ static ushort AscInitMicroCodeVar(ASC_DVC_VAR *asc_dvc)
6316 PortAddr iop_base; 6316 PortAddr iop_base;
6317 ASC_PADDR phy_addr; 6317 ASC_PADDR phy_addr;
6318 ASC_DCNT phy_size; 6318 ASC_DCNT phy_size;
6319 struct asc_board *board = asc_dvc_to_board(asc_dvc);
6319 6320
6320 iop_base = asc_dvc->iop_base; 6321 iop_base = asc_dvc->iop_base;
6321 warn_code = 0; 6322 warn_code = 0;
@@ -6330,12 +6331,14 @@ static ushort AscInitMicroCodeVar(ASC_DVC_VAR *asc_dvc)
6330 AscWriteLramByte(iop_base, ASCV_HOSTSCSI_ID_B, 6331 AscWriteLramByte(iop_base, ASCV_HOSTSCSI_ID_B,
6331 ASC_TID_TO_TARGET_ID(asc_dvc->cfg->chip_scsi_id)); 6332 ASC_TID_TO_TARGET_ID(asc_dvc->cfg->chip_scsi_id));
6332 6333
6333 /* Align overrun buffer on an 8 byte boundary. */ 6334 /* Ensure overrun buffer is aligned on an 8 byte boundary. */
6334 phy_addr = virt_to_bus(asc_dvc->cfg->overrun_buf); 6335 BUG_ON((unsigned long)asc_dvc->overrun_buf & 7);
6335 phy_addr = cpu_to_le32((phy_addr + 7) & ~0x7); 6336 asc_dvc->overrun_dma = dma_map_single(board->dev, asc_dvc->overrun_buf,
6337 ASC_OVERRUN_BSIZE, DMA_FROM_DEVICE);
6338 phy_addr = cpu_to_le32(asc_dvc->overrun_dma);
6336 AscMemDWordCopyPtrToLram(iop_base, ASCV_OVERRUN_PADDR_D, 6339 AscMemDWordCopyPtrToLram(iop_base, ASCV_OVERRUN_PADDR_D,
6337 (uchar *)&phy_addr, 1); 6340 (uchar *)&phy_addr, 1);
6338 phy_size = cpu_to_le32(ASC_OVERRUN_BSIZE - 8); 6341 phy_size = cpu_to_le32(ASC_OVERRUN_BSIZE);
6339 AscMemDWordCopyPtrToLram(iop_base, ASCV_OVERRUN_BSIZE_D, 6342 AscMemDWordCopyPtrToLram(iop_base, ASCV_OVERRUN_BSIZE_D,
6340 (uchar *)&phy_size, 1); 6343 (uchar *)&phy_size, 1);
6341 6344
@@ -13404,7 +13407,6 @@ static int __devinit advansys_board_found(struct Scsi_Host *shost,
13404 asc_dvc_varp->bus_type = bus_type; 13407 asc_dvc_varp->bus_type = bus_type;
13405 asc_dvc_varp->drv_ptr = boardp; 13408 asc_dvc_varp->drv_ptr = boardp;
13406 asc_dvc_varp->cfg = &boardp->dvc_cfg.asc_dvc_cfg; 13409 asc_dvc_varp->cfg = &boardp->dvc_cfg.asc_dvc_cfg;
13407 asc_dvc_varp->cfg->overrun_buf = &overrun_buf[0];
13408 asc_dvc_varp->iop_base = iop; 13410 asc_dvc_varp->iop_base = iop;
13409 } else { 13411 } else {
13410#ifdef CONFIG_PCI 13412#ifdef CONFIG_PCI
@@ -13880,19 +13882,23 @@ static int __devinit advansys_board_found(struct Scsi_Host *shost,
13880 */ 13882 */
13881static int advansys_release(struct Scsi_Host *shost) 13883static int advansys_release(struct Scsi_Host *shost)
13882{ 13884{
13883 struct asc_board *boardp = shost_priv(shost); 13885 struct asc_board *board = shost_priv(shost);
13884 ASC_DBG(1, "begin\n"); 13886 ASC_DBG(1, "begin\n");
13885 scsi_remove_host(shost); 13887 scsi_remove_host(shost);
13886 free_irq(boardp->irq, shost); 13888 free_irq(board->irq, shost);
13887 if (shost->dma_channel != NO_ISA_DMA) { 13889 if (shost->dma_channel != NO_ISA_DMA) {
13888 ASC_DBG(1, "free_dma()\n"); 13890 ASC_DBG(1, "free_dma()\n");
13889 free_dma(shost->dma_channel); 13891 free_dma(shost->dma_channel);
13890 } 13892 }
13891 if (!ASC_NARROW_BOARD(boardp)) { 13893 if (ASC_NARROW_BOARD(board)) {
13892 iounmap(boardp->ioremap_addr); 13894 dma_unmap_single(board->dev,
13893 advansys_wide_free_mem(boardp); 13895 board->dvc_var.asc_dvc_var.overrun_dma,
13896 ASC_OVERRUN_BSIZE, DMA_FROM_DEVICE);
13897 } else {
13898 iounmap(board->ioremap_addr);
13899 advansys_wide_free_mem(board);
13894 } 13900 }
13895 kfree(boardp->prtbuf); 13901 kfree(board->prtbuf);
13896 scsi_host_put(shost); 13902 scsi_host_put(shost);
13897 ASC_DBG(1, "end\n"); 13903 ASC_DBG(1, "end\n");
13898 return 0; 13904 return 0;