transfer.c (read_sf): Rename uinty to readlen.
authorPaul Brook <paul@codesourcery.com>
Tue, 31 Aug 2004 15:53:31 +0000 (15:53 +0000)
committerPaul Brook <pbrook@gcc.gnu.org>
Tue, 31 Aug 2004 15:53:31 +0000 (15:53 +0000)
* io/transfer.c (read_sf): Rename uinty to readlen.  Detect EOF.
(finalize_transfer): Move setjmp after namlist IO.
* io/unix.c (mem_alloc_r_at): Calculate remaining length correctly.
testsuite/
* gfortran.dg/eof_1.f90: New test.

From-SVN: r86831

gcc/testsuite/ChangeLog
gcc/testsuite/gfortran.dg/eof_1.f90 [new file with mode: 0644]
libgfortran/ChangeLog
libgfortran/io/transfer.c
libgfortran/io/unix.c

index 0bca0f1722900a48b8cb798756786ae45dba4cc4..df86733ee71bf6587e93566147891ff86417d3a7 100644 (file)
@@ -1,3 +1,7 @@
+2004-08-31  Paul Brook  <paul@codesourcery.com>
+
+       * gfortran.dg/eof_1.f90: New test.
+
 2004-08-31  Paul Brook  <paul@codesourcery.com>
 
        * gfortran.dg/list_read_1.f90: New file.
diff --git a/gcc/testsuite/gfortran.dg/eof_1.f90 b/gcc/testsuite/gfortran.dg/eof_1.f90
new file mode 100644 (file)
index 0000000..05726bd
--- /dev/null
@@ -0,0 +1,18 @@
+! { dg-do run }
+! Program to test for proper EOF errors when reading past the end of a file.
+! We used to get this wrong when a formatted read followed a list formatted
+! read.
+program eof_1
+  character(len=5) :: s
+
+  open (unit=11, status="SCRATCH")
+  write (11, '(a)') "Hello"
+  rewind(11)
+  read(11, *) s
+  if (s .ne. "Hello") call abort
+  read(11, '(a5)', end=10) s
+  call abort
+10 continue
+  close (11)
+end
+
index 28329d2608cf0480d4e55897874a910584f33b24..1c76245bb391509931d501699599d1933b19785c 100644 (file)
@@ -1,3 +1,9 @@
+2004-08-31  Paul Brook  <paul@codesourcery.com>
+
+       * io/transfer.c (read_sf): Rename uinty to readlen.  Detect EOF.
+       (finalize_transfer): Move setjmp after namlist IO.
+       * io/unix.c (mem_alloc_r_at): Calculate remaining length correctly.
+
 2004-08-31  Paul Brook  <paul@codesourcery.com>
 
        * list_read.c (eat_separator): Set at_eo when a '/' is seen.
index 5d4dcd592a0e1f1afe1910b4b6fe94018ad8924f..ca920724b0d31f293ad0c41f9dcd35d208433995 100644 (file)
@@ -119,7 +119,7 @@ read_sf (int *length)
 {
   static char data[SCRATCH_SIZE];
   char *base, *p, *q;
-  int n, unity;
+  int n, readlen;
 
   if (*length > SCRATCH_SIZE)
     p = base = line_buffer = get_mem (*length);
@@ -129,24 +129,33 @@ read_sf (int *length)
   memset(base,'\0',*length);
 
   current_unit->bytes_left = options.default_recl;
-  unity = 1;
+  readlen = 1;
   n = 0;
 
   do
     {
       if (is_internal_unit())
         {
-         /* unity may be modified inside salloc_r if 
+         /* readlen may be modified inside salloc_r if 
             is_internal_unit() is true.  */
-          unity = 1;
+          readlen = 1;
         }
 
-      q = salloc_r (current_unit->s, &unity);
+      q = salloc_r (current_unit->s, &readlen);
       if (q == NULL)
        break;
 
-      if (*q == '\n')
+      /* If we have a line without a terminating \n, drop through to
+        EOR below.  */
+      if (readlen < 1 & n == 0)
        {
+         generate_error (ERROR_END, NULL);
+         return NULL;
+       }
+
+      if (readlen < 1 || *q == '\n')
+       {
+         /* ??? What is this for?  */
           if (current_unit->unit_number == options.stdin_unit)
             {
               if (n <= 0)
@@ -1345,12 +1354,6 @@ static void
 finalize_transfer (void)
 {
 
-  if (setjmp (g.eof_jump))
-    {
-       generate_error (ERROR_END, NULL);
-       return;
-    }
-
   if ((ionml != NULL) && (ioparm.namelist_name != NULL))
     {
        if (ioparm.namelist_read_mode)
@@ -1363,6 +1366,12 @@ finalize_transfer (void)
   if (current_unit == NULL)
     return;
 
+  if (setjmp (g.eof_jump))
+    {
+      generate_error (ERROR_END, NULL);
+      return;
+    }
+
   if (ioparm.list_format && g.mode == READING)
     finish_list_read ();
   else
index 0c652581c0450740e28b0051b3367d73a7a0e01c..33d7fda4514fd900ce1991779367ea5392af4d60 100644 (file)
@@ -751,7 +751,7 @@ mem_alloc_r_at (unix_stream * s, int *len, gfc_offset where)
 
   s->logical_offset = where + *len;
 
-  n = (where - s->buffer_offset) - s->active;
+  n = s->buffer_offset + s->active - where;
   if (*len > n)
     *len = n;