The simple code below:

==============================
#include <stdio.h>
#include <stdint.h>

#define ppc_mask64(n)   ((n) == 64 ? (-1LL) : (1LL << (n)) - 1)

uint64_t ppc_set_field64u(uint64_t v, uint64_t s, int32_t u, int32_t l) {
        uint64_t mask = ppc_mask64(u - l + 1) << l;
        return (v & ~mask) | ((s << l) & mask);
}

double ppc_set_fieldd(double v, uint64_t s, int32_t u, int32_t l) {
        double x;
        *((uint64_t *)&x) = ppc_set_field64u(*((uint64_t *)&v), s, u, l);
        return x;
}

double ppc_set_fieldd_bug(double v, uint64_t s, int32_t u, int32_t l) {
        *((uint64_t *)&v) = ppc_set_field64u(*((uint64_t *)&v), s, u, l);
        return v;
}

int main(void) {
        double x = 1.1, y, z;
        printf("%016Lx\n", *(uint64_t *)&x);
        y = ppc_set_fieldd(x, 0xff, 31, 24);
        printf("%016Lx\n", *(uint64_t *)&y);
        z = ppc_set_fieldd_bug(x, 0xff, 31, 24);
        printf("%016Lx\n", *(uint64_t *)&z);
}
====================

produces with -O2 or -O3 :

3ff199999999999a
3ff19999ff99999a
3ff199999999999a

while it should produces (no optimization or -O):
3ff199999999999a
3ff19999ff99999a
3ff19999ff99999a


-- 
           Summary: Bad generated code with integer/float pointer cast
                    assignment and with optimization.
           Product: gcc
           Version: 4.4.1
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: c
        AssignedTo: unassigned at gcc dot gnu dot org
        ReportedBy: casse at irit dot fr
 GCC build triplet: i486-linux-elf
  GCC host triplet: i486-linux-elf
GCC target triplet: i486-linux-elf


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

Reply via email to