简体   繁体   English

软件中断异常还是未定义的指令异常?

[英]Software interrupt exception or undefined instruction exception?

I am running a program on a bare-metal ARM (v5TE-compliant) with a JTAG connector and gdb. 我正在使用JTAG连接器和gdb在裸机ARM(兼容v5TE)上运行程序。 The program runs from some SDRAM in supervisor mode, and uses only arm instructions. 该程序在管理员模式下从某些SDRAM运行,并仅使用arm指令。

At some point an exception occurs. 在某些时候发生异常。 Stopping gdb with ctrl+CI can see that the CPSR indicates an undefined exception mode, however the program counter indicates a software interrupt exception ( 0xffff0008 ). 使用ctrl + CI停止gdb可以看到CPSR指示未定义的异常模式,但程序计数器指示软件中断异常( 0xffff0008 )。 According to the ARM ARM, when an undefined instruction exception occurs, the PC_und should be 0xffff0004 or 0x00000004 . 根据ARM ARM,当发生未定义的指令异常时, PC_und应为0xffff00040x00000004 What's happening to my program, did a SWI happen or an undefined instruction exception? 我的程序发生了什么,发生了SWI还是未定义的指令异常?

edit to make my question clearer: 编辑以使我的问题更清楚:

My program purpose is to test the hardware of the custom board. 我的程序目的是测试自定义板的硬件。 When there is a hardware problem, there can be a corruption from the program in RAM (as can be seen below) which is the cause of the exception generated. 当存在硬件问题时,RAM中的程序可能会损坏(如下所示),这是产生异常的原因。 When the hardware is normal the test software runs without problem. 当硬件正常时,测试软件运行没有问题。 My RAM addresses range from 0 to 0x40000000, the program is loaded between 0x1000 and 0x2000. 我的RAM地址范围从0到0x40000000,程序加载在0x1000和0x2000之间。 The supervisor mode stack pointer is set to 0xff0. 管理程序模式堆栈指针设置为0xff0。 The interruption vector consists only of breakpoints. 中断向量仅包含断点。

(gdb) c
Continuing.
^C^C
Program received signal SIGTRAP, Trace/breakpoint trap.
0xffff0008 in ?? ()

Registers from the undefined exception mode: 从未定义的异常模式注册:

(gdb) i r 
r0             0x52878  338040
r1             0x2020000    33685504
r2             0x2020000    33685504
r3             0x2020000    33685504
r4             0x2020000    33685504
r5             0x2020000    33685504
r6             0x2020000    33685504
r7             0x2020000    33685504
r8             0x2020000    33685504
r9             0x2020000    33685504
r10            0x2020000    33685504
r11            0x2020000    33685504
r12            0x2020000    33685504
sp             0x2020000    0x2020000
lr             0xffff0008   4294901768
pc             0xffff0008   0xffff0008
fps            0x0  0
cpsr           0x800000db   2147483867

Registers from the supervisor mode: 来自主管模式的注册:

(gdb) set $cpsr=0xd3
(gdb) i r
r0             0x52878  338040
r1             0x2020000    33685504
r2             0x2020000    33685504
r3             0x2020000    33685504
r4             0x2020000    33685504
r5             0x2020000    33685504
r6             0x2020000    33685504
r7             0x2020000    33685504
r8             0x2020000    33685504
r9             0x2020000    33685504
r10            0x2020000    33685504
r11            0x2020000    33685504
r12            0x2020000    33685504
sp             0xff3ffffe   0xff3ffffe
lr             0x1020   4128
pc             0xffff0008   0xffff0008
fps            0x0  0
cpsr           0xd3 211 

Here is the (corrupted)program in RAM around the address pointed by the supervisor link register: 这是RAM中的(损坏的)程序,它围绕着管理程序链接寄存器指向的地址:

(gdb) x/5i 0x1020-8
0x1018 <_start+24>: bic r0, r0, #135168 ; 0x21000
0x101c <_start+28>: strbcs  r0, [r0], #1025
0x1020 <_start+32>: mcr 15, 0, r0, cr1, cr0, {0}
0x1024 <_start+36>: ldr r1, [pc, #120]  ; 0x10a4 <skip_intreg_reset+100>
0x1028 <_start+40>: ldr r2, [r1, #8]

(gdb) x/4w 0x1018
0x1018 <_start+24>: 0xe3c00a01  
0x101C <_start+28>: 0xfec00401
0x1020 <_start+32>: 0xee010f10  
0x1024 <_start+36>: 0xe59f1078

dump from the program object file: 从程序对象文件转储:

  18:   e3c00a01    bic r0, r0, #4096   ; 0x1000
  1c:   e3c00001    bic r0, r0, #1  ; 0x1
  20:   ee010f10    mcr 15, 0, r0, cr1, cr0, {0}
  24:   e59f1078    ldr r1, [pc, #120]  ; a4 <skip_intreg_reset+0x64>
  28:   e5912000    ldr r2, [r1]

This is a community wiki answer. 这是社区维基的答案。

The issue was caused by two different problems: 问题是由两个不同的问题引起的:

  • The wrong vector table was being initialized. 正在初始化错误的向量表。 The ARM has selectable high and low vectors and high 0xffff0000 was the default, whereas the code was initialized as if the vector table was at 0x00000000 . ARM具有可选的高和低向量,高0xffff0000是默认值,而代码初始化,就像向量表位于0x00000000 The high vector table contained the following instructions (infinite loops on exceptions): 高向量表包含以下指令(异常上的无限循环):
 0xffff0000: b 0xffff0020 0xffff0004: b 0xffff0004 0xffff0008: b 0xffff0008 0xffff000c: b 0xffff000c 0xffff0010: b 0xffff0010 0xffff0014: b 0xffff0014 0xffff0018: b 0xffff0018 0xffff001c: b 0xffff001c 
  • The SDRAM issues on the board caused the program content in RAM to be corrupted and to generate undefined exceptions. 电路板上的SDRAM问题导致RAM中的程序内容被破坏并产生未定义的异常。 Following that the program stopped responding as it was in an infinite loop and the OP stopped gdb. 之后程序停止响应,因为它处于无限循环中并且OP停止了gdb。 The JTAG debugger used (peedi) actually jumps to the next instruction when gdb is stopped with ctrl+C , that's why the pc was 0xffff0008 even though the cpsr indicated an undefined exception situated at 0xffff0004 . 当使用ctrl+C停止gdb时,使用的JTAG调试器(peedi)实际上会跳转到下一条指令,这就是为什么pc0xffff0008即使cpsr指示位于0xffff0004的未定义异常。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM