fhpib.c revision 1.3 1 /* $NetBSD: fhpib.c,v 1.3 2003/11/14 16:52:40 tsutsui 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. Neither the name of the University nor the names of its contributors
16 * may be used to endorse or promote products derived from this software
17 * without specific prior written permission.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
20 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
23 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
24 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
25 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
26 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
27 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
28 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
29 * SUCH DAMAGE.
30 *
31 * @(#)fhpib.c 8.1 (Berkeley) 6/10/93
32 */
33
34 /*
35 * 98625A/B HPIB driver
36 */
37
38 #include <sys/param.h>
39
40 #include <hp300/dev/fhpibreg.h>
41
42 #include <hp300/stand/common/hpibvar.h>
43 #include <hp300/stand/common/samachdep.h>
44
45 static int fhpibwait(struct fhpibdevice *, uint8_t);
46
47 int
48 fhpibinit(unit)
49 int unit;
50 {
51 struct hpib_softc *hs = &hpib_softc[unit];
52 struct fhpibdevice *hd = (void *)hs->sc_addr;
53
54 if (hd->hpib_cid != HPIBC)
55 return 0;
56 hs->sc_type = HPIBC;
57 hs->sc_ba = HPIBC_BA;
58 fhpibreset(unit);
59 return 1;
60 }
61
62 void
63 fhpibreset(unit)
64 {
65 struct hpib_softc *hs = &hpib_softc[unit];
66 struct fhpibdevice *hd;
67
68 hd = (void *)hs->sc_addr;
69 hd->hpib_cid = 0xFF;
70 DELAY(100);
71 hd->hpib_cmd = CT_8BIT;
72 hd->hpib_ar = AR_ARONC;
73 hd->hpib_cmd |= CT_IFC;
74 hd->hpib_cmd |= CT_INITFIFO;
75 DELAY(100);
76 hd->hpib_cmd &= ~CT_IFC;
77 hd->hpib_cmd |= CT_REN;
78 hd->hpib_stat = ST_ATN;
79 hd->hpib_data = C_DCL;
80 DELAY(100000);
81 }
82
83 int
84 fhpibsend(unit, slave, sec, buf, cnt)
85 int unit, slave, sec;
86 char *buf;
87 int cnt;
88 {
89 struct hpib_softc *hs = &hpib_softc[unit];
90 struct fhpibdevice *hd;
91 int origcnt = cnt;
92
93 hd = (void *)hs->sc_addr;
94 hd->hpib_stat = 0;
95 hd->hpib_imask = IM_IDLE | IM_ROOM;
96 fhpibwait(hd, IM_IDLE);
97 hd->hpib_stat = ST_ATN;
98 hd->hpib_data = C_UNL;
99 hd->hpib_data = C_TAG + hs->sc_ba;
100 hd->hpib_data = C_LAG + slave;
101 if (sec != -1)
102 hd->hpib_data = C_SCG + sec;
103 fhpibwait(hd, IM_IDLE);
104 hd->hpib_stat = ST_WRITE;
105 if (cnt) {
106 while (--cnt) {
107 hd->hpib_data = *buf++;
108 if (fhpibwait(hd, IM_ROOM) < 0)
109 break;
110 }
111 hd->hpib_stat = ST_EOI;
112 hd->hpib_data = *buf;
113 if (fhpibwait(hd, IM_ROOM) < 0)
114 cnt++;
115 hd->hpib_stat = ST_ATN;
116 /* XXX: HP-UX claims bug with CS80 transparent messages */
117 if (sec == 0x12)
118 DELAY(150);
119 hd->hpib_data = C_UNL;
120 fhpibwait(hd, IM_IDLE);
121 }
122 hd->hpib_imask = 0;
123 return origcnt - cnt;
124 }
125
126 int
127 fhpibrecv(unit, slave, sec, buf, cnt)
128 int unit, slave, sec;
129 char *buf;
130 int cnt;
131 {
132 struct hpib_softc *hs = &hpib_softc[unit];
133 struct fhpibdevice *hd;
134 int origcnt = cnt;
135
136 hd = (void *)hs->sc_addr;
137 hd->hpib_stat = 0;
138 hd->hpib_imask = IM_IDLE | IM_ROOM | IM_BYTE;
139 fhpibwait(hd, IM_IDLE);
140 hd->hpib_stat = ST_ATN;
141 hd->hpib_data = C_UNL;
142 hd->hpib_data = C_LAG + hs->sc_ba;
143 hd->hpib_data = C_TAG + slave;
144 if (sec != -1)
145 hd->hpib_data = C_SCG + sec;
146 fhpibwait(hd, IM_IDLE);
147 hd->hpib_stat = ST_READ0;
148 hd->hpib_data = 0;
149 if (cnt) {
150 while (--cnt >= 0) {
151 if (fhpibwait(hd, IM_BYTE) < 0)
152 break;
153 *buf++ = hd->hpib_data;
154 }
155 cnt++;
156 fhpibwait(hd, IM_ROOM);
157 hd->hpib_stat = ST_ATN;
158 hd->hpib_data = (slave == 31) ? C_UNA : C_UNT;
159 fhpibwait(hd, IM_IDLE);
160 }
161 hd->hpib_imask = 0;
162 return origcnt - cnt;
163 }
164
165 int
166 fhpibppoll(unit)
167 int unit;
168 {
169 struct hpib_softc *hs = &hpib_softc[unit];
170 struct fhpibdevice *hd;
171 int ppoll;
172
173 hd = (void *)hs->sc_addr;
174 hd->hpib_stat = 0;
175 hd->hpib_psense = 0;
176 hd->hpib_pmask = 0xFF;
177 hd->hpib_imask = IM_PPRESP | IM_PABORT;
178 DELAY(25);
179 hd->hpib_intr = IM_PABORT;
180 ppoll = hd->hpib_data;
181 if (hd->hpib_intr & IM_PABORT)
182 ppoll = 0;
183 hd->hpib_imask = 0;
184 hd->hpib_pmask = 0;
185 hd->hpib_stat = ST_IENAB;
186 return ppoll;
187 }
188
189 static int
190 fhpibwait(hd, x)
191 struct fhpibdevice *hd;
192 uint8_t x;
193 {
194 int timo = 100000;
195
196 while ((hd->hpib_intr & x) == 0 && --timo)
197 ;
198 if (timo == 0)
199 return -1;
200 return 0;
201 }
202