aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/gdth.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/scsi/gdth.c')
-rw-r--r--drivers/scsi/gdth.c296
1 files changed, 162 insertions, 134 deletions
diff --git a/drivers/scsi/gdth.c b/drivers/scsi/gdth.c
index fe5db2da26b7..add2ebbc2939 100644
--- a/drivers/scsi/gdth.c
+++ b/drivers/scsi/gdth.c
@@ -445,13 +445,11 @@ static int gdth_internal_cache_cmd(int hanum,Scsi_Cmnd *scp);
445static int gdth_fill_cache_cmd(int hanum,Scsi_Cmnd *scp,ushort hdrive); 445static int gdth_fill_cache_cmd(int hanum,Scsi_Cmnd *scp,ushort hdrive);
446 446
447static int gdth_search_eisa(ushort eisa_adr); 447static int gdth_search_eisa(ushort eisa_adr);
448static int gdth_search_isa(ulong32 bios_adr);
449static int gdth_search_pci(gdth_pci_str *pcistr); 448static int gdth_search_pci(gdth_pci_str *pcistr);
450static void gdth_search_dev(gdth_pci_str *pcistr, ushort *cnt, 449static void gdth_search_dev(gdth_pci_str *pcistr, ushort *cnt,
451 ushort vendor, ushort dev); 450 ushort vendor, ushort dev);
452static void gdth_sort_pci(gdth_pci_str *pcistr, int cnt); 451static void gdth_sort_pci(gdth_pci_str *pcistr, int cnt);
453static int gdth_init_eisa(ushort eisa_adr,gdth_ha_str *ha); 452static int gdth_init_eisa(ushort eisa_adr,gdth_ha_str *ha);
454static int gdth_init_isa(ulong32 bios_adr,gdth_ha_str *ha);
455static int gdth_init_pci(gdth_pci_str *pcistr,gdth_ha_str *ha); 453static int gdth_init_pci(gdth_pci_str *pcistr,gdth_ha_str *ha);
456 454
457static void gdth_enable_int(int hanum); 455static void gdth_enable_int(int hanum);
@@ -476,6 +474,9 @@ static void gdth_flush(int hanum);
476static int gdth_halt(struct notifier_block *nb, ulong event, void *buf); 474static int gdth_halt(struct notifier_block *nb, ulong event, void *buf);
477static int gdth_queuecommand(Scsi_Cmnd *scp,void (*done)(Scsi_Cmnd *)); 475static int gdth_queuecommand(Scsi_Cmnd *scp,void (*done)(Scsi_Cmnd *));
478static void gdth_scsi_done(struct scsi_cmnd *scp); 476static void gdth_scsi_done(struct scsi_cmnd *scp);
477#ifdef CONFIG_ISA
478static int gdth_isa_probe_one(struct scsi_host_template *, ulong32);
479#endif
479 480
480#ifdef DEBUG_GDTH 481#ifdef DEBUG_GDTH
481static unchar DebugState = DEBUG_GDTH; 482static unchar DebugState = DEBUG_GDTH;
@@ -584,7 +585,10 @@ static struct timer_list gdth_timer;
584#define gdth_writew(b,addr) writew((b),(addr)) 585#define gdth_writew(b,addr) writew((b),(addr))
585#define gdth_writel(b,addr) writel((b),(addr)) 586#define gdth_writel(b,addr) writel((b),(addr))
586 587
588#ifdef CONFIG_ISA
587static unchar gdth_drq_tab[4] = {5,6,7,7}; /* DRQ table */ 589static unchar gdth_drq_tab[4] = {5,6,7,7}; /* DRQ table */
590#endif
591
588static unchar gdth_irq_tab[6] = {0,10,11,12,14,0}; /* IRQ table */ 592static unchar gdth_irq_tab[6] = {0,10,11,12,14,0}; /* IRQ table */
589static unchar gdth_polling; /* polling if TRUE */ 593static unchar gdth_polling; /* polling if TRUE */
590static unchar gdth_from_wait = FALSE; /* gdth_wait() */ 594static unchar gdth_from_wait = FALSE; /* gdth_wait() */
@@ -838,7 +842,7 @@ static int __init gdth_search_eisa(ushort eisa_adr)
838 return 0; 842 return 0;
839} 843}
840 844
841 845#ifdef CONFIG_ISA
842static int __init gdth_search_isa(ulong32 bios_adr) 846static int __init gdth_search_isa(ulong32 bios_adr)
843{ 847{
844 void __iomem *addr; 848 void __iomem *addr;
@@ -853,7 +857,7 @@ static int __init gdth_search_isa(ulong32 bios_adr)
853 } 857 }
854 return 0; 858 return 0;
855} 859}
856 860#endif /* CONFIG_ISA */
857 861
858static int __init gdth_search_pci(gdth_pci_str *pcistr) 862static int __init gdth_search_pci(gdth_pci_str *pcistr)
859{ 863{
@@ -1064,7 +1068,7 @@ static int __init gdth_init_eisa(ushort eisa_adr,gdth_ha_str *ha)
1064 return 1; 1068 return 1;
1065} 1069}
1066 1070
1067 1071#ifdef CONFIG_ISA
1068static int __init gdth_init_isa(ulong32 bios_adr,gdth_ha_str *ha) 1072static int __init gdth_init_isa(ulong32 bios_adr,gdth_ha_str *ha)
1069{ 1073{
1070 register gdt2_dpram_str __iomem *dp2_ptr; 1074 register gdt2_dpram_str __iomem *dp2_ptr;
@@ -1163,7 +1167,7 @@ static int __init gdth_init_isa(ulong32 bios_adr,gdth_ha_str *ha)
1163 ha->dma64_support = 0; 1167 ha->dma64_support = 0;
1164 return 1; 1168 return 1;
1165} 1169}
1166 1170#endif /* CONFIG_ISA */
1167 1171
1168static int __init gdth_init_pci(gdth_pci_str *pcistr,gdth_ha_str *ha) 1172static int __init gdth_init_pci(gdth_pci_str *pcistr,gdth_ha_str *ha)
1169{ 1173{
@@ -4282,6 +4286,7 @@ int __init option_setup(char *str)
4282 return 1; 4286 return 1;
4283} 4287}
4284 4288
4289
4285#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0) 4290#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0)
4286static int __init gdth_detect(struct scsi_host_template *shtp) 4291static int __init gdth_detect(struct scsi_host_template *shtp)
4287#else 4292#else
@@ -4291,7 +4296,6 @@ static int __init gdth_detect(Scsi_Host_Template *shtp)
4291 struct Scsi_Host *shp; 4296 struct Scsi_Host *shp;
4292 gdth_pci_str pcistr[MAXHA]; 4297 gdth_pci_str pcistr[MAXHA];
4293 gdth_ha_str *ha; 4298 gdth_ha_str *ha;
4294 ulong32 isa_bios;
4295 ushort eisa_slot; 4299 ushort eisa_slot;
4296 int i,hanum,cnt,ctr,err; 4300 int i,hanum,cnt,ctr,err;
4297 unchar b; 4301 unchar b;
@@ -4328,135 +4332,16 @@ static int __init gdth_detect(Scsi_Host_Template *shtp)
4328 /* As default we do not probe for EISA or ISA controllers */ 4332 /* As default we do not probe for EISA or ISA controllers */
4329 if (probe_eisa_isa) { 4333 if (probe_eisa_isa) {
4330 /* scanning for controllers, at first: ISA controller */ 4334 /* scanning for controllers, at first: ISA controller */
4331 for (isa_bios=0xc8000UL; isa_bios<=0xd8000UL; isa_bios+=0x8000UL) { 4335#ifdef CONFIG_ISA
4332 dma_addr_t scratch_dma_handle; 4336 ulong32 isa_bios;
4333 scratch_dma_handle = 0; 4337 for (isa_bios = 0xc8000UL; isa_bios <= 0xd8000UL;
4334 4338 isa_bios += 0x8000UL) {
4335 if (gdth_ctr_count >= MAXHA) 4339 if (gdth_ctr_count >= MAXHA)
4336 break; 4340 break;
4337 if (gdth_search_isa(isa_bios)) { /* controller found */ 4341 gdth_isa_probe_one(shtp, isa_bios);
4338 shp = scsi_register(shtp,sizeof(gdth_ext_str));
4339 if (shp == NULL)
4340 continue;
4341
4342 ha = HADATA(shp);
4343 if (!gdth_init_isa(isa_bios,ha)) {
4344 scsi_unregister(shp);
4345 continue;
4346 }
4347#ifdef __ia64__
4348 break;
4349#else
4350 /* controller found and initialized */
4351 printk("Configuring GDT-ISA HA at BIOS 0x%05X IRQ %u DRQ %u\n",
4352 isa_bios,ha->irq,ha->drq);
4353
4354 if (request_irq(ha->irq,gdth_interrupt,IRQF_DISABLED,"gdth",ha)) {
4355 printk("GDT-ISA: Unable to allocate IRQ\n");
4356 scsi_unregister(shp);
4357 continue;
4358 }
4359 if (request_dma(ha->drq,"gdth")) {
4360 printk("GDT-ISA: Unable to allocate DMA channel\n");
4361 free_irq(ha->irq,ha);
4362 scsi_unregister(shp);
4363 continue;
4364 }
4365 set_dma_mode(ha->drq,DMA_MODE_CASCADE);
4366 enable_dma(ha->drq);
4367 shp->unchecked_isa_dma = 1;
4368 shp->irq = ha->irq;
4369 shp->dma_channel = ha->drq;
4370 hanum = gdth_ctr_count;
4371 gdth_ctr_tab[gdth_ctr_count++] = shp;
4372 gdth_ctr_vtab[gdth_ctr_vcount++] = shp;
4373
4374 NUMDATA(shp)->hanum = (ushort)hanum;
4375 NUMDATA(shp)->busnum= 0;
4376
4377 ha->pccb = CMDDATA(shp);
4378 ha->ccb_phys = 0L;
4379 ha->pdev = NULL;
4380 ha->pscratch = pci_alloc_consistent(ha->pdev, GDTH_SCRATCH,
4381 &scratch_dma_handle);
4382 ha->scratch_phys = scratch_dma_handle;
4383 ha->pmsg = pci_alloc_consistent(ha->pdev, sizeof(gdth_msg_str),
4384 &scratch_dma_handle);
4385 ha->msg_phys = scratch_dma_handle;
4386#ifdef INT_COAL
4387 ha->coal_stat = (gdth_coal_status *)
4388 pci_alloc_consistent(ha->pdev, sizeof(gdth_coal_status) *
4389 MAXOFFSETS, &scratch_dma_handle);
4390 ha->coal_stat_phys = scratch_dma_handle;
4391#endif
4392
4393 ha->scratch_busy = FALSE;
4394 ha->req_first = NULL;
4395 ha->tid_cnt = MAX_HDRIVES;
4396 if (max_ids > 0 && max_ids < ha->tid_cnt)
4397 ha->tid_cnt = max_ids;
4398 for (i=0; i<GDTH_MAXCMDS; ++i)
4399 ha->cmd_tab[i].cmnd = UNUSED_CMND;
4400 ha->scan_mode = rescan ? 0x10 : 0;
4401
4402 if (ha->pscratch == NULL || ha->pmsg == NULL ||
4403 !gdth_search_drives(hanum)) {
4404 printk("GDT-ISA: Error during device scan\n");
4405 --gdth_ctr_count;
4406 --gdth_ctr_vcount;
4407
4408#ifdef INT_COAL
4409 if (ha->coal_stat)
4410 pci_free_consistent(ha->pdev, sizeof(gdth_coal_status) *
4411 MAXOFFSETS, ha->coal_stat,
4412 ha->coal_stat_phys);
4413#endif
4414 if (ha->pscratch)
4415 pci_free_consistent(ha->pdev, GDTH_SCRATCH,
4416 ha->pscratch, ha->scratch_phys);
4417 if (ha->pmsg)
4418 pci_free_consistent(ha->pdev, sizeof(gdth_msg_str),
4419 ha->pmsg, ha->msg_phys);
4420
4421 free_irq(ha->irq,ha);
4422 scsi_unregister(shp);
4423 continue;
4424 }
4425 if (hdr_channel < 0 || hdr_channel > ha->bus_cnt)
4426 hdr_channel = ha->bus_cnt;
4427 ha->virt_bus = hdr_channel;
4428
4429#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,20) && \
4430 LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0)
4431 shp->highmem_io = 0;
4432#endif
4433 if (ha->cache_feat & ha->raw_feat & ha->screen_feat & GDT_64BIT)
4434 shp->max_cmd_len = 16;
4435
4436 shp->max_id = ha->tid_cnt;
4437 shp->max_lun = MAXLUN;
4438 shp->max_channel = virt_ctr ? 0 : ha->bus_cnt;
4439 if (virt_ctr) {
4440 virt_ctr = 1;
4441 /* register addit. SCSI channels as virtual controllers */
4442 for (b = 1; b < ha->bus_cnt + 1; ++b) {
4443 shp = scsi_register(shtp,sizeof(gdth_num_str));
4444 shp->unchecked_isa_dma = 1;
4445 shp->irq = ha->irq;
4446 shp->dma_channel = ha->drq;
4447 gdth_ctr_vtab[gdth_ctr_vcount++] = shp;
4448 NUMDATA(shp)->hanum = (ushort)hanum;
4449 NUMDATA(shp)->busnum = b;
4450 }
4451 }
4452
4453 spin_lock_init(&ha->smp_lock);
4454 gdth_enable_int(hanum);
4455#endif /* !__ia64__ */
4456 }
4457 } 4342 }
4343#endif
4458 4344
4459 /* scanning for EISA controllers */
4460 for (eisa_slot=0x1000; eisa_slot<=0x8000; eisa_slot+=0x1000) { 4345 for (eisa_slot=0x1000; eisa_slot<=0x8000; eisa_slot+=0x1000) {
4461 dma_addr_t scratch_dma_handle; 4346 dma_addr_t scratch_dma_handle;
4462 scratch_dma_handle = 0; 4347 scratch_dma_handle = 0;
@@ -4754,7 +4639,7 @@ static int gdth_release(struct Scsi_Host *shp)
4754 if (shp->irq) { 4639 if (shp->irq) {
4755 free_irq(shp->irq,ha); 4640 free_irq(shp->irq,ha);
4756 } 4641 }
4757#ifndef __ia64__ 4642#ifdef CONFIG_ISA
4758 if (shp->dma_channel != 0xff) { 4643 if (shp->dma_channel != 0xff) {
4759 free_dma(shp->dma_channel); 4644 free_dma(shp->dma_channel);
4760 } 4645 }
@@ -5674,6 +5559,149 @@ static Scsi_Host_Template driver_template = {
5674#endif 5559#endif
5675}; 5560};
5676 5561
5562#ifdef CONFIG_ISA
5563static int gdth_isa_probe_one(struct scsi_host_template *shtp, ulong32 isa_bios)
5564{
5565 struct Scsi_Host *shp;
5566 gdth_ha_str *ha;
5567 dma_addr_t scratch_dma_handle = 0;
5568 int error, hanum, i;
5569 u8 b;
5570
5571 if (!gdth_search_isa(isa_bios))
5572 return -ENXIO;
5573
5574 shp = scsi_register(shtp, sizeof(gdth_ext_str));
5575 if (!shp)
5576 return -ENOMEM;
5577 ha = HADATA(shp);
5578
5579 error = -ENODEV;
5580 if (!gdth_init_isa(isa_bios,ha))
5581 goto out_host_put;
5582
5583 /* controller found and initialized */
5584 printk("Configuring GDT-ISA HA at BIOS 0x%05X IRQ %u DRQ %u\n",
5585 isa_bios, ha->irq, ha->drq);
5586
5587 error = request_irq(ha->irq, gdth_interrupt, IRQF_DISABLED, "gdth", ha);
5588 if (error) {
5589 printk("GDT-ISA: Unable to allocate IRQ\n");
5590 goto out_host_put;
5591 }
5592
5593 error = request_dma(ha->drq, "gdth");
5594 if (error) {
5595 printk("GDT-ISA: Unable to allocate DMA channel\n");
5596 goto out_free_irq;
5597 }
5598
5599 set_dma_mode(ha->drq,DMA_MODE_CASCADE);
5600 enable_dma(ha->drq);
5601 shp->unchecked_isa_dma = 1;
5602 shp->irq = ha->irq;
5603 shp->dma_channel = ha->drq;
5604 hanum = gdth_ctr_count;
5605 gdth_ctr_tab[gdth_ctr_count++] = shp;
5606 gdth_ctr_vtab[gdth_ctr_vcount++] = shp;
5607
5608 NUMDATA(shp)->hanum = (ushort)hanum;
5609 NUMDATA(shp)->busnum= 0;
5610
5611 ha->pccb = CMDDATA(shp);
5612 ha->ccb_phys = 0L;
5613 ha->pdev = NULL;
5614
5615 error = -ENOMEM;
5616
5617 ha->pscratch = pci_alloc_consistent(ha->pdev, GDTH_SCRATCH,
5618 &scratch_dma_handle);
5619 if (!ha->pscratch)
5620 goto out_dec_counters;
5621 ha->scratch_phys = scratch_dma_handle;
5622
5623 ha->pmsg = pci_alloc_consistent(ha->pdev, sizeof(gdth_msg_str),
5624 &scratch_dma_handle);
5625 if (!ha->pmsg)
5626 goto out_free_pscratch;
5627 ha->msg_phys = scratch_dma_handle;
5628
5629#ifdef INT_COAL
5630 ha->coal_stat = pci_alloc_consistent(ha->pdev,
5631 sizeof(gdth_coal_status) * MAXOFFSETS,
5632 &scratch_dma_handle);
5633 if (!ha->coal_stat)
5634 goto out_free_pmsg;
5635 ha->coal_stat_phys = scratch_dma_handle;
5636#endif
5637
5638 ha->scratch_busy = FALSE;
5639 ha->req_first = NULL;
5640 ha->tid_cnt = MAX_HDRIVES;
5641 if (max_ids > 0 && max_ids < ha->tid_cnt)
5642 ha->tid_cnt = max_ids;
5643 for (i = 0; i < GDTH_MAXCMDS; ++i)
5644 ha->cmd_tab[i].cmnd = UNUSED_CMND;
5645 ha->scan_mode = rescan ? 0x10 : 0;
5646
5647 error = -ENODEV;
5648 if (!gdth_search_drives(hanum)) {
5649 printk("GDT-ISA: Error during device scan\n");
5650 goto out_free_coal_stat;
5651 }
5652
5653 if (hdr_channel < 0 || hdr_channel > ha->bus_cnt)
5654 hdr_channel = ha->bus_cnt;
5655 ha->virt_bus = hdr_channel;
5656
5657 if (ha->cache_feat & ha->raw_feat & ha->screen_feat & GDT_64BIT)
5658 shp->max_cmd_len = 16;
5659
5660 shp->max_id = ha->tid_cnt;
5661 shp->max_lun = MAXLUN;
5662 shp->max_channel = virt_ctr ? 0 : ha->bus_cnt;
5663 if (virt_ctr) {
5664 virt_ctr = 1;
5665 /* register addit. SCSI channels as virtual controllers */
5666 for (b = 1; b < ha->bus_cnt + 1; ++b) {
5667 shp = scsi_register(shtp,sizeof(gdth_num_str));
5668 shp->unchecked_isa_dma = 1;
5669 shp->irq = ha->irq;
5670 shp->dma_channel = ha->drq;
5671 gdth_ctr_vtab[gdth_ctr_vcount++] = shp;
5672 NUMDATA(shp)->hanum = (ushort)hanum;
5673 NUMDATA(shp)->busnum = b;
5674 }
5675 }
5676
5677 spin_lock_init(&ha->smp_lock);
5678 gdth_enable_int(hanum);
5679
5680 return 0;
5681
5682 out_free_coal_stat:
5683#ifdef INT_COAL
5684 pci_free_consistent(ha->pdev, sizeof(gdth_coal_status) * MAXOFFSETS,
5685 ha->coal_stat, ha->coal_stat_phys);
5686 out_free_pmsg:
5687#endif
5688 pci_free_consistent(ha->pdev, sizeof(gdth_msg_str),
5689 ha->pmsg, ha->msg_phys);
5690 out_free_pscratch:
5691 pci_free_consistent(ha->pdev, GDTH_SCRATCH,
5692 ha->pscratch, ha->scratch_phys);
5693 out_dec_counters:
5694 gdth_ctr_count--;
5695 gdth_ctr_vcount--;
5696 out_free_irq:
5697 free_irq(ha->irq, ha);
5698 out_host_put:
5699 scsi_unregister(shp);
5700 return error;
5701}
5702#endif /* CONFIG_ISA */
5703
5704
5677#include "scsi_module.c" 5705#include "scsi_module.c"
5678#ifndef MODULE 5706#ifndef MODULE
5679__setup("gdth=", option_setup); 5707__setup("gdth=", option_setup);