試したソースはこれです。
/*volatile*/
unsigned
char bar1;
/*volatile*/
unsigned
char bar;
void
tst_bar_bit0(void)
{
if(bar1&1)
bar &= ~1;
else
bar |= 1;
}rx-elf-gccで-O2 -fomitframe-pointerでコンパイルすると
0000 FB E2 00 00 00 00 mov.L #_bar1, r14
0006 CC EE mov.B [r14], r14
0008 FD 74 CE 01 tst #1, r14
000c FB E2 00 00 00 00 mov.L #_bar, r14
0012 1C bne .L5
0013 F0 E0 bset #0, [r14].B
0015 02 rts
.L5:
0016 F0 E8 bclr #0, [r14].B
0018 02 rtsこうなります。(注:改造したrx-elf-gccを使っているので出力コードが違うことがあります)
色の付いたところをbtst命令を使うようにしてみます。
rx.mdの
tstsiの前に以下を追加します。
(define_insn "*btstsi"
[(set (reg:CC_ZS CC_REG)
(compare:CC_ZS
(and:SI (match_operand:SI 0 "register_operand" "r")
(match_operand:SI 1 "const_int_operand" "i"))
(const_int 0)))]
"reload_completed
&& exact_log2 (INTVAL (operands[1]) & 0xff) >= 0
&& exact_log2 (INTVAL (operands[1]) & 0xff) <= 31"
"*
{
rtx xoperands[2];
xoperands[0] = operands[0];
xoperands[1] = GEN_INT (exact_log2 (INTVAL (operands[1])));
output_asm_insn (\"btst\\t%1, %0\", xoperands);
return \"\";
}
"
[(set_attr "timings" "11")
(set_attr "length" "3")]
)
ビルドしたgccでコンパイルすると
0000 FB E2 00 00 00 00 mov.L #_bar1, r14
0006 CC EE mov.B [r14], r14
0008 7C 0E btst #0, r14
000a FB E2 00 00 00 00 mov.L #_bar, r14
0010 1C bne .L5
0011 F0 E0 bset #0, [r14].B
0013 02 rts
.L5:
0014 F0 E8 bclr #0, [r14].B
0016 02 rts
btst命令を使うようになりました。おまけにサイズも小さくなってます。
[0回]
PR