some disasm listings to show what is going wrong..
i cant find the guilty source files:-(
000fa8b2 <___pack_d>:
<snip>
fadb7:   75 42           push.w:g r2    //pushing 64 bit exponent [63:48]
fadb9:   75 42           push.w:g r2    //pushing 64 bit exponent [47:32]
fadbb:   75 42           push.w:g r2    //pushing 64 bit exponent [31:16]
fadbd:   75 40           push.w:g r0    //pushing 64 bit exponent [15:0]
fadbf:   75 c2 34 00     mov.w:g #52,r2 //shift count to get exponent in
[62:52]
fadc3:   fd 83 6f 0f     jsr.a f6f83 <___ashldi3>
___ashldi3 detects that it needs to shift more then 32 bits and prepares to
shift by -(32-52) = 20 bits (and after that 'shift' by 32 by moving registers
around)

000f6f83 <___ashldi3>:
<snip>
f7055:   73 b2 07        mov.w:g 7[fb],r2     //src bit[15:0]
f7058:   73 b0 05        mov.w:g 5[fb],r0     //src bit[31:16]
f705b:   72 b2 e2        mov.b:g -30[fb],r1l  //shift count (20)
f705e:   72 23           mov.b:g r1l,r1h      //shift count (20)
f7060:   eb 21           sha.l r1h,r2r0       //the shift

The M16C/60, M16C/20, M16C/Tine Series Software Manual says:
"If src is a register and you selected (.W) or (.L) for
 the size specifier (.size), the number of shifts 
 is –16 to +16. Although you can set 0, no bits are shifted and
 no flags are changed. If you set a value less than –16 or 
 greater than +16, the result of shift is indeterminate."

the actual result on my hardware is a shift by 4 (20 & 0xf).

i think ___ashldi3 (and friends!)
should (also) check if the shift is >16 
and only do the shift % 16 with the shift instruction and do the rest of the
shift by moving registers.


-- 
           Summary: M16C invalid shift count used by pack_d -> ashldi3
           Product: gcc
           Version: 4.1.1
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: c
        AssignedTo: unassigned at gcc dot gnu dot org
        ReportedBy: eightdot at hotmail dot com
 GCC build triplet: i686-pc-linux-gnu
  GCC host triplet: i686-pc-linux-gnu
GCC target triplet: m32c-unknown-elf


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=40129

Reply via email to