hpib.c revision 1.12 1 /* $NetBSD: hpib.c,v 1.12 1996/12/09 03:16:27 thorpej Exp $ */
2
3 /*
4 * Copyright (c) 1982, 1990, 1993
5 * The Regents of the University of California. All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * 3. All advertising materials mentioning features or use of this software
16 * must display the following acknowledgement:
17 * This product includes software developed by the University of
18 * California, Berkeley and its contributors.
19 * 4. Neither the name of the University nor the names of its contributors
20 * may be used to endorse or promote products derived from this software
21 * without specific prior written permission.
22 *
23 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
24 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
27 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
28 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
29 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
31 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
32 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
33 * SUCH DAMAGE.
34 *
35 * @(#)hpib.c 8.2 (Berkeley) 1/12/94
36 */
37
38 /*
39 * HPIB driver
40 */
41 #include "hpib.h"
42 #if NHPIB > 0
43
44 #include <sys/param.h>
45 #include <sys/systm.h>
46 #include <sys/buf.h>
47
48 #include <hp300/dev/device.h>
49 #include <hp300/dev/hpibvar.h>
50 #include <hp300/dev/dmavar.h>
51
52 #include <machine/cpu.h>
53 #include <hp300/hp300/isr.h>
54
55 int hpibmatch __P((struct hp_ctlr *));
56 void hpibattach __P((struct hp_ctlr *));
57 void hpibstart __P((int));
58 void hpibgo __P((int, int, int, void *, int, int, int));
59 void hpibdone __P((int));
60 int hpibintr __P((void *));
61
62 struct driver hpibdriver = {
63 hpibmatch,
64 hpibattach,
65 "hpib",
66 (int(*)())hpibstart, /* XXX */
67 (int(*)())hpibgo, /* XXX */
68 hpibintr,
69 (int(*)())hpibdone, /* XXX */
70 };
71
72 struct hpib_softc hpib_softc[NHPIB];
73
74 extern int nhpibtype __P((struct hp_ctlr *)); /* XXX */
75 extern int fhpibtype __P((struct hp_ctlr *)); /* XXX */
76 extern void nhpibattach __P((struct hp_ctlr *)); /* XXX */
77 extern void fhpibattach __P((struct hp_ctlr *)); /* XXX */
78
79 int hpibtimeout = 100000; /* # of status tests before we give up */
80 int hpibidtimeout = 10000; /* # of status tests for hpibid() calls */
81 int hpibdmathresh = 3; /* byte count beyond which to attempt dma */
82
83 int
84 hpibmatch(hc)
85 register struct hp_ctlr *hc;
86 {
87 struct hp_hw *hw = hc->hp_args;
88 extern caddr_t internalhpib;
89
90 /* Special case for internal HP-IB. */
91 if ((hw->hw_sc == 7) && internalhpib)
92 goto hwid_ok;
93
94 switch (hw->hw_id) {
95 case 8: /* 98625B */
96 case 128: /* 98624A */
97 hwid_ok:
98 if (nhpibtype(hc) || fhpibtype(hc))
99 return (1);
100 }
101
102 return (0);
103 }
104
105 void
106 hpibattach(hc)
107 struct hp_ctlr *hc;
108 {
109 struct hpib_softc *hs = &hpib_softc[hc->hp_unit];
110
111 /*
112 * Call the appropriate "attach" routine for this controller.
113 * The type is set in the "type" routine.
114 *
115 * XXX This is, by the way, exactly backwards.
116 */
117 switch (hs->sc_type) {
118 case HPIBA:
119 case HPIBB:
120 nhpibattach(hc);
121 break;
122
123 case HPIBC:
124 fhpibattach(hc);
125 break;
126
127 default:
128 panic("hpibattach: unknown type 0x%x", hs->sc_type);
129 /* NOTREACHED */
130 }
131
132 hs->sc_hc = hc;
133 hs->sc_dq.dq_unit = hc->hp_unit;
134 hs->sc_dq.dq_driver = &hpibdriver;
135 hs->sc_sq.dq_forw = hs->sc_sq.dq_back = &hs->sc_sq;
136
137 /* Establish the interrupt handler. */
138 (void) isrlink(hpibintr, hs, hc->hp_ipl, ISRPRI_BIO);
139 dmacomputeipl();
140
141 /* Reset the controller, display what we've seen, and we're done. */
142 hpibreset(hc->hp_unit);
143 printf(": %s\n", hs->sc_descrip);
144 }
145
146 void
147 hpibreset(unit)
148 register int unit;
149 {
150
151 (hpib_softc[unit].sc_controller->hpib_reset)(unit);
152 }
153
154 int
155 hpibreq(dq)
156 register struct devqueue *dq;
157 {
158 register struct devqueue *hq;
159
160 hq = &hpib_softc[dq->dq_ctlr].sc_sq;
161 insque(dq, hq->dq_back);
162 if (dq->dq_back == hq)
163 return(1);
164 return(0);
165 }
166
167 void
168 hpibfree(dq)
169 register struct devqueue *dq;
170 {
171 register struct devqueue *hq;
172
173 hq = &hpib_softc[dq->dq_ctlr].sc_sq;
174 remque(dq);
175 if ((dq = hq->dq_forw) != hq)
176 (dq->dq_driver->d_start)(dq->dq_unit);
177 }
178
179 int
180 hpibid(unit, slave)
181 int unit, slave;
182 {
183 short id;
184 int ohpibtimeout;
185
186 /*
187 * XXX shorten timeout value so autoconfig doesn't
188 * take forever on slow CPUs.
189 */
190 ohpibtimeout = hpibtimeout;
191 hpibtimeout = hpibidtimeout * (cpuspeed / 8);
192 if (hpibrecv(unit, 31, slave, &id, 2) != 2)
193 id = 0;
194 hpibtimeout = ohpibtimeout;
195 return(id);
196 }
197
198 int
199 hpibsend(unit, slave, sec, addr, cnt)
200 int unit, slave, sec, cnt;
201 void *addr;
202 {
203
204 return ((hpib_softc[unit].sc_controller->hpib_send)(unit, slave,
205 sec, addr, cnt));
206 }
207
208 int
209 hpibrecv(unit, slave, sec, addr, cnt)
210 int unit, slave, sec, cnt;
211 void *addr;
212 {
213
214 return ((hpib_softc[unit].sc_controller->hpib_recv)(unit, slave,
215 sec, addr, cnt));
216 }
217
218 int
219 hpibpptest(unit, slave)
220 register int unit;
221 int slave;
222 {
223
224 return ((hpib_softc[unit].sc_controller->hpib_ppoll)(unit) &
225 (0x80 >> slave));
226 }
227
228 void
229 hpibppclear(unit)
230 int unit;
231 {
232 hpib_softc[unit].sc_flags &= ~HPIBF_PPOLL;
233 }
234
235 hpibawait(unit)
236 int unit;
237 {
238 register struct hpib_softc *hs = &hpib_softc[unit];
239
240 hs->sc_flags |= HPIBF_PPOLL;
241 (hs->sc_controller->hpib_ppwatch)((void *)unit);
242 }
243
244 int
245 hpibswait(unit, slave)
246 register int unit;
247 int slave;
248 {
249 register int timo = hpibtimeout;
250 register int mask, (*ppoll) __P((int));
251
252 ppoll = hpib_softc[unit].sc_controller->hpib_ppoll;
253 mask = 0x80 >> slave;
254 while (((ppoll)(unit) & mask) == 0)
255 if (--timo == 0) {
256 printf("%s: swait timeout\n",
257 hpib_softc[unit].sc_hc->hp_xname);
258 return(-1);
259 }
260 return(0);
261 }
262
263 int
264 hpibustart(unit)
265 int unit;
266 {
267 register struct hpib_softc *hs = &hpib_softc[unit];
268
269 if (hs->sc_type == HPIBA)
270 hs->sc_dq.dq_ctlr = DMA0;
271 else
272 hs->sc_dq.dq_ctlr = DMA0 | DMA1;
273 if (dmareq(&hs->sc_dq))
274 return(1);
275 return(0);
276 }
277
278 void
279 hpibstart(unit)
280 int unit;
281 {
282 register struct devqueue *dq;
283
284 dq = hpib_softc[unit].sc_sq.dq_forw;
285 (dq->dq_driver->d_go)(dq->dq_unit);
286 }
287
288 void
289 hpibgo(unit, slave, sec, addr, count, rw, timo)
290 int unit, slave, sec, count, rw, timo;
291 void *addr;
292 {
293
294 (hpib_softc[unit].sc_controller->hpib_go)(unit, slave, sec,
295 addr, count, rw, timo);
296 }
297
298 void
299 hpibdone(unit)
300 register int unit;
301 {
302
303 (hpib_softc[unit].sc_controller->hpib_done)(unit);
304 }
305
306 int
307 hpibintr(arg)
308 void *arg;
309 {
310 struct hpib_softc *hs = arg;
311
312 return ((hs->sc_controller->hpib_intr)(arg));
313 }
314 #endif /* NHPIB > 0 */
315