Annotation of sys/arch/sparc/dev/xbox.c, Revision 1.1.1.1
1.1 nbrk 1: /* $OpenBSD: xbox.c,v 1.5 2006/06/02 20:00:54 miod Exp $ */
2:
3: /*
4: * Copyright (c) 1999 Jason L. Wright (jason@thought.net)
5: * 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: *
16: * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17: * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18: * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19: * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
20: * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21: * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
22: * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
24: * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
25: * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26: * POSSIBILITY OF SUCH DAMAGE.
27: */
28:
29: /*
30: * Driver for the Sun SBus Expansion Subsystem
31: */
32:
33: #include <sys/param.h>
34: #include <sys/systm.h>
35: #include <sys/kernel.h>
36: #include <sys/errno.h>
37: #include <sys/ioctl.h>
38: #include <sys/syslog.h>
39: #include <sys/device.h>
40: #include <sys/malloc.h>
41:
42: #include <machine/autoconf.h>
43: #include <sparc/cpu.h>
44: #include <sparc/sparc/cpuvar.h>
45: #include <sparc/dev/sbusvar.h>
46: #include <sparc/dev/dmareg.h> /* for SBUS_BURST_* */
47:
48: #include <sparc/dev/xboxreg.h>
49: #include <sparc/dev/xboxvar.h>
50:
51: int xboxmatch(struct device *, void *, void *);
52: void xboxattach(struct device *, struct device *, void *);
53: int xboxprint(void *, const char *);
54: void xbox_fix_range(struct xbox_softc *sc, struct sbus_softc *sbp);
55:
56: struct cfattach xbox_ca = {
57: sizeof (struct xbox_softc), xboxmatch, xboxattach
58: };
59:
60: struct cfdriver xbox_cd = {
61: NULL, "xbox", DV_DULL
62: };
63:
64: int
65: xboxmatch(parent, vcf, aux)
66: struct device *parent;
67: void *vcf, *aux;
68: {
69: struct confargs *ca = aux;
70: register struct romaux *ra = &ca->ca_ra;
71:
72: if (strcmp("SUNW,xbox", ra->ra_name))
73: return (0);
74:
75: if (!sbus_testdma((struct sbus_softc *)parent, ca))
76: return(0);
77: return (1);
78: }
79:
80: void
81: xboxattach(parent, self, aux)
82: struct device *parent, *self;
83: void *aux;
84: {
85: struct xbox_softc *sc = (struct xbox_softc *)self;
86: struct confargs *ca = aux;
87: struct romaux *ra = &ca->ca_ra;
88: int node = ca->ca_ra.ra_node;
89: struct confargs oca;
90: char *s;
91:
92: s = getpropstring(node, "model");
93: printf(": model %s", s);
94:
95: s = getpropstring(node, "child-present");
96: if (strcmp(s, "false") == 0) {
97: printf(": no devices\n");
98: return;
99: }
100:
101: sc->sc_regs.xa_write0 = mapiodev(&ca->ca_ra.ra_reg[0], 0,
102: sizeof(*sc->sc_regs.xa_write0));
103: sc->sc_regs.xa_errs = mapiodev(&ca->ca_ra.ra_reg[1], 0,
104: sizeof(*sc->sc_regs.xa_errs));
105: sc->sc_regs.xa_ctl0 = mapiodev(&ca->ca_ra.ra_reg[2], 0,
106: sizeof(*sc->sc_regs.xa_ctl0));
107: sc->sc_regs.xa_ctl1 = mapiodev(&ca->ca_ra.ra_reg[3], 0,
108: sizeof(*sc->sc_regs.xa_ctl1));
109: sc->sc_regs.xa_elua = mapiodev(&ca->ca_ra.ra_reg[4], 0,
110: sizeof(*sc->sc_regs.xa_elua));
111: sc->sc_regs.xa_ella = mapiodev(&ca->ca_ra.ra_reg[5], 0,
112: sizeof(*sc->sc_regs.xa_ella));
113: sc->sc_regs.xa_rsrv = mapiodev(&ca->ca_ra.ra_reg[6], 0,
114: sizeof(*sc->sc_regs.xa_rsrv));
115: sc->sc_regs.xb_errs = mapiodev(&ca->ca_ra.ra_reg[7], 0,
116: sizeof(*sc->sc_regs.xb_errs));
117: sc->sc_regs.xb_ctl0 = mapiodev(&ca->ca_ra.ra_reg[8], 0,
118: sizeof(*sc->sc_regs.xb_ctl0));
119: sc->sc_regs.xb_ctl1 = mapiodev(&ca->ca_ra.ra_reg[9], 0,
120: sizeof(*sc->sc_regs.xb_ctl1));
121: sc->sc_regs.xb_elua = mapiodev(&ca->ca_ra.ra_reg[10], 0,
122: sizeof(*sc->sc_regs.xb_elua));
123: sc->sc_regs.xb_ella = mapiodev(&ca->ca_ra.ra_reg[11], 0,
124: sizeof(*sc->sc_regs.xb_ella));
125: sc->sc_regs.xb_rsrv = mapiodev(&ca->ca_ra.ra_reg[12], 0,
126: sizeof(*sc->sc_regs.xb_rsrv));
127:
128: if (ra->ra_bp != NULL && strcmp(ra->ra_bp->name, "SUNW,xbox") == 0)
129: oca.ca_ra.ra_bp = ca->ca_ra.ra_bp + 1;
130: else
131: oca.ca_ra.ra_bp = NULL;
132:
133: sc->sc_key = getpropint(node, "write0-key", -1);
134: sc->sc_node = node;
135:
136: *sc->sc_regs.xa_write0 = (sc->sc_key << 24) | XAC_CTL1_OFFSET |
137: XBOX_CTL1_CSIE | XBOX_CTL1_TRANSPARENT;
138: *sc->sc_regs.xa_write0 = (sc->sc_key << 24) | XBC_CTL1_OFFSET |
139: XBOX_CTL1_XSIE | XBOX_CTL1_XSBRE | XBOX_CTL1_XSSE;
140: DELAY(100);
141:
142: xbox_fix_range(sc, (struct sbus_softc *)parent);
143:
144: printf("\n");
145:
146: oca = (*ca);
147: oca.ca_bustype = BUS_XBOX;
148: if (ca->ca_ra.ra_bp != NULL)
149: oca.ca_ra.ra_bp = ca->ca_ra.ra_bp + 1;
150: else
151: oca.ca_ra.ra_bp = NULL;
152:
153: (void)config_found(&sc->sc_dv, (void *)&oca, xboxprint);
154: }
155:
156: /*
157: * Fix up our address ranges based on parent address spaces.
158: */
159: void
160: xbox_fix_range(sc, sbp)
161: struct xbox_softc *sc;
162: struct sbus_softc *sbp;
163: {
164: int rlen, i, j;
165:
166: rlen = getproplen(sc->sc_node, "ranges");
167: sc->sc_range =
168: (struct rom_range *)malloc(rlen, M_DEVBUF, M_NOWAIT);
169: if (sc->sc_range == NULL) {
170: printf("%s: PROM ranges too large: %d\n",
171: sc->sc_dv.dv_xname, rlen);
172: return;
173: }
174: sc->sc_nrange = rlen / sizeof(struct rom_range);
175: (void)getprop(sc->sc_node, "ranges", sc->sc_range, rlen);
176:
177: for (i = 0; i < sc->sc_nrange; i++) {
178: for (j = 0; j < sbp->sc_nrange; j++) {
179: if (sc->sc_range[i].pspace == sbp->sc_range[j].cspace) {
180: sc->sc_range[i].poffset +=
181: sbp->sc_range[j].poffset;
182: sc->sc_range[i].pspace =
183: sbp->sc_range[j].pspace;
184: break;
185: }
186: }
187: }
188: }
189:
190: int
191: xboxprint(args, sbus)
192: void *args;
193: const char *sbus;
194: {
195: struct confargs *ca = args;
196:
197: if (sbus)
198: printf("%s at %s", ca->ca_ra.ra_name, sbus);
199: return (UNCONF);
200: }
CVSweb