1 /* $NetBSD: autoconf.c,v 1.74 2009/07/20 17:05:13 tsutsui Exp $ */ 2 3 /* 4 * Copyright (c) 1992, 1993 5 * The Regents of the University of California. All rights reserved. 6 * 7 * This code is derived from software contributed to Berkeley by 8 * the Systems Programming Group of the University of Utah Computer 9 * Science Department and Ralph Campbell. 10 * 11 * Redistribution and use in source and binary forms, with or without 12 * modification, are permitted provided that the following conditions 13 * are met: 14 * 1. Redistributions of source code must retain the above copyright 15 * notice, this list of conditions and the following disclaimer. 16 * 2. Redistributions in binary form must reproduce the above copyright 17 * notice, this list of conditions and the following disclaimer in the 18 * documentation and/or other materials provided with the distribution. 19 * 3. Neither the name of the University nor the names of its contributors 20 * may be used to endorse or promote products derived from this software 21 * without specific prior written permission. 22 * 23 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 24 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 25 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 26 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 27 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 28 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 29 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 30 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 31 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 32 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 33 * SUCH DAMAGE. 34 * 35 * from: Utah Hdr: autoconf.c 1.31 91/01/21 36 * 37 * @(#)autoconf.c 8.1 (Berkeley) 6/10/93 38 */ 39 /* 40 * Copyright (c) 1988 University of Utah. 41 * 42 * This code is derived from software contributed to Berkeley by 43 * the Systems Programming Group of the University of Utah Computer 44 * Science Department and Ralph Campbell. 45 * 46 * Redistribution and use in source and binary forms, with or without 47 * modification, are permitted provided that the following conditions 48 * are met: 49 * 1. Redistributions of source code must retain the above copyright 50 * notice, this list of conditions and the following disclaimer. 51 * 2. Redistributions in binary form must reproduce the above copyright 52 * notice, this list of conditions and the following disclaimer in the 53 * documentation and/or other materials provided with the distribution. 54 * 3. All advertising materials mentioning features or use of this software 55 * must display the following acknowledgement: 56 * This product includes software developed by the University of 57 * California, Berkeley and its contributors. 58 * 4. Neither the name of the University nor the names of its contributors 59 * may be used to endorse or promote products derived from this software 60 * without specific prior written permission. 61 * 62 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 63 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 64 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 65 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 66 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 67 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 68 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 69 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 70 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 71 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 72 * SUCH DAMAGE. 73 * 74 * from: Utah Hdr: autoconf.c 1.31 91/01/21 75 * 76 * @(#)autoconf.c 8.1 (Berkeley) 6/10/93 77 */ 78 79 #include <sys/cdefs.h> /* RCS ID & Copyright macro defns */ 80 __KERNEL_RCSID(0, "$NetBSD: autoconf.c,v 1.74 2009/07/20 17:05:13 tsutsui Exp $"); 81 82 #include <sys/param.h> 83 #include <sys/systm.h> 84 #include <sys/conf.h> 85 #include <sys/reboot.h> 86 #include <sys/device.h> 87 88 #include <machine/autoconf.h> 89 #include <machine/intr.h> 90 #include <machine/sysconf.h> 91 92 #include <pmax/pmax/pmaxtype.h> 93 94 #include <dev/tc/tcvar.h> 95 96 #include <dev/scsipi/scsi_all.h> 97 #include <dev/scsipi/scsipi_all.h> 98 #include <dev/scsipi/scsiconf.h> 99 100 #include "opt_dec_3100.h" 101 #include "opt_dec_5100.h" 102 103 struct intrhand intrtab[MAX_DEV_NCOOKIES]; 104 static struct device *booted_controller; 105 static int booted_slot, booted_unit; 106 static const char *booted_protocol; 107 108 /* 109 * Configure all devices on system 110 */ 111 void 112 cpu_configure(void) 113 { 114 115 /* Kick off autoconfiguration. */ 116 (void)splhigh(); 117 118 evcnt_attach_static(&pmax_clock_evcnt); 119 evcnt_attach_static(&pmax_fpu_evcnt); 120 evcnt_attach_static(&pmax_memerr_evcnt); 121 122 if (config_rootfound("mainbus", NULL) == NULL) 123 panic("no mainbus found"); 124 125 /* Reset any bus errors due to probing nonexistent devices. */ 126 (*platform.bus_reset)(); 127 128 /* Configuration is finished, turn on interrupts. */ 129 _splnone(); /* enable all source forcing SOFT_INTs cleared */ 130 } 131 132 /* 133 * Look at the string 'cp' and decode the boot device. Boot names 134 * can be something like 'rz(0,0,0)vmunix' or '5/rz0/vmunix'. 135 * 136 * 2100/3100/5100 allows abbrivation; 137 * dev(controller[,uni-number[,partition-number]]])[filename] 138 */ 139 void 140 makebootdev(char *cp) 141 { 142 booted_device = NULL; 143 booted_slot = booted_unit = booted_partition = 0; 144 booted_protocol = NULL; 145 146 #if defined(DEC_3100) || defined(DEC_5100) 147 if (cp[0] == 'r' && cp[1] == 'z' && cp[2] == '(') { 148 cp += 3; 149 if (*cp >= '0' && *cp <= '9') 150 booted_slot = *cp++ - '0'; 151 if (*cp == ',') 152 cp += 1; 153 if (*cp >= '0' && *cp <= '9') 154 booted_unit = *cp++ - '0'; 155 if (*cp == ',') 156 cp += 1; 157 if (*cp >= '0' && *cp <= '9') 158 booted_partition = *cp - '0'; 159 booted_protocol = "SCSI"; 160 return; 161 } 162 if (strncmp(cp, "tftp(", 5) == 0) { 163 booted_protocol = "BOOTP"; 164 return; 165 } 166 if (strncmp(cp, "mop(", 4) == 0) { 167 booted_protocol = "MOP"; 168 return; 169 } 170 #endif 171 172 if (cp[0] >= '0' && cp[0] <= '9' && cp[1] == '/') { 173 booted_slot = cp[0] - '0'; 174 if (cp[2] == 'r' && cp[3] == 'z' 175 && cp[4] >= '0' && cp[4] <= '9') { 176 booted_protocol = "SCSI"; 177 booted_unit = cp[4] - '0'; 178 } 179 else if (strncmp(cp+2, "tftp", 4) == 0) 180 booted_protocol = "BOOTP"; 181 else if (strncmp(cp+2, "mop", 3) == 0) 182 booted_protocol = "MOP"; 183 } 184 } 185 186 void 187 cpu_rootconf(void) 188 { 189 190 printf("boot device: %s\n", 191 booted_device ? booted_device->dv_xname : "<unknown>"); 192 193 setroot(booted_device, booted_partition); 194 } 195 196 /* 197 * Try to determine the boot device. 198 */ 199 void 200 device_register(struct device *dev, void *aux) 201 { 202 static int found, initted, scsiboot, netboot; 203 static struct device *ioasicdev; 204 struct device *parent = device_parent(dev); 205 206 if (found) 207 return; 208 209 if (!initted) { 210 scsiboot = strcmp(booted_protocol, "SCSI") == 0; 211 netboot = (strcmp(booted_protocol, "BOOTP") == 0) || 212 (strcmp(booted_protocol, "MOP") == 0); 213 initted = 1; 214 } 215 216 /* 217 * Check if IOASIC was the boot slot. 218 */ 219 if (device_is_a(dev, "ioasic")) { 220 struct tc_attach_args *ta = aux; 221 222 if (ta->ta_slot == booted_slot) 223 ioasicdev = dev; 224 return; 225 } 226 227 /* 228 * Check for ASC controller on either IOASIC or TC option card. 229 */ 230 if (scsiboot && device_is_a(dev, "asc")) { 231 struct tc_attach_args *ta = aux; 232 233 /* 234 * If boot was from IOASIC controller, ioasicdev will 235 * be the ASC parent. 236 * If boot was from a TC option card, the TC slot number 237 * of the ASC will match the boot slot. 238 */ 239 if (parent == ioasicdev || 240 ta->ta_slot == booted_slot) { 241 booted_controller = dev; 242 return; 243 } 244 } 245 246 /* 247 * If an SII device is configured, it's currently the only 248 * possible SCSI boot device. 249 */ 250 if (scsiboot && device_is_a(dev, "sii")) { 251 booted_controller = dev; 252 return; 253 } 254 255 /* 256 * If we found the boot controller, if check disk/tape/cdrom device 257 * on that controller matches. 258 */ 259 if (booted_controller && 260 (device_is_a(dev, "sd") || 261 device_is_a(dev, "st") || 262 device_is_a(dev, "cd"))) { 263 struct scsipibus_attach_args *sa = aux; 264 265 if (device_parent(parent) != booted_controller) 266 return; 267 if (booted_unit != sa->sa_periph->periph_target) 268 return; 269 booted_device = dev; 270 found = 1; 271 return; 272 } 273 274 /* 275 * Check if netboot device. 276 */ 277 if (netboot) { 278 struct tc_attach_args *ta = aux; 279 280 if (( 281 #if defined(DEC_3100) || defined(DEC_5100) 282 /* Only one Ethernet interface on 2100/3100/5100. */ 283 systype == DS_PMAX || systype == DS_MIPSMATE || 284 #endif 285 /* Only one Ethernet interface at IOASIC. */ 286 parent == ioasicdev) 287 && device_is_a(dev, "le")) { 288 booted_device = dev; 289 found = 1; 290 return; 291 } 292 293 /* allow any TC network adapter */ 294 if (device_class(dev) == DV_IFNET && 295 device_is_a(parent, "tc") && 296 ta->ta_slot == booted_slot) { 297 booted_device = dev; 298 found = 1; 299 return; 300 } 301 } 302 } 303