1769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn/* 2769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * OpenRISC traps.c 3769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * 4769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * Linux architectural port borrowing liberally from similar works of 5769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * others. All original copyrights apply as per the original source 6769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * declaration. 7769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * 8769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * Modifications for the OpenRISC architecture: 9769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * Copyright (C) 2003 Matjaz Breskvar <phoenix@bsemi.com> 10769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * Copyright (C) 2010-2011 Jonas Bonn <jonas@southpole.se> 11769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * 12769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * This program is free software; you can redistribute it and/or 13769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * modify it under the terms of the GNU General Public License 14769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * as published by the Free Software Foundation; either version 15769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * 2 of the License, or (at your option) any later version. 16769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * 17769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * Here we handle the break vectors not used by the system call 18769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * mechanism, as well as some general stack/register dumping 19769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * things. 20769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * 21769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn */ 22769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 23769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <linux/init.h> 24769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <linux/sched.h> 25769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <linux/kernel.h> 26769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <linux/module.h> 27769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <linux/kmod.h> 28769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <linux/string.h> 29769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <linux/errno.h> 30769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <linux/ptrace.h> 31769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <linux/timer.h> 32769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <linux/mm.h> 33769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <linux/kallsyms.h> 34769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <asm/uaccess.h> 35769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 36769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <asm/segment.h> 37769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <asm/io.h> 38769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#include <asm/pgtable.h> 39769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 40769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnextern char _etext, _stext; 41769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 42769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnint kstack_depth_to_print = 0x180; 43769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 44769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnstatic inline int valid_stack_ptr(struct thread_info *tinfo, void *p) 45769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 46769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn return p > (void *)tinfo && p < (void *)tinfo + THREAD_SIZE - 3; 47769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 48769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 49769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnvoid show_trace(struct task_struct *task, unsigned long *stack) 50769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 51769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn struct thread_info *context; 52769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn unsigned long addr; 53769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 54769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn context = (struct thread_info *) 55769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn ((unsigned long)stack & (~(THREAD_SIZE - 1))); 56769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 57769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn while (valid_stack_ptr(context, stack)) { 58769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn addr = *stack++; 59769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (__kernel_text_address(addr)) { 60769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk(" [<%08lx>]", addr); 61769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn print_symbol(" %s", addr); 62769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\n"); 63769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 64769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 65769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk(" =======================\n"); 66769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 67769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 68769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn/* displays a short stack trace */ 69769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnvoid show_stack(struct task_struct *task, unsigned long *esp) 70769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 71769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn unsigned long addr, *stack; 72769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn int i; 73769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 74769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (esp == NULL) 75769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn esp = (unsigned long *)&esp; 76769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 77769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn stack = esp; 78769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 79769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("Stack dump [0x%08lx]:\n", (unsigned long)esp); 80769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn for (i = 0; i < kstack_depth_to_print; i++) { 81769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (kstack_end(stack)) 82769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn break; 83769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (__get_user(addr, stack)) { 84769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn /* This message matches "failing address" marked 85769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn s390 in ksymoops, so lines containing it will 86769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn not be filtered out by ksymoops. */ 87769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("Failing address 0x%lx\n", (unsigned long)stack); 88769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn break; 89769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 90769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn stack++; 91769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 92769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("sp + %02d: 0x%08lx\n", i * 4, addr); 93769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 94769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\n"); 95769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 96769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn show_trace(task, esp); 97769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 98769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn return; 99769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 100769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 101769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnvoid show_trace_task(struct task_struct *tsk) 102769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 103769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn /* 104769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * TODO: SysRq-T trace dump... 105769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn */ 106769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 107769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 108769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn/* 109769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * The architecture-independent backtrace generator 110769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn */ 111769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnvoid dump_stack(void) 112769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 113769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn unsigned long stack; 114769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 115769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn show_stack(current, &stack); 116769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 11701c4d33ac5ca7920f0e0f6b25bdfd3fa479fd973Richard WeinbergerEXPORT_SYMBOL(dump_stack); 118769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 119769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnvoid show_registers(struct pt_regs *regs) 120769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 121769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn int i; 122769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn int in_kernel = 1; 123769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn unsigned long esp; 124769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 125769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn esp = (unsigned long)(®s->sp); 126769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (user_mode(regs)) 127769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn in_kernel = 0; 128769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 129769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("CPU #: %d\n" 130769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn " PC: %08lx SR: %08lx SP: %08lx\n", 131769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn smp_processor_id(), regs->pc, regs->sr, regs->sp); 132769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR00: %08lx GPR01: %08lx GPR02: %08lx GPR03: %08lx\n", 133769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 0L, regs->gpr[1], regs->gpr[2], regs->gpr[3]); 134769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR04: %08lx GPR05: %08lx GPR06: %08lx GPR07: %08lx\n", 135769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[4], regs->gpr[5], regs->gpr[6], regs->gpr[7]); 136769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR08: %08lx GPR09: %08lx GPR10: %08lx GPR11: %08lx\n", 137769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[8], regs->gpr[9], regs->gpr[10], regs->gpr[11]); 138769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR12: %08lx GPR13: %08lx GPR14: %08lx GPR15: %08lx\n", 139769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[12], regs->gpr[13], regs->gpr[14], regs->gpr[15]); 140769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR16: %08lx GPR17: %08lx GPR18: %08lx GPR19: %08lx\n", 141769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[16], regs->gpr[17], regs->gpr[18], regs->gpr[19]); 142769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR20: %08lx GPR21: %08lx GPR22: %08lx GPR23: %08lx\n", 143769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[20], regs->gpr[21], regs->gpr[22], regs->gpr[23]); 144769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR24: %08lx GPR25: %08lx GPR26: %08lx GPR27: %08lx\n", 145769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[24], regs->gpr[25], regs->gpr[26], regs->gpr[27]); 146769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR28: %08lx GPR29: %08lx GPR30: %08lx GPR31: %08lx\n", 147769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[28], regs->gpr[29], regs->gpr[30], regs->gpr[31]); 1486cbe5e95267449ea0b79c0b049342409949da3acJonas Bonn printk(" RES: %08lx oGPR11: %08lx\n", 1496cbe5e95267449ea0b79c0b049342409949da3acJonas Bonn regs->gpr[11], regs->orig_gpr11); 150769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 151769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("Process %s (pid: %d, stackpage=%08lx)\n", 152769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn current->comm, current->pid, (unsigned long)current); 153769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn /* 154769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * When in-kernel, we also print out the stack and code at the 155769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn * time of the fault.. 156769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn */ 157769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (in_kernel) { 158769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 159769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\nStack: "); 160769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn show_stack(NULL, (unsigned long *)esp); 161769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 162769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\nCode: "); 163769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (regs->pc < PAGE_OFFSET) 164769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn goto bad; 165769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 166769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn for (i = -24; i < 24; i++) { 167769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn unsigned char c; 168769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (__get_user(c, &((unsigned char *)regs->pc)[i])) { 169769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnbad: 170769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk(" Bad PC value."); 171769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn break; 172769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 173769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 174769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (i == 0) 175769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("(%02x) ", c); 176769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn else 177769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("%02x ", c); 178769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 179769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 180769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\n"); 181769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 182769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 183769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnvoid nommu_dump_state(struct pt_regs *regs, 184769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn unsigned long ea, unsigned long vector) 185769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 186769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn int i; 187769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn unsigned long addr, stack = regs->sp; 188769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 189769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\n\r[nommu_dump_state] :: ea %lx, vector %lx\n\r", ea, vector); 190769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 191769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("CPU #: %d\n" 192769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn " PC: %08lx SR: %08lx SP: %08lx\n", 193769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 0, regs->pc, regs->sr, regs->sp); 194769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR00: %08lx GPR01: %08lx GPR02: %08lx GPR03: %08lx\n", 195769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 0L, regs->gpr[1], regs->gpr[2], regs->gpr[3]); 196769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR04: %08lx GPR05: %08lx GPR06: %08lx GPR07: %08lx\n", 197769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[4], regs->gpr[5], regs->gpr[6], regs->gpr[7]); 198769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR08: %08lx GPR09: %08lx GPR10: %08lx GPR11: %08lx\n", 199769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[8], regs->gpr[9], regs->gpr[10], regs->gpr[11]); 200769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR12: %08lx GPR13: %08lx GPR14: %08lx GPR15: %08lx\n", 201769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[12], regs->gpr[13], regs->gpr[14], regs->gpr[15]); 202769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR16: %08lx GPR17: %08lx GPR18: %08lx GPR19: %08lx\n", 203769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[16], regs->gpr[17], regs->gpr[18], regs->gpr[19]); 204769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR20: %08lx GPR21: %08lx GPR22: %08lx GPR23: %08lx\n", 205769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[20], regs->gpr[21], regs->gpr[22], regs->gpr[23]); 206769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR24: %08lx GPR25: %08lx GPR26: %08lx GPR27: %08lx\n", 207769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[24], regs->gpr[25], regs->gpr[26], regs->gpr[27]); 208769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("GPR28: %08lx GPR29: %08lx GPR30: %08lx GPR31: %08lx\n", 209769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->gpr[28], regs->gpr[29], regs->gpr[30], regs->gpr[31]); 2106cbe5e95267449ea0b79c0b049342409949da3acJonas Bonn printk(" RES: %08lx oGPR11: %08lx\n", 2116cbe5e95267449ea0b79c0b049342409949da3acJonas Bonn regs->gpr[11], regs->orig_gpr11); 212769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 213769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("Process %s (pid: %d, stackpage=%08lx)\n", 214769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn ((struct task_struct *)(__pa(current)))->comm, 215769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn ((struct task_struct *)(__pa(current)))->pid, 216769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn (unsigned long)current); 217769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 218769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\nStack: "); 219769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("Stack dump [0x%08lx]:\n", (unsigned long)stack); 220769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn for (i = 0; i < kstack_depth_to_print; i++) { 221769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (((long)stack & (THREAD_SIZE - 1)) == 0) 222769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn break; 223769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn stack++; 224769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 225769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("%lx :: sp + %02d: 0x%08lx\n", stack, i * 4, 226769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn *((unsigned long *)(__pa(stack)))); 227769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 228769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\n"); 229769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 230769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("Call Trace: "); 231769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn i = 1; 232769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn while (((long)stack & (THREAD_SIZE - 1)) != 0) { 233769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn addr = *((unsigned long *)__pa(stack)); 234769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn stack++; 235769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 236769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (kernel_text_address(addr)) { 237769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (i && ((i % 6) == 0)) 238769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\n "); 239769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk(" [<%08lx>]", addr); 240769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn i++; 241769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 242769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 243769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\n"); 244769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 245769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\nCode: "); 246769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 247769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn for (i = -24; i < 24; i++) { 248769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn unsigned char c; 249769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn c = ((unsigned char *)(__pa(regs->pc)))[i]; 250769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 251769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (i == 0) 252769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("(%02x) ", c); 253769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn else 254769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("%02x ", c); 255769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 256769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\n"); 257769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 258769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 259769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn/* This is normally the 'Oops' routine */ 260769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnvoid die(const char *str, struct pt_regs *regs, long err) 261769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 262769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 263769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn console_verbose(); 264769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\n%s#: %04lx\n", str, err & 0xffff); 265769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn show_registers(regs); 266769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#ifdef CONFIG_JUMP_UPON_UNHANDLED_EXCEPTION 267769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("\n\nUNHANDLED_EXCEPTION: entering infinite loop\n"); 268769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 269769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn /* shut down interrupts */ 270769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn local_irq_disable(); 271769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 272769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn __asm__ __volatile__("l.nop 1"); 273769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn do {} while (1); 274769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn#endif 275769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn do_exit(SIGSEGV); 276769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 277769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 278769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn/* This is normally the 'Oops' routine */ 279769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnvoid die_if_kernel(const char *str, struct pt_regs *regs, long err) 280769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 281769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (user_mode(regs)) 282769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn return; 283769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 284769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn die(str, regs, err); 285769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 286769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 287769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnvoid unhandled_exception(struct pt_regs *regs, int ea, int vector) 288769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 289769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("Unable to handle exception at EA =0x%x, vector 0x%x", 290769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn ea, vector); 291769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn die("Oops", regs, 9); 292769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 293769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 294769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnvoid __init trap_init(void) 295769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 296769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn /* Nothing needs to be done */ 297769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 298769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 299769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnasmlinkage void do_trap(struct pt_regs *regs, unsigned long address) 300769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 301769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn siginfo_t info; 302769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn memset(&info, 0, sizeof(info)); 303769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_signo = SIGTRAP; 304769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_code = TRAP_TRACE; 305769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_addr = (void *)address; 306769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn force_sig_info(SIGTRAP, &info, current); 307769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 308769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn regs->pc += 4; 309769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 310769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 311769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnasmlinkage void do_unaligned_access(struct pt_regs *regs, unsigned long address) 312769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 313769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn siginfo_t info; 314769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 315769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (user_mode(regs)) { 316769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn /* Send a SIGSEGV */ 317769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_signo = SIGSEGV; 318769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_errno = 0; 319769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn /* info.si_code has been set above */ 320769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_addr = (void *)address; 321769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn force_sig_info(SIGSEGV, &info, current); 322769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } else { 323769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("KERNEL: Unaligned Access 0x%.8lx\n", address); 324769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn show_registers(regs); 325769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn die("Die:", regs, address); 326769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 327769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 328769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 329769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 330769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnasmlinkage void do_bus_fault(struct pt_regs *regs, unsigned long address) 331769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 332769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn siginfo_t info; 333769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 334769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (user_mode(regs)) { 335769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn /* Send a SIGBUS */ 336769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_signo = SIGBUS; 337769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_errno = 0; 338769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_code = BUS_ADRERR; 339769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_addr = (void *)address; 340769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn force_sig_info(SIGBUS, &info, current); 341769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } else { /* Kernel mode */ 342769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("KERNEL: Bus error (SIGBUS) 0x%.8lx\n", address); 343769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn show_registers(regs); 344769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn die("Die:", regs, address); 345769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 346769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 347769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 348769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonnasmlinkage void do_illegal_instruction(struct pt_regs *regs, 349769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn unsigned long address) 350769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn{ 351769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn siginfo_t info; 352769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn 353769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn if (user_mode(regs)) { 354769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn /* Send a SIGILL */ 355769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_signo = SIGILL; 356769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_errno = 0; 357769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_code = ILL_ILLOPC; 358769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn info.si_addr = (void *)address; 359769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn force_sig_info(SIGBUS, &info, current); 360769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } else { /* Kernel mode */ 361769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn printk("KERNEL: Illegal instruction (SIGILL) 0x%.8lx\n", 362769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn address); 363769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn show_registers(regs); 364769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn die("Die:", regs, address); 365769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn } 366769a8a96229e6b2f1e3a2b3b38e27981f7fb9902Jonas Bonn} 367