Skip to content

Latest commit

 

History

History
190 lines (144 loc) · 5.51 KB

200904201502.txt.md

File metadata and controls

190 lines (144 loc) · 5.51 KB

24.14 MIPS/Debian上嵌入式汇编中自动插入nop充任delay slot

http://scz.617.cn/unix/200904201502.txt

Q:

$ as -v GNU assembler version 2.17 (mips-linux-gnu) using BFD version 2.17 Debian GNU/Linux $ gcc-2.95 -v gcc version 2.95.4 20011002 (Debian prerelease)


int main ( int argc, char * argv[] ) { asm volatile ("

text_begin:

lui     $3, %hi(0x51211314)
jalr    $3
/*
 * 我想让这条ori充任delay slot,结果编译下来,在jalr与ori之间自动插入
 * 了nop指令充任delay slot,有办法禁止这个行为吗?
 */
ori     $3, %lo(0x51211314)

");

return( 0 );

} /* end of main */

$ gcc-2.95 -Wall -pipe -o mips_inline_asm mips_inline_asm.c $ gdb ./mips_inline_asm (gdb) x/4i text_begin 0x400748 <text_begin>: lui v1,0x5121 0x40074c <text_begin+4>: jalr v1 0x400750 <text_begin+8>: nop // 自动插入nop充任delay slot 0x400754 <text_begin+12>: ori v1,v1,0x1314 (gdb)

编译过程中as自动在jalr指令后面插入nop充任delay slot,但这个行为干挠了我的 实验,有无办法禁止这种自动插入nop充任delay slot的行为。

D: Nineveh@SMTH


int main ( int argc, char * argv[] ) { asm volatile ("

text_begin:

li      $3, 0x51211314
jalr    $3
/*
 * 我想让这条ori充任delay slot,结果编译下来,在jalr与ori之间自动插入
 * 了nop指令充任delay slot,有办法禁止这个行为吗?
 */
ori     $4, $0, 0x7F

");

return( 0 );

} /* end of main */

$ gcc-2.95 -Wall -pipe -o mips_inline_asm mips_inline_asm.c $ gdb ./mips_inline_asm (gdb) x/5i text_begin 0x400748 <text_begin>: lui v1,0x5121 0x40074c <text_begin+4>: ori v1,v1,0x1314 0x400750 <text_begin+8>: jalr v1 0x400754 <text_begin+12>: nop // 自动插入nop充任delay slot 0x400758 <text_begin+16>: li a0,0x7f (gdb)

关于delay slot,填什么指令是汇编器决定的,写的时候把"ori $4, $0, 0x7F"放到 jalr前面,汇编出来的ori就会被放到delay slot里。


int main ( int argc, char * argv[] ) { asm volatile ("

text_begin:

li      $3, 0x51211314
ori     $4, $0, 0x7F
jalr    $3

");

return( 0 );

} /* end of main */

$ gcc-2.95 -Wall -pipe -o mips_inline_asm mips_inline_asm.c $ gdb ./mips_inline_asm (gdb) x/4i text_begin 0x400748 <text_begin>: lui v1,0x5121 0x40074c <text_begin+4>: ori v1,v1,0x1314 0x400750 <text_begin+8>: jalr v1 0x400754 <text_begin+12>: li a0,0x7f // 就是那条"ori $4, $0, 0x7F",现在是伪指令形式 (gdb)

A: scz@nsfocus 2009-04-20 15:02

由汇编器决定delay slot是什么无法满足我的原始需求,现在我需要精确控制每一条 汇编指令,即使我将错误的指令放在delay slot上也不能自动替我"修正"。


int main ( int argc, char * argv[] ) { asm volatile ("

text_begin:

lui     $3, 0x5121
/*
 * 我想让这条指令充任jalr的delay slot,若按Nineveh所述将该指令置于jalr
 * 之前,最终并不能达到目的。
 */
ori     $3, $3, 0x1314
jalr    $3

");

return( 0 );

} /* end of main */

$ gcc-2.95 -Wall -pipe -o mips_inline_asm mips_inline_asm.c $ gdb ./mips_inline_asm (gdb) x/4i text_begin 0x400748 <text_begin>: lui v1,0x5121 0x40074c <text_begin+4>: ori v1,v1,0x1314 // 该指令未被放到delay slot上 0x400750 <text_begin+8>: jalr v1 0x400754 <text_begin+12>: nop (gdb)

我的原始需求动用".set noreorder"即可解决:


int main ( int argc, char * argv[] ) { asm volatile ("

.set    noreorder

text_begin:

lui     $3, %hi(0x51211314)
jalr    $3
ori     $3, %lo(0x51211314)

.set    reorder

");

return( 0 );

} /* end of main */

$ gcc-2.95 -Wall -pipe -o mips_inline_asm mips_inline_asm.c $ gdb ./mips_inline_asm (gdb) x/3i text_begin 0x400748 <text_begin>: lui v1,0x5121 0x40074c <text_begin+4>: jalr v1 0x400750 <text_begin+8>: ori v1,v1,0x1314 // 这次没有自动插入nop

顺便说一句,我的原始实验如下:

(gdb) r

Program received signal SIGSEGV, Segmentation fault.

0x51210000 in ?? () (gdb) i r v1 pc v1: 0x51211314 pc: 0x51210000

jalr导致跳转进行中,然后位于delay slot的ori指令被执行,这个实验仅仅是想验 证妄图以此方式跳转到0x51211314是不可能的,delay slot被执行时跳转已在进行中, delay slot不能用来改变跳转的目标地址。