This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[patch, libgfortran] PR 31915 - fix reading/writing of real(10) variables with convert="SWAP"
- From: Tobias Burnus <burnus at net-b dot de>
- To: gcc-patches <gcc-patches at gcc dot gnu dot org>, "'fortran at gcc dot gnu dot org'" <fortran at gcc dot gnu dot org>
- Date: Mon, 14 May 2007 22:15:29 +0200
- Subject: [patch, libgfortran] PR 31915 - fix reading/writing of real(10) variables with convert="SWAP"
:ADDPATCH fortran:
The following was failing:
real(10) :: a,b
open(10,convert="swap",form="unformatted")
write(10) a
backspace 10
read (10) b
if (a /= b) call abort
real(10) == long double on my machine; sizeof(long double) == 16 and
kind == 10. Therefore, we wrote/read to few bytes from the unformatted file.
Test case: gfortran.dg/unf_io_convert_3.f90. Ask Dominique or Jerry why
this test is not used.
Build and regression tested on x86_64-unknown-linux-gnu.
Ok for the trunk? Ok for GCC 4.2.1?
Tobias
PS: This does not fix all problems. If I run valgrind on the produced
a.out, I still get the following output.
==28541== Syscall param write(buf) points to uninitialised byte(s)
==28541== at 0x5601550: write (in /lib64/libc-2.5.so)
==28541== by 0x4EBF610: do_write (unix.c:336)
==28541== by 0x4EBF6B1: fd_flush (unix.c:386)
==28541== by 0x4EB3512: _gfortran_st_backspace (file_pos.c:230)
==28541== by 0x400AF1: MAIN__ (in /dev/shm/a.out)
==28541== by 0x400D8B: main (fmain.c:22)
==28541== Address 0x40517E1 is 153 bytes inside a block of size 8,344
alloc'd
==28541== at 0x4C22D06: malloc (in
/usr/lib64/valgrind/amd64-linux/vgpreload_memcheck.so)
==28541== by 0x4E3EFB8: _gfortrani_get_mem (memory.c:53)
==28541== by 0x4EC0079: fd_to_stream (unix.c:1043)
==28541== by 0x4EB9574: _gfortrani_new_unit (open.c:376)
==28541== by 0x4EB9BDA: _gfortran_st_open (open.c:561)
==28541== by 0x400A66: MAIN__ (in /dev/shm/a.out)
==28541== by 0x400D8B: main (fmain.c:22)
2007-05-14 Tobias Burnus <burnus@net-b.de>
PR libfortran/31915
* io/transfer.c (unformatted_read): Use proper size for real(10).
(unformatted_write): Ditto.
Index: libgfortran/io/transfer.c
===================================================================
--- libgfortran/io/transfer.c (Revision 124718)
+++ libgfortran/io/transfer.c (Arbeitskopie)
@@ -726,7 +726,11 @@ unformatted_read (st_parameter_dt *dtp,
of the padding. If we hit a short record, then sz is
adjusted accordingly, making later reads no-ops. */
- sz = kind;
+ if (type == BT_REAL || BT_COMPLEX)
+ sz = size_from_real_kind (kind);
+ else
+ sz = kind;
+
for (i=0; i<nelems; i++)
{
read_block_direct (dtp, buffer, &sz);
@@ -771,7 +775,11 @@ unformatted_write (st_parameter_dt *dtp,
read kind bytes. We don't care about the contents
of the padding. */
- sz = kind;
+ if (type == BT_REAL || BT_COMPLEX)
+ sz = size_from_real_kind (kind);
+ else
+ sz = kind;
+
for (i=0; i<nelems; i++)
{
reverse_memcpy(buffer, p, size);