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] fix PR libfortran/20179


One component of PR libfortran/20179 is that currently, the library truncates preconnected units before the first write (the reason, indicated in a comment in the code, is that "it is always safe to truncate the file on the first write"). Which leads to the following behaviour:

$ cat > a.f
      print *, "foo"
      end
$ cat > bar
bar
$ gfortran a.f && ./a.out >> bar
$ cat bar
 foo

Attached patch fixes this issue by adding a check (is_preconnected) to know if a given stream is a preconnected file. In that case, it does not truncate it on the first write.

The patch is regtested no i386-linux. I could not manage to make a testcase out of the example above (it would need to tell dejagnu to redirect stdout in a file when the testcase runs; how can one do that?)

OK for mainline and 4.0?

FX
2005-09-11  Francois-Xavier Coudert  <coudert@clipper.ens.fr>

	PR libfortran/20179
	* io/unix.c (is_preconnected): Add function to test if a stream
	corresponds to a preconnected unit.
	* io/io.h: Add prototype for is_preconnected.
	* io/transfer.c (data_transfer_init): Do not truncate
	preconnected units.

Index: libgfortran/io/io.h
===================================================================
RCS file: /cvsroot/gcc/gcc/libgfortran/io/io.h,v
retrieving revision 1.29
diff -u -3 -p -r1.29 io.h
--- libgfortran/io/io.h	9 Sep 2005 18:21:37 -0000	1.29
+++ libgfortran/io/io.h	11 Sep 2005 12:57:30 -0000
@@ -493,6 +493,9 @@ internal_proto(file_position);
 extern int is_seekable (stream *);
 internal_proto(is_seekable);
 
+extern int is_preconnected (stream *);
+internal_proto(is_preconnected);
+
 extern void empty_internal_buffer(stream *);
 internal_proto(empty_internal_buffer);
 
Index: libgfortran/io/transfer.c
===================================================================
RCS file: /cvsroot/gcc/gcc/libgfortran/io/transfer.c,v
retrieving revision 1.57
diff -u -3 -p -r1.57 transfer.c
--- libgfortran/io/transfer.c	7 Sep 2005 21:25:40 -0000	1.57
+++ libgfortran/io/transfer.c	11 Sep 2005 12:57:30 -0000
@@ -1183,7 +1183,7 @@ data_transfer_init (int read_flag)
      it is always safe to truncate the file on the first write */
   if (g.mode == WRITING
       && current_unit->flags.access == ACCESS_SEQUENTIAL
-      && current_unit->last_record == 0)
+      && current_unit->last_record == 0 && !is_preconnected(current_unit->s))
 	struncate(current_unit->s);
 
   current_unit->mode = g.mode;
Index: libgfortran/io/unix.c
===================================================================
RCS file: /cvsroot/gcc/gcc/libgfortran/io/unix.c,v
retrieving revision 1.37
diff -u -3 -p -r1.37 unix.c
--- libgfortran/io/unix.c	7 Sep 2005 21:25:40 -0000	1.37
+++ libgfortran/io/unix.c	11 Sep 2005 12:57:30 -0000
@@ -218,6 +218,17 @@ fix_fd (int fd)
   return fd;
 }
 
+int
+is_preconnected (stream * s)
+{
+  int fd;
+
+  fd = ((unix_stream *) s)->fd;
+  if (fd == STDIN_FILENO || fd == STDOUT_FILENO || fd == STDERR_FILENO)
+    return 1;
+  else
+    return 0;
+}
 
 /* write()-- Write a buffer to a descriptor, allowing for short writes */
 

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