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

Richard Biener <rguenth at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
          Component|middle-end                  |fortran

--- Comment #5 from Richard Biener <rguenth at gcc dot gnu.org> ---
So the testcase with the loop boils down to optimizing

_Bool foo (int *p, int n, _Bool q)
{
  _Bool any = false;
  for (i = 0; i < n; ++i)
    any |= p[i];
  return any || q;
}

where we want swapping of the operands (and its computations) of || (or &&).

Nothing in GCC does this kind of transform and I don't see where it would
fit best.  I think that

logical function bar(a,b,c)
  logical, intent(in) :: a, b
  logical, intent(in), dimension(3) :: c
  bar = a .and. b .and. any(c)
end

is translated in a bad way by the fortran FE, not honoring left-to-right
evaluation.  So "optimized source" is pessimized here.  Even when writing

logical function bar(a,b,c)
  logical, intent(in) :: a, b
  logical, intent(in), dimension(32) :: c
  bar = any (c) .and. (a .and. b)
end

I get the same -- any () is evaluated first and only then the scalar variant.


The original C testcase shows we eventually miss a scalar-to-CFG pass on GIMPLE
before RTL expansion so we can run sinking on that.

That said, the any() thing is a frontend issue IMHO.

Reply via email to