1 /* $NetBSD: autoconf.c,v 1.20 2002/06/09 19:21:08 matt Exp $ */ 2 /* 3 * Copyright (c) 1994, 1998 Ludd, University of Lule}, Sweden. 4 * All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 3. All advertising materials mentioning features or use of this software 15 * must display the following acknowledgement: 16 * This product includes software developed at Ludd, University of Lule}. 17 * 4. The name of the author may not be used to endorse or promote products 18 * derived from this software without specific prior written permission 19 * 20 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 21 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 22 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 23 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 24 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 25 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 26 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 27 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 29 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 30 */ 31 32 /* All bugs are subject to removal without further notice */ 33 34 35 36 #include <sys/param.h> 37 38 #include <lib/libsa/stand.h> 39 40 #include "../include/mtpr.h" 41 #include "../include/sid.h" 42 #include "../include/intr.h" 43 #include "../include/rpb.h" 44 #include "../include/scb.h" 45 46 #include "vaxstand.h" 47 48 void autoconf(void); 49 void findcpu(void); 50 void consinit(void); 51 void scbinit(void); 52 int getsecs(void); 53 void scb_stray(void *); 54 void longjmp(int *, int); 55 void rtimer(void *); 56 57 long *bootregs; 58 59 /* 60 * Do some initial setup. Also create a fake RPB for net-booted machines 61 * that don't have an in-prom VMB. 62 */ 63 64 void 65 autoconf() 66 { 67 int copyrpb = 1; 68 int fromnet = (bootregs[12] != -1); 69 70 findcpu(); /* Configures CPU variables */ 71 consinit(); /* Allow us to print out things */ 72 scbinit(); /* Fix interval clock etc */ 73 74 #ifdef DEV_DEBUG 75 printf("Register contents:\n"); 76 for (copyrpb = 0; copyrpb < 13; copyrpb++) 77 printf("r%d: %lx\n", copyrpb, bootregs[copyrpb]); 78 #endif 79 switch (vax_boardtype) { 80 81 case VAX_BTYP_780: 82 case VAX_BTYP_790: 83 case VAX_BTYP_8000: 84 case VAX_BTYP_9CC: 85 case VAX_BTYP_9RR: 86 case VAX_BTYP_1202: 87 if (fromnet == 0) 88 break; 89 copyrpb = 0; 90 bootrpb.devtyp = bootregs[0]; 91 bootrpb.adpphy = bootregs[1]; 92 bootrpb.csrphy = bootregs[2]; 93 bootrpb.unit = bootregs[3]; 94 bootrpb.rpb_bootr5 = bootregs[5]; 95 bootrpb.pfncnt = 0; 96 break; 97 98 case VAX_BTYP_46: 99 case VAX_BTYP_48: 100 {int *map, i; 101 102 /* Map all 16MB of I/O space to low 16MB of memory */ 103 map = (int *)0x700000; /* XXX */ 104 *(int *)0x20080008 = (int)map; /* XXX */ 105 for (i = 0; i < 0x8000; i++) 106 map[i] = 0x80000000 | i; 107 }break; 108 109 break; 110 } 111 112 if (copyrpb) { 113 struct rpb *prpb = (struct rpb *)bootregs[11]; 114 bcopy((caddr_t)prpb, &bootrpb, sizeof(struct rpb)); 115 if (prpb->iovec) { 116 bootrpb.iovec = (int)alloc(prpb->iovecsz); 117 bcopy((caddr_t)prpb->iovec, (caddr_t)bootrpb.iovec, 118 prpb->iovecsz); 119 } 120 } 121 } 122 123 /* 124 * Clock handling routines, needed to do timing in standalone programs. 125 */ 126 127 volatile int tickcnt; 128 129 int 130 getsecs() 131 { 132 return tickcnt/100; 133 } 134 135 struct ivec_dsp **scb; 136 struct ivec_dsp *scb_vec; 137 extern struct ivec_dsp idsptch; 138 extern int jbuf[10]; 139 140 static void 141 mcheck(void *arg) 142 { 143 int off, *mfp = (int *)&arg; 144 145 off = (mfp[7]/4 + 8); 146 printf("Machine check, pc=%x, psl=%x\n", mfp[off], mfp[off+1]); 147 longjmp(jbuf, 1); 148 } 149 150 /* 151 * Init the SCB and set up a handler for all vectors in the lower space, 152 * to detect unwanted interrupts. 153 */ 154 void 155 scbinit() 156 { 157 int i; 158 159 /* 160 * Allocate space. We need one page for the SCB, and 128*20 == 2.5k 161 * for the vectors. The SCB must be on a page boundary. 162 */ 163 i = (int)alloc(VAX_NBPG + 128*sizeof(scb_vec[0])) + VAX_PGOFSET; 164 i &= ~VAX_PGOFSET; 165 166 mtpr(i, PR_SCBB); 167 scb = (void *)i; 168 scb_vec = (struct ivec_dsp *)(i + VAX_NBPG); 169 170 for (i = 0; i < 128; i++) { 171 scb[i] = &scb_vec[i]; 172 (int)scb[i] |= SCB_ISTACK; /* Only interrupt stack */ 173 scb_vec[i] = idsptch; 174 scb_vec[i].hoppaddr = scb_stray; 175 scb_vec[i].pushlarg = (void *) (i * 4); 176 scb_vec[i].ev = NULL; 177 } 178 scb_vec[0xc0/4].hoppaddr = rtimer; 179 scb_vec[4/4].hoppaddr = mcheck; 180 181 if (vax_boardtype != VAX_BTYP_VXT) 182 mtpr(-10000, PR_NICR); /* Load in count register */ 183 mtpr(0x800000d1, PR_ICCS); /* Start clock and enable interrupt */ 184 185 mtpr(20, PR_IPL); 186 } 187 188 extern int sluttid, senast, skip; 189 190 void 191 rtimer(void *arg) 192 { 193 mtpr(IPL_HIGH, PR_IPL); 194 tickcnt++; 195 mtpr(0xc1, PR_ICCS); 196 if (skip) 197 return; 198 if ((vax_boardtype == VAX_BTYP_46) || 199 (vax_boardtype == VAX_BTYP_48) || 200 (vax_boardtype == VAX_BTYP_49)) { 201 int nu = sluttid - getsecs(); 202 if (senast != nu) { 203 mtpr(20, PR_IPL); 204 longjmp(jbuf, 1); 205 } 206 } 207 } 208 209 #ifdef __ELF__ 210 #define IDSPTCH "idsptch" 211 #define EIDSPTCH "eidsptch" 212 #define CMN_IDSPTCH "cmn_idsptch" 213 #else 214 #define IDSPTCH "_idsptch" 215 #define EIDSPTCH "_eidsptch" 216 #define CMN_IDSPTCH "_cmn_idsptch" 217 #endif 218 219 asm( 220 " .text;" 221 " .align 2;" 222 " .globl " IDSPTCH ", " EIDSPTCH ";" 223 IDSPTCH ":;" 224 " pushr $0x3f;" 225 " .word 0x9f16;" 226 " .long " CMN_IDSPTCH ";" 227 " .long 0;" 228 " .long 0;" 229 " .long 0;" 230 EIDSPTCH ":;" 231 232 CMN_IDSPTCH ":;" 233 " movl (%sp)+,%r0;" 234 " pushl 4(%r0);" 235 " calls $1,*(%r0);" 236 " popr $0x3f;" 237 " rei;" 238 ); 239 240 /* 241 * Stray interrupt handler. 242 * This function must _not_ save any registers (in the reg save mask). 243 */ 244 void 245 scb_stray(void *arg) 246 { 247 static int vector, ipl; 248 249 ipl = mfpr(PR_IPL); 250 vector = (int) arg; 251 printf("stray interrupt: vector 0x%x, ipl %d\n", vector, ipl); 252 } 253