我想为我的测试夹具的测试导致ARM Cortex-M3未定义指令异常。IAR编译器支持这样的内联汇编:
asm("udf.w #0");
字符串不幸的是,GNU CC内联汇编程序不知道NXP LPC 177 x8 x的此操作码。它编写诊断:
ccw3kZ46.s:404: Error: bad instruction `udf.w #0'
型如何创建一个导致未定义指令异常的函数?
kse8i1jr1#
基于 * Masta 79 * 的回答:在ARMv7-M架构参考手册- ARM DDI 0403 D(documentation placeholder, registration required)中列出了一种“永久未定义”的编码。编码为0xf 7 fXaXXX(其中忽略“X”)。当然,指令提取是little-endian的,所以(没有测试):第一个月应该在任何ARMv7-M或更高版本的处理器上产生有保证的未定义指令。
t9aqgxwy2#
一些额外的信息…GCC的builtins之一是void __builtin_trap(void)
此函数会导致程序异常退出。GCC通过使用依赖于目标的机制(例如故意执行非法指令)或调用abort来实现此功能。使用的机制可能因版本而异,因此您不应依赖任何特定的实现。
implementation for ARMv7 is:
(define_insn "trap" [(trap_if (const_int 1) (const_int 0))] "" "* if (TARGET_ARM) return \".inst\\t0xe7f000f0\"; else return \".inst\\t0xdeff\"; " [(set (attr "length") (if_then_else (eq_attr "is_thumb" "yes") (const_int 2) (const_int 4))) (set_attr "type" "trap") (set_attr "conds" "unconditional")])
(define_insn "trap"
[(trap_if (const_int 1) (const_int 0))]
""
"*
if (TARGET_ARM)
return \".inst\\t0xe7f000f0\";
else
return \".inst\\t0xdeff\";
"
[(set (attr "length")
(if_then_else (eq_attr "is_thumb" "yes")
(const_int 2)
(const_int 4)))
(set_attr "type" "trap")
(set_attr "conds" "unconditional")]
)
字符串因此,对于ARM模式,gcc将生成0x7f000f0 (f0 00 f0 07),对于其他模式,将生成0xdeff (ff de)(在反汇编/调试时很方便)。Also note that:
0x7f000f0 (f0 00 f0 07)
0xdeff (ff de)
these encodings match the UDF instruction that is defined in the mostrecent edition of the ARM architecture reference manual.Thumb: 0xde00 | imm8 (we chose 0xff for the imm8)ARM: 0xe7f000f0 | (imm12 << 8) | imm4 (we chose to use 0 for both imms)
these encodings match the UDF instruction that is defined in the most
recent edition of the ARM architecture reference manual.
Thumb: 0xde00 | imm8 (we chose 0xff for the imm8)
ARM: 0xe7f000f0 | (imm12 << 8) | imm4 (we chose to use 0 for both imms)
型对于LLVM__builtin_trap,生成的值为0xe7ffdefe和0xdefe:
__builtin_trap
0xe7ffdefe
0xdefe
case ARM::TRAP: { // Non-Darwin binutils don't yet support the "trap" mnemonic. // FIXME: Remove this special case when they do. if (!Subtarget->isTargetDarwin()) { //.long 0xe7ffdefe @ trap uint32_t Val = 0xe7ffdefeUL; OutStreamer.AddComment("trap"); OutStreamer.EmitIntValue(Val, 4); return; } break;}case ARM::tTRAP: { // Non-Darwin binutils don't yet support the "trap" mnemonic. // FIXME: Remove this special case when they do. if (!Subtarget->isTargetDarwin()) { //.short 57086 @ trap uint16_t Val = 0xdefe; OutStreamer.AddComment("trap"); OutStreamer.EmitIntValue(Val, 2); return; } break;}
case ARM::TRAP: {
// Non-Darwin binutils don't yet support the "trap" mnemonic.
// FIXME: Remove this special case when they do.
if (!Subtarget->isTargetDarwin()) {
//.long 0xe7ffdefe @ trap
uint32_t Val = 0xe7ffdefeUL;
OutStreamer.AddComment("trap");
OutStreamer.EmitIntValue(Val, 4);
return;
}
break;
case ARM::tTRAP: {
//.short 57086 @ trap
uint16_t Val = 0xdefe;
OutStreamer.EmitIntValue(Val, 2);
型
vltsax253#
在[1]中有不同的官方未定义指令(查找UDF;下面的.可以用任何十六进制数字替换):
.
0xe7f...f.
0xde..
0xf7f.a...
0x0000....
还有其他的,但这些可能是未来的证明,因为它得到。至于生成触发它的代码,您可以使用.short或.word,如下所示:
.short
.word
asm volatile (".short 0xde00\n");
asm volatile (".word 0xe7f000f0\n");
asm volatile (".word 0xe7f0def0\n");
注意,最后一个将在thumb上下文中解码为0xdef0,0xe7f0,因此也会导致未定义的指令异常。[1][http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.subset.architecture.reference/index.html](http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.subset.architecture.reference/index.html)[2] DDI0487D_b_armv8_arm.pdf
0xdef0
0xe7f0
xuo3flqw4#
永久未定义指令的thumb-16版本是0xDExx。因此,您可以在代码中执行以下操作来触发异常:
0xDExx
.inst 0xde00
字符串参考:ARMv7-M架构参考手册,第A5.2.6节。(Note 0xF 7 Fx,0xAxxx编码也是永久未定义的,但它是32位指令。)
4条答案
按热度按时间kse8i1jr1#
基于 * Masta 79 * 的回答:
在ARMv7-M架构参考手册- ARM DDI 0403 D(documentation placeholder, registration required)中列出了一种“永久未定义”的编码。编码为0xf 7 fXaXXX(其中忽略“X”)。当然,指令提取是little-endian的,所以(没有测试):
第一个月
应该在任何ARMv7-M或更高版本的处理器上产生有保证的未定义指令。
t9aqgxwy2#
一些额外的信息…
GCC的builtins之一是
void __builtin_trap(void)
此函数会导致程序异常退出。GCC通过使用依赖于目标的机制(例如故意执行非法指令)或调用abort来实现此功能。使用的机制可能因版本而异,因此您不应依赖任何特定的实现。
implementation for ARMv7 is:
字符串
因此,对于ARM模式,gcc将生成
0x7f000f0 (f0 00 f0 07)
,对于其他模式,将生成0xdeff (ff de)
(在反汇编/调试时很方便)。Also note that:
型
对于LLVM
__builtin_trap
,生成的值为0xe7ffdefe
和0xdefe
:型
vltsax253#
在[1]中有不同的官方未定义指令(查找UDF;下面的
.
可以用任何十六进制数字替换):0xe7f...f.
- ARM或A1编码(ARMv 4 T、ARMv 5 T、ARMv 6、ARMv7、ARMv 8)0xde..
- Thumb或T1编码(ARMv 4 T、ARMv 5 T、ARMv 6、ARMv7、ARMv 8)0xf7f.a...
-Thumb 2或T2编码(ARMv 6 T2、ARMv7、ARMv 8)0x0000....
-ARMv 8-A永久未定义还有其他的,但这些可能是未来的证明,因为它得到。
至于生成触发它的代码,您可以使用
.short
或.word
,如下所示:asm volatile (".short 0xde00\n");
/* thumb非法指令 */asm volatile (".word 0xe7f000f0\n");
/* arm非法指令 */asm volatile (".word 0xe7f0def0\n");
/* arm+thumb非法指令 */注意,最后一个将在thumb上下文中解码为
0xdef0
,0xe7f0
,因此也会导致未定义的指令异常。[1][http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.subset.architecture.reference/index.html](http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.subset.architecture.reference/index.html)
[2] DDI0487D_b_armv8_arm.pdf
xuo3flqw4#
永久未定义指令的thumb-16版本是
0xDExx
。因此,您可以在代码中执行以下操作来触发异常:字符串
参考:ARMv7-M架构参考手册,第A5.2.6节。
(Note 0xF 7 Fx,0xAxxx编码也是永久未定义的,但它是32位指令。)