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

            Bug ID: 80794
           Summary: constant objects can be assumed to be immutable
           Product: gcc
           Version: 7.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: tree-optimization
          Assignee: unassigned at gcc dot gnu.org
          Reporter: msebor at gcc dot gnu.org
  Target Milestone: ---

Modifying a const object is undefined (1.9, p4 and 3.3, p1.1 of C++17). 
Therefore, valid C++ programs can be relied on not to modify const objects or
subobjects to improve the efficiency of accessing such objects.  For example,
in both function foo and bar in the test case below, GCC can assume that the
value of the s.i member after the call to s.f() is the same as its value before
the call, and eliminate the test for the inequality.

This should also hold for C but I suspect C programs more commonly violate this
constraint than C++ programs do.

$ cat t.C && gcc -O2 -S -Wall -Wextra -fdump-tree-optimized=/dev/stdout t.C
struct S
{
  const int i;

  S (int x): i (x) { }

  void f () const;
};

const S s (123);

void foo ()
{
  int i = s.i;
  s.f ();
  int j = s.i;

  if (i != j) __builtin_abort ();
}

void bar (const S &s)
{
  int i = s.i;
  s.f ();
  int j = s.i;

  if (i != j) __builtin_abort ();
}


;; Function void foo() (_Z3foov, funcdef_no=3, decl_uid=2318, cgraph_uid=3,
symbol_order=4)

void foo() ()
{
  int j;
  int i;

  <bb 2> [100.00%]:
  i_2 = s.i;
  S::f (&s);
  j_4 = s.i;
  if (i_2 != j_4)
    goto <bb 3>; [0.04%]
  else
    goto <bb 4>; [99.96%]

  <bb 3> [0.04%]:
  __builtin_abort ();

  <bb 4> [99.96%]:
  return;

}



;; Function void bar(const S&) (_Z3barRK1S, funcdef_no=4, decl_uid=2323,
cgraph_uid=4, symbol_order=5)

void bar(const S&) (const struct S & s)
{
  int j;
  int i;

  <bb 2> [100.00%]:
  i_3 = s_2(D)->i;
  S::f (s_2(D));
  j_5 = s_2(D)->i;
  if (i_3 != j_5)
    goto <bb 3>; [0.04%]
  else
    goto <bb 4>; [99.96%]

  <bb 3> [0.04%]:
  __builtin_abort ();

  <bb 4> [99.96%]:
  return;

}



;; Function (static initializers for t.C) (_GLOBAL__sub_I__Z3foov,
funcdef_no=6, decl_uid=2332, cgraph_uid=6, symbol_order=7) (executed once)

(static initializers for t.C) ()
{
  <bb 2> [100.00%]:
  MEM[(struct  &)&s] ={v} {CLOBBER};
  s.i = 123;
  return;

}

Reply via email to