ka43.c revision 1.4 1 /* $NetBSD: ka43.c,v 1.4 1997/02/19 10:04:14 ragge Exp $ */
2 /*
3 * Copyright (c) 1996 Ludd, University of Lule}, Sweden.
4 * All rights reserved.
5 *
6 * This code is derived from software contributed to Ludd by Bertram Barth.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
10 * are met:
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
16 * 3. All advertising materials mentioning features or use of this software
17 * must display the following acknowledgement:
18 * This product includes software developed at Ludd, University of
19 * Lule}, Sweden and its contributors.
20 * 4. The name of the author may not be used to endorse or promote products
21 * derived from this software without specific prior written permission
22 *
23 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
24 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
25 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
26 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
27 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
28 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
29 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
30 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
31 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
32 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33 */
34
35 #include <sys/param.h>
36 #include <sys/types.h>
37 #include <sys/device.h>
38 #include <sys/kernel.h>
39
40 #include <vm/vm.h>
41 #include <vm/vm_kern.h>
42
43 #include <machine/pte.h>
44 #include <machine/cpu.h>
45 #include <machine/mtpr.h>
46 #include <machine/sid.h>
47 #include <machine/pmap.h>
48 #include <machine/nexus.h>
49 #include <machine/uvax.h>
50 #include <machine/ka43.h>
51 #include <machine/clock.h>
52 #include <machine/ka650.h> /* cache ??? */
53
54 #define xtrace(x)
55
56 void ka43_conf __P((struct device*, struct device*, void*));
57 void ka43_steal_pages __P((void));
58
59 void ka43_memerr __P((void));
60 int ka43_mchk __P((caddr_t));
61
62 struct ka43_clock *ka43_clkptr;
63
64
65 static struct uc_map ka43_map[] = {
66 { KA43_CFGTST, KA43_CFGTST, 4, 0 },
67 { KA43_ROM_BASE, KA43_ROM_END, KA43_ROM_SIZE, 0 },
68 { KA43_CPU_BASE, KA43_CPU_END, KA43_CPU_SIZE, 0 },
69 { KA43_CT2_BASE, KA43_CT2_END, KA43_CT2_SIZE, 0 },
70 { KA43_CH2_CREG, KA43_CH2_CREG, 4, 0 },
71 { KA43_NWA_BASE, KA43_NWA_END, KA43_NWA_SIZE, 0 },
72 { KA43_SER_BASE, KA43_SER_END, KA43_SER_SIZE, 0 },
73 { KA43_WAT_BASE, KA43_WAT_END, KA43_WAT_SIZE, 0 },
74 { KA43_SCS_BASE, KA43_SCS_END, KA43_SCS_SIZE, 0 },
75 { KA43_LAN_BASE, KA43_LAN_END, KA43_LAN_SIZE, 0 },
76 { KA43_CUR_BASE, KA43_CUR_END, KA43_CUR_SIZE, 0 },
77 { KA43_DMA_BASE, KA43_DMA_END, KA43_DMA_SIZE, 0 },
78 { KA43_VME_BASE, KA43_VME_END, KA43_VME_SIZE, 0 },
79 /*
80 * there's more to come, eg. framebuffers (GPX/SPX)
81 */
82 {0, 0, 0, 0},
83 };
84
85 struct cpu_dep ka43_calls = {
86 ka43_steal_pages,
87 no_nicr_clock,
88 ka43_mchk,
89 ka43_memerr,
90 ka43_conf,
91 ka43_clkread,
92 ka43_clkwrite,
93 4,
94 (void*)KA43_INTREQ,
95 (void*)KA43_INTCLR,
96 (void*)KA43_INTMSK,
97 ka43_map,
98 };
99
100 #define CH1_BITS \
101 "\020\015BCHIT\014BUSERR\013PPERR\012DPERR\011TPERR\010TRAP1" \
102 "\007TRAP2\006INTR\005HIT\004REFRESH\003FLUSH\002ENABLE\001FORCEHIT"
103
104 #define CH2_BITS \
105 "\020\010TPE\007DPE\006MISS\005DIRTY\004CERR\003LERR\002SERR\001ENAB"
106
107 void
108 ka43_memerr()
109 {
110 int mapen;
111 int *ch2reg;
112
113 printf("memory error!\n");
114 printf("primary cache status: %b\n", mfpr(PR_PCSTS), CH1_BITS);
115
116 mapen = mfpr(PR_MAPEN);
117 if (mapen)
118 ch2reg = (void*)uvax_phys2virt(KA43_CH2_CREG);
119 else
120 ch2reg = (void*)KA43_CH2_CREG;
121 printf("secondary cache status: %b\n", *ch2reg, CH2_BITS);
122 }
123
124 static char *mcc43[] = {
125 "no error (0)",
126 "FPA signalled protocoll error",
127 "FPA signalled illegal opcode",
128 "FPA detected parity error",
129 "FPA returned unknown status",
130 "FPA result has parity error",
131 "unused (6)",
132 "unused (7)",
133 "MMU error (TLB miss)",
134 "MMU error (TLB hit)",
135 "HW interrupt at unused IPL",
136 "impossible microcode state",
137 "undefined trap code (i-box)",
138 "undefined control store address",
139 "unused (14)",
140 "unused (15)",
141 "PC tag or data parity error",
142 "data bus parity error",
143 "data bus error (NXM)",
144 "undefined data bus state",
145 };
146
147 int
148 ka43_mchk(addr)
149 caddr_t addr;
150 {
151 struct {
152 int bcount; /* byte count (0x18) */
153 int mcc; /* "R"-flag and machine check code */
154 int mrva; /* most recent virtual address */
155 int viba; /* contents of VIBA register */
156 int sisr; /* ICCS bit 6 and SISR bits 15:0 */
157 int isd; /* internal state */
158 int scr; /* shift count register */
159 int pc; /* program counter */
160 int psl; /* processor status longword */
161 } *p = (void*)addr;
162
163 printf("machine check: 0x%x\n", p->mcc);
164 printf("reason: %s\n", mcc43[p->mcc & 0xff]);
165
166 printf("bcount:0x%x, check-code:0x%x, virtaddr:0x%x\n",
167 p->bcount, p->mcc, p->mrva);
168 printf("pc:0x%x, psl:0x%x, viba: %x, state: %x\n",
169 p->pc, p->psl, p->viba, p->isd);
170
171 return (-1);
172 }
173
174 int
175 ka43_setup(uc,flags)
176 struct uvax_calls *uc;
177 int flags;
178 {
179 uc->uc_name = "ka43";
180
181 uc->uc_physmap = ka43_map;
182 }
183
184 ka43_discache()
185 {
186 int *ctag;
187 int *creg;
188 int mapen;
189 int i;
190
191 xtrace(("ka43_discache()\n"));
192 return (0);
193
194 /*
195 * first disable primary cache
196 */
197 #if 0
198 mtpr(0, PR_PCSTS);
199 mtpr(0, PR_PCERR);
200 mtpr(0, PR_PCIDX);
201 mtpr(0, PR_PCTAG);
202 #else
203 i = mfpr(PR_PCSTS);
204 mtpr((i & ~2), PR_PCSTS);
205 printf("pcsts: %x --> %x\n", i, mfpr(PR_PCSTS));
206 #endif
207 /*
208 * now secondary cache
209 */
210 mapen = mfpr(PR_MAPEN);
211 if (mapen) {
212 ctag = (void*)uvax_phys2virt(KA43_CT2_BASE);
213 creg = (void*)uvax_phys2virt(KA43_CH2_CREG);
214 } else {
215 ctag = (void*)KA43_CT2_BASE;
216 creg = (void*)KA43_CH2_CREG;
217 }
218 i = *creg;
219 *creg = (i & ~1);
220 printf("creg: %x --> %x\n", i, *creg);
221
222 xtrace(("ka43_discache() done.\n"));
223 }
224
225 ka43_encache()
226 {
227 int *ctag;
228 int *creg;
229 int mapen;
230 int i;
231
232 xtrace(("ka43_encache()\n"));
233
234 ka43_discache();
235
236 /*
237 * first enable primary cache
238 */
239 printf("P-0");
240 i = mfpr(PR_PCSTS);
241 mtpr((i & ~2), PR_PCSTS);
242 mtpr(0, PR_PCSTS);
243 printf("P-1");
244 #if 1
245 mtpr(KA43_PCS_ENABLE | KA43_PCS_FLUSH | KA43_PCS_REFRESH, PR_PCSTS);
246 #else
247 mtpr(KA43_PCS_ENABLE, PR_PCSTS);
248 #endif
249 printf("P-2");
250
251 /*
252 * now secondary cache
253 */
254 mapen = mfpr(PR_MAPEN);
255 if (mapen) {
256 ctag = (void*)uvax_phys2virt(KA43_CT2_BASE);
257 creg = (void*)uvax_phys2virt(KA43_CH2_CREG);
258 } else {
259 ctag = (void*)KA43_CT2_BASE;
260 creg = (void*)KA43_CH2_CREG;
261 }
262 printf("ctag: %x, creg: %x\n", ctag, creg);
263 printf("S-1");
264 i = *creg;
265 printf("creg=[%x] ", *creg);
266 #if 0
267 *creg = (i & ~1);
268 printf("creg=[%x] ", *creg);
269 printf("S-2");
270 for (i = 0; i < KA43_CT2_SIZE; i += 4) /* Quadword entries */
271 ctag[i/4] = 0; /* reset lower half */
272 printf("S-3");
273 i = *creg;
274 printf("creg=[%x] ", *creg);
275 *creg = (i & ~1);
276 printf("creg=[%x] ", *creg);
277 printf("S-4");
278 /* *creg = 1; */
279 printf("S-5");
280 #endif
281 xtrace(("ka43_encache() done.\n"));
282
283 printf("primary cache status: %b\n", mfpr(PR_PCSTS), CH1_BITS);
284 printf("secondary cache status: %b\n", *creg, CH2_BITS);
285 }
286
287 void
288 ka43_conf(parent, self, aux)
289 struct device *parent, *self;
290 void *aux;
291 {
292 extern char cpu_model[];
293 extern int vax_siedata;
294
295 if (vax_siedata & 0x02) /* "single-user" flag */
296 strcpy(cpu_model,"VAXstation 3100 model 76");
297 else if (vax_siedata & 0x01) /* "multiuser" flag */
298 strcpy(cpu_model,"MicroVAX 3100 model 76(?)");
299 else
300 strcpy(cpu_model, "unknown KA43 board");
301
302 printf(": %s\n", cpu_model);
303
304 ka43_encache();
305 }
306
307
308 /*
309 *
310 */
311 u_long le_iomem; /* base addr of RAM -- CPU's view */
312 u_long le_ioaddr; /* base addr of RAM -- LANCE's view */
313
314 void
315 ka43_steal_pages()
316 {
317 extern vm_offset_t avail_start, virtual_avail, avail_end;
318 int junk;
319 int i;
320 struct {
321 u_long :2;
322 u_long data:8;
323 u_long :22;
324 } *p;
325 int *srp; /* Scratch Ram */
326 int *pctl; /* parity control register */
327 char *q = (void*)&srp;
328 char line[20];
329
330 ka43_encache();
331
332 pctl = (void*)KA43_PARCTL;
333 printf("parctl: 0x%x\n", *pctl);
334 #if 0
335 *pctl = KA43_PCTL_DPEN | KA43_PCTL_CPEN;
336 #else
337 *pctl = KA43_PCTL_CPEN;
338 #endif
339 panic("No support for ka43");
340 #if 0
341 printf("new value for parctl: ");
342 gets(line);
343 #endif
344 *pctl = *line - '0';
345 printf("parctl: 0x%x\n", *pctl);
346
347 srp = NULL;
348 p = (void*)KA43_SCR;
349 for (i=0; i<4; i++) {
350 printf("p[%d] = %x, ", i, p[i].data);
351 q[i] = p[i].data;
352 }
353 p = (void*)KA43_SCRLEN;
354 printf("\nlen = %d\n", p->data);
355 printf("srp = 0x%x\n", srp);
356
357 for (i=0; i<0x2; i++) {
358 printf("%x:0x%x ", i*4, srp[i]);
359 if ((i & 0x07) == 0x07)
360 printf("\n");
361 }
362 printf("\n");
363
364 printf ("ka43_steal_pages: avail_end=0x%x\n", avail_end);
365
366 /*
367 * SCB is already copied/initialized at addr avail_start
368 * by pmap_bootstrap(), but it's not yet mapped. Thus we use
369 * the MAPPHYS() macro to reserve these two pages and to
370 * perform the mapping. The mapped address is assigned to junk.
371 */
372 MAPPHYS(junk, 2, VM_PROT_READ|VM_PROT_WRITE);
373
374 /*
375 * At top of physical memory there are some console-prom and/or
376 * restart-specific data. Make this area unavailable.
377 */
378 #if 1
379 avail_end -= 10 * NBPG;
380 #endif
381
382 /*
383 * If we need to map physical areas also, we can decrease avail_end
384 * (the highest available memory-address), copy the stuff into the
385 * gap between and use pmap_map to map it...
386 *
387 * Don't use the MAPPHYS macro here, since this uses and changes(!)
388 * the value of avail_start. Use MAPVIRT even if it's name misleads.
389 */
390 avail_end &= ~0xffff;
391 avail_end -= (64 * 1024);
392
393 avail_end = 0xf00000;
394 le_ioaddr = 0xf40000;
395
396 MAPVIRT(le_iomem, (64 * 1024)/NBPG);
397 pmap_map((vm_offset_t)le_iomem, le_ioaddr, le_ioaddr + 0xffff,
398 VM_PROT_READ|VM_PROT_WRITE);
399
400 if (1 || le_ioaddr > 0xffffff) {
401 le_ioaddr &= 0xffffff;
402 *pctl |= KA43_PCTL_DMA;
403 }
404 printf("le_iomem: %x, le_ioaddr: %x, parctl:%x\n",
405 le_iomem, le_ioaddr, *pctl);
406
407 /*
408 * now map in anything listed in ka43_map...
409 */
410 uvax_fillmap();
411
412 /*
413 * Clear restart and boot in progress flags in the CPMBX.
414 */
415 ((struct ka43_clock*)ka43_clkptr)->cpmbx =
416 ((struct ka43_clock*)ka43_clkptr)->cpmbx & 0xF0;
417
418 /*
419 * Enable memory parity error detection and clear error bits.
420 */
421 ((struct ka43_cpu *)KA43_CPU_BASE)->ka43_mser = 0x01;
422 /* (UVAXIIMSER_PEN | UVAXIIMSER_MERR | UVAXIIMSER_LEB); */
423
424 /*
425 * MM is not yet enabled, thus we still used the physical addresses,
426 * but before leaving this routine, we need to reset them to virtual.
427 */
428 ka43_clkptr = (void*)uvax_phys2virt(KA43_WAT_BASE);
429 }
430
431 /*
432 * define what we need and overwrite the uVAX_??? names
433 */
434
435 #define NEED_UVAX_GENCLOCK
436 #define NEED_UVAX_PROTOCLOCK
437
438 #define uVAX_clock ka43_clock
439 #define uVAX_clkptr ka43_clkptr
440 #define uVAX_clkread ka43_clkread
441 #define uVAX_clkwrite ka43_clkwrite
442 #define uVAX_genclock ka43_genclock
443
444 #include <arch/vax/vax/uvax_proto.c>
445