aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2010-05-27 13:19:19 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2010-05-27 13:19:19 -0400
commita9a0aff5b56d4c40288c000ff09c3f238b6b6fec (patch)
tree496cce8240689a61b4c76a4318ac53487287c74b /drivers/scsi
parentade61088bc77dd209f8edadbe544f1e5dad6c287 (diff)
parent0779c862e43e052c58a350a8bd2bf97e6908de04 (diff)
Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/geert/linux-m68k
* 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/geert/linux-m68k: (24 commits) m68k: amiga - RTC platform device conversion m68k: amiga - Parallel port platform device conversion m68k: amiga - Serial port platform device conversion m68k: amiga - Mouse platform device conversion m68k: amiga - Keyboard platform device conversion m68k: amiga - Amiga Gayle IDE platform device conversion m68k: amiga - A4000T SCSI platform device conversion m68k/scsi: a3000 - Do not use legacy Scsi_Host.base m68k: amiga - A3000 SCSI platform device conversion m68k/scsi: gvp11 - Do not use legacy Scsi_Host.base m68k: amiga - GVP Series II SCSI zorro_driver conversion m68k/scsi: a2091 - Do not use legacy Scsi_Host.base m68k: amiga - A2091/A590 SCSI zorro_driver conversion m68k/scsi: mvme147 - Kill obsolete HOSTS_C logic m68k/scsi: a3000 - Kill a3000_scsiregs typedef m68k/scsi: gvp11 - Kill gvp11_scsiregs typedef m68k/scsi: a2091 - Kill a2091_scsiregs typedef m68k/scsi: gvp11 - Extract check_wd33c93() m68k/scsi: a3000 - Kill static global a3000_host m68k/scsi: mvme147 - Kill static global mvme147_host ...
Diffstat (limited to 'drivers/scsi')
-rw-r--r--drivers/scsi/a2091.c245
-rw-r--r--drivers/scsi/a2091.h4
-rw-r--r--drivers/scsi/a3000.c256
-rw-r--r--drivers/scsi/a3000.h4
-rw-r--r--drivers/scsi/a4000t.c101
-rw-r--r--drivers/scsi/gvp11.c541
-rw-r--r--drivers/scsi/gvp11.h11
-rw-r--r--drivers/scsi/mvme147.c33
8 files changed, 641 insertions, 554 deletions
diff --git a/drivers/scsi/a2091.c b/drivers/scsi/a2091.c
index 308541ff85cf..1bb5d3f0e260 100644
--- a/drivers/scsi/a2091.c
+++ b/drivers/scsi/a2091.c
@@ -1,34 +1,31 @@
1#include <linux/types.h> 1#include <linux/types.h>
2#include <linux/mm.h>
3#include <linux/slab.h>
4#include <linux/blkdev.h>
5#include <linux/init.h> 2#include <linux/init.h>
6#include <linux/interrupt.h> 3#include <linux/interrupt.h>
4#include <linux/mm.h>
5#include <linux/slab.h>
6#include <linux/spinlock.h>
7#include <linux/zorro.h>
7 8
8#include <asm/setup.h>
9#include <asm/page.h> 9#include <asm/page.h>
10#include <asm/pgtable.h> 10#include <asm/pgtable.h>
11#include <asm/amigaints.h> 11#include <asm/amigaints.h>
12#include <asm/amigahw.h> 12#include <asm/amigahw.h>
13#include <linux/zorro.h>
14#include <asm/irq.h>
15#include <linux/spinlock.h>
16 13
17#include "scsi.h" 14#include "scsi.h"
18#include <scsi/scsi_host.h>
19#include "wd33c93.h" 15#include "wd33c93.h"
20#include "a2091.h" 16#include "a2091.h"
21 17
22#include <linux/stat.h>
23
24 18
25static int a2091_release(struct Scsi_Host *instance); 19struct a2091_hostdata {
20 struct WD33C93_hostdata wh;
21 struct a2091_scsiregs *regs;
22};
26 23
27static irqreturn_t a2091_intr(int irq, void *data) 24static irqreturn_t a2091_intr(int irq, void *data)
28{ 25{
29 struct Scsi_Host *instance = data; 26 struct Scsi_Host *instance = data;
30 a2091_scsiregs *regs = (a2091_scsiregs *)(instance->base); 27 struct a2091_hostdata *hdata = shost_priv(instance);
31 unsigned int status = regs->ISTR; 28 unsigned int status = hdata->regs->ISTR;
32 unsigned long flags; 29 unsigned long flags;
33 30
34 if (!(status & (ISTR_INT_F | ISTR_INT_P)) || !(status & ISTR_INTS)) 31 if (!(status & (ISTR_INT_F | ISTR_INT_P)) || !(status & ISTR_INTS))
@@ -43,38 +40,39 @@ static irqreturn_t a2091_intr(int irq, void *data)
43static int dma_setup(struct scsi_cmnd *cmd, int dir_in) 40static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
44{ 41{
45 struct Scsi_Host *instance = cmd->device->host; 42 struct Scsi_Host *instance = cmd->device->host;
46 struct WD33C93_hostdata *hdata = shost_priv(instance); 43 struct a2091_hostdata *hdata = shost_priv(instance);
47 a2091_scsiregs *regs = (a2091_scsiregs *)(instance->base); 44 struct WD33C93_hostdata *wh = &hdata->wh;
45 struct a2091_scsiregs *regs = hdata->regs;
48 unsigned short cntr = CNTR_PDMD | CNTR_INTEN; 46 unsigned short cntr = CNTR_PDMD | CNTR_INTEN;
49 unsigned long addr = virt_to_bus(cmd->SCp.ptr); 47 unsigned long addr = virt_to_bus(cmd->SCp.ptr);
50 48
51 /* don't allow DMA if the physical address is bad */ 49 /* don't allow DMA if the physical address is bad */
52 if (addr & A2091_XFER_MASK) { 50 if (addr & A2091_XFER_MASK) {
53 hdata->dma_bounce_len = (cmd->SCp.this_residual + 511) & ~0x1ff; 51 wh->dma_bounce_len = (cmd->SCp.this_residual + 511) & ~0x1ff;
54 hdata->dma_bounce_buffer = kmalloc(hdata->dma_bounce_len, 52 wh->dma_bounce_buffer = kmalloc(wh->dma_bounce_len,
55 GFP_KERNEL); 53 GFP_KERNEL);
56 54
57 /* can't allocate memory; use PIO */ 55 /* can't allocate memory; use PIO */
58 if (!hdata->dma_bounce_buffer) { 56 if (!wh->dma_bounce_buffer) {
59 hdata->dma_bounce_len = 0; 57 wh->dma_bounce_len = 0;
60 return 1; 58 return 1;
61 } 59 }
62 60
63 /* get the physical address of the bounce buffer */ 61 /* get the physical address of the bounce buffer */
64 addr = virt_to_bus(hdata->dma_bounce_buffer); 62 addr = virt_to_bus(wh->dma_bounce_buffer);
65 63
66 /* the bounce buffer may not be in the first 16M of physmem */ 64 /* the bounce buffer may not be in the first 16M of physmem */
67 if (addr & A2091_XFER_MASK) { 65 if (addr & A2091_XFER_MASK) {
68 /* we could use chipmem... maybe later */ 66 /* we could use chipmem... maybe later */
69 kfree(hdata->dma_bounce_buffer); 67 kfree(wh->dma_bounce_buffer);
70 hdata->dma_bounce_buffer = NULL; 68 wh->dma_bounce_buffer = NULL;
71 hdata->dma_bounce_len = 0; 69 wh->dma_bounce_len = 0;
72 return 1; 70 return 1;
73 } 71 }
74 72
75 if (!dir_in) { 73 if (!dir_in) {
76 /* copy to bounce buffer for a write */ 74 /* copy to bounce buffer for a write */
77 memcpy(hdata->dma_bounce_buffer, cmd->SCp.ptr, 75 memcpy(wh->dma_bounce_buffer, cmd->SCp.ptr,
78 cmd->SCp.this_residual); 76 cmd->SCp.this_residual);
79 } 77 }
80 } 78 }
@@ -84,7 +82,7 @@ static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
84 cntr |= CNTR_DDIR; 82 cntr |= CNTR_DDIR;
85 83
86 /* remember direction */ 84 /* remember direction */
87 hdata->dma_dir = dir_in; 85 wh->dma_dir = dir_in;
88 86
89 regs->CNTR = cntr; 87 regs->CNTR = cntr;
90 88
@@ -108,20 +106,21 @@ static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
108static void dma_stop(struct Scsi_Host *instance, struct scsi_cmnd *SCpnt, 106static void dma_stop(struct Scsi_Host *instance, struct scsi_cmnd *SCpnt,
109 int status) 107 int status)
110{ 108{
111 struct WD33C93_hostdata *hdata = shost_priv(instance); 109 struct a2091_hostdata *hdata = shost_priv(instance);
112 a2091_scsiregs *regs = (a2091_scsiregs *)(instance->base); 110 struct WD33C93_hostdata *wh = &hdata->wh;
111 struct a2091_scsiregs *regs = hdata->regs;
113 112
114 /* disable SCSI interrupts */ 113 /* disable SCSI interrupts */
115 unsigned short cntr = CNTR_PDMD; 114 unsigned short cntr = CNTR_PDMD;
116 115
117 if (!hdata->dma_dir) 116 if (!wh->dma_dir)
118 cntr |= CNTR_DDIR; 117 cntr |= CNTR_DDIR;
119 118
120 /* disable SCSI interrupts */ 119 /* disable SCSI interrupts */
121 regs->CNTR = cntr; 120 regs->CNTR = cntr;
122 121
123 /* flush if we were reading */ 122 /* flush if we were reading */
124 if (hdata->dma_dir) { 123 if (wh->dma_dir) {
125 regs->FLUSH = 1; 124 regs->FLUSH = 1;
126 while (!(regs->ISTR & ISTR_FE_FLG)) 125 while (!(regs->ISTR & ISTR_FE_FLG))
127 ; 126 ;
@@ -137,95 +136,37 @@ static void dma_stop(struct Scsi_Host *instance, struct scsi_cmnd *SCpnt,
137 regs->CNTR = CNTR_PDMD | CNTR_INTEN; 136 regs->CNTR = CNTR_PDMD | CNTR_INTEN;
138 137
139 /* copy from a bounce buffer, if necessary */ 138 /* copy from a bounce buffer, if necessary */
140 if (status && hdata->dma_bounce_buffer) { 139 if (status && wh->dma_bounce_buffer) {
141 if (hdata->dma_dir) 140 if (wh->dma_dir)
142 memcpy(SCpnt->SCp.ptr, hdata->dma_bounce_buffer, 141 memcpy(SCpnt->SCp.ptr, wh->dma_bounce_buffer,
143 SCpnt->SCp.this_residual); 142 SCpnt->SCp.this_residual);
144 kfree(hdata->dma_bounce_buffer); 143 kfree(wh->dma_bounce_buffer);
145 hdata->dma_bounce_buffer = NULL; 144 wh->dma_bounce_buffer = NULL;
146 hdata->dma_bounce_len = 0; 145 wh->dma_bounce_len = 0;
147 }
148}
149
150static int __init a2091_detect(struct scsi_host_template *tpnt)
151{
152 static unsigned char called = 0;
153 struct Scsi_Host *instance;
154 unsigned long address;
155 struct zorro_dev *z = NULL;
156 wd33c93_regs wdregs;
157 a2091_scsiregs *regs;
158 struct WD33C93_hostdata *hdata;
159 int num_a2091 = 0;
160
161 if (!MACH_IS_AMIGA || called)
162 return 0;
163 called = 1;
164
165 tpnt->proc_name = "A2091";
166 tpnt->proc_info = &wd33c93_proc_info;
167
168 while ((z = zorro_find_device(ZORRO_WILDCARD, z))) {
169 if (z->id != ZORRO_PROD_CBM_A590_A2091_1 &&
170 z->id != ZORRO_PROD_CBM_A590_A2091_2)
171 continue;
172 address = z->resource.start;
173 if (!request_mem_region(address, 256, "wd33c93"))
174 continue;
175
176 instance = scsi_register(tpnt, sizeof(struct WD33C93_hostdata));
177 if (instance == NULL)
178 goto release;
179 instance->base = ZTWO_VADDR(address);
180 instance->irq = IRQ_AMIGA_PORTS;
181 instance->unique_id = z->slotaddr;
182 regs = (a2091_scsiregs *)(instance->base);
183 regs->DAWR = DAWR_A2091;
184 wdregs.SASR = &regs->SASR;
185 wdregs.SCMD = &regs->SCMD;
186 hdata = shost_priv(instance);
187 hdata->no_sync = 0xff;
188 hdata->fast = 0;
189 hdata->dma_mode = CTRL_DMA;
190 wd33c93_init(instance, wdregs, dma_setup, dma_stop,
191 WD33C93_FS_8_10);
192 if (request_irq(IRQ_AMIGA_PORTS, a2091_intr, IRQF_SHARED,
193 "A2091 SCSI", instance))
194 goto unregister;
195 regs->CNTR = CNTR_PDMD | CNTR_INTEN;
196 num_a2091++;
197 continue;
198
199unregister:
200 scsi_unregister(instance);
201release:
202 release_mem_region(address, 256);
203 } 146 }
204
205 return num_a2091;
206} 147}
207 148
208static int a2091_bus_reset(struct scsi_cmnd *cmd) 149static int a2091_bus_reset(struct scsi_cmnd *cmd)
209{ 150{
151 struct Scsi_Host *instance = cmd->device->host;
152
210 /* FIXME perform bus-specific reset */ 153 /* FIXME perform bus-specific reset */
211 154
212 /* FIXME 2: kill this function, and let midlayer fall back 155 /* FIXME 2: kill this function, and let midlayer fall back
213 to the same action, calling wd33c93_host_reset() */ 156 to the same action, calling wd33c93_host_reset() */
214 157
215 spin_lock_irq(cmd->device->host->host_lock); 158 spin_lock_irq(instance->host_lock);
216 wd33c93_host_reset(cmd); 159 wd33c93_host_reset(cmd);
217 spin_unlock_irq(cmd->device->host->host_lock); 160 spin_unlock_irq(instance->host_lock);
218 161
219 return SUCCESS; 162 return SUCCESS;
220} 163}
221 164
222#define HOSTS_C 165static struct scsi_host_template a2091_scsi_template = {
223 166 .module = THIS_MODULE,
224static struct scsi_host_template driver_template = {
225 .proc_name = "A2901",
226 .name = "Commodore A2091/A590 SCSI", 167 .name = "Commodore A2091/A590 SCSI",
227 .detect = a2091_detect, 168 .proc_info = wd33c93_proc_info,
228 .release = a2091_release, 169 .proc_name = "A2901",
229 .queuecommand = wd33c93_queuecommand, 170 .queuecommand = wd33c93_queuecommand,
230 .eh_abort_handler = wd33c93_abort, 171 .eh_abort_handler = wd33c93_abort,
231 .eh_bus_reset_handler = a2091_bus_reset, 172 .eh_bus_reset_handler = a2091_bus_reset,
@@ -237,19 +178,103 @@ static struct scsi_host_template driver_template = {
237 .use_clustering = DISABLE_CLUSTERING 178 .use_clustering = DISABLE_CLUSTERING
238}; 179};
239 180
181static int __devinit a2091_probe(struct zorro_dev *z,
182 const struct zorro_device_id *ent)
183{
184 struct Scsi_Host *instance;
185 int error;
186 struct a2091_scsiregs *regs;
187 wd33c93_regs wdregs;
188 struct a2091_hostdata *hdata;
240 189
241#include "scsi_module.c" 190 if (!request_mem_region(z->resource.start, 256, "wd33c93"))
191 return -EBUSY;
242 192
243static int a2091_release(struct Scsi_Host *instance) 193 instance = scsi_host_alloc(&a2091_scsi_template,
194 sizeof(struct a2091_hostdata));
195 if (!instance) {
196 error = -ENOMEM;
197 goto fail_alloc;
198 }
199
200 instance->irq = IRQ_AMIGA_PORTS;
201 instance->unique_id = z->slotaddr;
202
203 regs = (struct a2091_scsiregs *)ZTWO_VADDR(z->resource.start);
204 regs->DAWR = DAWR_A2091;
205
206 wdregs.SASR = &regs->SASR;
207 wdregs.SCMD = &regs->SCMD;
208
209 hdata = shost_priv(instance);
210 hdata->wh.no_sync = 0xff;
211 hdata->wh.fast = 0;
212 hdata->wh.dma_mode = CTRL_DMA;
213 hdata->regs = regs;
214
215 wd33c93_init(instance, wdregs, dma_setup, dma_stop, WD33C93_FS_8_10);
216 error = request_irq(IRQ_AMIGA_PORTS, a2091_intr, IRQF_SHARED,
217 "A2091 SCSI", instance);
218 if (error)
219 goto fail_irq;
220
221 regs->CNTR = CNTR_PDMD | CNTR_INTEN;
222
223 error = scsi_add_host(instance, NULL);
224 if (error)
225 goto fail_host;
226
227 zorro_set_drvdata(z, instance);
228
229 scsi_scan_host(instance);
230 return 0;
231
232fail_host:
233 free_irq(IRQ_AMIGA_PORTS, instance);
234fail_irq:
235 scsi_host_put(instance);
236fail_alloc:
237 release_mem_region(z->resource.start, 256);
238 return error;
239}
240
241static void __devexit a2091_remove(struct zorro_dev *z)
244{ 242{
245#ifdef MODULE 243 struct Scsi_Host *instance = zorro_get_drvdata(z);
246 a2091_scsiregs *regs = (a2091_scsiregs *)(instance->base); 244 struct a2091_hostdata *hdata = shost_priv(instance);
247 245
248 regs->CNTR = 0; 246 hdata->regs->CNTR = 0;
249 release_mem_region(ZTWO_PADDR(instance->base), 256); 247 scsi_remove_host(instance);
250 free_irq(IRQ_AMIGA_PORTS, instance); 248 free_irq(IRQ_AMIGA_PORTS, instance);
251#endif 249 scsi_host_put(instance);
252 return 1; 250 release_mem_region(z->resource.start, 256);
251}
252
253static struct zorro_device_id a2091_zorro_tbl[] __devinitdata = {
254 { ZORRO_PROD_CBM_A590_A2091_1 },
255 { ZORRO_PROD_CBM_A590_A2091_2 },
256 { 0 }
257};
258MODULE_DEVICE_TABLE(zorro, a2091_zorro_tbl);
259
260static struct zorro_driver a2091_driver = {
261 .name = "a2091",
262 .id_table = a2091_zorro_tbl,
263 .probe = a2091_probe,
264 .remove = __devexit_p(a2091_remove),
265};
266
267static int __init a2091_init(void)
268{
269 return zorro_register_driver(&a2091_driver);
270}
271module_init(a2091_init);
272
273static void __exit a2091_exit(void)
274{
275 zorro_unregister_driver(&a2091_driver);
253} 276}
277module_exit(a2091_exit);
254 278
279MODULE_DESCRIPTION("Commodore A2091/A590 SCSI");
255MODULE_LICENSE("GPL"); 280MODULE_LICENSE("GPL");
diff --git a/drivers/scsi/a2091.h b/drivers/scsi/a2091.h
index 1c3daa1fd754..794b8e65c711 100644
--- a/drivers/scsi/a2091.h
+++ b/drivers/scsi/a2091.h
@@ -25,7 +25,7 @@
25 */ 25 */
26#define A2091_XFER_MASK (0xff000001) 26#define A2091_XFER_MASK (0xff000001)
27 27
28typedef struct { 28struct a2091_scsiregs {
29 unsigned char pad1[64]; 29 unsigned char pad1[64];
30 volatile unsigned short ISTR; 30 volatile unsigned short ISTR;
31 volatile unsigned short CNTR; 31 volatile unsigned short CNTR;
@@ -44,7 +44,7 @@ typedef struct {
44 volatile unsigned short CINT; 44 volatile unsigned short CINT;
45 unsigned char pad7[2]; 45 unsigned char pad7[2];
46 volatile unsigned short FLUSH; 46 volatile unsigned short FLUSH;
47} a2091_scsiregs; 47};
48 48
49#define DAWR_A2091 (3) 49#define DAWR_A2091 (3)
50 50
diff --git a/drivers/scsi/a3000.c b/drivers/scsi/a3000.c
index bc6eb69f5fd0..d9468027fb61 100644
--- a/drivers/scsi/a3000.c
+++ b/drivers/scsi/a3000.c
@@ -1,53 +1,52 @@
1#include <linux/types.h> 1#include <linux/types.h>
2#include <linux/mm.h> 2#include <linux/mm.h>
3#include <linux/slab.h>
4#include <linux/blkdev.h>
5#include <linux/ioport.h> 3#include <linux/ioport.h>
6#include <linux/init.h> 4#include <linux/init.h>
5#include <linux/slab.h>
7#include <linux/spinlock.h> 6#include <linux/spinlock.h>
8#include <linux/interrupt.h> 7#include <linux/interrupt.h>
8#include <linux/platform_device.h>
9 9
10#include <asm/setup.h>
11#include <asm/page.h> 10#include <asm/page.h>
12#include <asm/pgtable.h> 11#include <asm/pgtable.h>
13#include <asm/amigaints.h> 12#include <asm/amigaints.h>
14#include <asm/amigahw.h> 13#include <asm/amigahw.h>
15#include <asm/irq.h>
16 14
17#include "scsi.h" 15#include "scsi.h"
18#include <scsi/scsi_host.h>
19#include "wd33c93.h" 16#include "wd33c93.h"
20#include "a3000.h" 17#include "a3000.h"
21 18
22#include <linux/stat.h>
23
24 19
25#define DMA(ptr) ((a3000_scsiregs *)((ptr)->base)) 20struct a3000_hostdata {
26 21 struct WD33C93_hostdata wh;
27static struct Scsi_Host *a3000_host = NULL; 22 struct a3000_scsiregs *regs;
28 23};
29static int a3000_release(struct Scsi_Host *instance);
30 24
31static irqreturn_t a3000_intr(int irq, void *dummy) 25static irqreturn_t a3000_intr(int irq, void *data)
32{ 26{
27 struct Scsi_Host *instance = data;
28 struct a3000_hostdata *hdata = shost_priv(instance);
29 unsigned int status = hdata->regs->ISTR;
33 unsigned long flags; 30 unsigned long flags;
34 unsigned int status = DMA(a3000_host)->ISTR;
35 31
36 if (!(status & ISTR_INT_P)) 32 if (!(status & ISTR_INT_P))
37 return IRQ_NONE; 33 return IRQ_NONE;
38 if (status & ISTR_INTS) { 34 if (status & ISTR_INTS) {
39 spin_lock_irqsave(a3000_host->host_lock, flags); 35 spin_lock_irqsave(instance->host_lock, flags);
40 wd33c93_intr(a3000_host); 36 wd33c93_intr(instance);
41 spin_unlock_irqrestore(a3000_host->host_lock, flags); 37 spin_unlock_irqrestore(instance->host_lock, flags);
42 return IRQ_HANDLED; 38 return IRQ_HANDLED;
43 } 39 }
44 printk("Non-serviced A3000 SCSI-interrupt? ISTR = %02x\n", status); 40 pr_warning("Non-serviced A3000 SCSI-interrupt? ISTR = %02x\n", status);
45 return IRQ_NONE; 41 return IRQ_NONE;
46} 42}
47 43
48static int dma_setup(struct scsi_cmnd *cmd, int dir_in) 44static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
49{ 45{
50 struct WD33C93_hostdata *hdata = shost_priv(a3000_host); 46 struct Scsi_Host *instance = cmd->device->host;
47 struct a3000_hostdata *hdata = shost_priv(instance);
48 struct WD33C93_hostdata *wh = &hdata->wh;
49 struct a3000_scsiregs *regs = hdata->regs;
51 unsigned short cntr = CNTR_PDMD | CNTR_INTEN; 50 unsigned short cntr = CNTR_PDMD | CNTR_INTEN;
52 unsigned long addr = virt_to_bus(cmd->SCp.ptr); 51 unsigned long addr = virt_to_bus(cmd->SCp.ptr);
53 52
@@ -58,23 +57,23 @@ static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
58 * buffer 57 * buffer
59 */ 58 */
60 if (addr & A3000_XFER_MASK) { 59 if (addr & A3000_XFER_MASK) {
61 hdata->dma_bounce_len = (cmd->SCp.this_residual + 511) & ~0x1ff; 60 wh->dma_bounce_len = (cmd->SCp.this_residual + 511) & ~0x1ff;
62 hdata->dma_bounce_buffer = kmalloc(hdata->dma_bounce_len, 61 wh->dma_bounce_buffer = kmalloc(wh->dma_bounce_len,
63 GFP_KERNEL); 62 GFP_KERNEL);
64 63
65 /* can't allocate memory; use PIO */ 64 /* can't allocate memory; use PIO */
66 if (!hdata->dma_bounce_buffer) { 65 if (!wh->dma_bounce_buffer) {
67 hdata->dma_bounce_len = 0; 66 wh->dma_bounce_len = 0;
68 return 1; 67 return 1;
69 } 68 }
70 69
71 if (!dir_in) { 70 if (!dir_in) {
72 /* copy to bounce buffer for a write */ 71 /* copy to bounce buffer for a write */
73 memcpy(hdata->dma_bounce_buffer, cmd->SCp.ptr, 72 memcpy(wh->dma_bounce_buffer, cmd->SCp.ptr,
74 cmd->SCp.this_residual); 73 cmd->SCp.this_residual);
75 } 74 }
76 75
77 addr = virt_to_bus(hdata->dma_bounce_buffer); 76 addr = virt_to_bus(wh->dma_bounce_buffer);
78 } 77 }
79 78
80 /* setup dma direction */ 79 /* setup dma direction */
@@ -82,12 +81,12 @@ static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
82 cntr |= CNTR_DDIR; 81 cntr |= CNTR_DDIR;
83 82
84 /* remember direction */ 83 /* remember direction */
85 hdata->dma_dir = dir_in; 84 wh->dma_dir = dir_in;
86 85
87 DMA(a3000_host)->CNTR = cntr; 86 regs->CNTR = cntr;
88 87
89 /* setup DMA *physical* address */ 88 /* setup DMA *physical* address */
90 DMA(a3000_host)->ACR = addr; 89 regs->ACR = addr;
91 90
92 if (dir_in) { 91 if (dir_in) {
93 /* invalidate any cache */ 92 /* invalidate any cache */
@@ -99,7 +98,7 @@ static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
99 98
100 /* start DMA */ 99 /* start DMA */
101 mb(); /* make sure setup is completed */ 100 mb(); /* make sure setup is completed */
102 DMA(a3000_host)->ST_DMA = 1; 101 regs->ST_DMA = 1;
103 mb(); /* make sure DMA has started before next IO */ 102 mb(); /* make sure DMA has started before next IO */
104 103
105 /* return success */ 104 /* return success */
@@ -109,22 +108,24 @@ static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
109static void dma_stop(struct Scsi_Host *instance, struct scsi_cmnd *SCpnt, 108static void dma_stop(struct Scsi_Host *instance, struct scsi_cmnd *SCpnt,
110 int status) 109 int status)
111{ 110{
112 struct WD33C93_hostdata *hdata = shost_priv(instance); 111 struct a3000_hostdata *hdata = shost_priv(instance);
112 struct WD33C93_hostdata *wh = &hdata->wh;
113 struct a3000_scsiregs *regs = hdata->regs;
113 114
114 /* disable SCSI interrupts */ 115 /* disable SCSI interrupts */
115 unsigned short cntr = CNTR_PDMD; 116 unsigned short cntr = CNTR_PDMD;
116 117
117 if (!hdata->dma_dir) 118 if (!wh->dma_dir)
118 cntr |= CNTR_DDIR; 119 cntr |= CNTR_DDIR;
119 120
120 DMA(instance)->CNTR = cntr; 121 regs->CNTR = cntr;
121 mb(); /* make sure CNTR is updated before next IO */ 122 mb(); /* make sure CNTR is updated before next IO */
122 123
123 /* flush if we were reading */ 124 /* flush if we were reading */
124 if (hdata->dma_dir) { 125 if (wh->dma_dir) {
125 DMA(instance)->FLUSH = 1; 126 regs->FLUSH = 1;
126 mb(); /* don't allow prefetch */ 127 mb(); /* don't allow prefetch */
127 while (!(DMA(instance)->ISTR & ISTR_FE_FLG)) 128 while (!(regs->ISTR & ISTR_FE_FLG))
128 barrier(); 129 barrier();
129 mb(); /* no IO until FLUSH is done */ 130 mb(); /* no IO until FLUSH is done */
130 } 131 }
@@ -133,96 +134,54 @@ static void dma_stop(struct Scsi_Host *instance, struct scsi_cmnd *SCpnt,
133 /* I think that this CINT is only necessary if you are 134 /* I think that this CINT is only necessary if you are
134 * using the terminal count features. HM 7 Mar 1994 135 * using the terminal count features. HM 7 Mar 1994
135 */ 136 */
136 DMA(instance)->CINT = 1; 137 regs->CINT = 1;
137 138
138 /* stop DMA */ 139 /* stop DMA */
139 DMA(instance)->SP_DMA = 1; 140 regs->SP_DMA = 1;
140 mb(); /* make sure DMA is stopped before next IO */ 141 mb(); /* make sure DMA is stopped before next IO */
141 142
142 /* restore the CONTROL bits (minus the direction flag) */ 143 /* restore the CONTROL bits (minus the direction flag) */
143 DMA(instance)->CNTR = CNTR_PDMD | CNTR_INTEN; 144 regs->CNTR = CNTR_PDMD | CNTR_INTEN;
144 mb(); /* make sure CNTR is updated before next IO */ 145 mb(); /* make sure CNTR is updated before next IO */
145 146
146 /* copy from a bounce buffer, if necessary */ 147 /* copy from a bounce buffer, if necessary */
147 if (status && hdata->dma_bounce_buffer) { 148 if (status && wh->dma_bounce_buffer) {
148 if (SCpnt) { 149 if (SCpnt) {
149 if (hdata->dma_dir && SCpnt) 150 if (wh->dma_dir && SCpnt)
150 memcpy(SCpnt->SCp.ptr, 151 memcpy(SCpnt->SCp.ptr, wh->dma_bounce_buffer,
151 hdata->dma_bounce_buffer,
152 SCpnt->SCp.this_residual); 152 SCpnt->SCp.this_residual);
153 kfree(hdata->dma_bounce_buffer); 153 kfree(wh->dma_bounce_buffer);
154 hdata->dma_bounce_buffer = NULL; 154 wh->dma_bounce_buffer = NULL;
155 hdata->dma_bounce_len = 0; 155 wh->dma_bounce_len = 0;
156 } else { 156 } else {
157 kfree(hdata->dma_bounce_buffer); 157 kfree(wh->dma_bounce_buffer);
158 hdata->dma_bounce_buffer = NULL; 158 wh->dma_bounce_buffer = NULL;
159 hdata->dma_bounce_len = 0; 159 wh->dma_bounce_len = 0;
160 } 160 }
161 } 161 }
162} 162}
163 163
164static int __init a3000_detect(struct scsi_host_template *tpnt)
165{
166 wd33c93_regs regs;
167 struct WD33C93_hostdata *hdata;
168
169 if (!MACH_IS_AMIGA || !AMIGAHW_PRESENT(A3000_SCSI))
170 return 0;
171 if (!request_mem_region(0xDD0000, 256, "wd33c93"))
172 return 0;
173
174 tpnt->proc_name = "A3000";
175 tpnt->proc_info = &wd33c93_proc_info;
176
177 a3000_host = scsi_register(tpnt, sizeof(struct WD33C93_hostdata));
178 if (a3000_host == NULL)
179 goto fail_register;
180
181 a3000_host->base = ZTWO_VADDR(0xDD0000);
182 a3000_host->irq = IRQ_AMIGA_PORTS;
183 DMA(a3000_host)->DAWR = DAWR_A3000;
184 regs.SASR = &(DMA(a3000_host)->SASR);
185 regs.SCMD = &(DMA(a3000_host)->SCMD);
186 hdata = shost_priv(a3000_host);
187 hdata->no_sync = 0xff;
188 hdata->fast = 0;
189 hdata->dma_mode = CTRL_DMA;
190 wd33c93_init(a3000_host, regs, dma_setup, dma_stop, WD33C93_FS_12_15);
191 if (request_irq(IRQ_AMIGA_PORTS, a3000_intr, IRQF_SHARED, "A3000 SCSI",
192 a3000_intr))
193 goto fail_irq;
194 DMA(a3000_host)->CNTR = CNTR_PDMD | CNTR_INTEN;
195
196 return 1;
197
198fail_irq:
199 scsi_unregister(a3000_host);
200fail_register:
201 release_mem_region(0xDD0000, 256);
202 return 0;
203}
204
205static int a3000_bus_reset(struct scsi_cmnd *cmd) 164static int a3000_bus_reset(struct scsi_cmnd *cmd)
206{ 165{
166 struct Scsi_Host *instance = cmd->device->host;
167
207 /* FIXME perform bus-specific reset */ 168 /* FIXME perform bus-specific reset */
208 169
209 /* FIXME 2: kill this entire function, which should 170 /* FIXME 2: kill this entire function, which should
210 cause mid-layer to call wd33c93_host_reset anyway? */ 171 cause mid-layer to call wd33c93_host_reset anyway? */
211 172
212 spin_lock_irq(cmd->device->host->host_lock); 173 spin_lock_irq(instance->host_lock);
213 wd33c93_host_reset(cmd); 174 wd33c93_host_reset(cmd);
214 spin_unlock_irq(cmd->device->host->host_lock); 175 spin_unlock_irq(instance->host_lock);
215 176
216 return SUCCESS; 177 return SUCCESS;
217} 178}
218 179
219#define HOSTS_C 180static struct scsi_host_template amiga_a3000_scsi_template = {
220 181 .module = THIS_MODULE,
221static struct scsi_host_template driver_template = {
222 .proc_name = "A3000",
223 .name = "Amiga 3000 built-in SCSI", 182 .name = "Amiga 3000 built-in SCSI",
224 .detect = a3000_detect, 183 .proc_info = wd33c93_proc_info,
225 .release = a3000_release, 184 .proc_name = "A3000",
226 .queuecommand = wd33c93_queuecommand, 185 .queuecommand = wd33c93_queuecommand,
227 .eh_abort_handler = wd33c93_abort, 186 .eh_abort_handler = wd33c93_abort,
228 .eh_bus_reset_handler = a3000_bus_reset, 187 .eh_bus_reset_handler = a3000_bus_reset,
@@ -234,15 +193,104 @@ static struct scsi_host_template driver_template = {
234 .use_clustering = ENABLE_CLUSTERING 193 .use_clustering = ENABLE_CLUSTERING
235}; 194};
236 195
196static int __init amiga_a3000_scsi_probe(struct platform_device *pdev)
197{
198 struct resource *res;
199 struct Scsi_Host *instance;
200 int error;
201 struct a3000_scsiregs *regs;
202 wd33c93_regs wdregs;
203 struct a3000_hostdata *hdata;
204
205 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
206 if (!res)
207 return -ENODEV;
208
209 if (!request_mem_region(res->start, resource_size(res), "wd33c93"))
210 return -EBUSY;
211
212 instance = scsi_host_alloc(&amiga_a3000_scsi_template,
213 sizeof(struct a3000_hostdata));
214 if (!instance) {
215 error = -ENOMEM;
216 goto fail_alloc;
217 }
218
219 instance->irq = IRQ_AMIGA_PORTS;
237 220
238#include "scsi_module.c" 221 regs = (struct a3000_scsiregs *)ZTWO_VADDR(res->start);
222 regs->DAWR = DAWR_A3000;
223
224 wdregs.SASR = &regs->SASR;
225 wdregs.SCMD = &regs->SCMD;
226
227 hdata = shost_priv(instance);
228 hdata->wh.no_sync = 0xff;
229 hdata->wh.fast = 0;
230 hdata->wh.dma_mode = CTRL_DMA;
231 hdata->regs = regs;
232
233 wd33c93_init(instance, wdregs, dma_setup, dma_stop, WD33C93_FS_12_15);
234 error = request_irq(IRQ_AMIGA_PORTS, a3000_intr, IRQF_SHARED,
235 "A3000 SCSI", instance);
236 if (error)
237 goto fail_irq;
238
239 regs->CNTR = CNTR_PDMD | CNTR_INTEN;
240
241 error = scsi_add_host(instance, NULL);
242 if (error)
243 goto fail_host;
244
245 platform_set_drvdata(pdev, instance);
246
247 scsi_scan_host(instance);
248 return 0;
249
250fail_host:
251 free_irq(IRQ_AMIGA_PORTS, instance);
252fail_irq:
253 scsi_host_put(instance);
254fail_alloc:
255 release_mem_region(res->start, resource_size(res));
256 return error;
257}
258
259static int __exit amiga_a3000_scsi_remove(struct platform_device *pdev)
260{
261 struct Scsi_Host *instance = platform_get_drvdata(pdev);
262 struct a3000_hostdata *hdata = shost_priv(instance);
263 struct resource *res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
264
265 hdata->regs->CNTR = 0;
266 scsi_remove_host(instance);
267 free_irq(IRQ_AMIGA_PORTS, instance);
268 scsi_host_put(instance);
269 release_mem_region(res->start, resource_size(res));
270 return 0;
271}
272
273static struct platform_driver amiga_a3000_scsi_driver = {
274 .remove = __exit_p(amiga_a3000_scsi_remove),
275 .driver = {
276 .name = "amiga-a3000-scsi",
277 .owner = THIS_MODULE,
278 },
279};
280
281static int __init amiga_a3000_scsi_init(void)
282{
283 return platform_driver_probe(&amiga_a3000_scsi_driver,
284 amiga_a3000_scsi_probe);
285}
286module_init(amiga_a3000_scsi_init);
239 287
240static int a3000_release(struct Scsi_Host *instance) 288static void __exit amiga_a3000_scsi_exit(void)
241{ 289{
242 DMA(instance)->CNTR = 0; 290 platform_driver_unregister(&amiga_a3000_scsi_driver);
243 release_mem_region(0xDD0000, 256);
244 free_irq(IRQ_AMIGA_PORTS, a3000_intr);
245 return 1;
246} 291}
292module_exit(amiga_a3000_scsi_exit);
247 293
294MODULE_DESCRIPTION("Amiga 3000 built-in SCSI");
248MODULE_LICENSE("GPL"); 295MODULE_LICENSE("GPL");
296MODULE_ALIAS("platform:amiga-a3000-scsi");
diff --git a/drivers/scsi/a3000.h b/drivers/scsi/a3000.h
index 684813ee378c..49db4a335aab 100644
--- a/drivers/scsi/a3000.h
+++ b/drivers/scsi/a3000.h
@@ -25,7 +25,7 @@
25 */ 25 */
26#define A3000_XFER_MASK (0x00000003) 26#define A3000_XFER_MASK (0x00000003)
27 27
28typedef struct { 28struct a3000_scsiregs {
29 unsigned char pad1[2]; 29 unsigned char pad1[2];
30 volatile unsigned short DAWR; 30 volatile unsigned short DAWR;
31 volatile unsigned int WTC; 31 volatile unsigned int WTC;
@@ -46,7 +46,7 @@ typedef struct {
46 volatile unsigned char SASR; 46 volatile unsigned char SASR;
47 unsigned char pad9; 47 unsigned char pad9;
48 volatile unsigned char SCMD; 48 volatile unsigned char SCMD;
49} a3000_scsiregs; 49};
50 50
51#define DAWR_A3000 (3) 51#define DAWR_A3000 (3)
52 52
diff --git a/drivers/scsi/a4000t.c b/drivers/scsi/a4000t.c
index 11ae6be8aeaf..23c76f41883c 100644
--- a/drivers/scsi/a4000t.c
+++ b/drivers/scsi/a4000t.c
@@ -20,10 +20,6 @@
20 20
21#include "53c700.h" 21#include "53c700.h"
22 22
23MODULE_AUTHOR("Alan Hourihane <alanh@fairlite.demon.co.uk> / Kars de Jong <jongk@linux-m68k.org>");
24MODULE_DESCRIPTION("Amiga A4000T NCR53C710 driver");
25MODULE_LICENSE("GPL");
26
27 23
28static struct scsi_host_template a4000t_scsi_driver_template = { 24static struct scsi_host_template a4000t_scsi_driver_template = {
29 .name = "A4000T builtin SCSI", 25 .name = "A4000T builtin SCSI",
@@ -32,30 +28,35 @@ static struct scsi_host_template a4000t_scsi_driver_template = {
32 .module = THIS_MODULE, 28 .module = THIS_MODULE,
33}; 29};
34 30
35static struct platform_device *a4000t_scsi_device;
36 31
37#define A4000T_SCSI_ADDR 0xdd0040 32#define A4000T_SCSI_OFFSET 0x40
38 33
39static int __devinit a4000t_probe(struct platform_device *dev) 34static int __init amiga_a4000t_scsi_probe(struct platform_device *pdev)
40{ 35{
41 struct Scsi_Host *host; 36 struct resource *res;
37 phys_addr_t scsi_addr;
42 struct NCR_700_Host_Parameters *hostdata; 38 struct NCR_700_Host_Parameters *hostdata;
39 struct Scsi_Host *host;
43 40
44 if (!(MACH_IS_AMIGA && AMIGAHW_PRESENT(A4000_SCSI))) 41 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
45 goto out; 42 if (!res)
43 return -ENODEV;
46 44
47 if (!request_mem_region(A4000T_SCSI_ADDR, 0x1000, 45 if (!request_mem_region(res->start, resource_size(res),
48 "A4000T builtin SCSI")) 46 "A4000T builtin SCSI"))
49 goto out; 47 return -EBUSY;
50 48
51 hostdata = kzalloc(sizeof(struct NCR_700_Host_Parameters), GFP_KERNEL); 49 hostdata = kzalloc(sizeof(struct NCR_700_Host_Parameters),
50 GFP_KERNEL);
52 if (!hostdata) { 51 if (!hostdata) {
53 printk(KERN_ERR "a4000t-scsi: Failed to allocate host data\n"); 52 dev_err(&pdev->dev, "Failed to allocate host data\n");
54 goto out_release; 53 goto out_release;
55 } 54 }
56 55
56 scsi_addr = res->start + A4000T_SCSI_OFFSET;
57
57 /* Fill in the required pieces of hostdata */ 58 /* Fill in the required pieces of hostdata */
58 hostdata->base = (void __iomem *)ZTWO_VADDR(A4000T_SCSI_ADDR); 59 hostdata->base = (void __iomem *)ZTWO_VADDR(scsi_addr);
59 hostdata->clock = 50; 60 hostdata->clock = 50;
60 hostdata->chip710 = 1; 61 hostdata->chip710 = 1;
61 hostdata->dmode_extra = DMODE_FC2; 62 hostdata->dmode_extra = DMODE_FC2;
@@ -63,26 +64,25 @@ static int __devinit a4000t_probe(struct platform_device *dev)
63 64
64 /* and register the chip */ 65 /* and register the chip */
65 host = NCR_700_detect(&a4000t_scsi_driver_template, hostdata, 66 host = NCR_700_detect(&a4000t_scsi_driver_template, hostdata,
66 &dev->dev); 67 &pdev->dev);
67 if (!host) { 68 if (!host) {
68 printk(KERN_ERR "a4000t-scsi: No host detected; " 69 dev_err(&pdev->dev,
69 "board configuration problem?\n"); 70 "No host detected; board configuration problem?\n");
70 goto out_free; 71 goto out_free;
71 } 72 }
72 73
73 host->this_id = 7; 74 host->this_id = 7;
74 host->base = A4000T_SCSI_ADDR; 75 host->base = scsi_addr;
75 host->irq = IRQ_AMIGA_PORTS; 76 host->irq = IRQ_AMIGA_PORTS;
76 77
77 if (request_irq(host->irq, NCR_700_intr, IRQF_SHARED, "a4000t-scsi", 78 if (request_irq(host->irq, NCR_700_intr, IRQF_SHARED, "a4000t-scsi",
78 host)) { 79 host)) {
79 printk(KERN_ERR "a4000t-scsi: request_irq failed\n"); 80 dev_err(&pdev->dev, "request_irq failed\n");
80 goto out_put_host; 81 goto out_put_host;
81 } 82 }
82 83
83 platform_set_drvdata(dev, host); 84 platform_set_drvdata(pdev, host);
84 scsi_scan_host(host); 85 scsi_scan_host(host);
85
86 return 0; 86 return 0;
87 87
88 out_put_host: 88 out_put_host:
@@ -90,58 +90,49 @@ static int __devinit a4000t_probe(struct platform_device *dev)
90 out_free: 90 out_free:
91 kfree(hostdata); 91 kfree(hostdata);
92 out_release: 92 out_release:
93 release_mem_region(A4000T_SCSI_ADDR, 0x1000); 93 release_mem_region(res->start, resource_size(res));
94 out:
95 return -ENODEV; 94 return -ENODEV;
96} 95}
97 96
98static __devexit int a4000t_device_remove(struct platform_device *dev) 97static int __exit amiga_a4000t_scsi_remove(struct platform_device *pdev)
99{ 98{
100 struct Scsi_Host *host = platform_get_drvdata(dev); 99 struct Scsi_Host *host = platform_get_drvdata(pdev);
101 struct NCR_700_Host_Parameters *hostdata = shost_priv(host); 100 struct NCR_700_Host_Parameters *hostdata = shost_priv(host);
101 struct resource *res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
102 102
103 scsi_remove_host(host); 103 scsi_remove_host(host);
104
105 NCR_700_release(host); 104 NCR_700_release(host);
106 kfree(hostdata); 105 kfree(hostdata);
107 free_irq(host->irq, host); 106 free_irq(host->irq, host);
108 release_mem_region(A4000T_SCSI_ADDR, 0x1000); 107 release_mem_region(res->start, resource_size(res));
109
110 return 0; 108 return 0;
111} 109}
112 110
113static struct platform_driver a4000t_scsi_driver = { 111static struct platform_driver amiga_a4000t_scsi_driver = {
114 .driver = { 112 .remove = __exit_p(amiga_a4000t_scsi_remove),
115 .name = "a4000t-scsi", 113 .driver = {
116 .owner = THIS_MODULE, 114 .name = "amiga-a4000t-scsi",
115 .owner = THIS_MODULE,
117 }, 116 },
118 .probe = a4000t_probe,
119 .remove = __devexit_p(a4000t_device_remove),
120}; 117};
121 118
122static int __init a4000t_scsi_init(void) 119static int __init amiga_a4000t_scsi_init(void)
123{ 120{
124 int err; 121 return platform_driver_probe(&amiga_a4000t_scsi_driver,
125 122 amiga_a4000t_scsi_probe);
126 err = platform_driver_register(&a4000t_scsi_driver);
127 if (err)
128 return err;
129
130 a4000t_scsi_device = platform_device_register_simple("a4000t-scsi",
131 -1, NULL, 0);
132 if (IS_ERR(a4000t_scsi_device)) {
133 platform_driver_unregister(&a4000t_scsi_driver);
134 return PTR_ERR(a4000t_scsi_device);
135 }
136
137 return err;
138} 123}
139 124
140static void __exit a4000t_scsi_exit(void) 125module_init(amiga_a4000t_scsi_init);
126
127static void __exit amiga_a4000t_scsi_exit(void)
141{ 128{
142 platform_device_unregister(a4000t_scsi_device); 129 platform_driver_unregister(&amiga_a4000t_scsi_driver);
143 platform_driver_unregister(&a4000t_scsi_driver);
144} 130}
145 131
146module_init(a4000t_scsi_init); 132module_exit(amiga_a4000t_scsi_exit);
147module_exit(a4000t_scsi_exit); 133
134MODULE_AUTHOR("Alan Hourihane <alanh@fairlite.demon.co.uk> / "
135 "Kars de Jong <jongk@linux-m68k.org>");
136MODULE_DESCRIPTION("Amiga A4000T NCR53C710 driver");
137MODULE_LICENSE("GPL");
138MODULE_ALIAS("platform:amiga-a4000t-scsi");
diff --git a/drivers/scsi/gvp11.c b/drivers/scsi/gvp11.c
index 18b7102bb80e..2ce26eb7a1ec 100644
--- a/drivers/scsi/gvp11.c
+++ b/drivers/scsi/gvp11.c
@@ -1,36 +1,35 @@
1#include <linux/types.h> 1#include <linux/types.h>
2#include <linux/mm.h>
3#include <linux/slab.h>
4#include <linux/blkdev.h>
5#include <linux/init.h> 2#include <linux/init.h>
6#include <linux/interrupt.h> 3#include <linux/interrupt.h>
4#include <linux/mm.h>
5#include <linux/slab.h>
6#include <linux/spinlock.h>
7#include <linux/zorro.h>
7 8
8#include <asm/setup.h>
9#include <asm/page.h> 9#include <asm/page.h>
10#include <asm/pgtable.h> 10#include <asm/pgtable.h>
11#include <asm/amigaints.h> 11#include <asm/amigaints.h>
12#include <asm/amigahw.h> 12#include <asm/amigahw.h>
13#include <linux/zorro.h>
14#include <asm/irq.h>
15#include <linux/spinlock.h>
16 13
17#include "scsi.h" 14#include "scsi.h"
18#include <scsi/scsi_host.h>
19#include "wd33c93.h" 15#include "wd33c93.h"
20#include "gvp11.h" 16#include "gvp11.h"
21 17
22#include <linux/stat.h>
23 18
19#define CHECK_WD33C93
24 20
25#define DMA(ptr) ((gvp11_scsiregs *)((ptr)->base)) 21struct gvp11_hostdata {
22 struct WD33C93_hostdata wh;
23 struct gvp11_scsiregs *regs;
24};
26 25
27static irqreturn_t gvp11_intr(int irq, void *_instance) 26static irqreturn_t gvp11_intr(int irq, void *data)
28{ 27{
28 struct Scsi_Host *instance = data;
29 struct gvp11_hostdata *hdata = shost_priv(instance);
30 unsigned int status = hdata->regs->CNTR;
29 unsigned long flags; 31 unsigned long flags;
30 unsigned int status;
31 struct Scsi_Host *instance = (struct Scsi_Host *)_instance;
32 32
33 status = DMA(instance)->CNTR;
34 if (!(status & GVP11_DMAC_INT_PENDING)) 33 if (!(status & GVP11_DMAC_INT_PENDING))
35 return IRQ_NONE; 34 return IRQ_NONE;
36 35
@@ -50,64 +49,66 @@ void gvp11_setup(char *str, int *ints)
50static int dma_setup(struct scsi_cmnd *cmd, int dir_in) 49static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
51{ 50{
52 struct Scsi_Host *instance = cmd->device->host; 51 struct Scsi_Host *instance = cmd->device->host;
53 struct WD33C93_hostdata *hdata = shost_priv(instance); 52 struct gvp11_hostdata *hdata = shost_priv(instance);
53 struct WD33C93_hostdata *wh = &hdata->wh;
54 struct gvp11_scsiregs *regs = hdata->regs;
54 unsigned short cntr = GVP11_DMAC_INT_ENABLE; 55 unsigned short cntr = GVP11_DMAC_INT_ENABLE;
55 unsigned long addr = virt_to_bus(cmd->SCp.ptr); 56 unsigned long addr = virt_to_bus(cmd->SCp.ptr);
56 int bank_mask; 57 int bank_mask;
57 static int scsi_alloc_out_of_range = 0; 58 static int scsi_alloc_out_of_range = 0;
58 59
59 /* use bounce buffer if the physical address is bad */ 60 /* use bounce buffer if the physical address is bad */
60 if (addr & hdata->dma_xfer_mask) { 61 if (addr & wh->dma_xfer_mask) {
61 hdata->dma_bounce_len = (cmd->SCp.this_residual + 511) & ~0x1ff; 62 wh->dma_bounce_len = (cmd->SCp.this_residual + 511) & ~0x1ff;
62 63
63 if (!scsi_alloc_out_of_range) { 64 if (!scsi_alloc_out_of_range) {
64 hdata->dma_bounce_buffer = 65 wh->dma_bounce_buffer =
65 kmalloc(hdata->dma_bounce_len, GFP_KERNEL); 66 kmalloc(wh->dma_bounce_len, GFP_KERNEL);
66 hdata->dma_buffer_pool = BUF_SCSI_ALLOCED; 67 wh->dma_buffer_pool = BUF_SCSI_ALLOCED;
67 } 68 }
68 69
69 if (scsi_alloc_out_of_range || 70 if (scsi_alloc_out_of_range ||
70 !hdata->dma_bounce_buffer) { 71 !wh->dma_bounce_buffer) {
71 hdata->dma_bounce_buffer = 72 wh->dma_bounce_buffer =
72 amiga_chip_alloc(hdata->dma_bounce_len, 73 amiga_chip_alloc(wh->dma_bounce_len,
73 "GVP II SCSI Bounce Buffer"); 74 "GVP II SCSI Bounce Buffer");
74 75
75 if (!hdata->dma_bounce_buffer) { 76 if (!wh->dma_bounce_buffer) {
76 hdata->dma_bounce_len = 0; 77 wh->dma_bounce_len = 0;
77 return 1; 78 return 1;
78 } 79 }
79 80
80 hdata->dma_buffer_pool = BUF_CHIP_ALLOCED; 81 wh->dma_buffer_pool = BUF_CHIP_ALLOCED;
81 } 82 }
82 83
83 /* check if the address of the bounce buffer is OK */ 84 /* check if the address of the bounce buffer is OK */
84 addr = virt_to_bus(hdata->dma_bounce_buffer); 85 addr = virt_to_bus(wh->dma_bounce_buffer);
85 86
86 if (addr & hdata->dma_xfer_mask) { 87 if (addr & wh->dma_xfer_mask) {
87 /* fall back to Chip RAM if address out of range */ 88 /* fall back to Chip RAM if address out of range */
88 if (hdata->dma_buffer_pool == BUF_SCSI_ALLOCED) { 89 if (wh->dma_buffer_pool == BUF_SCSI_ALLOCED) {
89 kfree(hdata->dma_bounce_buffer); 90 kfree(wh->dma_bounce_buffer);
90 scsi_alloc_out_of_range = 1; 91 scsi_alloc_out_of_range = 1;
91 } else { 92 } else {
92 amiga_chip_free(hdata->dma_bounce_buffer); 93 amiga_chip_free(wh->dma_bounce_buffer);
93 } 94 }
94 95
95 hdata->dma_bounce_buffer = 96 wh->dma_bounce_buffer =
96 amiga_chip_alloc(hdata->dma_bounce_len, 97 amiga_chip_alloc(wh->dma_bounce_len,
97 "GVP II SCSI Bounce Buffer"); 98 "GVP II SCSI Bounce Buffer");
98 99
99 if (!hdata->dma_bounce_buffer) { 100 if (!wh->dma_bounce_buffer) {
100 hdata->dma_bounce_len = 0; 101 wh->dma_bounce_len = 0;
101 return 1; 102 return 1;
102 } 103 }
103 104
104 addr = virt_to_bus(hdata->dma_bounce_buffer); 105 addr = virt_to_bus(wh->dma_bounce_buffer);
105 hdata->dma_buffer_pool = BUF_CHIP_ALLOCED; 106 wh->dma_buffer_pool = BUF_CHIP_ALLOCED;
106 } 107 }
107 108
108 if (!dir_in) { 109 if (!dir_in) {
109 /* copy to bounce buffer for a write */ 110 /* copy to bounce buffer for a write */
110 memcpy(hdata->dma_bounce_buffer, cmd->SCp.ptr, 111 memcpy(wh->dma_bounce_buffer, cmd->SCp.ptr,
111 cmd->SCp.this_residual); 112 cmd->SCp.this_residual);
112 } 113 }
113 } 114 }
@@ -116,11 +117,11 @@ static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
116 if (!dir_in) 117 if (!dir_in)
117 cntr |= GVP11_DMAC_DIR_WRITE; 118 cntr |= GVP11_DMAC_DIR_WRITE;
118 119
119 hdata->dma_dir = dir_in; 120 wh->dma_dir = dir_in;
120 DMA(cmd->device->host)->CNTR = cntr; 121 regs->CNTR = cntr;
121 122
122 /* setup DMA *physical* address */ 123 /* setup DMA *physical* address */
123 DMA(cmd->device->host)->ACR = addr; 124 regs->ACR = addr;
124 125
125 if (dir_in) { 126 if (dir_in) {
126 /* invalidate any cache */ 127 /* invalidate any cache */
@@ -130,12 +131,12 @@ static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
130 cache_push(addr, cmd->SCp.this_residual); 131 cache_push(addr, cmd->SCp.this_residual);
131 } 132 }
132 133
133 bank_mask = (~hdata->dma_xfer_mask >> 18) & 0x01c0; 134 bank_mask = (~wh->dma_xfer_mask >> 18) & 0x01c0;
134 if (bank_mask) 135 if (bank_mask)
135 DMA(cmd->device->host)->BANK = bank_mask & (addr >> 18); 136 regs->BANK = bank_mask & (addr >> 18);
136 137
137 /* start DMA */ 138 /* start DMA */
138 DMA(cmd->device->host)->ST_DMA = 1; 139 regs->ST_DMA = 1;
139 140
140 /* return success */ 141 /* return success */
141 return 0; 142 return 0;
@@ -144,236 +145,53 @@ static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
144static void dma_stop(struct Scsi_Host *instance, struct scsi_cmnd *SCpnt, 145static void dma_stop(struct Scsi_Host *instance, struct scsi_cmnd *SCpnt,
145 int status) 146 int status)
146{ 147{
147 struct WD33C93_hostdata *hdata = shost_priv(instance); 148 struct gvp11_hostdata *hdata = shost_priv(instance);
149 struct WD33C93_hostdata *wh = &hdata->wh;
150 struct gvp11_scsiregs *regs = hdata->regs;
148 151
149 /* stop DMA */ 152 /* stop DMA */
150 DMA(instance)->SP_DMA = 1; 153 regs->SP_DMA = 1;
151 /* remove write bit from CONTROL bits */ 154 /* remove write bit from CONTROL bits */
152 DMA(instance)->CNTR = GVP11_DMAC_INT_ENABLE; 155 regs->CNTR = GVP11_DMAC_INT_ENABLE;
153 156
154 /* copy from a bounce buffer, if necessary */ 157 /* copy from a bounce buffer, if necessary */
155 if (status && hdata->dma_bounce_buffer) { 158 if (status && wh->dma_bounce_buffer) {
156 if (hdata->dma_dir && SCpnt) 159 if (wh->dma_dir && SCpnt)
157 memcpy(SCpnt->SCp.ptr, hdata->dma_bounce_buffer, 160 memcpy(SCpnt->SCp.ptr, wh->dma_bounce_buffer,
158 SCpnt->SCp.this_residual); 161 SCpnt->SCp.this_residual);
159 162
160 if (hdata->dma_buffer_pool == BUF_SCSI_ALLOCED) 163 if (wh->dma_buffer_pool == BUF_SCSI_ALLOCED)
161 kfree(hdata->dma_bounce_buffer); 164 kfree(wh->dma_bounce_buffer);
162 else
163 amiga_chip_free(hdata->dma_bounce_buffer);
164
165 hdata->dma_bounce_buffer = NULL;
166 hdata->dma_bounce_len = 0;
167 }
168}
169
170#define CHECK_WD33C93
171
172int __init gvp11_detect(struct scsi_host_template *tpnt)
173{
174 static unsigned char called = 0;
175 struct Scsi_Host *instance;
176 unsigned long address;
177 unsigned int epc;
178 struct zorro_dev *z = NULL;
179 unsigned int default_dma_xfer_mask;
180 struct WD33C93_hostdata *hdata;
181 wd33c93_regs regs;
182 int num_gvp11 = 0;
183#ifdef CHECK_WD33C93
184 volatile unsigned char *sasr_3393, *scmd_3393;
185 unsigned char save_sasr;
186 unsigned char q, qq;
187#endif
188
189 if (!MACH_IS_AMIGA || called)
190 return 0;
191 called = 1;
192
193 tpnt->proc_name = "GVP11";
194 tpnt->proc_info = &wd33c93_proc_info;
195
196 while ((z = zorro_find_device(ZORRO_WILDCARD, z))) {
197 /*
198 * This should (hopefully) be the correct way to identify
199 * all the different GVP SCSI controllers (except for the
200 * SERIES I though).
201 */
202
203 if (z->id == ZORRO_PROD_GVP_COMBO_030_R3_SCSI ||
204 z->id == ZORRO_PROD_GVP_SERIES_II)
205 default_dma_xfer_mask = ~0x00ffffff;
206 else if (z->id == ZORRO_PROD_GVP_GFORCE_030_SCSI ||
207 z->id == ZORRO_PROD_GVP_A530_SCSI ||
208 z->id == ZORRO_PROD_GVP_COMBO_030_R4_SCSI)
209 default_dma_xfer_mask = ~0x01ffffff;
210 else if (z->id == ZORRO_PROD_GVP_A1291 ||
211 z->id == ZORRO_PROD_GVP_GFORCE_040_SCSI_1)
212 default_dma_xfer_mask = ~0x07ffffff;
213 else 165 else
214 continue; 166 amiga_chip_free(wh->dma_bounce_buffer);
215
216 /*
217 * Rumors state that some GVP ram boards use the same product
218 * code as the SCSI controllers. Therefore if the board-size
219 * is not 64KB we asume it is a ram board and bail out.
220 */
221 if (z->resource.end - z->resource.start != 0xffff)
222 continue;
223 167
224 address = z->resource.start; 168 wh->dma_bounce_buffer = NULL;
225 if (!request_mem_region(address, 256, "wd33c93")) 169 wh->dma_bounce_len = 0;
226 continue;
227
228#ifdef CHECK_WD33C93
229
230 /*
231 * These darn GVP boards are a problem - it can be tough to tell
232 * whether or not they include a SCSI controller. This is the
233 * ultimate Yet-Another-GVP-Detection-Hack in that it actually
234 * probes for a WD33c93 chip: If we find one, it's extremely
235 * likely that this card supports SCSI, regardless of Product_
236 * Code, Board_Size, etc.
237 */
238
239 /* Get pointers to the presumed register locations and save contents */
240
241 sasr_3393 = &(((gvp11_scsiregs *)(ZTWO_VADDR(address)))->SASR);
242 scmd_3393 = &(((gvp11_scsiregs *)(ZTWO_VADDR(address)))->SCMD);
243 save_sasr = *sasr_3393;
244
245 /* First test the AuxStatus Reg */
246
247 q = *sasr_3393; /* read it */
248 if (q & 0x08) /* bit 3 should always be clear */
249 goto release;
250 *sasr_3393 = WD_AUXILIARY_STATUS; /* setup indirect address */
251 if (*sasr_3393 == WD_AUXILIARY_STATUS) { /* shouldn't retain the write */
252 *sasr_3393 = save_sasr; /* Oops - restore this byte */
253 goto release;
254 }
255 if (*sasr_3393 != q) { /* should still read the same */
256 *sasr_3393 = save_sasr; /* Oops - restore this byte */
257 goto release;
258 }
259 if (*scmd_3393 != q) /* and so should the image at 0x1f */
260 goto release;
261
262 /*
263 * Ok, we probably have a wd33c93, but let's check a few other places
264 * for good measure. Make sure that this works for both 'A and 'B
265 * chip versions.
266 */
267
268 *sasr_3393 = WD_SCSI_STATUS;
269 q = *scmd_3393;
270 *sasr_3393 = WD_SCSI_STATUS;
271 *scmd_3393 = ~q;
272 *sasr_3393 = WD_SCSI_STATUS;
273 qq = *scmd_3393;
274 *sasr_3393 = WD_SCSI_STATUS;
275 *scmd_3393 = q;
276 if (qq != q) /* should be read only */
277 goto release;
278 *sasr_3393 = 0x1e; /* this register is unimplemented */
279 q = *scmd_3393;
280 *sasr_3393 = 0x1e;
281 *scmd_3393 = ~q;
282 *sasr_3393 = 0x1e;
283 qq = *scmd_3393;
284 *sasr_3393 = 0x1e;
285 *scmd_3393 = q;
286 if (qq != q || qq != 0xff) /* should be read only, all 1's */
287 goto release;
288 *sasr_3393 = WD_TIMEOUT_PERIOD;
289 q = *scmd_3393;
290 *sasr_3393 = WD_TIMEOUT_PERIOD;
291 *scmd_3393 = ~q;
292 *sasr_3393 = WD_TIMEOUT_PERIOD;
293 qq = *scmd_3393;
294 *sasr_3393 = WD_TIMEOUT_PERIOD;
295 *scmd_3393 = q;
296 if (qq != (~q & 0xff)) /* should be read/write */
297 goto release;
298#endif
299
300 instance = scsi_register(tpnt, sizeof(struct WD33C93_hostdata));
301 if (instance == NULL)
302 goto release;
303 instance->base = ZTWO_VADDR(address);
304 instance->irq = IRQ_AMIGA_PORTS;
305 instance->unique_id = z->slotaddr;
306
307 hdata = shost_priv(instance);
308 if (gvp11_xfer_mask)
309 hdata->dma_xfer_mask = gvp11_xfer_mask;
310 else
311 hdata->dma_xfer_mask = default_dma_xfer_mask;
312
313 DMA(instance)->secret2 = 1;
314 DMA(instance)->secret1 = 0;
315 DMA(instance)->secret3 = 15;
316 while (DMA(instance)->CNTR & GVP11_DMAC_BUSY)
317 ;
318 DMA(instance)->CNTR = 0;
319
320 DMA(instance)->BANK = 0;
321
322 epc = *(unsigned short *)(ZTWO_VADDR(address) + 0x8000);
323
324 /*
325 * Check for 14MHz SCSI clock
326 */
327 regs.SASR = &(DMA(instance)->SASR);
328 regs.SCMD = &(DMA(instance)->SCMD);
329 hdata->no_sync = 0xff;
330 hdata->fast = 0;
331 hdata->dma_mode = CTRL_DMA;
332 wd33c93_init(instance, regs, dma_setup, dma_stop,
333 (epc & GVP_SCSICLKMASK) ? WD33C93_FS_8_10
334 : WD33C93_FS_12_15);
335
336 if (request_irq(IRQ_AMIGA_PORTS, gvp11_intr, IRQF_SHARED,
337 "GVP11 SCSI", instance))
338 goto unregister;
339 DMA(instance)->CNTR = GVP11_DMAC_INT_ENABLE;
340 num_gvp11++;
341 continue;
342
343unregister:
344 scsi_unregister(instance);
345release:
346 release_mem_region(address, 256);
347 } 170 }
348
349 return num_gvp11;
350} 171}
351 172
352static int gvp11_bus_reset(struct scsi_cmnd *cmd) 173static int gvp11_bus_reset(struct scsi_cmnd *cmd)
353{ 174{
175 struct Scsi_Host *instance = cmd->device->host;
176
354 /* FIXME perform bus-specific reset */ 177 /* FIXME perform bus-specific reset */
355 178
356 /* FIXME 2: shouldn't we no-op this function (return 179 /* FIXME 2: shouldn't we no-op this function (return
357 FAILED), and fall back to host reset function, 180 FAILED), and fall back to host reset function,
358 wd33c93_host_reset ? */ 181 wd33c93_host_reset ? */
359 182
360 spin_lock_irq(cmd->device->host->host_lock); 183 spin_lock_irq(instance->host_lock);
361 wd33c93_host_reset(cmd); 184 wd33c93_host_reset(cmd);
362 spin_unlock_irq(cmd->device->host->host_lock); 185 spin_unlock_irq(instance->host_lock);
363 186
364 return SUCCESS; 187 return SUCCESS;
365} 188}
366 189
367 190static struct scsi_host_template gvp11_scsi_template = {
368#define HOSTS_C 191 .module = THIS_MODULE,
369
370#include "gvp11.h"
371
372static struct scsi_host_template driver_template = {
373 .proc_name = "GVP11",
374 .name = "GVP Series II SCSI", 192 .name = "GVP Series II SCSI",
375 .detect = gvp11_detect, 193 .proc_info = wd33c93_proc_info,
376 .release = gvp11_release, 194 .proc_name = "GVP11",
377 .queuecommand = wd33c93_queuecommand, 195 .queuecommand = wd33c93_queuecommand,
378 .eh_abort_handler = wd33c93_abort, 196 .eh_abort_handler = wd33c93_abort,
379 .eh_bus_reset_handler = gvp11_bus_reset, 197 .eh_bus_reset_handler = gvp11_bus_reset,
@@ -385,17 +203,230 @@ static struct scsi_host_template driver_template = {
385 .use_clustering = DISABLE_CLUSTERING 203 .use_clustering = DISABLE_CLUSTERING
386}; 204};
387 205
206static int __devinit check_wd33c93(struct gvp11_scsiregs *regs)
207{
208#ifdef CHECK_WD33C93
209 volatile unsigned char *sasr_3393, *scmd_3393;
210 unsigned char save_sasr;
211 unsigned char q, qq;
388 212
389#include "scsi_module.c" 213 /*
214 * These darn GVP boards are a problem - it can be tough to tell
215 * whether or not they include a SCSI controller. This is the
216 * ultimate Yet-Another-GVP-Detection-Hack in that it actually
217 * probes for a WD33c93 chip: If we find one, it's extremely
218 * likely that this card supports SCSI, regardless of Product_
219 * Code, Board_Size, etc.
220 */
221
222 /* Get pointers to the presumed register locations and save contents */
223
224 sasr_3393 = &regs->SASR;
225 scmd_3393 = &regs->SCMD;
226 save_sasr = *sasr_3393;
227
228 /* First test the AuxStatus Reg */
229
230 q = *sasr_3393; /* read it */
231 if (q & 0x08) /* bit 3 should always be clear */
232 return -ENODEV;
233 *sasr_3393 = WD_AUXILIARY_STATUS; /* setup indirect address */
234 if (*sasr_3393 == WD_AUXILIARY_STATUS) { /* shouldn't retain the write */
235 *sasr_3393 = save_sasr; /* Oops - restore this byte */
236 return -ENODEV;
237 }
238 if (*sasr_3393 != q) { /* should still read the same */
239 *sasr_3393 = save_sasr; /* Oops - restore this byte */
240 return -ENODEV;
241 }
242 if (*scmd_3393 != q) /* and so should the image at 0x1f */
243 return -ENODEV;
244
245 /*
246 * Ok, we probably have a wd33c93, but let's check a few other places
247 * for good measure. Make sure that this works for both 'A and 'B
248 * chip versions.
249 */
250
251 *sasr_3393 = WD_SCSI_STATUS;
252 q = *scmd_3393;
253 *sasr_3393 = WD_SCSI_STATUS;
254 *scmd_3393 = ~q;
255 *sasr_3393 = WD_SCSI_STATUS;
256 qq = *scmd_3393;
257 *sasr_3393 = WD_SCSI_STATUS;
258 *scmd_3393 = q;
259 if (qq != q) /* should be read only */
260 return -ENODEV;
261 *sasr_3393 = 0x1e; /* this register is unimplemented */
262 q = *scmd_3393;
263 *sasr_3393 = 0x1e;
264 *scmd_3393 = ~q;
265 *sasr_3393 = 0x1e;
266 qq = *scmd_3393;
267 *sasr_3393 = 0x1e;
268 *scmd_3393 = q;
269 if (qq != q || qq != 0xff) /* should be read only, all 1's */
270 return -ENODEV;
271 *sasr_3393 = WD_TIMEOUT_PERIOD;
272 q = *scmd_3393;
273 *sasr_3393 = WD_TIMEOUT_PERIOD;
274 *scmd_3393 = ~q;
275 *sasr_3393 = WD_TIMEOUT_PERIOD;
276 qq = *scmd_3393;
277 *sasr_3393 = WD_TIMEOUT_PERIOD;
278 *scmd_3393 = q;
279 if (qq != (~q & 0xff)) /* should be read/write */
280 return -ENODEV;
281#endif /* CHECK_WD33C93 */
390 282
391int gvp11_release(struct Scsi_Host *instance) 283 return 0;
284}
285
286static int __devinit gvp11_probe(struct zorro_dev *z,
287 const struct zorro_device_id *ent)
392{ 288{
393#ifdef MODULE 289 struct Scsi_Host *instance;
394 DMA(instance)->CNTR = 0; 290 unsigned long address;
395 release_mem_region(ZTWO_PADDR(instance->base), 256); 291 int error;
292 unsigned int epc;
293 unsigned int default_dma_xfer_mask;
294 struct gvp11_hostdata *hdata;
295 struct gvp11_scsiregs *regs;
296 wd33c93_regs wdregs;
297
298 default_dma_xfer_mask = ent->driver_data;
299
300 /*
301 * Rumors state that some GVP ram boards use the same product
302 * code as the SCSI controllers. Therefore if the board-size
303 * is not 64KB we asume it is a ram board and bail out.
304 */
305 if (zorro_resource_len(z) != 0x10000)
306 return -ENODEV;
307
308 address = z->resource.start;
309 if (!request_mem_region(address, 256, "wd33c93"))
310 return -EBUSY;
311
312 regs = (struct gvp11_scsiregs *)(ZTWO_VADDR(address));
313
314 error = check_wd33c93(regs);
315 if (error)
316 goto fail_check_or_alloc;
317
318 instance = scsi_host_alloc(&gvp11_scsi_template,
319 sizeof(struct gvp11_hostdata));
320 if (!instance) {
321 error = -ENOMEM;
322 goto fail_check_or_alloc;
323 }
324
325 instance->irq = IRQ_AMIGA_PORTS;
326 instance->unique_id = z->slotaddr;
327
328 regs->secret2 = 1;
329 regs->secret1 = 0;
330 regs->secret3 = 15;
331 while (regs->CNTR & GVP11_DMAC_BUSY)
332 ;
333 regs->CNTR = 0;
334 regs->BANK = 0;
335
336 wdregs.SASR = &regs->SASR;
337 wdregs.SCMD = &regs->SCMD;
338
339 hdata = shost_priv(instance);
340 if (gvp11_xfer_mask)
341 hdata->wh.dma_xfer_mask = gvp11_xfer_mask;
342 else
343 hdata->wh.dma_xfer_mask = default_dma_xfer_mask;
344
345 hdata->wh.no_sync = 0xff;
346 hdata->wh.fast = 0;
347 hdata->wh.dma_mode = CTRL_DMA;
348 hdata->regs = regs;
349
350 /*
351 * Check for 14MHz SCSI clock
352 */
353 epc = *(unsigned short *)(ZTWO_VADDR(address) + 0x8000);
354 wd33c93_init(instance, wdregs, dma_setup, dma_stop,
355 (epc & GVP_SCSICLKMASK) ? WD33C93_FS_8_10
356 : WD33C93_FS_12_15);
357
358 error = request_irq(IRQ_AMIGA_PORTS, gvp11_intr, IRQF_SHARED,
359 "GVP11 SCSI", instance);
360 if (error)
361 goto fail_irq;
362
363 regs->CNTR = GVP11_DMAC_INT_ENABLE;
364
365 error = scsi_add_host(instance, NULL);
366 if (error)
367 goto fail_host;
368
369 zorro_set_drvdata(z, instance);
370 scsi_scan_host(instance);
371 return 0;
372
373fail_host:
396 free_irq(IRQ_AMIGA_PORTS, instance); 374 free_irq(IRQ_AMIGA_PORTS, instance);
397#endif 375fail_irq:
398 return 1; 376 scsi_host_put(instance);
377fail_check_or_alloc:
378 release_mem_region(address, 256);
379 return error;
380}
381
382static void __devexit gvp11_remove(struct zorro_dev *z)
383{
384 struct Scsi_Host *instance = zorro_get_drvdata(z);
385 struct gvp11_hostdata *hdata = shost_priv(instance);
386
387 hdata->regs->CNTR = 0;
388 scsi_remove_host(instance);
389 free_irq(IRQ_AMIGA_PORTS, instance);
390 scsi_host_put(instance);
391 release_mem_region(z->resource.start, 256);
392}
393
394 /*
395 * This should (hopefully) be the correct way to identify
396 * all the different GVP SCSI controllers (except for the
397 * SERIES I though).
398 */
399
400static struct zorro_device_id gvp11_zorro_tbl[] __devinitdata = {
401 { ZORRO_PROD_GVP_COMBO_030_R3_SCSI, ~0x00ffffff },
402 { ZORRO_PROD_GVP_SERIES_II, ~0x00ffffff },
403 { ZORRO_PROD_GVP_GFORCE_030_SCSI, ~0x01ffffff },
404 { ZORRO_PROD_GVP_A530_SCSI, ~0x01ffffff },
405 { ZORRO_PROD_GVP_COMBO_030_R4_SCSI, ~0x01ffffff },
406 { ZORRO_PROD_GVP_A1291, ~0x07ffffff },
407 { ZORRO_PROD_GVP_GFORCE_040_SCSI_1, ~0x07ffffff },
408 { 0 }
409};
410MODULE_DEVICE_TABLE(zorro, gvp11_zorro_tbl);
411
412static struct zorro_driver gvp11_driver = {
413 .name = "gvp11",
414 .id_table = gvp11_zorro_tbl,
415 .probe = gvp11_probe,
416 .remove = __devexit_p(gvp11_remove),
417};
418
419static int __init gvp11_init(void)
420{
421 return zorro_register_driver(&gvp11_driver);
422}
423module_init(gvp11_init);
424
425static void __exit gvp11_exit(void)
426{
427 zorro_unregister_driver(&gvp11_driver);
399} 428}
429module_exit(gvp11_exit);
400 430
431MODULE_DESCRIPTION("GVP Series II SCSI");
401MODULE_LICENSE("GPL"); 432MODULE_LICENSE("GPL");
diff --git a/drivers/scsi/gvp11.h b/drivers/scsi/gvp11.h
index e2efdf9601ef..852913cde5dd 100644
--- a/drivers/scsi/gvp11.h
+++ b/drivers/scsi/gvp11.h
@@ -11,9 +11,6 @@
11 11
12#include <linux/types.h> 12#include <linux/types.h>
13 13
14int gvp11_detect(struct scsi_host_template *);
15int gvp11_release(struct Scsi_Host *);
16
17#ifndef CMD_PER_LUN 14#ifndef CMD_PER_LUN
18#define CMD_PER_LUN 2 15#define CMD_PER_LUN 2
19#endif 16#endif
@@ -22,15 +19,13 @@ int gvp11_release(struct Scsi_Host *);
22#define CAN_QUEUE 16 19#define CAN_QUEUE 16
23#endif 20#endif
24 21
25#ifndef HOSTS_C
26
27/* 22/*
28 * if the transfer address ANDed with this results in a non-zero 23 * if the transfer address ANDed with this results in a non-zero
29 * result, then we can't use DMA. 24 * result, then we can't use DMA.
30 */ 25 */
31#define GVP11_XFER_MASK (0xff000001) 26#define GVP11_XFER_MASK (0xff000001)
32 27
33typedef struct { 28struct gvp11_scsiregs {
34 unsigned char pad1[64]; 29 unsigned char pad1[64];
35 volatile unsigned short CNTR; 30 volatile unsigned short CNTR;
36 unsigned char pad2[31]; 31 unsigned char pad2[31];
@@ -46,7 +41,7 @@ typedef struct {
46 volatile unsigned short SP_DMA; 41 volatile unsigned short SP_DMA;
47 volatile unsigned short secret2; /* store 1 here */ 42 volatile unsigned short secret2; /* store 1 here */
48 volatile unsigned short secret3; /* store 15 here */ 43 volatile unsigned short secret3; /* store 15 here */
49} gvp11_scsiregs; 44};
50 45
51/* bits in CNTR */ 46/* bits in CNTR */
52#define GVP11_DMAC_BUSY (1<<0) 47#define GVP11_DMAC_BUSY (1<<0)
@@ -54,6 +49,4 @@ typedef struct {
54#define GVP11_DMAC_INT_ENABLE (1<<3) 49#define GVP11_DMAC_INT_ENABLE (1<<3)
55#define GVP11_DMAC_DIR_WRITE (1<<4) 50#define GVP11_DMAC_DIR_WRITE (1<<4)
56 51
57#endif /* else def HOSTS_C */
58
59#endif /* GVP11_H */ 52#endif /* GVP11_H */
diff --git a/drivers/scsi/mvme147.c b/drivers/scsi/mvme147.c
index 716d1785cda7..c29d0dbb9660 100644
--- a/drivers/scsi/mvme147.c
+++ b/drivers/scsi/mvme147.c
@@ -16,12 +16,12 @@
16#include <linux/stat.h> 16#include <linux/stat.h>
17 17
18 18
19static struct Scsi_Host *mvme147_host = NULL; 19static irqreturn_t mvme147_intr(int irq, void *data)
20
21static irqreturn_t mvme147_intr(int irq, void *dummy)
22{ 20{
21 struct Scsi_Host *instance = data;
22
23 if (irq == MVME147_IRQ_SCSI_PORT) 23 if (irq == MVME147_IRQ_SCSI_PORT)
24 wd33c93_intr(mvme147_host); 24 wd33c93_intr(instance);
25 else 25 else
26 m147_pcc->dma_intr = 0x89; /* Ack and enable ints */ 26 m147_pcc->dma_intr = 0x89; /* Ack and enable ints */
27 return IRQ_HANDLED; 27 return IRQ_HANDLED;
@@ -29,7 +29,8 @@ static irqreturn_t mvme147_intr(int irq, void *dummy)
29 29
30static int dma_setup(struct scsi_cmnd *cmd, int dir_in) 30static int dma_setup(struct scsi_cmnd *cmd, int dir_in)
31{ 31{
32 struct WD33C93_hostdata *hdata = shost_priv(mvme147_host); 32 struct Scsi_Host *instance = cmd->device->host;
33 struct WD33C93_hostdata *hdata = shost_priv(instance);
33 unsigned char flags = 0x01; 34 unsigned char flags = 0x01;
34 unsigned long addr = virt_to_bus(cmd->SCp.ptr); 35 unsigned long addr = virt_to_bus(cmd->SCp.ptr);
35 36
@@ -66,6 +67,7 @@ static void dma_stop(struct Scsi_Host *instance, struct scsi_cmnd *SCpnt,
66int mvme147_detect(struct scsi_host_template *tpnt) 67int mvme147_detect(struct scsi_host_template *tpnt)
67{ 68{
68 static unsigned char called = 0; 69 static unsigned char called = 0;
70 struct Scsi_Host *instance;
69 wd33c93_regs regs; 71 wd33c93_regs regs;
70 struct WD33C93_hostdata *hdata; 72 struct WD33C93_hostdata *hdata;
71 73
@@ -76,25 +78,25 @@ int mvme147_detect(struct scsi_host_template *tpnt)
76 tpnt->proc_name = "MVME147"; 78 tpnt->proc_name = "MVME147";
77 tpnt->proc_info = &wd33c93_proc_info; 79 tpnt->proc_info = &wd33c93_proc_info;
78 80
79 mvme147_host = scsi_register(tpnt, sizeof(struct WD33C93_hostdata)); 81 instance = scsi_register(tpnt, sizeof(struct WD33C93_hostdata));
80 if (!mvme147_host) 82 if (!instance)
81 goto err_out; 83 goto err_out;
82 84
83 mvme147_host->base = 0xfffe4000; 85 instance->base = 0xfffe4000;
84 mvme147_host->irq = MVME147_IRQ_SCSI_PORT; 86 instance->irq = MVME147_IRQ_SCSI_PORT;
85 regs.SASR = (volatile unsigned char *)0xfffe4000; 87 regs.SASR = (volatile unsigned char *)0xfffe4000;
86 regs.SCMD = (volatile unsigned char *)0xfffe4001; 88 regs.SCMD = (volatile unsigned char *)0xfffe4001;
87 hdata = shost_priv(mvme147_host); 89 hdata = shost_priv(instance);
88 hdata->no_sync = 0xff; 90 hdata->no_sync = 0xff;
89 hdata->fast = 0; 91 hdata->fast = 0;
90 hdata->dma_mode = CTRL_DMA; 92 hdata->dma_mode = CTRL_DMA;
91 wd33c93_init(mvme147_host, regs, dma_setup, dma_stop, WD33C93_FS_8_10); 93 wd33c93_init(instance, regs, dma_setup, dma_stop, WD33C93_FS_8_10);
92 94
93 if (request_irq(MVME147_IRQ_SCSI_PORT, mvme147_intr, 0, 95 if (request_irq(MVME147_IRQ_SCSI_PORT, mvme147_intr, 0,
94 "MVME147 SCSI PORT", mvme147_intr)) 96 "MVME147 SCSI PORT", instance))
95 goto err_unregister; 97 goto err_unregister;
96 if (request_irq(MVME147_IRQ_SCSI_DMA, mvme147_intr, 0, 98 if (request_irq(MVME147_IRQ_SCSI_DMA, mvme147_intr, 0,
97 "MVME147 SCSI DMA", mvme147_intr)) 99 "MVME147 SCSI DMA", instance))
98 goto err_free_irq; 100 goto err_free_irq;
99#if 0 /* Disabled; causes problems booting */ 101#if 0 /* Disabled; causes problems booting */
100 m147_pcc->scsi_interrupt = 0x10; /* Assert SCSI bus reset */ 102 m147_pcc->scsi_interrupt = 0x10; /* Assert SCSI bus reset */
@@ -113,7 +115,7 @@ int mvme147_detect(struct scsi_host_template *tpnt)
113err_free_irq: 115err_free_irq:
114 free_irq(MVME147_IRQ_SCSI_PORT, mvme147_intr); 116 free_irq(MVME147_IRQ_SCSI_PORT, mvme147_intr);
115err_unregister: 117err_unregister:
116 scsi_unregister(mvme147_host); 118 scsi_unregister(instance);
117err_out: 119err_out:
118 return 0; 120 return 0;
119} 121}
@@ -132,9 +134,6 @@ static int mvme147_bus_reset(struct scsi_cmnd *cmd)
132 return SUCCESS; 134 return SUCCESS;
133} 135}
134 136
135#define HOSTS_C
136
137#include "mvme147.h"
138 137
139static struct scsi_host_template driver_template = { 138static struct scsi_host_template driver_template = {
140 .proc_name = "MVME147", 139 .proc_name = "MVME147",