1 /* $NetBSD: imc.c,v 1.2 2001/07/08 23:59:31 thorpej Exp $ */ 2 3 /* 4 * Copyright (c) 2001 Rafal K. Boni 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 * 3. The name of the author may not be used to endorse or promote products 16 * derived from this software without specific prior written permission. 17 * 18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 19 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 20 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 21 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 22 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 23 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 24 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 25 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 26 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 27 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 28 */ 29 30 #include <sys/param.h> 31 #include <sys/device.h> 32 #include <sys/systm.h> 33 34 #include <machine/cpu.h> 35 #include <machine/locore.h> 36 #include <machine/autoconf.h> 37 #include <machine/bus.h> 38 #include <machine/machtype.h> 39 40 #include "locators.h" 41 42 struct imc_softc { 43 struct device sc_dev; 44 45 int eisa_present : 1; 46 }; 47 48 static int imc_match(struct device *, struct cfdata *, void *); 49 static void imc_attach(struct device *, struct device *, void *); 50 static int imc_print(void *, const char *); 51 52 struct cfattach imc_ca = { 53 sizeof(struct imc_softc), imc_match, imc_attach 54 }; 55 56 struct imc_attach_args { 57 const char* iaa_name; 58 59 bus_space_tag_t iaa_st; 60 bus_space_handle_t iaa_sh; 61 62 /* ? */ 63 long iaa_offset; 64 int iaa_intr; 65 #if 0 66 int iaa_stride; 67 #endif 68 }; 69 70 static int 71 imc_match(parent, match, aux) 72 struct device *parent; 73 struct cfdata *match; 74 void *aux; 75 { 76 77 /* 78 * The IMC is an INDY/INDIGO2 thing. 79 */ 80 if (mach_type != MACH_SGI_IP22) 81 return (0); 82 83 /* Make sure it's actually there and readable */ 84 if (badaddr((void*)MIPS_PHYS_TO_KSEG1(0x1fa0001c), sizeof(u_int32_t))) 85 return (0); 86 87 return (1); 88 } 89 90 static void 91 imc_attach(parent, self, aux) 92 struct device *parent; 93 struct device *self; 94 void *aux; 95 { 96 u_int32_t reg; 97 struct imc_attach_args iaa; 98 struct imc_softc *isc = (void *) self; 99 u_int32_t sysid = *(volatile u_int32_t *)MIPS_PHYS_TO_KSEG1(0x1fa0001c); 100 101 isc->eisa_present = (sysid >> 4) & 1; 102 103 printf("\nimc0: Revision %d", (sysid & 0x03)); 104 105 if (isc->eisa_present) 106 printf(", EISA bus present"); 107 108 printf("\n"); 109 110 /* Clear CPU/GIO error status registers to clear any leftover bits. */ 111 *(volatile u_int32_t *)MIPS_PHYS_TO_KSEG1(0x1fa000ec) = 0; 112 *(volatile u_int32_t *)MIPS_PHYS_TO_KSEG1(0x1fa000fc) = 0; 113 114 /* 115 * Enable parity reporting on memory/GIO accesses, turn off parity 116 * checking on CPU reads from memory (flags cribbed from Linux -- 117 * why is the last one off?). Also, enable MC interrupt writes to 118 * the CPU. 119 */ 120 reg = *(volatile u_int32_t *)MIPS_PHYS_TO_KSEG1(0x1fa00004); 121 reg |= 0x4002060; 122 *(volatile u_int32_t *)MIPS_PHYS_TO_KSEG1(0x1fa00004) = reg; 123 124 /* Setup the MC write buffer depth */ 125 reg = *(volatile u_int32_t *)MIPS_PHYS_TO_KSEG1(0x1fa0000c); 126 reg &= ~0xf; 127 reg |= 0xd; 128 *(volatile u_int32_t *)MIPS_PHYS_TO_KSEG1(0x1fa0000c) = reg; 129 130 /* Set GIO64 arbitrator configuration register. */ 131 132 /* GIO64 invariant for all IP22 platforms: one GIO bus, HPC1 @ 64 */ 133 reg = 0x401; 134 135 /* XXXrkb: I2 setting for now */ 136 reg |= 0xc222; /* GFX, HPC2 @ 64, EXP1,2 pipelined, EISA masters */ 137 *(volatile u_int32_t *)MIPS_PHYS_TO_KSEG1(0x1fa00084) = reg; 138 139 if (isc->eisa_present) { 140 #if notyet 141 memset(&iaa, 0, sizeof(iaa)); 142 143 iaa.iaa_name = "eisa"; 144 (void)config_found(self, (void*)&iaa, imc_print); 145 #endif 146 } 147 148 memset(&iaa, 0, sizeof(iaa)); 149 150 iaa.iaa_name = "gio"; 151 (void)config_found(self, (void*)&iaa, imc_print); 152 } 153 154 155 static int 156 imc_print(aux, name) 157 void *aux; 158 const char *name; 159 { 160 struct imc_attach_args* iaa = aux; 161 162 if (name) 163 printf("%s at %s", iaa->iaa_name, name); 164 165 return UNCONF; 166 } 167 168