On such platforms:
gcc version 3.2.2 20030222 (Red Hat Linux 3.2.2-5)
gcc version 3.3.3 (SuSE Linux)

Source Code:
void func(unsigned char *buf)
{
        unsigned short *p, a, b, c, d;
        unsigned int *q, m, n;
        unsigned int i1 = 0x1111;
        unsigned int i2 = 0x2222;
        unsigned int i3 = 0x3333;
        unsigned int i4 = 0x4444;
        unsigned int mod1 = 0x5555;
        unsigned int mod2 = 0x6666;
        unsigned int mod3 = 0x7777;
        unsigned int mod4 = 0x8888;

        p = (unsigned short *)buf;
        a = *p;
        b = *(p + 2);
        c = *(p + 4);
        d = *(p + 6);

        c = d^0x1234;
        b = c^0x2345;
        a = b^0x3456;

        *p = a;
        *(p + 2) = b;
        *(p + 4) = c;

        q = (unsigned int *)buf;
        m = *q;
        *q = ((*q * i1) % mod1) ^ 0xabcd;
        q++;
        n = *q;
        *q = ((*q * i2) % mod2) ^ 0xbcde ^ (m & 0xffff);
        q++;
        m = *q;
        *q = ((*q * i3) % mod3) ^ 0xcdef ^ (n & 0xffff);
        q++;
        *q = ((*q * i4) % mod4) ^ 0xdef1 ^ (m & 0xffff);
        return; 
}

when compiled with O2 or O3 options, such as "gcc -O2 a.c", the problem is:
when "m" was assigned first, buf[0] & buf[1] was NOT updated by "a".
the asm code like this:
...
xor 0x3456, eax; <- a
mov [ebx], esi; <- m was assigned value of OLD buf[0 ~ 3]
mov ax, [ebx]; <- buf[0] & buf[1] was updated by a
imul 0x1111, esi;
...

as a constrast, when compiled with O1 or none options, such like "gcc -O1 a.c"
or "gcc a.c", the asm code like this:
...
xor 0x3456, eax;
mov ax, [ebx]; 
mov [ebx], esi;
imul 0x1111, esi;
...

when change the order of "*p = a; *(p + 2) = b; *(p + 4) =c" 
to "*(p + 4) = c; *(p + 2) = b; *p = a",
compiled with O2 or O3 option, the result was correct too.


-- 
           Summary: program was compiled wrong when use GCC O2 or O3 option
           Product: gcc
           Version: 3.3.3
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: c
        AssignedTo: unassigned at gcc dot gnu dot org
        ReportedBy: lucifer_ww at yahoo dot com


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

Reply via email to