Make sure to disable interrupts, as U-Boot may call us with interrupts

enabled, causing quite unpleasant effects (e.g. by decrementer interrupts).

When DEBUG is defined, an exception handler will be installed, which reports
about all exceptions while altboot is running, including register dump and
stack frame backtrace.
This commit is contained in:
phx 2011-10-30 20:42:09 +00:00
parent 1309a94f0a
commit d250ff0e1c
3 changed files with 225 additions and 20 deletions

View File

@ -1,4 +1,4 @@
# $NetBSD: Makefile,v 1.11 2011/05/25 19:26:21 phx Exp $
# $NetBSD: Makefile,v 1.12 2011/10/30 20:42:09 phx Exp $
S= ${.CURDIR}/../../../..
@ -8,7 +8,7 @@ NOMAN= # defined
SRCS= entry.S main.c brdsetup.c pci.c devopen.c dev_net.c memfs.c
SRCS+= nif.c fxp.c tlp.c rge.c skg.c stg.c
SRCS+= dsk.c pciide.c siisata.c
SRCS+= vers.c
SRCS+= exception.c vers.c
CLEANFILES+= vers.c ${PROG} ${PROG}.bin ${PROG}.img
CFLAGS+= -Wall -Wno-main -ffreestanding -msoft-float -mmultiple
CFLAGS+= -Wmissing-prototypes -Wstrict-prototypes -Wpointer-arith

View File

@ -1,4 +1,4 @@
/* $NetBSD: entry.S,v 1.3 2011/03/13 15:23:43 phx Exp $ */
/* $NetBSD: entry.S,v 1.4 2011/10/30 20:42:09 phx Exp $ */
#include <powerpc/psl.h>
#include <powerpc/spr.h>
@ -20,13 +20,20 @@ _start:
mr 28,6
mr 29,7
/* Disable interrupts and everything except the MMU. */
mfmsr 3
andi. 3,3,PSL_DR|PSL_IR
mtmsr 3
isync
/*
* U-Boot/PPCBoot forgets to flush the cache when using the "bootm"
* command, so we have to do that now.
*/
lis 11,_start@ha
addi 11,11,_start@l
andi. 11,11,~31@l
li 10,-32
and 11,11,10
lis 12,(_edata+31)@ha
addi 12,12,(_edata+31)@l
bl syncicache
@ -41,8 +48,8 @@ _start:
mfmsr 0
andi. 0,0,PSL_DR
beq 2f
lis 5, 0xfec00000@ha /* CONFIG_ADDR of PCI */
lis 6, 0xfee00000@ha /* CONFIG_DATA of PCI */
lis 5,0xfec00000@ha /* CONFIG_ADDR of PCI */
lis 6,0xfee00000@ha /* CONFIG_DATA of PCI */
mfspr 3,SPR_DBAT0U
mfspr 4,SPR_DBAT0L
bl dbat_sanity_check
@ -104,13 +111,18 @@ _start:
b 5b
6:
/* prepare stack at +1MB from _start. */
lis 1,_start@h
ori 1,1,_start@l
addis 1,1,0x10
addi 1,1,-4
/* prepare stack at +1MB from _start, 16-byte aligned */
lis 1,_start@ha
addi 1,1,_start@l
addis 1,1,0x100000@ha
li 10,-16
and 1,1,10
stw 0,0(1)
bl brdsetup
#ifdef DEBUG
bl init_vectors
#endif
mr 3,30
mr 4,31
mr 5,28
@ -152,7 +164,7 @@ dbat_sanity_check:
*/
.globl run
run:
mtctr 7 /* hat trick jump to entry point */
mtctr 7 /* hat trick jump to entry point */
bctr
/*
@ -198,38 +210,115 @@ newaltboot_end:
/*
* reverse endian access to mimic outw/outl/inw/inl
*/
.globl out16rb
.globl iohtole16
.globl out16rb
.globl iohtole16
out16rb:
iohtole16:
sthbrx 4,0,3
eieio
blr
.globl out32rb
.globl iohtole32
.globl out32rb
.globl iohtole32
out32rb:
iohtole32:
stwbrx 4,0,3
eieio
blr
.global in16rb
.global iole16toh
.globl in16rb
.globl iole16toh
in16rb:
iole16toh:
lhbrx 3,0,3
eieio
blr
.global in32rb
.global iole32toh
.globl in32rb
.globl iole32toh
in32rb:
iole32toh:
lwbrx 3,0,3
eieio
blr
#ifdef DEBUG
/*
* Call an exception handler, which prints out all information
* about the type of exception, cpu registers, stack frame
* backtrace, etc.
* Use a new stack at 0x2000 and make room for 32 GPRs, and 15
* special registers. The layout will be:
* 0x00: link area
* 0x10: R0
* ...
* 0x8c: R31
* 0x90: CR, XER, LR, CTR
* 0xa0: SRR0, SRR1, DAR, DSISR
* 0xb0: DMISS, DCMP, HASH1, HASH2
* 0xc0: IMISS, ICMP, RPA
*
*/
.globl trap
trap:
mtsprg1 1
mfmsr 1
andis. 1,1,PSL_TGPR@h
beq 1f
andi. 1,1,0xffff /* make sure TGPR is disabled */
mtmsr 1
isync
mtsprg1 1 /* and save the real r1 again */
1: li 1,0x2000-16-(32*4+15*4)
stmw 2,24(1) /* save r2..r31 */
stw 0,16(1) /* save r0 */
mfsprg1 3
stw 3,20(1) /* and finally r1 */
mfcr 3
stw 3,0x90(1)
mfxer 3
stw 3,0x94(1)
mflr 3
stw 3,0x98(1)
mfctr 3
stw 3,0x9c(1)
mfsrr0 3
stw 3,0xa0(1)
mfsrr1 3
stw 3,0xa4(1)
mfdar 3
stw 3,0xa8(1)
mfdsisr 3
stw 3,0xac(1)
mfspr 3,976
stw 3,0xb0(1)
mfspr 3,977
stw 3,0xb4(1)
mfspr 3,978
stw 3,0xb8(1)
mfspr 3,979
stw 3,0xbc(1)
mfspr 3,980
stw 3,0xc0(1)
mfspr 3,981
stw 3,0xc4(1)
mfspr 3,982
stw 3,0xc8(1)
bl call_handler
call_handler:
lis 11,exception_handler@ha
addi 11,11,exception_handler@l
mtsrr0 11
li 0,PSL_DR|PSL_IR
mtsrr1 0
mflr 3
subi 3,3,call_handler-trap
addi 4,1,16
rfi
.globl trap_end
trap_end:
#endif
.data
#define xBATL(pa, wimg, pp) \
((pa) | (wimg) | (pp))

