Commit 55948b69 by Bud Davis Committed by Bud Davis

re PR libfortran/16597 (gfortran: bug in unformatted I/O on scratch files)

2004-08-27  Bud Davis  <bdavis9659@comcast.net>

        PR fortran/16597
        * io/io.h: created typedef for unit_mode.
        * io/io.h (gfc_unit): added mode to unit structure.
        * io/transfer.c (data_transfer_init): flush if a write then
        read is done on a unit (direct access files).
        * io/rewind.c (st_rewind): Used unit mode instead of global.

        * gfortran.dg/pr16597.f90: New test.

From-SVN: r86654
parent dc700f49
2004-08-27 Bud Davis <bdavis9659@comcast.net>
PR fortran/16597
* gfortran.dg/pr16597.f90: New test.
2004-08-26 Joseph S. Myers <jsm@polyomino.org.uk> 2004-08-26 Joseph S. Myers <jsm@polyomino.org.uk>
PR c/13801 PR c/13801
......
! pr 16597
! libgfortran
! reading a direct access record after it was written did
! not always return the correct data.
program gfbug4
implicit none
integer strlen
parameter (strlen = 4)
integer iunit
character string *4
iunit = 99
open (UNIT=iunit,FORM='unformatted',ACCESS='direct',RECL=strlen)
write (iunit, rec=1) 'ABCD'
read (iunit, rec=1) string
close (iunit)
if (string.ne.'ABCD') call abort
open (UNIT=iunit,FORM='unformatted',ACCESS='direct',STATUS='scratch',RECL=strlen)
write (iunit, rec=1) 'ABCD'
read (iunit, rec=1) string
close (iunit)
if (string.ne.'ABCD') call abort
end
2004-08-27 Bud Davis <bdavis9659@comcast.net>
PR fortran/16597
* io/io.h: created typedef for unit_mode.
* io/io.h (gfc_unit): added mode to unit structure.
* io/transfer.c (data_transfer_init): flush if a write then
read is done on a unit (direct access files).
* io/rewind.c (st_rewind): Used unit mode instead of global.
2004-08-24 Bud Davis <bdavis9659@comcast.net> 2004-08-24 Bud Davis <bdavis9659@comcast.net>
PR fortran/17143 PR fortran/17143
......
...@@ -144,7 +144,9 @@ typedef enum ...@@ -144,7 +144,9 @@ typedef enum
{ ADVANCE_YES, ADVANCE_NO, ADVANCE_UNSPECIFIED } { ADVANCE_YES, ADVANCE_NO, ADVANCE_UNSPECIFIED }
unit_advance; unit_advance;
typedef enum
{READING, WRITING}
unit_mode;
/* Statement parameters. These are all the things that can appear in /* Statement parameters. These are all the things that can appear in
an I/O statement. Some are inputs and some are outputs, but none an I/O statement. Some are inputs and some are outputs, but none
...@@ -271,6 +273,7 @@ typedef struct gfc_unit ...@@ -271,6 +273,7 @@ typedef struct gfc_unit
{ NO_ENDFILE, AT_ENDFILE, AFTER_ENDFILE } { NO_ENDFILE, AT_ENDFILE, AFTER_ENDFILE }
endfile; endfile;
unit_mode mode;
unit_flags flags; unit_flags flags;
gfc_offset recl, last_record, maxrec, bytes_left; gfc_offset recl, last_record, maxrec, bytes_left;
...@@ -299,7 +302,7 @@ typedef struct ...@@ -299,7 +302,7 @@ typedef struct
gfc_unit *unit_root; gfc_unit *unit_root;
int seen_dollar; int seen_dollar;
enum {READING, WRITING} mode; unit_mode mode;
unit_blank blank_status; unit_blank blank_status;
enum {SIGN_S, SIGN_SS, SIGN_SP} sign_status; enum {SIGN_S, SIGN_SS, SIGN_SP} sign_status;
......
...@@ -40,7 +40,7 @@ st_rewind (void) ...@@ -40,7 +40,7 @@ st_rewind (void)
"Cannot REWIND a file opened for DIRECT access"); "Cannot REWIND a file opened for DIRECT access");
else else
{ {
if (g.mode==WRITING) if (u->mode==WRITING)
struncate(u->s); struncate(u->s);
u->last_record = 0; u->last_record = 0;
if (sseek (u->s, 0) == FAILURE) if (sseek (u->s, 0) == FAILURE)
......
...@@ -1044,13 +1044,19 @@ data_transfer_init (int read_flag) ...@@ -1044,13 +1044,19 @@ data_transfer_init (int read_flag)
return; return;
} }
/* Position the file. */ /* Check to see if we might be reading what we wrote before */
if (g.mode == READING && current_unit->mode == WRITING)
flush(current_unit->s);
/* Position the file. */
if (sseek (current_unit->s, if (sseek (current_unit->s,
(ioparm.rec - 1) * current_unit->recl) == FAILURE) (ioparm.rec - 1) * current_unit->recl) == FAILURE)
generate_error (ERROR_OS, NULL); generate_error (ERROR_OS, NULL);
} }
current_unit->mode = g.mode;
/* Set the initial value of flags. */ /* Set the initial value of flags. */
g.blank_status = current_unit->flags.blank; g.blank_status = current_unit->flags.blank;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment