[BACK]Return to dino.c CVS log [TXT][DIR] Up to [local] / sys / arch / hppa / dev

Annotation of sys/arch/hppa/dev/dino.c, Revision 1.1.1.1

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

CVSweb