This is the mail archive of the gcc@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]

Re: For after egcs-2.0, when everything works and we get bored


>I think this pretty much has to be done in a higher-level intermediate
>language than our current RTL.  Anything else has too much hair.
>
>>       jc = m				! Outer loop count
>>       j  = 1				! Outer loop induction var j
>
>Incidentally, why does the fortran front end generate loops in this
>way?  Was the loop inversion code not working for you once upon a time?

No, at least I don't *think* that was a problem.

The Fortran standard requires an iterative DO loop be executed based on
("as if") the number of iterations precomputed using a fairly
straightforward calculation involving the begin, end, and increment
values, plus the type of the iteration variable, before the loop body
is actually executed.

This isn't because the iteration variable might be changed by the
body of the loop code -- because that's actually disallowed (presumably
for stylistic reasons, to avoid confusing the reader).

What it does accomplish, besides helping compilers generate faster
code for pipelined/parallel implementations, is the assurance that
the behavior will remain consistent even when the begin/end/incr
values are near the "boundaries" of the type of the iteration variable
(INTEGER, usually).

>Seems to me you should just emit
>
>	top = m
>	j = 1
>	if (j <= top) {
>	  do {
>	    ...
>	  } while (++j <= top);
>	}

That wouldn't work if `m' was 2147483647 and the types were 32-bit
two's-complement.

There are presumably some straightforward rules g77 could employ
to generate a simpler loop-control construct when it would
definitely run "as if" it used the current approach.

Certainly, "DO I=1,10" could be optimized this way, and it might
be the case that the gcc back end already does so (haven't checked
this myself).  And I think even "DO I=1,N" could be changed in
some way by g77 such that the back end produces better code
(e.g. compare I.EQ.N *before* incrementing it to decide whether
to exit the loop).  However, "DO I=1,N,J" would probably not be
so easy to improve in this way, though perhaps comparing I.GE.N-J+1
would still lead to more efficient code (though it might lead to
less, on some systems in some situations, than it does right now).

Unfortunately, unless g77 does some compile-time range checking,
"DO I=M, N" cannot be improved, because N.EQ.2147483647 .OR.
M.EQ.-2147483648 should work, for example.

A generic compiler back end can always, however, optimize away the
straightforward translation g77 performs, IMO.  And, the result
might be more optimal than our fiddling around with the front end's
translation would be, especially on systems with efficient
integer overflow checking, which I suspect could be beneficially used
on lots of loops, and not just those written in Fortran.

That's why I'd lean towards not changing the g77 front end, because
I'd rather not teach it about optimizing stuff in any situation where
the back end could reasonably come to equally strong conclusions
(though I do take practical matters into account, of course).

Note that what Fortran doesn't handle as well as the straightforward
C version would in this regard is the case where M.EQ.-2147483648
.AND. N.EQ.2147483646.  In that case, the value that causes the
loop to be exited, 2147483647, is representable, but, in Fortran,
the number of iterations exceeds the range of INTEGER, so the code
is not standard-conforming, and g77's particular implementation of
such a loop would almost certainly fail to produce the expected
results (i.e. the results one would expect from `for (i=-2147483648;
i <= 2147483646; ++i) ...').

        tq vm, (burley)


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