1/*	$NetBSD$	*/
2
3/*
4 * Copyright (c) 1988 University of Utah.
5 * Copyright (c) 1992, 1993
6 *	The Regents of the University of California.  All rights reserved.
7 *
8 * This code is derived from software contributed to Berkeley by
9 * the Systems Programming Group of the University of Utah Computer
10 * Science Department and Ralph Campbell.
11 *
12 * Redistribution and use in source and binary forms, with or without
13 * modification, are permitted provided that the following conditions
14 * are met:
15 * 1. Redistributions of source code must retain the above copyright
16 *    notice, this list of conditions and the following disclaimer.
17 * 2. Redistributions in binary form must reproduce the above copyright
18 *    notice, this list of conditions and the following disclaimer in the
19 *    documentation and/or other materials provided with the distribution.
20 * 3. Neither the name of the University nor the names of its contributors
21 *    may be used to endorse or promote products derived from this software
22 *    without specific prior written permission.
23 *
24 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
25 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
27 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
28 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
29 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
30 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
31 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
33 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34 * SUCH DAMAGE.
35 *
36 * from: Utah Hdr: autoconf.c 1.31 91/01/21
37 *
38 *	@(#)autoconf.c	8.1 (Berkeley) 6/10/93
39 */
40
41#include <sys/cdefs.h>
42__KERNEL_RCSID(0, "$NetBSD$");
43
44#include <sys/param.h>
45#include <sys/systm.h>
46#include <sys/conf.h>
47#include <sys/reboot.h>
48#include <sys/device.h>
49
50#include <machine/autoconf.h>
51#include <machine/intr.h>
52#include <machine/sysconf.h>
53
54static int		 booted_bus, booted_unit;
55static const char	*booted_controller;
56
57/*
58 * Configure all devices on system
59 */
60void
61cpu_configure(void)
62{
63
64	/* Kick off autoconfiguration. */
65	(void)splhigh();
66
67	/* Interrupt initialization. */
68	intr_init();
69
70	evcnt_attach_static(&emips_clock_evcnt);
71	evcnt_attach_static(&emips_fpu_evcnt);
72	evcnt_attach_static(&emips_memerr_evcnt);
73
74	if (config_rootfound("mainbus", NULL) == NULL)
75		panic("no mainbus found");
76
77	/* Reset any bus errors due to probing nonexistent devices. */
78	(*platform.bus_reset)();
79
80	/* Configuration is finished, turn on interrupts. */
81	spl0();		/* enable all source forcing SOFT_INTs cleared */
82}
83
84/*
85 * Look at the string 'cp' and decode the boot device.
86 * Boot names are something like '0/ace(0,0)/netbsd' or 'tftp()/nfsnetbsd'
87 * meaning:
88 *  [BusNumber/]<ControllerName>([<DiskNumber>,<PartitionNumber])/<kernelname>
89 */
90void
91makebootdev(char *cp)
92{
93	int i;
94	static char booted_controller_name[8];
95
96	booted_device = NULL;
97	booted_bus = booted_unit = booted_partition = 0;
98	booted_controller = NULL;
99
100	if (*cp >= '0' && *cp <= '9') {
101	        booted_bus = *cp++ - '0';
102		if (*cp == '/')
103			cp++;
104	}
105
106	if (strncmp(cp, "tftp(", 5) == 0) {
107		booted_controller = "BOOTP";
108		goto out;
109	}
110
111	/*
112	 * Stash away the controller name and use it later
113	 */
114	for (i = 0; i < 7 && *cp && *cp != '('; i++)
115		booted_controller_name[i] = *cp++;
116	booted_controller_name[7] = 0; /* sanity */
117
118	if (*cp == '(')
119		cp++;
120	if (*cp >= '0' && *cp <= '9')
121		booted_unit = *cp++ - '0';
122
123	if (*cp == ',')
124		cp++;
125	if (*cp >= '0' && *cp <= '9')
126		booted_partition = *cp - '0';
127	booted_controller = booted_controller_name;
128
129 out:
130#if DEBUG
131	printf("bootdev: %d/%s(%d,%d)\n",
132	    booted_bus, booted_controller, booted_unit, booted_partition);
133#endif
134	return;
135}
136
137void
138cpu_rootconf(void)
139{
140
141	printf("boot device: %s part%d\n",
142	    booted_device ? device_xname(booted_device) : "<unknown>",
143	    booted_partition);
144
145	rootconf();
146}
147
148/*
149 * Try to determine the boot device.
150 */
151void
152device_register(device_t dev, void *aux)
153{
154	static int found, initted, netboot;
155	static device_t ebusdev;
156	device_t parent = device_parent(dev);
157
158	if (found)
159		return;
160
161#if 0
162	printf("\n[device_register(%s,%d) class %d]\n",
163	    device_xname(dev), device_unit(dev), device_class(dev));
164#endif
165
166	if (!initted) {
167		netboot = (strcmp(booted_controller, "BOOTP") == 0);
168		initted = 1;
169	}
170
171	/*
172	 * Remember the EBUS
173	 */
174	if (device_is_a(dev, "ebus")) {
175		ebusdev = dev;
176		return;
177	}
178
179	/*
180	 * Check if netbooting.
181	 */
182	if (netboot) {
183
184		/* Only one Ethernet interface (on ebus). */
185		if ((parent == ebusdev) &&
186		    device_is_a(dev, "enic")) {
187			booted_device = dev;
188			found = 1;
189			return;
190		}
191
192		/* allow any network adapter */
193		if (device_class(dev) == DV_IFNET &&
194		    device_is_a(parent, "ebus")) {
195			booted_device = dev;
196			found = 1;
197			return;
198		}
199
200		/* The NIC might be found after the disk, so bail out here */
201		return;
202	}
203
204	/* BUGBUG How would I get to the bus */
205	if (device_is_a(dev, booted_controller) &&
206	    (device_unit(dev) == booted_unit)) {
207		booted_device = dev;
208		found = 1;
209		return;
210	}
211}
212