uboot/arch/arm/lib/interrupts.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0+
   2/*
   3 * (C) Copyright 2003
   4 * Texas Instruments <www.ti.com>
   5 *
   6 * (C) Copyright 2002
   7 * Sysgo Real-Time Solutions, GmbH <www.elinos.com>
   8 * Marius Groeger <mgroeger@sysgo.de>
   9 *
  10 * (C) Copyright 2002
  11 * Sysgo Real-Time Solutions, GmbH <www.elinos.com>
  12 * Alex Zuepke <azu@sysgo.de>
  13 *
  14 * (C) Copyright 2002-2004
  15 * Gary Jennejohn, DENX Software Engineering, <garyj@denx.de>
  16 *
  17 * (C) Copyright 2004
  18 * Philippe Robin, ARM Ltd. <philippe.robin@arm.com>
  19 */
  20
  21#include <common.h>
  22#include <efi_loader.h>
  23#include <asm/proc-armv/ptrace.h>
  24#include <asm/u-boot-arm.h>
  25#include <efi_loader.h>
  26
  27DECLARE_GLOBAL_DATA_PTR;
  28
  29int interrupt_init (void)
  30{
  31        /*
  32         * setup up stacks if necessary
  33         */
  34        IRQ_STACK_START_IN = gd->irq_sp + 8;
  35
  36        return 0;
  37}
  38
  39void enable_interrupts (void)
  40{
  41        return;
  42}
  43int disable_interrupts (void)
  44{
  45        return 0;
  46}
  47
  48void bad_mode (void)
  49{
  50        panic ("Resetting CPU ...\n");
  51        reset_cpu (0);
  52}
  53
  54static void show_efi_loaded_images(struct pt_regs *regs)
  55{
  56        efi_print_image_infos((void *)instruction_pointer(regs));
  57}
  58
  59static void dump_instr(struct pt_regs *regs)
  60{
  61        unsigned long addr = instruction_pointer(regs);
  62        const int thumb = thumb_mode(regs);
  63        const int width = thumb ? 4 : 8;
  64        int i;
  65
  66        if (thumb)
  67                addr &= ~1L;
  68        else
  69                addr &= ~3L;
  70        printf("Code: ");
  71        for (i = -4; i < 1 + !!thumb; i++) {
  72                unsigned int val;
  73
  74                if (thumb)
  75                        val = ((u16 *)addr)[i];
  76                else
  77                        val = ((u32 *)addr)[i];
  78                printf(i == 0 ? "(%0*x) " : "%0*x ", width, val);
  79        }
  80        printf("\n");
  81}
  82
  83void show_regs (struct pt_regs *regs)
  84{
  85        unsigned long __maybe_unused flags;
  86        const char __maybe_unused *processor_modes[] = {
  87        "USER_26",      "FIQ_26",       "IRQ_26",       "SVC_26",
  88        "UK4_26",       "UK5_26",       "UK6_26",       "UK7_26",
  89        "UK8_26",       "UK9_26",       "UK10_26",      "UK11_26",
  90        "UK12_26",      "UK13_26",      "UK14_26",      "UK15_26",
  91        "USER_32",      "FIQ_32",       "IRQ_32",       "SVC_32",
  92        "UK4_32",       "UK5_32",       "UK6_32",       "ABT_32",
  93        "UK8_32",       "UK9_32",       "HYP_32",       "UND_32",
  94        "UK12_32",      "UK13_32",      "UK14_32",      "SYS_32",
  95        };
  96
  97        flags = condition_codes (regs);
  98
  99        printf("pc : [<%08lx>]     lr : [<%08lx>]\n",
 100               instruction_pointer(regs), regs->ARM_lr);
 101        if (gd->flags & GD_FLG_RELOC) {
 102                printf("reloc pc : [<%08lx>]       lr : [<%08lx>]\n",
 103                       instruction_pointer(regs) - gd->reloc_off,
 104                       regs->ARM_lr - gd->reloc_off);
 105        }
 106        printf("sp : %08lx  ip : %08lx   fp : %08lx\n",
 107               regs->ARM_sp, regs->ARM_ip, regs->ARM_fp);
 108        printf ("r10: %08lx  r9 : %08lx  r8 : %08lx\n",
 109                regs->ARM_r10, regs->ARM_r9, regs->ARM_r8);
 110        printf ("r7 : %08lx  r6 : %08lx  r5 : %08lx  r4 : %08lx\n",
 111                regs->ARM_r7, regs->ARM_r6, regs->ARM_r5, regs->ARM_r4);
 112        printf ("r3 : %08lx  r2 : %08lx  r1 : %08lx  r0 : %08lx\n",
 113                regs->ARM_r3, regs->ARM_r2, regs->ARM_r1, regs->ARM_r0);
 114        printf ("Flags: %c%c%c%c",
 115                flags & CC_N_BIT ? 'N' : 'n',
 116                flags & CC_Z_BIT ? 'Z' : 'z',
 117                flags & CC_C_BIT ? 'C' : 'c', flags & CC_V_BIT ? 'V' : 'v');
 118        printf ("  IRQs %s  FIQs %s  Mode %s%s\n",
 119                interrupts_enabled (regs) ? "on" : "off",
 120                fast_interrupts_enabled (regs) ? "on" : "off",
 121                processor_modes[processor_mode (regs)],
 122                thumb_mode (regs) ? " (T)" : "");
 123        dump_instr(regs);
 124}
 125
 126/* fixup PC to point to the instruction leading to the exception */
 127static inline void fixup_pc(struct pt_regs *regs, int offset)
 128{
 129        uint32_t pc = instruction_pointer(regs) + offset;
 130        regs->ARM_pc = pc | (regs->ARM_pc & PCMASK);
 131}
 132
 133void do_undefined_instruction (struct pt_regs *pt_regs)
 134{
 135        efi_restore_gd();
 136        printf ("undefined instruction\n");
 137        fixup_pc(pt_regs, -4);
 138        show_regs (pt_regs);
 139        show_efi_loaded_images(pt_regs);
 140        bad_mode ();
 141}
 142
 143void do_software_interrupt (struct pt_regs *pt_regs)
 144{
 145        efi_restore_gd();
 146        printf ("software interrupt\n");
 147        fixup_pc(pt_regs, -4);
 148        show_regs (pt_regs);
 149        show_efi_loaded_images(pt_regs);
 150        bad_mode ();
 151}
 152
 153void do_prefetch_abort (struct pt_regs *pt_regs)
 154{
 155        efi_restore_gd();
 156        printf ("prefetch abort\n");
 157        fixup_pc(pt_regs, -8);
 158        show_regs (pt_regs);
 159        show_efi_loaded_images(pt_regs);
 160        bad_mode ();
 161}
 162
 163void do_data_abort (struct pt_regs *pt_regs)
 164{
 165        efi_restore_gd();
 166        printf ("data abort\n");
 167        fixup_pc(pt_regs, -8);
 168        show_regs (pt_regs);
 169        show_efi_loaded_images(pt_regs);
 170        bad_mode ();
 171}
 172
 173void do_not_used (struct pt_regs *pt_regs)
 174{
 175        efi_restore_gd();
 176        printf ("not used\n");
 177        fixup_pc(pt_regs, -8);
 178        show_regs (pt_regs);
 179        show_efi_loaded_images(pt_regs);
 180        bad_mode ();
 181}
 182
 183void do_fiq (struct pt_regs *pt_regs)
 184{
 185        efi_restore_gd();
 186        printf ("fast interrupt request\n");
 187        fixup_pc(pt_regs, -8);
 188        show_regs (pt_regs);
 189        show_efi_loaded_images(pt_regs);
 190        bad_mode ();
 191}
 192
 193void do_irq (struct pt_regs *pt_regs)
 194{
 195        efi_restore_gd();
 196        printf ("interrupt request\n");
 197        fixup_pc(pt_regs, -8);
 198        show_regs (pt_regs);
 199        show_efi_loaded_images(pt_regs);
 200        bad_mode ();
 201}
 202