View File

@ -0,0 +1,116 @@
/* $NetBSD: exception.c,v 1.1 2011/10/30 20:42:09 phx Exp $ */
/*-
* Copyright (c) 2011 Frank Wille.
* All rights reserved.
*
* Written by Frank Wille for The NetBSD Project.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
* ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include <sys/param.h>
#include <lib/libsa/stand.h>
#include <lib/libsa/loadfile.h>
#include <lib/libkern/libkern.h>
#include "globals.h"
#ifdef DEBUG
struct cpu_state {
uint32_t gpr[32];
uint32_t cr, xer, lr, ctr;
uint32_t srr0, srr1, dar, dsisr;
uint32_t dmiss, dcmp, hash1, hash2;
uint32_t imiss, icmp, rpa;
};
void init_vectors(void); /* called from early startup */
void exception_handler(unsigned, struct cpu_state *);
void
init_vectors(void)
{
extern uint8_t trap[], trap_end[];
uint8_t *exc;
uint32_t *ip;
/* install exception handlers */
for (exc = (uint8_t *)0x100; exc <= (uint8_t *)0x1400; exc += 0x100)
memcpy(exc, trap, trap_end - trap);
/* handle NULL-ptr calls from 0x0 to 0xfc */
for (ip = 0; ip < (uint32_t *)0x100; ip++)
*ip = 0x48000002 | (uint32_t)trap;
__syncicache(0, 0x1400);
}
void
exception_handler(unsigned vector, struct cpu_state *st)
{
static bool in_exception = false;
uint32_t *fp;
int i;
if (vector > 0x1400)
printf("\nCALL TO NULL POINTER FROM %08x\n", st->lr - 4);
else
printf("\nEXCEPTION VECTOR %04x\n", vector);
if (in_exception) {
printf("caused in exception handler! Restarting...\n");
_rtt();
}
in_exception = true;
/* register dump */
printf("\n SRR0=%08x SRR1=%08x DAR=%08x DSISR=%08x\n"
" CR=%08x XER=%08x LR=%08x CTR=%08x\n"
"DMISS=%08x DCMP=%08x HASH1=%08x HASH2=%08x\n"
"IMISS=%08x ICMP=%08x RPA=%08x\n\n",
st->srr0, st->srr1, st->dar, st->dsisr,
st->cr, st->xer, st->lr, st->ctr,
st->dmiss,st->dcmp,st->hash1,st->hash2,
st->imiss,st->icmp,st->rpa);
for (i = 0; i < 32; i++) {
if ((i & 7) == 0)
printf("GPR%02d:", i);
printf("%c%08x", (i & 7) == 4 ? ':' : ' ', st->gpr[i]);
if ((i & 7) == 7)
printf("\n");
}
/* V.4-ABI stack frame back trace */
printf("\nBacktrace:\n");
i = 0;
fp = (uint32_t *)st->gpr[1];
while ((fp = *(uint32_t **)fp) != NULL && i++ < 10)
printf("%p: called from %08x\n", fp, *(fp + 1) - 4);
printf("\nHit any key to reboot.\n");
(void)getchar();
_rtt();
}
#endif /* DEBUG */