mirror of
https://github.com/Telecominfraproject/OpenCellular.git
synced 2025-12-30 10:31:02 +00:00
Preparatory work to introduce a second SoC : 4/5 Allow to use the common code for most SoC. Also simplify the UART code, we don't need speed on the panic path. Signed-off-by: Vincent Palatin <vpalatin@chromium.org> BUG=None TEST=trigger a panic and check the UART output on BDS Change-Id: I11f7bbc571ab9efbc21fb7b805bf4e271b192c3b
109 lines
4.4 KiB
ArmAsm
109 lines
4.4 KiB
ArmAsm
/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
|
|
* Use of this source code is governed by a BSD-style license that can be
|
|
* found in the LICENSE file.
|
|
*
|
|
* Fatal exception handling and debug tracing
|
|
*/
|
|
|
|
#include "config.h"
|
|
|
|
.text
|
|
|
|
.syntax unified
|
|
.code 16
|
|
|
|
.macro hex_reg r, offset @ prepare to build
|
|
add r1, r3, #\offset @ .. hexadecimal string
|
|
mov r0, \r @ .. from the reg value
|
|
bl buildhex
|
|
.endm
|
|
|
|
/* fatal exception handler */
|
|
.global panic
|
|
.thumb_func
|
|
panic:
|
|
#ifndef CONFIG_DEBUG
|
|
b EcSystemReset @ Reboot the system
|
|
#else /* CONFIG_DEBUG */
|
|
/* check that the exception stack pointer is valid */
|
|
ldr r0, =CONFIG_RAM_BASE @ start of RAM
|
|
ldr r1, =CONFIG_RAM_BASE+CONFIG_RAM_SIZE @ end of RAM
|
|
mrs r12, psp @ process stack pointer
|
|
cmp r12, r0 @ is sp >= RAM start ?
|
|
it ge
|
|
cmpge r1, r12 @ is sp < RAM end ?
|
|
blt panic_print @ no => no values to read
|
|
/* output registers value */
|
|
ldr r3, =msg_excep @ pointer to the text buffer
|
|
mrs r2, ipsr @ get exception num from IPSR
|
|
bfc r2, #9, #23 @ the exception is the 3 LSB
|
|
hex_reg r2, 18 @ prepare hexa for excep number
|
|
hex_reg r4, 119 @ prepare hexa for R4
|
|
hex_reg r5, 132 @ prepare hexa for R5
|
|
hex_reg r6, 145 @ prepare hexa for R6
|
|
hex_reg r7, 156 @ prepare hexa for R7
|
|
hex_reg r8, 171 @ prepare hexa for R8
|
|
hex_reg r9, 184 @ prepare hexa for R9
|
|
hex_reg r10, 197 @ prepare hexa for R10
|
|
hex_reg r11, 210 @ prepare hexa for R11
|
|
ldmia r12!, {r4-r11} @ load saved r0-r3,r12,lr,pc,psr
|
|
hex_reg r4, 66 @ prepare hexa for R0
|
|
hex_reg r5, 79 @ prepare hexa for R1
|
|
hex_reg r6, 92 @ prepare hexa for R2
|
|
hex_reg r7, 105 @ prepare hexa for R3
|
|
hex_reg r8, 225 @ prepare hexa for R12
|
|
hex_reg r12, 238 @ prepare hexa for SP
|
|
hex_reg r9, 251 @ prepare hexa for LR
|
|
hex_reg r10, 264 @ prepare hexa for PC
|
|
hex_reg r11, 40 @ prepare hexa for xPSR
|
|
/* print exception trace */
|
|
panic_print:
|
|
ldr r0, =msg_excep @ pointer to the text buffer
|
|
bl emergency_puts @ print the banner
|
|
b system_reset @ Reboot the system
|
|
|
|
/* Helpers for exception trace */
|
|
/* print a string on the UART
|
|
* r0: asciiZ string pointer
|
|
*/
|
|
emergency_puts:
|
|
ldr r1, =CONFIG_UART_ADDRESS @ UART base address
|
|
1:
|
|
ldrb r3, [r0], #1 @ read one character
|
|
cmp r3, #0 @ end of the string ?
|
|
beq 3f @ if yes, return
|
|
2: /* putchar */
|
|
ldr r2, [r1, #CONFIG_UART_SR_OFFSET] @ read UART status
|
|
tst r2, #CONFIG_UART_SR_TXEMPTY @ free space on TX ?
|
|
beq 2b @ if no, wait
|
|
str r3, [r1, #CONFIG_UART_DR_OFFSET] @ send character to UART DR
|
|
b 1b @ goto next character
|
|
3: /* return */
|
|
bx lr
|
|
|
|
/* write a number in hexadecimal in a text buffer
|
|
* r0: number to print
|
|
* r1: pointer to *end* of the buffer (filled with '0')
|
|
*/
|
|
buildhex:
|
|
cmp r0, #0
|
|
it eq
|
|
bxeq lr
|
|
and r2, r0, #0xf
|
|
cmp r2, #10
|
|
ite lt
|
|
addlt r2, #'0'
|
|
addge r2, #'A'-10
|
|
strb r2, [r1],#-1
|
|
lsr r0, #4
|
|
b buildhex
|
|
|
|
.data
|
|
msg_excep: .ascii "\r\n=== EXCEPTION: 00 ====== xPSR: 00000000 ===========\r\n"
|
|
msg_reg0: .ascii "R0 :00000000 R1 :00000000 R2 :00000000 R3 :00000000\r\n"
|
|
msg_reg1: .ascii "R4 :00000000 R5 :00000000 R6 :00000000 R7 :00000000\r\n"
|
|
msg_reg2: .ascii "R8 :00000000 R9 :00000000 R10:00000000 R11:00000000\r\n"
|
|
msg_reg3: .ascii "R12:00000000 SP :00000000 LR :00000000 PC :00000000\r\n\0"
|
|
.align 4
|
|
#endif /* CONFIG_DEBUG */
|