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

--- Comment #2 from Jakub Jelinek <jakub at gcc dot gnu.org> ---
long long int c = 3623214276426624192LL;
unsigned short b;
char a = 42;
const long long &min(const long long &x, const long long &y) { return x < y ? x
: y; }
__attribute__((noipa)) void test() { b = min(a, min(a, c) +
5713568809962283044LL); }
int main() { test(); if (b != 42) __builtin_abort(); }

ifcombine "optimizes" the IMO correct:
  <bb 2> [local count: 1073741824]:
  a.1_1 = a;
  _2 = (long long int) a.1_1;
  _16 = c;
  if (_2 < _16)
    goto <bb 4>; [50.00%]
  else
    goto <bb 3>; [50.00%]

  <bb 3> [local count: 536870912]:
  _4 = _16 + 5713568809962283044;
  if (_4 > _2)
    goto <bb 4>; [20.00%]
  else
    goto <bb 5>; [80.00%]

  <bb 4> [local count: 536870912]:

  <bb 5> [local count: 1073741824]:
  # _5 = PHI <_2(4), _4(3)>
  _6 = (short unsigned int) _5;
  b = _6;
which for the testcase jumps from bb 2 to bb4 into:
  <bb 2> [local count: 1073741824]:
  a.1_1 = a;
  _2 = (long long int) a.1_1;
  _16 = c;
  _4 = _16 + 5713568809962283044;
  if (_2 < _4)
    goto <bb 3>; [60.00%]
  else
    goto <bb 4>; [40.00%]

  <bb 3> [local count: 536870912]:

  <bb 4> [local count: 1073741824]:
  # _5 = PHI <_2(3), _4(2)>
  _6 = (short unsigned int) _5;
  b = _6;
which invokes UB on the _16 + 5713568809962283044 addition (signed integer
overflow).  So, either it needs to make sure the no longer conditional addition
is performed in unsigned type, or it needs to give up.

Reply via email to