On 12/23/2009 06:12 PM, Dave Korn wrote:
Jie Zhang wrote:
typedef unsigned short u16;
typedef unsigned int u32;
u32 a(volatile u16* off) {
return *off;
}
mingw32-gcc-4.3.0.exe -c -O2 -fomit-frame-pointer -mtune=core2 test.c
it produces:
00000000<_a>:
0: 8b 44 24 04 mov 0x4(%esp),%eax
4: 0f b7 00 movzwl (%eax),%eax
7: 0f b7 c0 movzwl %ax,%eax<== The redundant insn
a: c3 ret
How does it look at the RTL level? I wonder if this situation is similar to
the one being discussed in the other current thread "Which optimizer should
remove redundant subreg of sign_extension?"
With my native GCC on Debian AMD64 unstable, in t.c.128r.expand:
(insn 6 5 7 3 t.c:5 (set (reg:HI 58 [ D.1595 ])
(mem/v:HI (reg/v/f:DI 60 [ off ]) [2 S2 A16])) -1 (nil))
(insn 7 6 8 3 t.c:5 (set (reg:SI 61)
(zero_extend:SI (reg:HI 58 [ D.1595 ]))) -1 (nil))
In t.c.201r.shorten:
(insn:TI 6 3 7 t.c:5 (set (reg:HI 0 ax [orig:58 D.1595 ] [58])
(mem/v:HI (reg/v/f:DI 5 di [orig:60 off ] [60]) [2 S2 A16])) 53
{*movhi_1} (expr_list:REG_DEAD (reg/v/f:DI 5 di [orig:60 off ] [60])
(nil)))
(insn:TI 7 6 18 t.c:5 (set (reg:SI 0 ax [orig:61 D.1595 ] [61])
(zero_extend:SI (reg:HI 0 ax [orig:58 D.1595 ] [58]))) 114
{*zero_extendhisi2_movzwl} (nil))
There is a volatile flag for mem operand. If there is no such flag, I
think one of RTL passes might combine them. It looks similar with the
issue in the thread you mentioned. But the cause is different.
Regards,
Jie