This source file includes following definitions.
- asc_tc_match
- asc_tc_attach
- asc_tc_reset
- asc_tc_intr
- asc_tc_setup
- asc_tc_go
- asc_tc_stop
- asc_dma_isintr
- asc_dma_isactive
- asc_clear_latched_intr
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40 #include <sys/param.h>
41 #include <sys/systm.h>
42 #include <sys/device.h>
43 #include <sys/buf.h>
44
45 #include <scsi/scsi_all.h>
46 #include <scsi/scsiconf.h>
47 #include <scsi/scsi_message.h>
48
49 #include <machine/bus.h>
50
51 #include <dev/ic/ncr53c9xreg.h>
52 #include <dev/ic/ncr53c9xvar.h>
53 #include <dev/tc/ascvar.h>
54
55 #include <dev/tc/tcvar.h>
56
57 struct asc_tc_softc {
58 struct asc_softc asc;
59
60
61 caddr_t sc_base, sc_bounce, sc_target;
62 };
63
64 int asc_tc_match(struct device *, void *, void *);
65 void asc_tc_attach(struct device *, struct device *, void *);
66
67 struct cfattach asc_tc_ca = {
68 sizeof(struct asc_tc_softc), asc_tc_match, asc_tc_attach
69 };
70
71 extern struct scsi_adapter asc_switch;
72 extern struct scsi_device asc_dev;
73
74 int asc_dma_isintr(struct ncr53c9x_softc *);
75 void asc_tc_reset(struct ncr53c9x_softc *);
76 int asc_tc_intr(struct ncr53c9x_softc *);
77 int asc_tc_setup(struct ncr53c9x_softc *, caddr_t *,
78 size_t *, int, size_t *);
79 void asc_tc_go(struct ncr53c9x_softc *);
80 void asc_tc_stop(struct ncr53c9x_softc *);
81 int asc_dma_isactive(struct ncr53c9x_softc *);
82 void asc_clear_latched_intr(struct ncr53c9x_softc *);
83
84 struct ncr53c9x_glue asc_tc_glue = {
85 asc_read_reg,
86 asc_write_reg,
87 asc_dma_isintr,
88 asc_tc_reset,
89 asc_tc_intr,
90 asc_tc_setup,
91 asc_tc_go,
92 asc_tc_stop,
93 asc_dma_isactive,
94 asc_clear_latched_intr,
95 };
96
97
98
99
100 #define PMAZ_OFFSET_53C94 0x0
101 #define PMAZ_OFFSET_DMAR 0x40000
102 #define PMAZ_OFFSET_RAM 0x80000
103 #define PMAZ_OFFSET_ROM 0xc0000
104
105 #define PMAZ_RAM_SIZE 0x20000
106 #define PER_TGT_DMA_SIZE ((PMAZ_RAM_SIZE/7) & ~(sizeof(int)-1))
107
108 #define PMAZ_DMAR_WRITE 0x80000000
109 #define PMAZ_DMAR_MASK 0x1ffff
110 #define PMAZ_DMA_ADDR(x) ((unsigned long)(x) & PMAZ_DMAR_MASK)
111
112 int
113 asc_tc_match(parent, cfdata, aux)
114 struct device *parent;
115 void *cfdata, *aux;
116 {
117 struct tc_attach_args *d = aux;
118
119 if (strncmp("PMAZ-AA ", d->ta_modname, TC_ROM_LLEN))
120 return (0);
121
122 return (1);
123 }
124
125 void
126 asc_tc_attach(parent, self, aux)
127 struct device *parent, *self;
128 void *aux;
129 {
130 struct tc_attach_args *ta = aux;
131 struct asc_tc_softc *asc = (struct asc_tc_softc *)self;
132 struct ncr53c9x_softc *sc = &asc->asc.sc_ncr53c9x;
133
134
135
136
137 sc->sc_glue = &asc_tc_glue;
138 asc->asc.sc_bst = ta->ta_memt;
139 asc->asc.sc_dmat = ta->ta_dmat;
140 if (bus_space_map(asc->asc.sc_bst, ta->ta_addr,
141 PMAZ_OFFSET_RAM + PMAZ_RAM_SIZE, 0, &asc->asc.sc_bsh)) {
142 printf("%s: unable to map device\n", sc->sc_dev.dv_xname);
143 return;
144 }
145 asc->sc_base = (caddr_t)ta->ta_addr;
146
147 tc_intr_establish(parent, ta->ta_cookie, IPL_BIO, ncr53c9x_intr, sc);
148
149 sc->sc_id = 7;
150 sc->sc_freq = (ta->ta_busspeed) ? 25000000 : 12500000;
151
152
153 sc->sc_freq /= 1000000;
154
155
156
157
158
159
160
161
162
163
164 sc->sc_cfg1 = sc->sc_id | NCRCFG1_PARENB;
165 sc->sc_cfg2 = NCRCFG2_SCSI2;
166 sc->sc_cfg3 = 0;
167 sc->sc_rev = NCR_VARIANT_NCR53C94;
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184 sc->sc_minsync = (1000 / sc->sc_freq) * 5 / 4;
185
186 sc->sc_maxxfer = 64 * 1024;
187
188
189 ncr53c9x_attach(sc, &asc_switch, &asc_dev);
190 }
191
192 void
193 asc_tc_reset(sc)
194 struct ncr53c9x_softc *sc;
195 {
196 struct asc_tc_softc *asc = (struct asc_tc_softc *)sc;
197
198 asc->asc.sc_flags &= ~(ASC_DMAACTIVE|ASC_MAPLOADED);
199 }
200
201 int
202 asc_tc_intr(sc)
203 struct ncr53c9x_softc *sc;
204 {
205 struct asc_tc_softc *asc = (struct asc_tc_softc *)sc;
206 int trans, resid;
207
208 resid = 0;
209 if ((asc->asc.sc_flags & ASC_ISPULLUP) == 0 &&
210 (resid = (NCR_READ_REG(sc, NCR_FFLAG) & NCRFIFO_FF)) != 0) {
211 NCR_DMA(("asc_tc_intr: empty FIFO of %d ", resid));
212 DELAY(1);
213 }
214
215 resid += NCR_READ_REG(sc, NCR_TCL);
216 resid += NCR_READ_REG(sc, NCR_TCM) << 8;
217
218 trans = asc->asc.sc_dmasize - resid;
219
220 if (asc->asc.sc_flags & ASC_ISPULLUP)
221 memcpy(asc->sc_target, asc->sc_bounce, trans);
222 *asc->asc.sc_dmalen -= trans;
223 *asc->asc.sc_dmaaddr += trans;
224 asc->asc.sc_flags &= ~(ASC_DMAACTIVE|ASC_MAPLOADED);
225
226 return (0);
227 }
228
229 int
230 asc_tc_setup(sc, addr, len, datain, dmasize)
231 struct ncr53c9x_softc *sc;
232 caddr_t *addr;
233 size_t *len;
234 int datain;
235 size_t *dmasize;
236 {
237 struct asc_tc_softc *asc = (struct asc_tc_softc *)sc;
238 u_int32_t tc_dmar;
239 size_t size;
240
241 asc->asc.sc_dmaaddr = addr;
242 asc->asc.sc_dmalen = len;
243 asc->asc.sc_flags = (datain) ? ASC_ISPULLUP : 0;
244
245 NCR_DMA(("asc_tc_setup: start %ld@%p, %s\n", (long)*asc->asc.sc_dmalen,
246 *asc->asc.sc_dmaaddr, datain ? "IN" : "OUT"));
247
248 size = *dmasize;
249 if (size > PER_TGT_DMA_SIZE)
250 size = PER_TGT_DMA_SIZE;
251 *dmasize = asc->asc.sc_dmasize = size;
252
253 NCR_DMA(("asc_tc_setup: dmasize = %ld\n", (long)asc->asc.sc_dmasize));
254
255 asc->sc_bounce = asc->sc_base + PMAZ_OFFSET_RAM;
256 asc->sc_bounce += PER_TGT_DMA_SIZE *
257 sc->sc_nexus->xs->sc_link->target;
258 asc->sc_target = *addr;
259
260 if ((asc->asc.sc_flags & ASC_ISPULLUP) == 0)
261 memcpy(asc->sc_bounce, asc->sc_target, size);
262
263 #if 1
264 if (asc->asc.sc_flags & ASC_ISPULLUP)
265 tc_dmar = PMAZ_DMA_ADDR(asc->sc_bounce);
266 else
267 tc_dmar = PMAZ_DMAR_WRITE | PMAZ_DMA_ADDR(asc->sc_bounce);
268 bus_space_write_4(asc->asc.sc_bst, asc->asc.sc_bsh, PMAZ_OFFSET_DMAR,
269 tc_dmar);
270 asc->asc.sc_flags |= ASC_MAPLOADED|ASC_DMAACTIVE;
271 #endif
272 return (0);
273 }
274
275 void
276 asc_tc_go(sc)
277 struct ncr53c9x_softc *sc;
278 {
279 #if 0
280 struct asc_tc_softc *asc = (struct asc_tc_softc *)sc;
281 u_int32_t tc_dmar;
282
283 if (asc->asc.sc_flags & ASC_ISPULLUP)
284 tc_dmar = PMAZ_DMA_ADDR(asc->sc_bounce);
285 else
286 tc_dmar = PMAZ_DMAR_WRITE | PMAZ_DMA_ADDR(asc->sc_bounce);
287 bus_space_write_4(asc->asc.sc_bst, asc->asc.sc_bsh, PMAZ_OFFSET_DMAR,
288 tc_dmar);
289 asc->asc.sc_flags |= ASC_DMAACTIVE;
290 #endif
291 }
292
293
294 void
295 asc_tc_stop(sc)
296 struct ncr53c9x_softc *sc;
297 {
298 #if 0
299 struct asc_tc_softc *asc = (struct asc_tc_softc *)sc;
300
301 if (asc->asc.sc_flags & ASC_ISPULLUP)
302 memcpy(asc->sc_target, asc->sc_bounce, asc->sc_dmasize);
303 asc->asc.sc_flags &= ~ASC_DMAACTIVE;
304 #endif
305 }
306
307
308
309
310 int
311 asc_dma_isintr(sc)
312 struct ncr53c9x_softc *sc;
313 {
314 return !!(NCR_READ_REG(sc, NCR_STAT) & NCRSTAT_INT);
315 }
316
317 int
318 asc_dma_isactive(sc)
319 struct ncr53c9x_softc *sc;
320 {
321 struct asc_tc_softc *asc = (struct asc_tc_softc *)sc;
322
323 return !!(asc->asc.sc_flags & ASC_DMAACTIVE);
324 }
325
326 void
327 asc_clear_latched_intr(sc)
328 struct ncr53c9x_softc *sc;
329 {
330 }