1 /* $OpenBSD: dino.c,v 1.33 2022/03/13 08:04:38 mpi Exp $ */
2
3 /*
4 * Copyright (c) 2003-2005 Michael Shalayeff
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 WARRANTIES
18 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19 * IN NO EVENT SHALL THE AUTHOR OR HIS RELATIVES 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 MIND, 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
25 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
26 * THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
29 #include "cardbus.h"
30
31 #include <sys/param.h>
32 #include <sys/systm.h>
33 #include <sys/device.h>
34 #include <sys/reboot.h>
35 #include <sys/malloc.h>
36 #include <sys/extent.h>
37
38 #include <machine/iomod.h>
39 #include <machine/autoconf.h>
40
41 #include <hppa/dev/cpudevs.h>
42
43 #if NCARDBUS > 0
44 #include <dev/cardbus/rbus.h>
45 #endif
46
47 #include <dev/pci/pcireg.h>
48 #include <dev/pci/pcivar.h>
49 #include <dev/pci/pcidevs.h>
50
51 #include <machine/pdc.h>
52 #include <dev/cons.h>
53
54 #define DINO_MEM_CHUNK 0x800000
55 #define DINO_MEM_WINDOW (2 * DINO_MEM_CHUNK)
56
57 struct dino_regs {
58 u_int32_t pad0; /* 0x000 */
59 u_int32_t iar0; /* 0x004 rw intr addr reg 0 */
60 u_int32_t iodc; /* 0x008 rw iodc data/addr */
61 u_int32_t irr0; /* 0x00c r intr req reg 0 */
62 u_int32_t iar1; /* 0x010 rw intr addr reg 1 */
63 u_int32_t irr1; /* 0x014 r intr req reg 1 */
64 u_int32_t imr; /* 0x018 rw intr mask reg */
65 u_int32_t ipr; /* 0x01c rw intr pending reg */
66 u_int32_t toc_addr; /* 0x020 rw TOC addr reg */
67 u_int32_t icr; /* 0x024 rw intr control reg */
68 u_int32_t ilr; /* 0x028 r intr level reg */
69 u_int32_t pad1; /* 0x02c */
70 u_int32_t io_command; /* 0x030 w command register */
71 u_int32_t io_status; /* 0x034 r status register */
72 u_int32_t io_control; /* 0x038 rw control register */
73 u_int32_t pad2; /* 0x03c AUX registers follow */
74 u_int32_t io_gsc_err_addr;/* 0x040 GSC error address */
75 u_int32_t io_err_info; /* 0x044 error info register */
76 u_int32_t io_pci_err_addr;/* 0x048 PCI error address */
77 u_int32_t pad3[4]; /* 0x04c */
78 u_int32_t io_fbb_en; /* 0x05c fast back2back enable reg */
79 u_int32_t io_addr_en; /* 0x060 address enable reg */
80 u_int32_t pci_addr; /* 0x064 PCI conf/io/mem addr reg */
81 u_int32_t pci_conf_data; /* 0x068 PCI conf data reg */
82 u_int32_t pci_io_data; /* 0x06c PCI io data reg */
83 u_int32_t pci_mem_data; /* 0x070 PCI memory data reg */
84 u_int32_t pad4[0x740/4]; /* 0x074 */
85 u_int32_t gsc2x_config; /* 0x7b4 GSC2X config reg */
86 u_int32_t pad5[0x48/4]; /* 0x7b8: BSRS registers follow */
87 u_int32_t gmask; /* 0x800 GSC arbitration mask */
88 u_int32_t pamr; /* 0x804 PCI arbitration mask */
89 u_int32_t papr; /* 0x808 PCI arbitration priority */
90 u_int32_t damode; /* 0x80c PCI arbitration mode */
91 u_int32_t pcicmd; /* 0x810 PCI command register */
92 u_int32_t pcists; /* 0x814 PCI status register */
93 u_int32_t pad6; /* 0x818 */
94 u_int32_t mltim; /* 0x81c PCI master latency timer */
95 u_int32_t brdg_feat; /* 0x820 PCI bridge feature enable */
96 u_int32_t pciror; /* 0x824 PCI read optimization reg */
97 u_int32_t pciwor; /* 0x828 PCI write optimization reg */
98 u_int32_t pad7; /* 0x82c */
99 u_int32_t tltim; /* 0x830 PCI target latency reg */
100 };
101
102 struct dino_softc {
103 struct device sc_dv;
104
105 int sc_ver;
106 void *sc_ih;
107 u_int32_t sc_imr;
108 bus_space_tag_t sc_bt;
109 bus_space_handle_t sc_bh;
110 bus_dma_tag_t sc_dmat;
111 volatile struct dino_regs *sc_regs;
112
113 struct hppa_pci_chipset_tag sc_pc;
114 struct hppa_bus_space_tag sc_iot;
115 char sc_ioexname[20];
116 struct extent *sc_ioex;
117 struct hppa_bus_space_tag sc_memt;
118 char sc_memexname[20];
119 struct extent *sc_memex;
120 struct hppa_bus_dma_tag sc_dmatag;
121
122 u_int32_t io_shadow;
123 };
124
125 int dinomatch(struct device *, void *, void *);
126 void dinoattach(struct device *, struct device *, void *);
127 int dino_intr(void *);
128
129 const struct cfattach dino_ca = {
130 sizeof(struct dino_softc), dinomatch, dinoattach
131 };
132
133 struct cfdriver dino_cd = {
134 NULL, "dino", DV_DULL
135 };
136
137 int
dinomatch(parent,cfdata,aux)138 dinomatch(parent, cfdata, aux)
139 struct device *parent;
140 void *cfdata;
141 void *aux;
142 {
143 struct confargs *ca = aux;
144 /* struct cfdata *cf = cfdata; */
145
146 /* there will be only one */
147 if (ca->ca_type.iodc_type != HPPA_TYPE_BRIDGE ||
148 ca->ca_type.iodc_sv_model != HPPA_BRIDGE_DINO)
149 return (0);
150
151 /* do not match on the elroy family */
152 if (ca->ca_type.iodc_model == 0x78)
153 return (0);
154
155 return (1);
156 }
157
158 void dino_attach_hook(struct device *, struct device *,
159 struct pcibus_attach_args *);
160 int dino_maxdevs(void *, int);
161 pcitag_t dino_make_tag(void *, int, int, int);
162 void dino_decompose_tag(void *, pcitag_t, int *, int *, int *);
163 int dino_conf_size(void *, pcitag_t);
164 pcireg_t dino_conf_read(void *, pcitag_t, int);
165 void dino_conf_write(void *, pcitag_t, int, pcireg_t);
166 int dino_intr_map(struct pci_attach_args *, pci_intr_handle_t *);
167 const char *dino_intr_string(void *, pci_intr_handle_t);
168 void * dino_intr_establish(void *, pci_intr_handle_t, int, int (*)(void *),
169 void *, const char *);
170 void dino_intr_disestablish(void *, void *);
171 int dino_iomap(void *, bus_addr_t, bus_size_t, int, bus_space_handle_t *);
172 int dino_memmap(void *, bus_addr_t, bus_size_t, int, bus_space_handle_t *);
173 int dino_subregion(void *, bus_space_handle_t, bus_size_t, bus_size_t,
174 bus_space_handle_t *);
175 int dino_ioalloc(void *, bus_addr_t, bus_addr_t, bus_size_t, bus_size_t,
176 bus_size_t, int, bus_addr_t *, bus_space_handle_t *);
177 int dino_memalloc(void *, bus_addr_t, bus_addr_t, bus_size_t, bus_size_t,
178 bus_size_t, int, bus_addr_t *, bus_space_handle_t *);
179 void dino_unmap(void *, bus_space_handle_t, bus_size_t);
180 void dino_free(void *, bus_space_handle_t, bus_size_t);
181 void dino_barrier(void *, bus_space_handle_t, bus_size_t, bus_size_t, int);
182 void * dino_alloc_parent(struct device *, struct pci_attach_args *, int);
183 void * dino_vaddr(void *, bus_space_handle_t);
184 u_int8_t dino_r1(void *, bus_space_handle_t, bus_size_t);
185 u_int16_t dino_r2(void *, bus_space_handle_t, bus_size_t);
186 u_int32_t dino_r4(void *, bus_space_handle_t, bus_size_t);
187 u_int64_t dino_r8(void *, bus_space_handle_t, bus_size_t);
188 void dino_w1(void *, bus_space_handle_t, bus_size_t, u_int8_t);
189 void dino_w2(void *, bus_space_handle_t, bus_size_t, u_int16_t);
190 void dino_w4(void *, bus_space_handle_t, bus_size_t, u_int32_t);
191 void dino_w8(void *, bus_space_handle_t, bus_size_t, u_int64_t);
192 void dino_rm_1(void *, bus_space_handle_t, bus_size_t, u_int8_t *,
193 bus_size_t);
194 void dino_rm_2(void *, bus_space_handle_t, bus_size_t, u_int16_t *,
195 bus_size_t);
196 void dino_rm_4(void *, bus_space_handle_t, bus_size_t, u_int32_t *,
197 bus_size_t);
198 void dino_rm_8(void *, bus_space_handle_t, bus_size_t, u_int64_t *,
199 bus_size_t);
200 void dino_wm_1(void *, bus_space_handle_t, bus_size_t, const u_int8_t *,
201 bus_size_t);
202 void dino_wm_2(void *, bus_space_handle_t, bus_size_t, const u_int16_t *,
203 bus_size_t);
204 void dino_wm_4(void *, bus_space_handle_t, bus_size_t, const u_int32_t *,
205 bus_size_t);
206 void dino_wm_8(void *, bus_space_handle_t, bus_size_t, const u_int64_t *,
207 bus_size_t);
208 void dino_sm_1(void *, bus_space_handle_t, bus_size_t, u_int8_t, bus_size_t);
209 void dino_sm_2(void *, bus_space_handle_t, bus_size_t, u_int16_t,
210 bus_size_t);
211 void dino_sm_4(void *, bus_space_handle_t, bus_size_t, u_int32_t,
212 bus_size_t);
213 void dino_sm_8(void *, bus_space_handle_t, bus_size_t, u_int64_t,
214 bus_size_t);
215 void dino_rrm_2(void *, bus_space_handle_t, bus_size_t, u_int8_t *,
216 bus_size_t);
217 void dino_rrm_4(void *, bus_space_handle_t, bus_size_t, u_int8_t *,
218 bus_size_t);
219 void dino_rrm_8(void *, bus_space_handle_t, bus_size_t, u_int8_t *,
220 bus_size_t);
221 void dino_wrm_2(void *, bus_space_handle_t, bus_size_t, const u_int8_t *,
222 bus_size_t);
223 void dino_wrm_4(void *, bus_space_handle_t, bus_size_t, const u_int8_t *,
224 bus_size_t);
225 void dino_wrm_8(void *, bus_space_handle_t, bus_size_t, const u_int8_t *,
226 bus_size_t);
227 void dino_rr_1(void *, bus_space_handle_t, bus_size_t, u_int8_t *,
228 bus_size_t);
229 void dino_rr_2(void *, bus_space_handle_t, bus_size_t, u_int16_t *,
230 bus_size_t);
231 void dino_rr_4(void *, bus_space_handle_t, bus_size_t, u_int32_t *,
232 bus_size_t);
233 void dino_rr_8(void *, bus_space_handle_t, bus_size_t, u_int64_t *,
234 bus_size_t);
235 void dino_wr_1(void *, bus_space_handle_t, bus_size_t, const u_int8_t *,
236 bus_size_t);
237 void dino_wr_2(void *, bus_space_handle_t, bus_size_t, const u_int16_t *,
238 bus_size_t);
239 void dino_wr_4(void *, bus_space_handle_t, bus_size_t, const u_int32_t *,
240 bus_size_t);
241 void dino_wr_8(void *, bus_space_handle_t, bus_size_t, const u_int64_t *,
242 bus_size_t);
243 void dino_rrr_2(void *, bus_space_handle_t, bus_size_t, u_int8_t *,
244 bus_size_t);
245 void dino_rrr_4(void *, bus_space_handle_t, bus_size_t, u_int8_t *,
246 bus_size_t);
247 void dino_rrr_8(void *, bus_space_handle_t, bus_size_t, u_int8_t *,
248 bus_size_t);
249 void dino_wrr_2(void *, bus_space_handle_t, bus_size_t, const u_int8_t *,
250 bus_size_t);
251 void dino_wrr_4(void *, bus_space_handle_t, bus_size_t, const u_int8_t *,
252 bus_size_t);
253 void dino_wrr_8(void *, bus_space_handle_t, bus_size_t, const u_int8_t *,
254 bus_size_t);
255 void dino_sr_1(void *, bus_space_handle_t, bus_size_t, u_int8_t, bus_size_t);
256 void dino_sr_2(void *, bus_space_handle_t, bus_size_t, u_int16_t,
257 bus_size_t);
258 void dino_sr_4(void *, bus_space_handle_t, bus_size_t, u_int32_t,
259 bus_size_t);
260 void dino_sr_8(void *, bus_space_handle_t, bus_size_t, u_int64_t,
261 bus_size_t);
262 void dino_cp_1(void *, bus_space_handle_t, bus_size_t, bus_space_handle_t,
263 bus_size_t, bus_size_t);
264 void dino_cp_2(void *, bus_space_handle_t, bus_size_t, bus_space_handle_t,
265 bus_size_t, bus_size_t);
266 void dino_cp_4(void *, bus_space_handle_t, bus_size_t, bus_space_handle_t,
267 bus_size_t, bus_size_t);
268 void dino_cp_8(void *, bus_space_handle_t, bus_size_t, bus_space_handle_t,
269 bus_size_t, bus_size_t);
270 int dino_dmamap_create(void *, bus_size_t, int, bus_size_t, bus_size_t, int,
271 bus_dmamap_t *);
272 void dino_dmamap_destroy(void *, bus_dmamap_t);
273 int dino_dmamap_load(void *, bus_dmamap_t, void *, bus_size_t,
274 struct proc *, int);
275 int dino_dmamap_load_mbuf(void *, bus_dmamap_t, struct mbuf *, int);
276 int dino_dmamap_load_uio(void *, bus_dmamap_t, struct uio *, int);
277 int dino_dmamap_load_raw(void *, bus_dmamap_t, bus_dma_segment_t *, int,
278 bus_size_t, int);
279 void dino_dmamap_unload(void *, bus_dmamap_t);
280 void dino_dmamap_sync(void *, bus_dmamap_t, bus_addr_t, bus_size_t, int);
281 int dino_dmamem_alloc(void *, bus_size_t, bus_size_t, bus_size_t,
282 bus_dma_segment_t *, int, int *, int);
283 void dino_dmamem_free(void *, bus_dma_segment_t *, int);
284 int dino_dmamem_map(void *, bus_dma_segment_t *, int, size_t, caddr_t *,
285 int);
286 void dino_dmamem_unmap(void *, caddr_t, size_t);
287 paddr_t dino_dmamem_mmap(void *, bus_dma_segment_t *, int, off_t, int, int);
288 int dinoprint(void *, const char *);
289 void dino_clear_pdc_mappings(void *);
290
291 void
dino_attach_hook(struct device * parent,struct device * self,struct pcibus_attach_args * pba)292 dino_attach_hook(struct device *parent, struct device *self,
293 struct pcibus_attach_args *pba)
294 {
295
296 }
297
298 int
dino_maxdevs(void * v,int bus)299 dino_maxdevs(void *v, int bus)
300 {
301 return (32);
302 }
303
304 pcitag_t
dino_make_tag(void * v,int bus,int dev,int func)305 dino_make_tag(void *v, int bus, int dev, int func)
306 {
307 if (bus > 255 || dev > 31 || func > 7)
308 panic("dino_make_tag: bad request");
309
310 return ((bus << 16) | (dev << 11) | (func << 8));
311 }
312
313 void
dino_decompose_tag(void * v,pcitag_t tag,int * bus,int * dev,int * func)314 dino_decompose_tag(void *v, pcitag_t tag, int *bus, int *dev, int *func)
315 {
316 if (bus)
317 *bus = (tag >> 16) & 0xff;
318 if (dev)
319 *dev = (tag >> 11) & 0x1f;
320 if (func)
321 *func= (tag >> 8) & 0x07;
322 }
323
324 int
dino_conf_size(void * v,pcitag_t tag)325 dino_conf_size(void *v, pcitag_t tag)
326 {
327 return PCI_CONFIG_SPACE_SIZE;
328 }
329
330 pcireg_t
dino_conf_read(void * v,pcitag_t tag,int reg)331 dino_conf_read(void *v, pcitag_t tag, int reg)
332 {
333 struct dino_softc *sc = v;
334 volatile struct dino_regs *r = sc->sc_regs;
335 pcireg_t data;
336 u_int32_t pamr;
337
338 /* fix arbitration errata by disabling all pci devs on config read */
339 pamr = r->pamr;
340 r->pamr = 0;
341
342 r->pci_addr = tag | reg;
343 data = r->pci_conf_data;
344
345 /* restore arbitration */
346 r->pamr = pamr;
347
348 return (letoh32(data));
349 }
350
351 void
dino_conf_write(void * v,pcitag_t tag,int reg,pcireg_t data)352 dino_conf_write(void *v, pcitag_t tag, int reg, pcireg_t data)
353 {
354 struct dino_softc *sc = v;
355 volatile struct dino_regs *r = sc->sc_regs;
356 pcireg_t data1;
357 u_int32_t pamr;
358
359 /* fix arbitration errata by disabling all pci devs on config read */
360 pamr = r->pamr;
361 r->pamr = 0;
362
363 r->pci_addr = tag | reg;
364 r->pci_conf_data = htole32(data);
365
366 /* fix coalescing config and io writes by interleaving w/ a read */
367 r->pci_addr = tag | PCI_ID_REG;
368 data1 = r->pci_conf_data;
369
370 /* restore arbitration */
371 r->pamr = pamr;
372 }
373
374 int
dino_intr_map(struct pci_attach_args * pa,pci_intr_handle_t * ihp)375 dino_intr_map(struct pci_attach_args *pa, pci_intr_handle_t *ihp)
376 {
377 /* struct dino_softc *sc = v;
378 volatile struct dino_regs *r = sc->sc_regs; */
379 pci_chipset_tag_t pc = pa->pa_pc;
380 pcitag_t tag = pa->pa_tag;
381 pcireg_t reg;
382
383 reg = pci_conf_read(pc, tag, PCI_INTERRUPT_REG);
384
385 if (PCI_INTERRUPT_LINE(reg) == 0xff)
386 return (1);
387
388 *ihp = PCI_INTERRUPT_LINE(reg) + 1;
389 return (0);
390 }
391
392 const char *
dino_intr_string(void * v,pci_intr_handle_t ih)393 dino_intr_string(void *v, pci_intr_handle_t ih)
394 {
395 static char buf[32];
396
397 snprintf(buf, 32, "dino irq %ld", ih);
398
399 return (buf);
400 }
401
402 void *
dino_intr_establish(void * v,pci_intr_handle_t ih,int pri,int (* handler)(void *),void * arg,const char * name)403 dino_intr_establish(void *v, pci_intr_handle_t ih,
404 int pri, int (*handler)(void *), void *arg, const char *name)
405 {
406 struct dino_softc *sc = v;
407 volatile struct dino_regs *r = sc->sc_regs;
408 void *iv;
409
410 /* no mapping or bogus */
411 if (ih <= 0 || ih > 11)
412 return (NULL);
413
414 if ((iv = cpu_intr_map(sc->sc_ih, pri, ih - 1, handler, arg, name))) {
415 if (cold)
416 sc->sc_imr |= (1 << (ih - 1));
417 else
418 r->imr = sc->sc_imr |= (1 << (ih - 1));
419 }
420
421 return (iv);
422 }
423
424 void
dino_intr_disestablish(void * v,void * cookie)425 dino_intr_disestablish(void *v, void *cookie)
426 {
427 #if 0
428 struct dino_softc *sc = v;
429 volatile struct dino_regs *r = sc->sc_regs;
430
431 r->imr &= ~(1 << (ih - 1));
432
433 TODO cpu_intr_unmap(sc->sc_ih, cookie);
434 #endif
435 }
436
437 int
dino_iomap(void * v,bus_addr_t bpa,bus_size_t size,int flags,bus_space_handle_t * bshp)438 dino_iomap(void *v, bus_addr_t bpa, bus_size_t size,
439 int flags, bus_space_handle_t *bshp)
440 {
441 struct dino_softc *sc = v;
442 int error;
443
444 if ((error = extent_alloc_region(sc->sc_ioex, bpa, size, EX_NOWAIT)))
445 return (error);
446
447 if (bshp)
448 *bshp = bpa;
449
450 return (0);
451 }
452
453 int
dino_memmap(void * v,bus_addr_t bpa,bus_size_t size,int flags,bus_space_handle_t * bshp)454 dino_memmap(void *v, bus_addr_t bpa, bus_size_t size,
455 int flags, bus_space_handle_t *bshp)
456 {
457 struct dino_softc *sc = v;
458 volatile struct dino_regs *r = sc->sc_regs;
459 bus_addr_t sbpa;
460 bus_space_handle_t bush;
461 u_int32_t reg;
462 int first = 1;
463 int error;
464
465 while (size != 0) {
466 sbpa = bpa & 0xff800000;
467 reg = sc->io_shadow;
468 reg |= 1 << ((bpa >> 23) & 0x1f);
469 if (reg & 0x80000001) {
470 #ifdef DEBUG
471 panic("mapping outside the mem extent range");
472 #endif
473 return (EINVAL);
474 }
475 /* map into the upper bus space, if not yet mapped this 8M */
476 if (reg != sc->io_shadow) {
477
478 if ((error = bus_space_map(sc->sc_bt, sbpa,
479 DINO_MEM_CHUNK, flags, &bush))) {
480 return (error);
481 }
482 r->io_addr_en |= reg;
483 sc->io_shadow = reg;
484
485 if (first) {
486 if (bshp)
487 *bshp = bush + (bpa - sbpa);
488 }
489 } else {
490 if (first) {
491 if (bshp)
492 *bshp = bpa;
493 }
494 }
495
496 if (first) {
497 size += (bpa - sbpa);
498 first = 0;
499 }
500
501 if (size < DINO_MEM_CHUNK)
502 size = 0;
503 else {
504 size -= DINO_MEM_CHUNK;
505 bpa = sbpa + DINO_MEM_CHUNK;
506 }
507 }
508
509 return (0);
510 }
511
512 int
dino_subregion(void * v,bus_space_handle_t bsh,bus_size_t offset,bus_size_t size,bus_space_handle_t * nbshp)513 dino_subregion(void *v, bus_space_handle_t bsh, bus_size_t offset,
514 bus_size_t size, bus_space_handle_t *nbshp)
515 {
516 *nbshp = bsh + offset;
517 return (0);
518 }
519
520 int
dino_ioalloc(void * v,bus_addr_t rstart,bus_addr_t rend,bus_size_t size,bus_size_t align,bus_size_t boundary,int flags,bus_addr_t * addrp,bus_space_handle_t * bshp)521 dino_ioalloc(void *v, bus_addr_t rstart, bus_addr_t rend, bus_size_t size,
522 bus_size_t align, bus_size_t boundary, int flags, bus_addr_t *addrp,
523 bus_space_handle_t *bshp)
524 {
525 struct dino_softc *sc = v;
526 struct extent *ex = sc->sc_ioex;
527 bus_addr_t bpa;
528 int error;
529
530 if (rstart < ex->ex_start || rend > ex->ex_end)
531 panic("dino_ioalloc: bad region start/end");
532
533 if ((error = extent_alloc_subregion(ex, rstart, rend, size,
534 align, 0, boundary, EX_NOWAIT, &bpa)))
535 return (error);
536
537 if (addrp)
538 *addrp = bpa;
539 if (bshp)
540 *bshp = bpa;
541
542 return (0);
543 }
544
545 int
dino_memalloc(void * v,bus_addr_t rstart,bus_addr_t rend,bus_size_t size,bus_size_t align,bus_size_t boundary,int flags,bus_addr_t * addrp,bus_space_handle_t * bshp)546 dino_memalloc(void *v, bus_addr_t rstart, bus_addr_t rend, bus_size_t size,
547 bus_size_t align, bus_size_t boundary, int flags, bus_addr_t *addrp,
548 bus_space_handle_t *bshp)
549 {
550 struct dino_softc *sc = v;
551 volatile struct dino_regs *r = sc->sc_regs;
552 u_int32_t reg;
553
554 if (bus_space_alloc(sc->sc_bt, rstart, rend, size,
555 align, boundary, flags, addrp, bshp))
556 return (ENOMEM);
557
558 reg = sc->io_shadow;
559 reg |= 1 << ((*addrp >> 23) & 0x1f);
560 if (reg & 0x80000001) {
561 #ifdef DEBUG
562 panic("mapping outside the mem extent range");
563 #endif
564 return (EINVAL);
565 }
566 r->io_addr_en |= reg;
567 sc->io_shadow = reg;
568
569 return (0);
570 }
571
572 void
dino_unmap(void * v,bus_space_handle_t bsh,bus_size_t size)573 dino_unmap(void *v, bus_space_handle_t bsh, bus_size_t size)
574 {
575 struct dino_softc *sc = v;
576 struct extent *ex;
577 bus_addr_t bpa;
578
579 bpa = bsh;
580 if (bsh & 0xf0000000) {
581 /* TODO dino_unmap mem */
582 /* TODO unmap from the upper bus if the last use in this 8M */
583 return;
584 } else
585 ex = sc->sc_ioex;
586
587 if (extent_free(ex, bpa, size, EX_NOWAIT))
588 printf("dino_unmap: ps 0x%lx, size 0x%lx\n"
589 "dino_unmap: can't free region\n", bpa, size);
590 }
591
592 void
dino_free(void * v,bus_space_handle_t bh,bus_size_t size)593 dino_free(void *v, bus_space_handle_t bh, bus_size_t size)
594 {
595 /* should be enough */
596 dino_unmap(v, bh, size);
597 }
598
599 void
dino_barrier(void * v,bus_space_handle_t h,bus_size_t o,bus_size_t l,int op)600 dino_barrier(void *v, bus_space_handle_t h, bus_size_t o, bus_size_t l, int op)
601 {
602 sync_caches();
603 }
604
605 #if NCARDBUS > 0
606 void *
dino_alloc_parent(struct device * self,struct pci_attach_args * pa,int io)607 dino_alloc_parent(struct device *self, struct pci_attach_args *pa, int io)
608 {
609 struct dino_softc *sc = pa->pa_pc->_cookie;
610 struct extent *ex;
611 bus_space_tag_t tag;
612 bus_addr_t start;
613 bus_size_t size;
614
615 if (io) {
616 ex = sc->sc_ioex;
617 tag = pa->pa_iot;
618 start = 0xa000;
619 size = 0x1000;
620 } else {
621 if (!sc->sc_memex) {
622 bus_space_handle_t memh;
623 bus_addr_t mem_start;
624
625 if (dino_memalloc(sc, 0xf0800000, 0xff7fffff,
626 DINO_MEM_WINDOW, DINO_MEM_WINDOW, EX_NOBOUNDARY,
627 0, &mem_start, &memh))
628 return (NULL);
629
630 snprintf(sc->sc_memexname, sizeof(sc->sc_memexname),
631 "%s_mem", sc->sc_dv.dv_xname);
632 if ((sc->sc_memex = extent_create(sc->sc_memexname,
633 mem_start, mem_start + DINO_MEM_WINDOW, M_DEVBUF,
634 NULL, 0, EX_NOWAIT | EX_MALLOCOK)) == NULL) {
635 extent_destroy(sc->sc_ioex);
636 bus_space_free(sc->sc_bt, memh,
637 DINO_MEM_WINDOW);
638 return (NULL);
639 }
640 }
641 ex = sc->sc_memex;
642 tag = pa->pa_memt;
643 start = ex->ex_start;
644 size = DINO_MEM_CHUNK;
645 }
646
647 if (extent_alloc_subregion(ex, start, ex->ex_end, size, size, 0,
648 EX_NOBOUNDARY, EX_NOWAIT, &start))
649 return (NULL);
650
651 extent_free(ex, start, size, EX_NOWAIT);
652 return rbus_new_root_share(tag, ex, start, size);
653 }
654 #endif
655
656 void *
dino_vaddr(void * v,bus_space_handle_t h)657 dino_vaddr(void *v, bus_space_handle_t h)
658 {
659 if (h & 0xf0000000)
660 return ((void *)h);
661 else
662 return (NULL);
663 }
664
665 u_int8_t
dino_r1(void * v,bus_space_handle_t h,bus_size_t o)666 dino_r1(void *v, bus_space_handle_t h, bus_size_t o)
667 {
668 h += o;
669 if (h & 0xf0000000)
670 return *(volatile u_int8_t *)h;
671 else {
672 struct dino_softc *sc = v;
673 volatile struct dino_regs *r = sc->sc_regs;
674 u_int8_t data;
675
676 r->pci_addr = h;
677 data = *((volatile u_int8_t *)&r->pci_io_data + (h & 3));
678 return (data);
679 }
680 }
681
682 u_int16_t
dino_r2(void * v,bus_space_handle_t h,bus_size_t o)683 dino_r2(void *v, bus_space_handle_t h, bus_size_t o)
684 {
685 volatile u_int16_t *p;
686
687 h += o;
688 if (h & 0xf0000000)
689 p = (volatile u_int16_t *)h;
690 else {
691 struct dino_softc *sc = v;
692 volatile struct dino_regs *r = sc->sc_regs;
693
694 r->pci_addr = h;
695 p = (volatile u_int16_t *)&r->pci_io_data;
696 if (h & 2)
697 p++;
698 }
699
700 return (letoh16(*p));
701 }
702
703 u_int32_t
dino_r4(void * v,bus_space_handle_t h,bus_size_t o)704 dino_r4(void *v, bus_space_handle_t h, bus_size_t o)
705 {
706 u_int32_t data;
707
708 h += o;
709 if (h & 0xf0000000)
710 data = *(volatile u_int32_t *)h;
711 else {
712 struct dino_softc *sc = v;
713 volatile struct dino_regs *r = sc->sc_regs;
714
715 r->pci_addr = h;
716 data = r->pci_io_data;
717 }
718
719 return (letoh32(data));
720 }
721
722 u_int64_t
dino_r8(void * v,bus_space_handle_t h,bus_size_t o)723 dino_r8(void *v, bus_space_handle_t h, bus_size_t o)
724 {
725 u_int64_t data;
726
727 h += o;
728 if (h & 0xf0000000)
729 data = *(volatile u_int64_t *)h;
730 else
731 panic("dino_r8: not implemented");
732
733 return (letoh64(data));
734 }
735
736 void
dino_w1(void * v,bus_space_handle_t h,bus_size_t o,u_int8_t vv)737 dino_w1(void *v, bus_space_handle_t h, bus_size_t o, u_int8_t vv)
738 {
739 h += o;
740 if (h & 0xf0000000)
741 *(volatile u_int8_t *)h = vv;
742 else {
743 struct dino_softc *sc = v;
744 volatile struct dino_regs *r = sc->sc_regs;
745
746 r->pci_addr = h;
747 *((volatile u_int8_t *)&r->pci_io_data + (h & 3)) = vv;
748 }
749 }
750
751 void
dino_w2(void * v,bus_space_handle_t h,bus_size_t o,u_int16_t vv)752 dino_w2(void *v, bus_space_handle_t h, bus_size_t o, u_int16_t vv)
753 {
754 volatile u_int16_t *p;
755
756 h += o;
757 if (h & 0xf0000000)
758 p = (volatile u_int16_t *)h;
759 else {
760 struct dino_softc *sc = v;
761 volatile struct dino_regs *r = sc->sc_regs;
762
763 r->pci_addr = h;
764 p = (volatile u_int16_t *)&r->pci_io_data;
765 if (h & 2)
766 p++;
767 }
768
769 *p = htole16(vv);
770 }
771
772 void
dino_w4(void * v,bus_space_handle_t h,bus_size_t o,u_int32_t vv)773 dino_w4(void *v, bus_space_handle_t h, bus_size_t o, u_int32_t vv)
774 {
775 h += o;
776 vv = htole32(vv);
777 if (h & 0xf0000000)
778 *(volatile u_int32_t *)h = vv;
779 else {
780 struct dino_softc *sc = v;
781 volatile struct dino_regs *r = sc->sc_regs;
782
783 r->pci_addr = h;
784 r->pci_io_data = vv;
785 }
786 }
787
788 void
dino_w8(void * v,bus_space_handle_t h,bus_size_t o,u_int64_t vv)789 dino_w8(void *v, bus_space_handle_t h, bus_size_t o, u_int64_t vv)
790 {
791 h += o;
792 if (h & 0xf0000000)
793 *(volatile u_int64_t *)h = htole64(vv);
794 else
795 panic("dino_w8: not implemented");
796 }
797
798
799 void
dino_rm_1(void * v,bus_space_handle_t h,bus_size_t o,u_int8_t * a,bus_size_t c)800 dino_rm_1(void *v, bus_space_handle_t h, bus_size_t o, u_int8_t *a, bus_size_t c)
801 {
802 volatile u_int8_t *p;
803
804 h += o;
805 if (h & 0xf0000000)
806 p = (volatile u_int8_t *)h;
807 else {
808 struct dino_softc *sc = v;
809 volatile struct dino_regs *r = sc->sc_regs;
810
811 r->pci_addr = h;
812 p = (volatile u_int8_t *)&r->pci_io_data + (h & 3);
813 }
814
815 while (c--)
816 *a++ = *p;
817 }
818
819 void
dino_rm_2(void * v,bus_space_handle_t h,bus_size_t o,u_int16_t * a,bus_size_t c)820 dino_rm_2(void *v, bus_space_handle_t h, bus_size_t o, u_int16_t *a, bus_size_t c)
821 {
822 volatile u_int16_t *p;
823
824 h += o;
825 if (h & 0xf0000000)
826 p = (volatile u_int16_t *)h;
827 else {
828 struct dino_softc *sc = v;
829 volatile struct dino_regs *r = sc->sc_regs;
830
831 r->pci_addr = h;
832 p = (volatile u_int16_t *)&r->pci_io_data;
833 if (h & 2)
834 p++;
835 }
836
837 while (c--)
838 *a++ = letoh16(*p);
839 }
840
841 void
dino_rm_4(void * v,bus_space_handle_t h,bus_size_t o,u_int32_t * a,bus_size_t c)842 dino_rm_4(void *v, bus_space_handle_t h, bus_size_t o, u_int32_t *a, bus_size_t c)
843 {
844 volatile u_int32_t *p;
845
846 h += o;
847 if (h & 0xf0000000)
848 p = (volatile u_int32_t *)h;
849 else {
850 struct dino_softc *sc = v;
851 volatile struct dino_regs *r = sc->sc_regs;
852
853 r->pci_addr = h;
854 p = (volatile u_int32_t *)&r->pci_io_data;
855 }
856
857 while (c--)
858 *a++ = letoh32(*p);
859 }
860
861 void
dino_rm_8(void * v,bus_space_handle_t h,bus_size_t o,u_int64_t * a,bus_size_t c)862 dino_rm_8(void *v, bus_space_handle_t h, bus_size_t o, u_int64_t *a, bus_size_t c)
863 {
864 panic("dino_rm_8: not implemented");
865 }
866
867 void
dino_wm_1(void * v,bus_space_handle_t h,bus_size_t o,const u_int8_t * a,bus_size_t c)868 dino_wm_1(void *v, bus_space_handle_t h, bus_size_t o, const u_int8_t *a, bus_size_t c)
869 {
870 volatile u_int8_t *p;
871
872 h += o;
873 if (h & 0xf0000000)
874 p = (volatile u_int8_t *)h;
875 else {
876 struct dino_softc *sc = v;
877 volatile struct dino_regs *r = sc->sc_regs;
878
879 r->pci_addr = h;
880 p = (volatile u_int8_t *)&r->pci_io_data + (h & 3);
881 }
882
883 while (c--)
884 *p = *a++;
885 }
886
887 void
dino_wm_2(void * v,bus_space_handle_t h,bus_size_t o,const u_int16_t * a,bus_size_t c)888 dino_wm_2(void *v, bus_space_handle_t h, bus_size_t o, const u_int16_t *a, bus_size_t c)
889 {
890 volatile u_int16_t *p;
891
892 h += o;
893 if (h & 0xf0000000)
894 p = (volatile u_int16_t *)h;
895 else {
896 struct dino_softc *sc = v;
897 volatile struct dino_regs *r = sc->sc_regs;
898
899 r->pci_addr = h;
900 p = (volatile u_int16_t *)&r->pci_io_data;
901 if (h & 2)
902 p++;
903 }
904
905 while (c--)
906 *p = htole16(*a++);
907 }
908
909 void
dino_wm_4(void * v,bus_space_handle_t h,bus_size_t o,const u_int32_t * a,bus_size_t c)910 dino_wm_4(void *v, bus_space_handle_t h, bus_size_t o, const u_int32_t *a, bus_size_t c)
911 {
912 volatile u_int32_t *p;
913
914 h += o;
915 if (h & 0xf0000000)
916 p = (volatile u_int32_t *)h;
917 else {
918 struct dino_softc *sc = v;
919 volatile struct dino_regs *r = sc->sc_regs;
920
921 r->pci_addr = h;
922 p = (volatile u_int32_t *)&r->pci_io_data;
923 }
924
925 while (c--)
926 *p = htole32(*a++);
927 }
928
929 void
dino_wm_8(void * v,bus_space_handle_t h,bus_size_t o,const u_int64_t * a,bus_size_t c)930 dino_wm_8(void *v, bus_space_handle_t h, bus_size_t o, const u_int64_t *a, bus_size_t c)
931 {
932 panic("dino_wm_8: not implemented");
933 }
934
935 void
dino_sm_1(void * v,bus_space_handle_t h,bus_size_t o,u_int8_t vv,bus_size_t c)936 dino_sm_1(void *v, bus_space_handle_t h, bus_size_t o, u_int8_t vv, bus_size_t c)
937 {
938 volatile u_int8_t *p;
939
940 h += o;
941 if (h & 0xf0000000)
942 p = (volatile u_int8_t *)h;
943 else {
944 struct dino_softc *sc = v;
945 volatile struct dino_regs *r = sc->sc_regs;
946
947 r->pci_addr = h;
948 p = (volatile u_int8_t *)&r->pci_io_data + (h & 3);
949 }
950
951 while (c--)
952 *p = vv;
953 }
954
955 void
dino_sm_2(void * v,bus_space_handle_t h,bus_size_t o,u_int16_t vv,bus_size_t c)956 dino_sm_2(void *v, bus_space_handle_t h, bus_size_t o, u_int16_t vv, bus_size_t c)
957 {
958 volatile u_int16_t *p;
959
960 h += o;
961 if (h & 0xf0000000)
962 p = (volatile u_int16_t *)h;
963 else {
964 struct dino_softc *sc = v;
965 volatile struct dino_regs *r = sc->sc_regs;
966
967 r->pci_addr = h;
968 p = (volatile u_int16_t *)&r->pci_io_data;
969 if (h & 2)
970 p++;
971 }
972
973 vv = htole16(vv);
974 while (c--)
975 *p = vv;
976 }
977
978 void
dino_sm_4(void * v,bus_space_handle_t h,bus_size_t o,u_int32_t vv,bus_size_t c)979 dino_sm_4(void *v, bus_space_handle_t h, bus_size_t o, u_int32_t vv, bus_size_t c)
980 {
981 volatile u_int32_t *p;
982
983 h += o;
984 if (h & 0xf0000000)
985 p = (volatile u_int32_t *)h;
986 else {
987 struct dino_softc *sc = v;
988 volatile struct dino_regs *r = sc->sc_regs;
989
990 r->pci_addr = h;
991 p = (volatile u_int32_t *)&r->pci_io_data;
992 }
993
994 vv = htole32(vv);
995 while (c--)
996 *p = vv;
997 }
998
999 void
dino_sm_8(void * v,bus_space_handle_t h,bus_size_t o,u_int64_t vv,bus_size_t c)1000 dino_sm_8(void *v, bus_space_handle_t h, bus_size_t o, u_int64_t vv, bus_size_t c)
1001 {
1002 panic("dino_sm_8: not implemented");
1003 }
1004
1005 void
dino_rrm_2(void * v,bus_space_handle_t h,bus_size_t o,u_int8_t * a,bus_size_t c)1006 dino_rrm_2(void *v, bus_space_handle_t h, bus_size_t o,
1007 u_int8_t *a, bus_size_t c)
1008 {
1009 volatile u_int16_t *p, *q = (u_int16_t *)a;
1010
1011 h += o;
1012 if (h & 0xf0000000)
1013 p = (volatile u_int16_t *)h;
1014 else {
1015 struct dino_softc *sc = v;
1016 volatile struct dino_regs *r = sc->sc_regs;
1017
1018 r->pci_addr = h;
1019 p = (volatile u_int16_t *)&r->pci_io_data;
1020 if (h & 2)
1021 p++;
1022 }
1023
1024 c /= 2;
1025 while (c--)
1026 *q++ = *p;
1027 }
1028
1029 void
dino_rrm_4(void * v,bus_space_handle_t h,bus_size_t o,u_int8_t * a,bus_size_t c)1030 dino_rrm_4(void *v, bus_space_handle_t h, bus_size_t o,
1031 u_int8_t *a, bus_size_t c)
1032 {
1033 volatile u_int32_t *p, *q = (u_int32_t *)a;
1034
1035 h += o;
1036 if (h & 0xf0000000)
1037 p = (volatile u_int32_t *)h;
1038 else {
1039 struct dino_softc *sc = v;
1040 volatile struct dino_regs *r = sc->sc_regs;
1041
1042 r->pci_addr = h;
1043 p = (volatile u_int32_t *)&r->pci_io_data;
1044 }
1045
1046 c /= 4;
1047 while (c--)
1048 *q++ = *p;
1049 }
1050
1051 void
dino_rrm_8(void * v,bus_space_handle_t h,bus_size_t o,u_int8_t * a,bus_size_t c)1052 dino_rrm_8(void *v, bus_space_handle_t h, bus_size_t o,
1053 u_int8_t *a, bus_size_t c)
1054 {
1055 panic("dino_rrm_8: not implemented");
1056 }
1057
1058 void
dino_wrm_2(void * v,bus_space_handle_t h,bus_size_t o,const u_int8_t * a,bus_size_t c)1059 dino_wrm_2(void *v, bus_space_handle_t h, bus_size_t o,
1060 const u_int8_t *a, bus_size_t c)
1061 {
1062 volatile u_int16_t *p;
1063 const u_int16_t *q = (const u_int16_t *)a;
1064
1065 h += o;
1066 if (h & 0xf0000000)
1067 p = (volatile u_int16_t *)h;
1068 else {
1069 struct dino_softc *sc = v;
1070 volatile struct dino_regs *r = sc->sc_regs;
1071
1072 r->pci_addr = h;
1073 p = (volatile u_int16_t *)&r->pci_io_data;
1074 if (h & 2)
1075 p++;
1076 }
1077
1078 c /= 2;
1079 while (c--)
1080 *p = *q++;
1081 }
1082
1083 void
dino_wrm_4(void * v,bus_space_handle_t h,bus_size_t o,const u_int8_t * a,bus_size_t c)1084 dino_wrm_4(void *v, bus_space_handle_t h, bus_size_t o,
1085 const u_int8_t *a, bus_size_t c)
1086 {
1087 volatile u_int32_t *p;
1088 const u_int32_t *q = (const u_int32_t *)a;
1089
1090 h += o;
1091 if (h & 0xf0000000)
1092 p = (volatile u_int32_t *)h;
1093 else {
1094 struct dino_softc *sc = v;
1095 volatile struct dino_regs *r = sc->sc_regs;
1096
1097 r->pci_addr = h;
1098 p = (volatile u_int32_t *)&r->pci_io_data;
1099 }
1100
1101 c /= 4;
1102 while (c--)
1103 *p = *q++;
1104 }
1105
1106 void
dino_wrm_8(void * v,bus_space_handle_t h,bus_size_t o,const u_int8_t * a,bus_size_t c)1107 dino_wrm_8(void *v, bus_space_handle_t h, bus_size_t o,
1108 const u_int8_t *a, bus_size_t c)
1109 {
1110 panic("dino_wrm_8: not implemented");
1111 }
1112
1113 void
dino_rr_1(void * v,bus_space_handle_t h,bus_size_t o,u_int8_t * a,bus_size_t c)1114 dino_rr_1(void *v, bus_space_handle_t h, bus_size_t o, u_int8_t *a, bus_size_t c)
1115 {
1116 volatile u_int8_t *p;
1117
1118 h += o;
1119 if (h & 0xf0000000) {
1120 p = (volatile u_int8_t *)h;
1121 while (c--)
1122 *a++ = *p++;
1123 } else {
1124 struct dino_softc *sc = v;
1125 volatile struct dino_regs *r = sc->sc_regs;
1126
1127 for (; c--; h++) {
1128 r->pci_addr = h;
1129 p = (volatile u_int8_t *)&r->pci_io_data + (h & 3);
1130 *a++ = *p;
1131 }
1132 }
1133 }
1134
1135 void
dino_rr_2(void * v,bus_space_handle_t h,bus_size_t o,u_int16_t * a,bus_size_t c)1136 dino_rr_2(void *v, bus_space_handle_t h, bus_size_t o, u_int16_t *a, bus_size_t c)
1137 {
1138 volatile u_int16_t *p, data;
1139
1140 h += o;
1141 if (h & 0xf0000000) {
1142 p = (volatile u_int16_t *)h;
1143 while (c--) {
1144 data = *p++;
1145 *a++ = letoh16(data);
1146 }
1147 } else {
1148 struct dino_softc *sc = v;
1149 volatile struct dino_regs *r = sc->sc_regs;
1150
1151 for (; c--; h += 2) {
1152 r->pci_addr = h;
1153 p = (volatile u_int16_t *)&r->pci_io_data;
1154 if (h & 2)
1155 p++;
1156 data = *p;
1157 *a++ = letoh16(data);
1158 }
1159 }
1160 }
1161
1162 void
dino_rr_4(void * v,bus_space_handle_t h,bus_size_t o,u_int32_t * a,bus_size_t c)1163 dino_rr_4(void *v, bus_space_handle_t h, bus_size_t o, u_int32_t *a, bus_size_t c)
1164 {
1165 volatile u_int32_t *p, data;
1166
1167 h += o;
1168 if (h & 0xf0000000) {
1169 p = (volatile u_int32_t *)h;
1170 while (c--) {
1171 data = *p++;
1172 *a++ = letoh32(data);
1173 }
1174 } else {
1175 struct dino_softc *sc = v;
1176 volatile struct dino_regs *r = sc->sc_regs;
1177
1178 for (; c--; h += 4) {
1179 r->pci_addr = h;
1180 data = r->pci_io_data;
1181 *a++ = letoh32(data);
1182 }
1183 }
1184 }
1185
1186 void
dino_rr_8(void * v,bus_space_handle_t h,bus_size_t o,u_int64_t * a,bus_size_t c)1187 dino_rr_8(void *v, bus_space_handle_t h, bus_size_t o, u_int64_t *a, bus_size_t c)
1188 {
1189 panic("dino_rr_8: not implemented");
1190 }
1191
1192 void
dino_wr_1(void * v,bus_space_handle_t h,bus_size_t o,const u_int8_t * a,bus_size_t c)1193 dino_wr_1(void *v, bus_space_handle_t h, bus_size_t o, const u_int8_t *a, bus_size_t c)
1194 {
1195 volatile u_int8_t *p;
1196
1197 h += o;
1198 if (h & 0xf0000000) {
1199 p = (volatile u_int8_t *)h;
1200 while (c--)
1201 *p++ = *a++;
1202 } else {
1203 struct dino_softc *sc = v;
1204 volatile struct dino_regs *r = sc->sc_regs;
1205
1206 for (; c--; h++) {
1207 r->pci_addr = h;
1208 p = (volatile u_int8_t *)&r->pci_io_data + (h & 3);
1209 *p = *a++;
1210 }
1211 }
1212 }
1213
1214 void
dino_wr_2(void * v,bus_space_handle_t h,bus_size_t o,const u_int16_t * a,bus_size_t c)1215 dino_wr_2(void *v, bus_space_handle_t h, bus_size_t o, const u_int16_t *a, bus_size_t c)
1216 {
1217 volatile u_int16_t *p, data;
1218
1219 h += o;
1220 if (h & 0xf0000000) {
1221 p = (volatile u_int16_t *)h;
1222 while (c--) {
1223 data = *a++;
1224 *p++ = htole16(data);
1225 }
1226 } else {
1227 struct dino_softc *sc = v;
1228 volatile struct dino_regs *r = sc->sc_regs;
1229
1230 for (; c--; h += 2) {
1231 r->pci_addr = h;
1232 p = (volatile u_int16_t *)&r->pci_io_data;
1233 if (h & 2)
1234 p++;
1235 data = *a++;
1236 *p = htole16(data);
1237 }
1238 }
1239 }
1240
1241 void
dino_wr_4(void * v,bus_space_handle_t h,bus_size_t o,const u_int32_t * a,bus_size_t c)1242 dino_wr_4(void *v, bus_space_handle_t h, bus_size_t o, const u_int32_t *a, bus_size_t c)
1243 {
1244 volatile u_int32_t *p, data;
1245
1246 h += o;
1247 if (h & 0xf0000000) {
1248 p = (volatile u_int32_t *)h;
1249 while (c--) {
1250 data = *a++;
1251 *p++ = htole32(data);
1252 }
1253 } else {
1254 struct dino_softc *sc = v;
1255 volatile struct dino_regs *r = sc->sc_regs;
1256
1257 for (; c--; h += 4) {
1258 r->pci_addr = h;
1259 data = *a++;
1260 r->pci_io_data = htole32(data);
1261 }
1262 }
1263 }
1264
1265 void
dino_wr_8(void * v,bus_space_handle_t h,bus_size_t o,const u_int64_t * a,bus_size_t c)1266 dino_wr_8(void *v, bus_space_handle_t h, bus_size_t o, const u_int64_t *a, bus_size_t c)
1267 {
1268 panic("dino_wr_8: not implemented");
1269 }
1270
1271 void
dino_rrr_2(void * v,bus_space_handle_t h,bus_size_t o,u_int8_t * a,bus_size_t c)1272 dino_rrr_2(void *v, bus_space_handle_t h, bus_size_t o,
1273 u_int8_t *a, bus_size_t c)
1274 {
1275 volatile u_int16_t *p, *q = (u_int16_t *)a;
1276
1277 c /= 2;
1278 h += o;
1279 if (h & 0xf0000000) {
1280 p = (volatile u_int16_t *)h;
1281 while (c--)
1282 *q++ = *p++;
1283 } else {
1284 struct dino_softc *sc = v;
1285 volatile struct dino_regs *r = sc->sc_regs;
1286
1287 for (; c--; h += 2) {
1288 r->pci_addr = h;
1289 p = (volatile u_int16_t *)&r->pci_io_data;
1290 if (h & 2)
1291 p++;
1292 *q++ = *p;
1293 }
1294 }
1295 }
1296
1297 void
dino_rrr_4(void * v,bus_space_handle_t h,bus_size_t o,u_int8_t * a,bus_size_t c)1298 dino_rrr_4(void *v, bus_space_handle_t h, bus_size_t o,
1299 u_int8_t *a, bus_size_t c)
1300 {
1301 volatile u_int32_t *p, *q = (u_int32_t *)a;
1302
1303 c /= 4;
1304 h += o;
1305 if (h & 0xf0000000) {
1306 p = (volatile u_int32_t *)h;
1307 while (c--)
1308 *q++ = *p++;
1309 } else {
1310 struct dino_softc *sc = v;
1311 volatile struct dino_regs *r = sc->sc_regs;
1312
1313 for (; c--; h += 4) {
1314 r->pci_addr = h;
1315 *q++ = r->pci_io_data;
1316 }
1317 }
1318 }
1319
1320 void
dino_rrr_8(void * v,bus_space_handle_t h,bus_size_t o,u_int8_t * a,bus_size_t c)1321 dino_rrr_8(void *v, bus_space_handle_t h, bus_size_t o,
1322 u_int8_t *a, bus_size_t c)
1323 {
1324 panic("dino_rrr_8: not implemented");
1325 }
1326
1327 void
dino_wrr_2(void * v,bus_space_handle_t h,bus_size_t o,const u_int8_t * a,bus_size_t c)1328 dino_wrr_2(void *v, bus_space_handle_t h, bus_size_t o,
1329 const u_int8_t *a, bus_size_t c)
1330 {
1331 volatile u_int16_t *p;
1332 const u_int16_t *q = (u_int16_t *)a;
1333
1334 c /= 2;
1335 h += o;
1336 if (h & 0xf0000000) {
1337 p = (volatile u_int16_t *)h;
1338 while (c--)
1339 *p++ = *q++;
1340 } else {
1341 struct dino_softc *sc = v;
1342 volatile struct dino_regs *r = sc->sc_regs;
1343
1344 for (; c--; h += 2) {
1345 r->pci_addr = h;
1346 p = (volatile u_int16_t *)&r->pci_io_data;
1347 if (h & 2)
1348 p++;
1349 *p = *q++;
1350 }
1351 }
1352 }
1353
1354 void
dino_wrr_4(void * v,bus_space_handle_t h,bus_size_t o,const u_int8_t * a,bus_size_t c)1355 dino_wrr_4(void *v, bus_space_handle_t h, bus_size_t o,
1356 const u_int8_t *a, bus_size_t c)
1357 {
1358 volatile u_int32_t *p;
1359 const u_int32_t *q = (u_int32_t *)a;
1360
1361 c /= 4;
1362 h += o;
1363 if (h & 0xf0000000) {
1364 p = (volatile u_int32_t *)h;
1365 while (c--)
1366 *p++ = *q++;
1367 } else {
1368 struct dino_softc *sc = v;
1369 volatile struct dino_regs *r = sc->sc_regs;
1370
1371 for (; c--; h += 4) {
1372 r->pci_addr = h;
1373 r->pci_io_data = *q++;
1374 }
1375 }
1376 }
1377
1378 void
dino_wrr_8(void * v,bus_space_handle_t h,bus_size_t o,const u_int8_t * a,bus_size_t c)1379 dino_wrr_8(void *v, bus_space_handle_t h, bus_size_t o,
1380 const u_int8_t *a, bus_size_t c)
1381 {
1382 panic("dino_wrr_8: not implemented");
1383 }
1384
1385 void
dino_sr_1(void * v,bus_space_handle_t h,bus_size_t o,u_int8_t vv,bus_size_t c)1386 dino_sr_1(void *v, bus_space_handle_t h, bus_size_t o, u_int8_t vv, bus_size_t c)
1387 {
1388 volatile u_int8_t *p;
1389
1390 h += o;
1391 if (h & 0xf0000000) {
1392 p = (volatile u_int8_t *)h;
1393 while (c--)
1394 *p++ = vv;
1395 } else {
1396 struct dino_softc *sc = v;
1397 volatile struct dino_regs *r = sc->sc_regs;
1398
1399 for (; c--; h++) {
1400 r->pci_addr = h;
1401 p = (volatile u_int8_t *)&r->pci_io_data + (h & 3);
1402 *p = vv;
1403 }
1404 }
1405 }
1406
1407 void
dino_sr_2(void * v,bus_space_handle_t h,bus_size_t o,u_int16_t vv,bus_size_t c)1408 dino_sr_2(void *v, bus_space_handle_t h, bus_size_t o, u_int16_t vv, bus_size_t c)
1409 {
1410 volatile u_int16_t *p;
1411
1412 h += o;
1413 vv = htole16(vv);
1414 if (h & 0xf0000000) {
1415 p = (volatile u_int16_t *)h;
1416 while (c--)
1417 *p++ = vv;
1418 } else {
1419 struct dino_softc *sc = v;
1420 volatile struct dino_regs *r = sc->sc_regs;
1421
1422 for (; c--; h += 2) {
1423 r->pci_addr = h;
1424 p = (volatile u_int16_t *)&r->pci_io_data;
1425 if (h & 2)
1426 p++;
1427 *p = vv;
1428 }
1429 }
1430 }
1431
1432 void
dino_sr_4(void * v,bus_space_handle_t h,bus_size_t o,u_int32_t vv,bus_size_t c)1433 dino_sr_4(void *v, bus_space_handle_t h, bus_size_t o, u_int32_t vv, bus_size_t c)
1434 {
1435 volatile u_int32_t *p;
1436
1437 h += o;
1438 vv = htole32(vv);
1439 if (h & 0xf0000000) {
1440 p = (volatile u_int32_t *)h;
1441 while (c--)
1442 *p++ = vv;
1443 } else {
1444 struct dino_softc *sc = v;
1445 volatile struct dino_regs *r = sc->sc_regs;
1446
1447 for (; c--; h += 4) {
1448 r->pci_addr = h;
1449 r->pci_io_data = vv;
1450 }
1451 }
1452 }
1453
1454 void
dino_sr_8(void * v,bus_space_handle_t h,bus_size_t o,u_int64_t vv,bus_size_t c)1455 dino_sr_8(void *v, bus_space_handle_t h, bus_size_t o, u_int64_t vv, bus_size_t c)
1456 {
1457 panic("dino_sr_8: not implemented");
1458 }
1459
1460 void
dino_cp_1(void * v,bus_space_handle_t h1,bus_size_t o1,bus_space_handle_t h2,bus_size_t o2,bus_size_t c)1461 dino_cp_1(void *v, bus_space_handle_t h1, bus_size_t o1,
1462 bus_space_handle_t h2, bus_size_t o2, bus_size_t c)
1463 {
1464 while (c--)
1465 dino_w1(v, h1, o1++, dino_r1(v, h2, o2++));
1466 }
1467
1468 void
dino_cp_2(void * v,bus_space_handle_t h1,bus_size_t o1,bus_space_handle_t h2,bus_size_t o2,bus_size_t c)1469 dino_cp_2(void *v, bus_space_handle_t h1, bus_size_t o1,
1470 bus_space_handle_t h2, bus_size_t o2, bus_size_t c)
1471 {
1472 while (c--) {
1473 dino_w2(v, h1, o1, dino_r2(v, h2, o2));
1474 o1 += 2;
1475 o2 += 2;
1476 }
1477 }
1478
1479 void
dino_cp_4(void * v,bus_space_handle_t h1,bus_size_t o1,bus_space_handle_t h2,bus_size_t o2,bus_size_t c)1480 dino_cp_4(void *v, bus_space_handle_t h1, bus_size_t o1,
1481 bus_space_handle_t h2, bus_size_t o2, bus_size_t c)
1482 {
1483 while (c--) {
1484 dino_w4(v, h1, o1, dino_r4(v, h2, o2));
1485 o1 += 4;
1486 o2 += 4;
1487 }
1488 }
1489
1490 void
dino_cp_8(void * v,bus_space_handle_t h1,bus_size_t o1,bus_space_handle_t h2,bus_size_t o2,bus_size_t c)1491 dino_cp_8(void *v, bus_space_handle_t h1, bus_size_t o1,
1492 bus_space_handle_t h2, bus_size_t o2, bus_size_t c)
1493 {
1494 while (c--) {
1495 dino_w8(v, h1, o1, dino_r8(v, h2, o2));
1496 o1 += 8;
1497 o2 += 8;
1498 }
1499 }
1500
1501
1502 const struct hppa_bus_space_tag dino_iomemt = {
1503 NULL,
1504
1505 NULL, dino_unmap, dino_subregion, NULL, dino_free,
1506 dino_barrier, dino_vaddr,
1507 dino_r1, dino_r2, dino_r4, dino_r8,
1508 dino_w1, dino_w2, dino_w4, dino_w8,
1509 dino_rm_1, dino_rm_2, dino_rm_4, dino_rm_8,
1510 dino_wm_1, dino_wm_2, dino_wm_4, dino_wm_8,
1511 dino_sm_1, dino_sm_2, dino_sm_4, dino_sm_8,
1512 dino_rrm_2, dino_rrm_4, dino_rrm_8,
1513 dino_wrm_2, dino_wrm_4, dino_wrm_8,
1514 dino_rr_1, dino_rr_2, dino_rr_4, dino_rr_8,
1515 dino_wr_1, dino_wr_2, dino_wr_4, dino_wr_8,
1516 dino_rrr_2, dino_rrr_4, dino_rrr_8,
1517 dino_wrr_2, dino_wrr_4, dino_wrr_8,
1518 dino_sr_1, dino_sr_2, dino_sr_4, dino_sr_8,
1519 dino_cp_1, dino_cp_2, dino_cp_4, dino_cp_8
1520 };
1521
1522 int
dino_dmamap_create(void * v,bus_size_t size,int nsegments,bus_size_t maxsegsz,bus_size_t boundary,int flags,bus_dmamap_t * dmamp)1523 dino_dmamap_create(void *v, bus_size_t size, int nsegments,
1524 bus_size_t maxsegsz, bus_size_t boundary, int flags, bus_dmamap_t *dmamp)
1525 {
1526 struct dino_softc *sc = v;
1527
1528 /* TODO check the addresses, boundary, enable dma */
1529
1530 return (bus_dmamap_create(sc->sc_dmat, size, nsegments,
1531 maxsegsz, boundary, flags, dmamp));
1532 }
1533
1534 void
dino_dmamap_destroy(void * v,bus_dmamap_t map)1535 dino_dmamap_destroy(void *v, bus_dmamap_t map)
1536 {
1537 struct dino_softc *sc = v;
1538
1539 bus_dmamap_destroy(sc->sc_dmat, map);
1540 }
1541
1542 int
dino_dmamap_load(void * v,bus_dmamap_t map,void * addr,bus_size_t size,struct proc * p,int flags)1543 dino_dmamap_load(void *v, bus_dmamap_t map, void *addr, bus_size_t size,
1544 struct proc *p, int flags)
1545 {
1546 struct dino_softc *sc = v;
1547
1548 return (bus_dmamap_load(sc->sc_dmat, map, addr, size, p, flags));
1549 }
1550
1551 int
dino_dmamap_load_mbuf(void * v,bus_dmamap_t map,struct mbuf * m,int flags)1552 dino_dmamap_load_mbuf(void *v, bus_dmamap_t map, struct mbuf *m, int flags)
1553 {
1554 struct dino_softc *sc = v;
1555
1556 return (bus_dmamap_load_mbuf(sc->sc_dmat, map, m, flags));
1557 }
1558
1559 int
dino_dmamap_load_uio(void * v,bus_dmamap_t map,struct uio * uio,int flags)1560 dino_dmamap_load_uio(void *v, bus_dmamap_t map, struct uio *uio, int flags)
1561 {
1562 struct dino_softc *sc = v;
1563
1564 return (bus_dmamap_load_uio(sc->sc_dmat, map, uio, flags));
1565 }
1566
1567 int
dino_dmamap_load_raw(void * v,bus_dmamap_t map,bus_dma_segment_t * segs,int nsegs,bus_size_t size,int flags)1568 dino_dmamap_load_raw(void *v, bus_dmamap_t map, bus_dma_segment_t *segs,
1569 int nsegs, bus_size_t size, int flags)
1570 {
1571 struct dino_softc *sc = v;
1572
1573 return (bus_dmamap_load_raw(sc->sc_dmat, map, segs, nsegs, size, flags));
1574 }
1575
1576 void
dino_dmamap_unload(void * v,bus_dmamap_t map)1577 dino_dmamap_unload(void *v, bus_dmamap_t map)
1578 {
1579 struct dino_softc *sc = v;
1580
1581 bus_dmamap_unload(sc->sc_dmat, map);
1582 }
1583
1584 void
dino_dmamap_sync(void * v,bus_dmamap_t map,bus_addr_t off,bus_size_t len,int ops)1585 dino_dmamap_sync(void *v, bus_dmamap_t map, bus_addr_t off,
1586 bus_size_t len, int ops)
1587 {
1588 struct dino_softc *sc = v;
1589
1590 return (bus_dmamap_sync(sc->sc_dmat, map, off, len, ops));
1591 }
1592
1593 int
dino_dmamem_alloc(void * v,bus_size_t size,bus_size_t alignment,bus_size_t boundary,bus_dma_segment_t * segs,int nsegs,int * rsegs,int flags)1594 dino_dmamem_alloc(void *v, bus_size_t size, bus_size_t alignment,
1595 bus_size_t boundary, bus_dma_segment_t *segs,
1596 int nsegs, int *rsegs, int flags)
1597 {
1598 struct dino_softc *sc = v;
1599
1600 return (bus_dmamem_alloc(sc->sc_dmat, size, alignment, boundary,
1601 segs, nsegs, rsegs, flags));
1602 }
1603
1604 void
dino_dmamem_free(void * v,bus_dma_segment_t * segs,int nsegs)1605 dino_dmamem_free(void *v, bus_dma_segment_t *segs, int nsegs)
1606 {
1607 struct dino_softc *sc = v;
1608
1609 bus_dmamem_free(sc->sc_dmat, segs, nsegs);
1610 }
1611
1612 int
dino_dmamem_map(void * v,bus_dma_segment_t * segs,int nsegs,size_t size,caddr_t * kvap,int flags)1613 dino_dmamem_map(void *v, bus_dma_segment_t *segs, int nsegs, size_t size,
1614 caddr_t *kvap, int flags)
1615 {
1616 struct dino_softc *sc = v;
1617
1618 return (bus_dmamem_map(sc->sc_dmat, segs, nsegs, size, kvap, flags));
1619 }
1620
1621 void
dino_dmamem_unmap(void * v,caddr_t kva,size_t size)1622 dino_dmamem_unmap(void *v, caddr_t kva, size_t size)
1623 {
1624 struct dino_softc *sc = v;
1625
1626 bus_dmamem_unmap(sc->sc_dmat, kva, size);
1627 }
1628
1629 paddr_t
dino_dmamem_mmap(void * v,bus_dma_segment_t * segs,int nsegs,off_t off,int prot,int flags)1630 dino_dmamem_mmap(void *v, bus_dma_segment_t *segs, int nsegs, off_t off,
1631 int prot, int flags)
1632 {
1633 struct dino_softc *sc = v;
1634
1635 return (bus_dmamem_mmap(sc->sc_dmat, segs, nsegs, off, prot, flags));
1636 }
1637
1638 const struct hppa_bus_dma_tag dino_dmat = {
1639 NULL,
1640 dino_dmamap_create, dino_dmamap_destroy,
1641 dino_dmamap_load, dino_dmamap_load_mbuf,
1642 dino_dmamap_load_uio, dino_dmamap_load_raw,
1643 dino_dmamap_unload, dino_dmamap_sync,
1644
1645 dino_dmamem_alloc, dino_dmamem_free, dino_dmamem_map,
1646 dino_dmamem_unmap, dino_dmamem_mmap
1647 };
1648
1649 const struct hppa_pci_chipset_tag dino_pc = {
1650 NULL,
1651 dino_attach_hook, dino_maxdevs, dino_make_tag, dino_decompose_tag,
1652 dino_conf_size, dino_conf_read, dino_conf_write,
1653 dino_intr_map, dino_intr_string,
1654 dino_intr_establish, dino_intr_disestablish,
1655 #if NCARDBUS > 0
1656 dino_alloc_parent
1657 #else
1658 NULL
1659 #endif
1660 };
1661
1662 int
dinoprint(void * aux,const char * pnp)1663 dinoprint(void *aux, const char *pnp)
1664 {
1665 struct pcibus_attach_args *pba = aux;
1666
1667 if (pnp)
1668 printf("%s at %s\n", pba->pba_busname, pnp);
1669 return (UNCONF);
1670 }
1671
1672 void
dinoattach(parent,self,aux)1673 dinoattach(parent, self, aux)
1674 struct device *parent;
1675 struct device *self;
1676 void *aux;
1677 {
1678 struct dino_softc *sc = (struct dino_softc *)self;
1679 struct confargs *ca = (struct confargs *)aux;
1680 struct pcibus_attach_args pba;
1681 volatile struct dino_regs *r;
1682 const char *p = NULL;
1683 u_int data;
1684 int s, irqbit;
1685
1686 sc->sc_bt = ca->ca_iot;
1687 sc->sc_dmat = ca->ca_dmatag;
1688 if (bus_space_map(sc->sc_bt, ca->ca_hpa, PAGE_SIZE, 0, &sc->sc_bh)) {
1689 printf(": can't map space\n");
1690 return;
1691 }
1692
1693 sc->sc_regs = r = (volatile struct dino_regs *)sc->sc_bh;
1694 r->pciror = 0;
1695 r->pciwor = 0;
1696
1697 /*
1698 * Do not reset enabled io mappings mask if we are still running
1699 * with PDC console - we'll do it after autoconf.
1700 */
1701 if (cn_tab->cn_putc != pdccnputc)
1702 r->io_addr_en = 0;
1703 sc->io_shadow = 0;
1704
1705 r->gmask &= ~1; /* allow GSC bus req */
1706 r->brdg_feat &= ~0xf00;
1707 r->brdg_feat |= 3;
1708 #ifdef notyet_card_mode
1709 r->io_control = 0x80;
1710 r->pamr = 0;
1711 r->papr = 0;
1712 r->io_fbb_en |= 1;
1713 r->damode = 0;
1714 r->brdg_feat = 0xc0000000 XXX;
1715 r->mltim = 0x40; /* 64 clocks */
1716 r->tltim = 0x8c; /* 12 clocks */
1717
1718 /* PCI reset */
1719 r->pcicmd = 0x6f;
1720 DELAY(10000); /* 10ms for reset to settle */
1721 #endif
1722
1723 snprintf(sc->sc_ioexname, sizeof(sc->sc_ioexname),
1724 "%s_io", sc->sc_dv.dv_xname);
1725 if ((sc->sc_ioex = extent_create(sc->sc_ioexname, 0, 0xffff,
1726 M_DEVBUF, NULL, 0, EX_NOWAIT | EX_MALLOCOK)) == NULL) {
1727 printf(": cannot allocate I/O extent map\n");
1728 bus_space_unmap(sc->sc_bt, sc->sc_bh, PAGE_SIZE);
1729 return;
1730 }
1731
1732 /* TODO reserve dino's pci space ? */
1733
1734 sc->sc_ver = ca->ca_type.iodc_revision;
1735 switch ((ca->ca_type.iodc_model << 4) |
1736 (ca->ca_type.iodc_revision >> 4)) {
1737 case 0x05d: /* j2240 */
1738 p = "Dino(card)";
1739 case 0x680:
1740 if (!p)
1741 p = "Dino";
1742 switch (ca->ca_type.iodc_revision & 0xf) {
1743 case 0: sc->sc_ver = 0x20; break;
1744 case 1: sc->sc_ver = 0x21; break;
1745 case 2: sc->sc_ver = 0x30; break;
1746 case 3: sc->sc_ver = 0x31; break;
1747 }
1748 break;
1749
1750 case 0x682:
1751 p = "Cujo";
1752 switch (ca->ca_type.iodc_revision & 0xf) {
1753 case 0: sc->sc_ver = 0x10; break;
1754 case 1: sc->sc_ver = 0x20; break;
1755 }
1756 break;
1757
1758 default:
1759 p = "Mojo";
1760 break;
1761 }
1762
1763 irqbit = cpu_intr_findirq();
1764 if (irqbit >= 0)
1765 printf(" irq %d", irqbit);
1766
1767 printf(": %s V%d.%d\n", p, sc->sc_ver >> 4, sc->sc_ver & 0xf);
1768
1769 s = splhigh();
1770 r->imr = ~0;
1771 data = r->irr0;
1772 data = r->irr1;
1773 r->imr = 0;
1774 __asm volatile ("" ::: "memory");
1775 r->icr = 0;
1776 if (irqbit >= 0)
1777 r->iar0 = cpu_gethpa(0) | (31 - irqbit);
1778 splx(s);
1779
1780 if (irqbit < 0)
1781 sc->sc_ih = NULL;
1782 else
1783 sc->sc_ih = cpu_intr_establish(IPL_NESTED, irqbit,
1784 dino_intr, (void *)sc->sc_regs, sc->sc_dv.dv_xname);
1785 if (sc->sc_ih == NULL) {
1786 printf("%s: can't establish interrupt\n", sc->sc_dv.dv_xname);
1787 return;
1788 }
1789
1790 /* TODO establish the bus error interrupt */
1791
1792 /* scan for ps2 kbd/ms, serial, and flying toasters */
1793 ca->ca_hpamask = -1;
1794 pdc_scanbus(self, ca, MAXMODBUS, 0, 0);
1795
1796 sc->sc_iot = dino_iomemt;
1797 sc->sc_iot.hbt_cookie = sc;
1798 sc->sc_iot.hbt_map = dino_iomap;
1799 sc->sc_iot.hbt_alloc = dino_ioalloc;
1800 sc->sc_memt = dino_iomemt;
1801 sc->sc_memt.hbt_cookie = sc;
1802 sc->sc_memt.hbt_map = dino_memmap;
1803 sc->sc_memt.hbt_alloc = dino_memalloc;
1804 sc->sc_pc = dino_pc;
1805 sc->sc_pc._cookie = sc;
1806 sc->sc_dmatag = dino_dmat;
1807 sc->sc_dmatag._cookie = sc;
1808
1809 bzero(&pba, sizeof(pba));
1810 pba.pba_busname = "pci";
1811 pba.pba_iot = &sc->sc_iot;
1812 pba.pba_memt = &sc->sc_memt;
1813 pba.pba_dmat = &sc->sc_dmatag;
1814 pba.pba_pc = &sc->sc_pc;
1815 pba.pba_domain = pci_ndomains++;
1816 pba.pba_bus = 0;
1817 config_found(self, &pba, dinoprint);
1818
1819 /* postpone cleanup if necessary */
1820 if (r->io_addr_en != sc->io_shadow)
1821 startuphook_establish(dino_clear_pdc_mappings, sc);
1822
1823 /* enable interrupts now that all the devices are there */
1824 r->imr = sc->sc_imr;
1825 }
1826
1827 void
dino_clear_pdc_mappings(void * v)1828 dino_clear_pdc_mappings(void *v)
1829 {
1830 struct dino_softc *sc = (struct dino_softc *)v;
1831 volatile struct dino_regs *r;
1832
1833 if (cn_tab->cn_putc == pdccnputc) {
1834 /* damn! */
1835 return;
1836 }
1837
1838 r = sc->sc_regs;
1839 r->io_addr_en = sc->io_shadow;
1840 }
1841