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

--- Comment #69 from rguenther at suse dot de <rguenther at suse dot de> ---
On Mon, 22 Feb 2016, tkoenig at gcc dot gnu.org wrote:

> https://gcc.gnu.org/bugzilla/show_bug.cgi?id=69368
> 
> Thomas Koenig <tkoenig at gcc dot gnu.org> changed:
> 
>            What    |Removed                     |Added
> ----------------------------------------------------------------------------
>            Severity|normal                      |major
> 
> --- Comment #68 from Thomas Koenig <tkoenig at gcc dot gnu.org> ---
> The problem here is that there is a large existing codebase
> which depends on memory management which was
> 
> - illegal from the start
> 
> - the only game in town if you wanted to do any
>   sort of dynamic memory management.
> 
> because FORTRAN 66 and 77 explicitly forbade any sort
> of dynamic memory management. We can lament the fact
> fifty years later, but we cannot change it.
> 
> The idea was to use
> 
>       COMMON /FOO/ A(1)
> 
> in a subroutine (even a library), and use
> 
>       COMMON /FOO/ A(10000)
> 
> or whatever 'dynamic' size you needed for your memory
> in the main program.
> 
> This idiom appears to be common enough that, if we
> don't support it, or support it only with a severe
> performance penalty, we will simply push people away from
> gfortran.

Ok, so we can also use sth like the following to work around that
unintended optimization side-effect of get_ref_base_and_extent.
Untested, not sure if it catches all cases, it at least "fixes"
some of the small undefined testcases in this PR (not tested on
416.gamess).  I'm not sure about testsuite fallout (I might have
decided to add a testcase for the surprising behavior).

Index: gcc/tree-dfa.c
===================================================================
--- gcc/tree-dfa.c      (revision 233598)
+++ gcc/tree-dfa.c      (working copy)
@@ -617,7 +617,19 @@ get_ref_base_and_extent (tree exp, HOST_
       if (maxsize == -1
          && DECL_SIZE (exp)
          && TREE_CODE (DECL_SIZE (exp)) == INTEGER_CST)
-       maxsize = wi::to_offset (DECL_SIZE (exp)) - bit_offset;
+       {
+         maxsize = wi::to_offset (DECL_SIZE (exp)) - bit_offset;
+         /* If we've seen a variable array ref and the above adjusted
+            maxsize to size make sure the caller doesn't mistake this
+            as a non-variable access by adjusting maxsize slightly.
+            ???  This is strictly pessimizing the case where a
+            one element array is accessed with a variable index
+            which should be a rare case in practice but hits legacy
+            fortran code - see PR69368 for example.  */
+         if (seen_variable_array_ref
+             && maxsize == bitsize)
+           maxsize *= 2;
+       }
     }
   else if (CONSTANT_CLASS_P (exp))
     {

Reply via email to