This is the mail archive of the gcc-bugs@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[Bug rtl-optimization/70526] GCC 6 miscompiles Firefox JIT compiler


https://gcc.gnu.org/bugzilla/show_bug.cgi?id=70526

--- Comment #2 from Marc Glisse <glisse at gcc dot gnu.org> ---
(In reply to Markus Trippelsdorf from comment #1)
> -Wstrict-aliasing=2 warns:
> 
> markus@x4 tmp % g++ -O2 -Wstrict-aliasing=2 test_fire.cpp
> test_fire.cpp: In instantiation of âconst T* AlignedStorage2<T>::addr()
> const [with T = Register]â:
> test_fire.cpp:41:52:   required from here
> test_fire.cpp:13:34: warning: dereferencing type-punned pointer will break
> strict-aliasing rules [-Wstrict-aliasing]
>    const T* addr() const { return reinterpret_cast<const T*>(u.mBytes); }
> 
> -fno-strict-aliasing fixes the issue, thus invalid.

Isn't that a bit fast? -Wstrict-aliasing=3 doesn't warn, the read and the write
are both done in type Register. Reducing a bit:

typedef unsigned uint32_t;

template<typename T>
struct AlignedStorage2
{
  char mBytes[sizeof(T)];

  const T* addr() const { return reinterpret_cast<const T*>(mBytes); }
  T* addr() { return reinterpret_cast<T*>(mBytes); }
};

struct Register {
    uint32_t reg_;
};

class TypedOrValueRegister
{
    AlignedStorage2<Register> typed;
    __attribute__((noinline)) Register& dataTyped() { return *typed.addr(); }
  public:
    TypedOrValueRegister(Register reg)
    {
      dataTyped() = reg;
    }
    Register typedReg() const { return *typed.addr(); }
};

int main() {
    Register reg = { 10u };
    if (TypedOrValueRegister(reg).typedReg().reg_ != 10)
      __builtin_abort();
    return 0;
}

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]