Annotation of src/sys/dev/isa/isic_isa_tel_s08.c, Revision 1.2
1.1 martin 1: /*
2: * Copyright (c) 1996 Arne Helme. All rights reserved.
3: *
4: * Copyright (c) 1996 Gary Jennejohn. All rights reserved.
5: *
6: * Copyright (c) 1997, 1999 Hellmuth Michaelis. All rights reserved.
7: *
8: * Redistribution and use in source and binary forms, with or without
9: * modification, are permitted provided that the following conditions
10: * are met:
11: *
12: * 1. Redistributions of source code must retain the above copyright
13: * notice, this list of conditions and the following disclaimer.
14: * 2. Redistributions in binary form must reproduce the above copyright
15: * notice, this list of conditions and the following disclaimer in the
16: * documentation and/or other materials provided with the distribution.
17: * 3. Neither the name of the author nor the names of any co-contributors
18: * may be used to endorse or promote products derived from this software
19: * without specific prior written permission.
20: * 4. Altered versions must be plainly marked as such, and must not be
21: * misrepresented as being the original software and/or documentation.
22: *
23: * THIS SOFTWARE IS PROVIDED BY THE AUTHOR 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 AUTHOR 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: *---------------------------------------------------------------------------
36: *
37: * isic - I4B Siemens ISDN Chipset Driver for Teles S0/8 and clones
38: * ================================================================
39: *
1.2 ! martin 40: * $Id: isic_isa_tel_s08.c,v 1.1 2001/02/18 13:54:34 martin Exp $
1.1 martin 41: *
42: * last edit-date: [Fri Jan 5 11:37:22 2001]
43: *
44: * -hm clean up
45: * -hm more cleanup
46: * -hm NetBSD patches from Martin
47: * -hm making it finally work (checked with board revision 1.2)
48: * -hm converting asm -> C
49: *
50: *---------------------------------------------------------------------------*/
51:
52: #include "opt_isicisa.h"
53: #ifdef ISICISA_TEL_S0_8
54:
55: #include <sys/param.h>
56: #if defined(__FreeBSD__) && __FreeBSD__ >= 3
57: #include <sys/ioccom.h>
58: #else
59: #include <sys/ioctl.h>
60: #endif
61: #include <sys/kernel.h>
62: #include <sys/systm.h>
63: #include <sys/mbuf.h>
64:
65: #if defined(__NetBSD__) && __NetBSD_Version__ >= 104230000
66: #include <sys/callout.h>
67: #endif
68:
69: #ifdef __FreeBSD__
70: #include <machine/clock.h>
71: #include <machine/md_var.h>
72: #include <i386/isa/isa_device.h>
73: #else
74: #include <machine/bus.h>
75: #include <sys/device.h>
76: #endif
77:
78: #include <sys/socket.h>
79: #include <net/if.h>
80:
81: #ifdef __FreeBSD__
82: #include <machine/i4b_debug.h>
83: #include <machine/i4b_ioctl.h>
84: #else
85: #include <netisdn/i4b_debug.h>
86: #include <netisdn/i4b_ioctl.h>
87: #endif
88:
1.2 ! martin 89: #include <dev/ic/isic_l1.h>
! 90: #include <dev/ic/isac.h>
! 91: #include <dev/ic/hscx.h>
1.1 martin 92:
93: #include <netisdn/i4b_global.h>
94: #include <netisdn/i4b_l1l2.h>
95: #include <netisdn/i4b_mbuf.h>
96:
97: #ifndef __FreeBSD__
98: static u_int8_t tels08_read_reg __P((struct l1_softc *sc, int what, bus_size_t offs));
99: static void tels08_write_reg __P((struct l1_softc *sc, int what, bus_size_t offs, u_int8_t data));
100: static void tels08_write_fifo __P((struct l1_softc *sc, int what, const void *data, size_t size));
101: static void tels08_read_fifo __P((struct l1_softc *sc, int what, void *buf, size_t size));
102: #endif
103:
104: /*---------------------------------------------------------------------------*
105: * Teles S0/8 write register routine
106: *---------------------------------------------------------------------------*/
107: #ifdef __FreeBSD__
108:
109: static void
110: tels08_write_reg(u_char *base, u_int i, u_int v)
111: {
112: if(i & 0x01)
113: i |= 0x200;
114: base[i] = v;
115: }
116:
117: #else
118:
119: static const bus_size_t offset[] = { 0x100, 0x180, 0x1c0 };
120:
121: static void
122: tels08_write_reg(struct l1_softc *sc, int what, bus_size_t offs, u_int8_t data)
123: {
124: bus_space_tag_t t = sc->sc_maps[0].t;
125: bus_space_handle_t h = sc->sc_maps[0].h;
126:
127: offs += offset[what];
128:
129: if (offs & 0x01)
130: offs |= 0x200;
131:
132: bus_space_write_1(t, h, offs, data);
133: }
134: #endif
135:
136: /*---------------------------------------------------------------------------*
137: * Teles S0/8 read register routine
138: *---------------------------------------------------------------------------*/
139: #ifdef __FreeBSD__
140:
141: static u_char
142: tels08_read_reg(u_char *base, u_int i)
143: {
144: if(i & 0x1)
145: i |= 0x200;
146: return(base[i]);
147: }
148:
149: #else
150:
151: static u_int8_t
152: tels08_read_reg(struct l1_softc *sc, int what, bus_size_t offs)
153: {
154: bus_space_tag_t t = sc->sc_maps[0].t;
155: bus_space_handle_t h = sc->sc_maps[0].h;
156:
157: offs += offset[what];
158:
159: if (offs & 0x01)
160: offs |= 0x200;
161:
162: return bus_space_read_1(t, h, offs);
163: }
164: #endif
165:
166: /*---------------------------------------------------------------------------*
167: * Teles S0/8 fifo read/write access
168: *---------------------------------------------------------------------------*/
169: #ifdef __FreeBSD__
170:
171: static void
172: tels08_memcpyb(void *to, const void *from, size_t len)
173: {
174: for(;len > 0; len--)
175: *((unsigned char *)to)++ = *((unsigned char *)from)++;
176: }
177:
178: #else
179:
180: static void
181: tels08_write_fifo(struct l1_softc *sc, int what, const void *data, size_t size)
182: {
183: bus_space_tag_t t = sc->sc_maps[0].t;
184: bus_space_handle_t h = sc->sc_maps[0].h;
185: bus_space_write_region_1(t, h, offset[what], data, size);
186: }
187:
188: static void
189: tels08_read_fifo(struct l1_softc *sc, int what, void *buf, size_t size)
190: {
191: bus_space_tag_t t = sc->sc_maps[0].t;
192: bus_space_handle_t h = sc->sc_maps[0].h;
193: bus_space_read_region_1(t, h, offset[what], buf, size);
194: }
195: #endif
196:
197: /*---------------------------------------------------------------------------*
198: * isic_probe_s08 - probe for Teles S0/8 and compatibles
199: *---------------------------------------------------------------------------*/
200: #ifdef __FreeBSD__
201:
202: int
203: isic_probe_s08(struct isa_device *dev)
204: {
205: struct l1_softc *sc = &l1_sc[dev->id_unit];
206:
207: /* check max unit range */
208:
209: if(dev->id_unit >= ISIC_MAXUNIT)
210: {
211: printf("isic%d: Error, unit %d >= ISIC_MAXUNIT for Teles S0/8!\n",
212: dev->id_unit, dev->id_unit);
213: return(0);
214: }
215: sc->sc_unit = dev->id_unit;
216:
217: /* check IRQ validity */
218:
219: switch(ffs(dev->id_irq)-1)
220: {
221: case 2:
222: case 9: /* XXX */
223: case 3:
224: case 4:
225: case 5:
226: case 6:
227: case 7:
228: break;
229:
230: default:
231: printf("isic%d: Error, invalid IRQ [%d] specified for Teles S0/8!\n",
232: dev->id_unit, ffs(dev->id_irq)-1);
233: return(0);
234: break;
235: }
236: sc->sc_irq = dev->id_irq;
237:
238: /* check if we got an iobase */
239:
240: if(dev->id_iobase > 0)
241: {
242: printf("isic%d: Error, iobase specified for Teles S0/8!\n",
243: dev->id_unit);
244: return(0);
245: }
246:
247: /* check if inside memory range of 0xA0000 .. 0xDF000 */
248:
249: if( (kvtop(dev->id_maddr) < 0xa0000) ||
250: (kvtop(dev->id_maddr) > 0xdf000) )
251: {
252: printf("isic%d: Error, mem addr 0x%lx outside 0xA0000-0xDF000 for Teles S0/8!\n",
253: dev->id_unit, kvtop(dev->id_maddr));
254: return(0);
255: }
256:
257: sc->sc_vmem_addr = (caddr_t) dev->id_maddr;
258: dev->id_msize = 0x1000;
259:
260: /* setup ISAC access routines */
261:
262: sc->clearirq = NULL;
263: sc->readreg = tels08_read_reg;
264: sc->writereg = tels08_write_reg;
265:
266: sc->readfifo = tels08_memcpyb;
267: sc->writefifo = tels08_memcpyb;
268:
269: /* setup card type */
270:
271: sc->sc_cardtyp = CARD_TYPEP_8;
272:
273: /* setup IOM bus type */
274:
275: sc->sc_bustyp = BUS_TYPE_IOM1;
276:
277: sc->sc_ipac = 0;
278: sc->sc_bfifolen = HSCX_FIFO_LEN;
279:
280: /* setup ISAC base addr */
281:
282: ISAC_BASE = (caddr_t)((dev->id_maddr) + 0x100);
283:
284: /* setup HSCX base addr */
285:
286: HSCX_A_BASE = (caddr_t)((dev->id_maddr) + 0x180);
287: HSCX_B_BASE = (caddr_t)((dev->id_maddr) + 0x1c0);
288:
289: return (1);
290: }
291:
292: #else
293:
294: int
295: isic_probe_s08(struct isic_attach_args *ia)
296: {
297: /* no real sensible probe is easy - write to fifo memory
298: and read back to verify there is memory doesn't work,
299: because you talk to tx fifo and rcv fifo. So, just check
300: HSCX version, which at least fails if no card present
301: at the given location. */
302: bus_space_tag_t t = ia->ia_maps[0].t;
303: bus_space_handle_t h = ia->ia_maps[0].h;
304: u_int8_t v1, v2;
305:
306: /* HSCX A VSTR */
307: v1 = bus_space_read_1(t, h, offset[1] + H_VSTR) & 0x0f;
308: if (v1 != HSCX_VA1 && v1 != HSCX_VA2 && v1 != HSCX_VA3 && v1 != HSCX_V21)
309: return 0;
310:
311: /* HSCX B VSTR */
312: v2 = bus_space_read_1(t, h, offset[2] + H_VSTR) & 0x0f;
313: if (v2 != HSCX_VA1 && v2 != HSCX_VA2 && v2 != HSCX_VA3 && v2 != HSCX_V21)
314: return 0;
315:
316: /* both HSCX channels should have the same version... */
317: if (v1 != v2)
318: return 0;
319:
320: return 1;
321: }
322: #endif
323:
324: /*---------------------------------------------------------------------------*
325: * isic_attach_s08 - attach Teles S0/8 and compatibles
326: *---------------------------------------------------------------------------*/
327: int
328: #ifdef __FreeBSD__
329: isic_attach_s08(struct isa_device *dev)
330: #else
331: isic_attach_s08(struct l1_softc *sc)
332: #endif
333: {
334: #ifdef __FreeBSD__
335: struct l1_softc *sc = &l1_sc[dev->id_unit];
336: #else
337: bus_space_tag_t t = sc->sc_maps[0].t;
338: bus_space_handle_t h = sc->sc_maps[0].h;
339: #endif
340:
341: /* set card off */
342:
343: #ifdef __FreeBSD__
344: sc->sc_vmem_addr[0x80] = 0;
345: #else
346: bus_space_write_1(t, h, 0x80, 0);
347: #endif
348:
349: DELAY(SEC_DELAY / 5);
350:
351: /* set card on */
352:
353: #ifdef __FreeBSD__
354: sc->sc_vmem_addr[0x80] = 1;
355: #else
356: bus_space_write_1(t, h, 0x80, 1);
357: #endif
358:
359: DELAY(SEC_DELAY / 5);
360:
361: #ifndef __FreeBSD__
362:
363: /* setup ISAC access routines */
364:
365: sc->clearirq = NULL;
366: sc->readreg = tels08_read_reg;
367: sc->writereg = tels08_write_reg;
368: sc->readfifo = tels08_read_fifo;
369: sc->writefifo = tels08_write_fifo;
370:
371: /* setup card type */
372:
373: sc->sc_cardtyp = CARD_TYPEP_8;
374:
375: /* setup IOM bus type */
376:
377: sc->sc_bustyp = BUS_TYPE_IOM1;
378:
379: sc->sc_ipac = 0;
380: sc->sc_bfifolen = HSCX_FIFO_LEN;
381:
382: #endif
383:
384: return (1);
385: }
386:
387: #endif /* ISICISA_TEL_S0_8 */
388:
CVSweb <webmaster@jp.NetBSD.org>