This is the mail archive of the gcc-patches@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]
Other format: [Raw text]

[patch, libfortran] Fix EOF handling in array I/O


Hello world,

the attached patch fixes a case where transforming

  do  j = 1,1000
     read (20,*,end=1)(tdat(j,k),k=1,10)
  end do
1 continue

which on straight transformation yields

  DO main:j=1 1000 1
    READ UNIT=20 FMT=-1
    DO main:k=1 10 1
      TRANSFER main:tdat(main:j , main:k)
    END DO
    DT_END END=1
  END DO
1     CONTINUE

into

 DO main:j=1 1000 1
    READ UNIT=20 FMT=-1
    TRANSFER main:tdat(main:j , 1:10:1)
    DT_END END=1
  END DO
1     CONTINUE

with front-end optimization led to a case where the END statement was
not interpreted correctly.

The solution, to jump out of transfer_array_inner when the file
was at its end, was found by Harald; I just added a NULL pointer
check to make some regressions go away.

Regression-tested. OK for all affected branches (trunk, gcc 9 and
gcc 8)?

Regards

	Thomas

Fix EOF handling for arrays.

2019-11-23  Thomas Koenig  <tkoenig@gcc.gnu.org>
        Harald Anlauf <anlauf@gmx.de>

        PR fortran/92569
        * io/transfer.c (transfer_array_inner):  If position is
        at AFTER_ENDFILE in current unit, return from data loop.

2019-11-23  Thomas Koenig  <tkoenig@gcc.gnu.org>
        Harald Anlauf <anlauf@gmx.de>

        PR fortran/92569
        * gfortran.dg/eof_4.f90: New test.
Index: io/transfer.c
===================================================================
--- io/transfer.c	(Revision 278025)
+++ io/transfer.c	(Arbeitskopie)
@@ -2544,6 +2544,10 @@ transfer_array_inner (st_parameter_dt *dtp, gfc_ar
 
   while (data)
     {
+      if (unlikely (dtp->u.p.current_unit
+		    && dtp->u.p.current_unit->endfile == AFTER_ENDFILE))
+	  return;
+
       dtp->u.p.transfer (dtp, iotype, data, kind, size, tsize);
       data += stride0 * tsize;
       count[0] += tsize;
! { dg-do run }
! { dg-options "-ffrontend-optimize" }
! PR 92569 - the EOF condition was not recognized with
! -ffrontend-optimize.  Originjal test case by Bill Lipa.
program main
  implicit none
  real(kind=8) ::  tdat(1000,10)
  real(kind=8) :: res (10, 3)
  integer :: i, j, k, np

  open (unit=20, status="scratch")
  res = reshape([(real(i),i=1,30)], shape(res))
  write (20,'(10G12.5)') res
  rewind 20
  do  j = 1,1000
     read (20,*,end=1)(tdat(j,k),k=1,10)
  end do
      
1 continue
  np = j-1
  if (np /= 3) stop 1
  if (any(transpose(res) /= tdat(1:np,:))) stop 2
end program main

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