locore2.c revision 1.20
1/* $NetBSD: locore2.c,v 1.20 1998/06/12 20:07:50 gwr Exp $ */ 2 3/*- 4 * Copyright (c) 1996 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by Gordon W. Ross and Jeremy Cooper. 9 * 10 * Redistribution and use in source and binary forms, with or without 11 * modification, are permitted provided that the following conditions 12 * are met: 13 * 1. Redistributions of source code must retain the above copyright 14 * notice, this list of conditions and the following disclaimer. 15 * 2. Redistributions in binary form must reproduce the above copyright 16 * notice, this list of conditions and the following disclaimer in the 17 * documentation and/or other materials provided with the distribution. 18 * 3. All advertising materials mentioning features or use of this software 19 * must display the following acknowledgement: 20 * This product includes software developed by the NetBSD 21 * Foundation, Inc. and its contributors. 22 * 4. Neither the name of The NetBSD Foundation nor the names of its 23 * contributors may be used to endorse or promote products derived 24 * from this software without specific prior written permission. 25 * 26 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 27 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 28 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 29 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 30 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 31 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 32 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 33 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 34 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 35 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 36 * POSSIBILITY OF SUCH DAMAGE. 37 */ 38 39#include <sys/param.h> 40#include <sys/systm.h> 41#include <sys/proc.h> 42#include <sys/reboot.h> 43#include <sys/user.h> 44#include <sys/exec_aout.h> 45 46#include <vm/vm.h> 47 48#include <machine/cpu.h> 49#include <machine/db_machdep.h> 50#include <machine/dvma.h> 51#include <machine/idprom.h> 52#include <machine/leds.h> 53#include <machine/mon.h> 54#include <machine/pmap.h> 55#include <machine/pte.h> 56 57#include <sun3/sun3/interreg.h> 58#include <sun3/sun3/machdep.h> 59#include <sun3/sun3/vector.h> 60 61/* This is defined in locore.s */ 62extern char kernel_text[]; 63 64/* These are defined by the linker */ 65extern char etext[], edata[], end[]; 66char *esym; /* DDB */ 67 68/* 69 * XXX: m68k common code needs these... 70 * ... but this port does not need to deal with anything except 71 * an mc68030, so these two variables are always ignored. 72 * XXX: Need to do something about <m68k/include/cpu.h> 73 */ 74int cputype = 1; /* CPU_68030 */ 75int mmutype = -1; /* MMU_68030 */ 76 77/* 78 * Now our own stuff. 79 */ 80 81struct user *proc0paddr; /* proc[0] pcb address (u-area VA) */ 82extern struct pcb *curpcb; 83 84/* First C code called by locore.s */ 85void _bootstrap __P((struct exec)); 86 87static void _vm_init __P((struct exec *kehp)); 88 89#if defined(DDB) && !defined(SYMTAB_SPACE) 90static void _save_symtab __P((struct exec *kehp)); 91 92/* 93 * Preserve DDB symbols and strings by setting esym. 94 */ 95static void 96_save_symtab(kehp) 97 struct exec *kehp; /* kernel exec header */ 98{ 99 int x, *symsz, *strsz; 100 char *endp, *errdesc; 101 102 /* Initialize */ 103 endp = end; 104 symsz = (int*)end; 105 106 /* 107 * Sanity-check the exec header. 108 */ 109 errdesc = "bad magic"; 110 if ((kehp->a_midmag & 0xFFF0) != 0x0100) 111 goto err; 112 113 /* Boundary between text and data varries a little. */ 114 errdesc = "bad header"; 115 x = kehp->a_text + kehp->a_data; 116 if (x != (edata - kernel_text)) 117 goto err; 118 if (kehp->a_bss != (end - edata)) 119 goto err; 120 if (kehp->a_entry != (int)kernel_text) 121 goto err; 122 if (kehp->a_trsize || kehp->a_drsize) 123 goto err; 124 /* The exec header looks OK... */ 125 126 /* Check the symtab length word. */ 127 errdesc = "bad symbols/strings"; 128 if (kehp->a_syms != *symsz) 129 goto err; 130 endp += sizeof(int); /* past length word */ 131 endp += *symsz; /* past nlist array */ 132 133 /* Sanity-check the string table length. */ 134 strsz = (int*)endp; 135 if ((*strsz < 4) || (*strsz > 0x80000)) 136 goto err; 137 /* OK, we have a valid symbol table. */ 138 endp += *strsz; /* past strings */ 139 140 /* Success! Advance esym past the symbol data. */ 141 esym = endp; 142 return; 143 144 err: 145 /* 146 * Make sure the later call to ddb_init() 147 * will pass zero as the symbol table size. 148 */ 149 *symsz = 0; 150 mon_printf("_save_symtab: %s\n", errdesc); 151} 152#endif /* DDB && !SYMTAB_SPACE */ 153 154/* 155 * This function is called from _bootstrap() to initialize 156 * pre-vm-sytem virtual memory. All this really does is to 157 * set virtual_avail to the first page following preloaded 158 * data (i.e. the kernel and its symbol table) and special 159 * things that may be needed very early (proc0 upages). 160 * Once that is done, pmap_bootstrap() is called to do the 161 * usual preparations for our use of the MMU. 162 */ 163static void 164_vm_init(kehp) 165 struct exec *kehp; /* kernel exec header */ 166{ 167 vm_offset_t nextva; 168 169 /* 170 * First preserve our symbol table, which might have been 171 * loaded after our BSS area by the boot loader. However, 172 * if DDB is not part of this kernel, ignore the symbols. 173 */ 174 esym = end + 4; 175#if defined(DDB) && !defined(SYMTAB_SPACE) 176 /* This will advance esym past the symbols. */ 177 _save_symtab(kehp); 178#endif 179 180 /* 181 * Steal some special-purpose, already mapped pages. 182 * Note: msgbuf is setup in machdep.c:cpu_startup() 183 */ 184 nextva = m68k_round_page(esym); 185 186 /* 187 * Setup the u-area pages (stack, etc.) for proc0. 188 * This is done very early (here) to make sure the 189 * fault handler works in case we hit an early bug. 190 * (The fault handler may reference proc0 stuff.) 191 */ 192 proc0paddr = (struct user *) nextva; 193 nextva += USPACE; 194 bzero((caddr_t)proc0paddr, USPACE); 195 proc0.p_addr = proc0paddr; 196 197 /* 198 * Now that proc0 exists, make it the "current" one. 199 */ 200 curproc = &proc0; 201 curpcb = &proc0paddr->u_pcb; 202 203 /* This does most of the real work. */ 204 pmap_bootstrap(nextva); 205} 206 207/* 208 * This is called from locore.s just after the kernel is remapped 209 * to its proper address, but before the call to main(). The work 210 * done here corresponds to various things done in locore.s on the 211 * hp300 port (and other m68k) but which we prefer to do in C code. 212 * Also do setup specific to the Sun PROM monitor and IDPROM here. 213 */ 214void 215_bootstrap(keh) 216 struct exec keh; /* kernel exec header */ 217{ 218 219 /* First, Clear BSS. */ 220 bzero(edata, end - edata); 221 222 /* Set v_handler, get boothowto. */ 223 sunmon_init(); 224 225 /* Handle kernel mapping, pmap_bootstrap(), etc. */ 226 _vm_init(&keh); 227 228 /* 229 * Find and save OBIO mappings needed early, 230 * and call some init functions. 231 */ 232 obio_init(); 233 234 /* 235 * Point interrupts/exceptions to our vector table. 236 * (Until now, we use the one setup by the PROM.) 237 * 238 * This is done after obio_init() / intreg_init() finds 239 * the interrupt register and disables the NMI clock so 240 * it will not cause "spurrious level 7" complaints. 241 * Done after _vm_init so the PROM can debug that. 242 */ 243 setvbr((void **)vector_table); 244 /* Interrupts are enabled later, after autoconfig. */ 245 246 /* 247 * Find the IDPROM and copy it to memory. 248 * Needs obio_init and setvbr earlier. 249 */ 250 idprom_init(); 251 252 /* 253 * Turn on the LEDs so we know power is on. 254 * Needs idprom_init and obio_init earlier. 255 */ 256 leds_init(); 257} 258