Elimination of duplicate sign extensions
Fu, Chao-Ying
fu@mips.com
Fri Sep 21 20:30:00 GMT 2007
Hi,
I found new regressions for fixed-point tests on 9/20/2007,
due to the missing of sign/zero extension.
Please check the following code for __cmpuha2 in libgcc.
The OLD CODE has zero extension, but the NEW CODE doesn't.
This causes wrong comparison results.
Any idea to fix this? Is my libgcc code wrong? Or should GCC
sign/zero-extend "x" and "y" after memcpy?
Thanks a lot!
Regards,
Chao-ying
Ex:
/* FIXED_C_TYPE is unsigned short _Accum (2 bytes), passed from a 32-bit register,
but the upper 16-bit is not zero/sign-extended on purpose. For fixed-point
arithmetic, we don't care about the bits beyond type sizes (2 bytes for example).
INT_C_TYPE is unsigned short.
After memcpy, I think x and y should be properly zero/sign-extended.*/
word_type
FIXED_CMP (FIXED_C_TYPE a, FIXED_C_TYPE b)
{
INT_C_TYPE x, y;
memcpy (&x, &a, FIXED_SIZE);
memcpy (&y, &b, FIXED_SIZE);
if (x < y)
return 0;
else if (x > y)
return 2;
return 1;
}
(OLD CODE)
80020d74 <__cmpuha2>:
80020d74: 3084ffff andi a0,a0,0xffff <----------------
80020d78: 30a3ffff andi v1,a1,0xffff <----------------
80020d7c: 0083102b sltu v0,a0,v1 <--------------
80020d80: 14400005 bnez v0,80020d98 <__cmpuha2+0x24>
80020d84: 00003021 move a2,zero
80020d88: 0064182b sltu v1,v1,a0
80020d8c: 24060001 li a2,1
80020d90: 24020002 li v0,2
80020d94: 0043300b movn a2,v0,v1
80020d98: 03e00008 jr ra
80020d9c: 00c01021 move v0,a2
(NEW CODE)
80020da8 <__cmpuha2>:
80020da8: 0085102b sltu v0,a0,a1 <---------------
80020dac: 14400006 bnez v0,80020dc8 <__cmpuha2+0x20>
80020db0: 00a4182b sltu v1,a1,a0
80020db4: 24020002 li v0,2
80020db8: 24060001 li a2,1
80020dbc: 0043300b movn a2,v0,v1
80020dc0: 03e00008 jr ra
80020dc4: 00c0102d move v0,a2
80020dc8: 0000302d move a2,zero
80020dcc: 03e00008 jr ra
80020dd0: 00c0102d move v0,a2
80020dd4: 00000000 nop
More information about the Gcc-patches
mailing list