Nothing in the IL of the following testcase prevents the stores
to *q and *r in function doit from being reordered:

extern "C" void * malloc(__SIZE_TYPE__);
extern "C" void abort(void);

void *p;
void __attribute__((noinline)) init(void)
{
  p = malloc(4);
}

inline void *operator new(__SIZE_TYPE__)
{
  return p;
}

inline void operator delete (void*) {}

int * __attribute__((noinline)) doit(void)
{
  float *q = new float;
  *q = 1.0;
  delete q;
  int *r = new int;
  *r = 1;
  return r;
}

int main()
{
  if (*doit() != 1)
    abort();
  return 0;
}

from the first alias run results:

int* doit() ()
{
  void * D.1643;
  void * D.1643;
  void * D.1639;
  void * D.1639;
  int * r;
  float * q;

<bb 2>:
  # VUSE <p_14(D)>
  D.1639_7 = p;
  q_2 = (float *) D.1639_7;
  # SMT.6_16 = VDEF <SMT.6_15(D)>
  *q_2 = 1.0e+0;
  # VUSE <p_14(D)>
  D.1643_8 = p;
  r_4 = (int *) D.1643_8;
  # SMT.7_18 = VDEF <SMT.7_17(D)>
  *r_4 = 1;
  return r_4;

}

One way to fix this is to make sure that if operator new is inlined
we insert a CHANGE_DYNAMIC_TYPE_EXPR.


-- 
           Summary: C++ operator new and new expression do not change
                    dynamic type
           Product: gcc
           Version: 4.3.0
            Status: UNCONFIRMED
          Keywords: wrong-code, alias
          Severity: normal
          Priority: P3
         Component: c++
        AssignedTo: unassigned at gcc dot gnu dot org
        ReportedBy: rguenth at gcc dot gnu dot org


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

Reply via email to