This source file includes following definitions.
- xboxmatch
- xboxattach
- xbox_fix_range
- xboxprint
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 #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 <machine/bus.h>
44 #include <machine/cpu.h>
45 #include <dev/sbus/sbusvar.h>
46
47 #include <dev/sbus/xboxreg.h>
48 #include <dev/sbus/xboxvar.h>
49
50 int xboxmatch(struct device *, void *, void *);
51 void xboxattach(struct device *, struct device *, void *);
52 int xboxprint(void *, const char *);
53 int xbox_fix_range(struct xbox_softc *sc, struct sbus_softc *sbp);
54
55 struct cfattach xbox_ca = {
56 sizeof (struct xbox_softc), xboxmatch, xboxattach
57 };
58
59 struct cfdriver xbox_cd = {
60 NULL, "xbox", DV_DULL
61 };
62
63 int
64 xboxmatch(struct device *parent, void *cf, void *aux)
65 {
66 struct sbus_attach_args *sa = aux;
67
68 if (strcmp("SUNW,xbox", sa->sa_name))
69 return (0);
70
71 return (1);
72 }
73
74 void
75 xboxattach(struct device *parent, struct device *self, void *aux)
76 {
77 struct xbox_softc *sc = (struct xbox_softc *)self;
78 struct sbus_attach_args *sa = aux;
79 int node = sa->sa_node;
80 struct xbox_attach_args xa;
81 bus_space_handle_t write0;
82 char *s;
83
84 s = getpropstring(node, "model");
85 printf(": model %s", s);
86
87 s = getpropstring(node, "child-present");
88 if (strcmp(s, "false") == 0) {
89 printf(": no devices\n");
90 return;
91 }
92
93 sc->sc_key = getpropint(node, "write0-key", -1);
94 sc->sc_node = node;
95
96
97
98
99
100 if (sbus_bus_map(sa->sa_bustag, sa->sa_reg[0].sbr_slot,
101 sa->sa_reg[0].sbr_offset, sa->sa_reg[0].sbr_size, 0, 0,
102 &write0) != 0) {
103 printf(": couldn't map write 0 register\n");
104 return;
105 }
106
107 bus_space_write_4(sa->sa_bustag, write0, 0,
108 (sc->sc_key << 24) | XAC_CTL1_OFFSET |
109 XBOX_CTL1_CSIE | XBOX_CTL1_TRANSPARENT);
110 bus_space_write_4(sa->sa_bustag, write0, 0,
111 (sc->sc_key << 24) | XBC_CTL1_OFFSET |
112 XBOX_CTL1_XSIE | XBOX_CTL1_XSBRE | XBOX_CTL1_XSSE);
113 DELAY(100);
114
115 bus_space_unmap(sa->sa_bustag, write0, sa->sa_reg[0].sbr_size);
116
117 printf("\n");
118
119 if (xbox_fix_range(sc, (struct sbus_softc *)parent) != 0)
120 return;
121
122 bzero(&xa, sizeof xa);
123 xa.xa_name = "sbus";
124 xa.xa_node = node;
125 xa.xa_bustag = sa->sa_bustag;
126 xa.xa_dmatag = sa->sa_dmatag;
127
128 (void)config_found(&sc->sc_dev, (void *)&xa, xboxprint);
129 }
130
131
132
133
134 int
135 xbox_fix_range(struct xbox_softc *sc, struct sbus_softc *sbp)
136 {
137 int error, i, j;
138
139 error = getprop(sc->sc_node, "ranges", sizeof(struct sbus_range),
140 &sc->sc_nrange, (void **)&sc->sc_range);
141 if (error != 0) {
142 printf("%s: PROM ranges too large\n", sc->sc_dev.dv_xname);
143 return (error);
144 }
145
146 for (i = 0; i < sc->sc_nrange; i++) {
147 for (j = 0; j < sbp->sc_nrange; j++) {
148 if (sc->sc_range[i].pspace == sbp->sc_range[j].cspace) {
149 sc->sc_range[i].poffset +=
150 sbp->sc_range[j].poffset;
151 sc->sc_range[i].pspace =
152 sbp->sc_range[j].pspace;
153 break;
154 }
155 }
156 }
157
158 return (0);
159 }
160
161 int
162 xboxprint(void *args, const char *bus)
163 {
164 struct xbox_attach_args *xa = args;
165
166 if (bus != NULL)
167 printf("%s at %s", xa->xa_name, bus);
168 return (UNCONF);
169 }