OSDN Git Service

729883586f87d7350ca84ca55170eb290f328f46
[pf3gnuchains/gcc-fork.git] / libgfortran / io / transfer.c
1 /* Copyright (C) 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
2    Contributed by Andy Vaught
3    Namelist transfer functions contributed by Paul Thomas
4
5 This file is part of the GNU Fortran 95 runtime library (libgfortran).
6
7 Libgfortran is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
10 any later version.
11
12 In addition to the permissions in the GNU General Public License, the
13 Free Software Foundation gives you unlimited permission to link the
14 compiled version of this file into combinations with other programs,
15 and to distribute those combinations without any restriction coming
16 from the use of this file.  (The General Public License restrictions
17 do apply in other respects; for example, they cover modification of
18 the file, and distribution when not linked into a combine
19 executable.)
20
21 Libgfortran is distributed in the hope that it will be useful,
22 but WITHOUT ANY WARRANTY; without even the implied warranty of
23 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
24 GNU General Public License for more details.
25
26 You should have received a copy of the GNU General Public License
27 along with Libgfortran; see the file COPYING.  If not, write to
28 the Free Software Foundation, 51 Franklin Street, Fifth Floor,
29 Boston, MA 02110-1301, USA.  */
30
31
32 /* transfer.c -- Top level handling of data transfer statements.  */
33
34 #include "config.h"
35 #include <string.h>
36 #include <assert.h>
37 #include "libgfortran.h"
38 #include "io.h"
39
40
41 /* Calling conventions:  Data transfer statements are unlike other
42    library calls in that they extend over several calls.
43
44    The first call is always a call to st_read() or st_write().  These
45    subroutines return no status unless a namelist read or write is
46    being done, in which case there is the usual status.  No further
47    calls are necessary in this case.
48
49    For other sorts of data transfer, there are zero or more data
50    transfer statement that depend on the format of the data transfer
51    statement.
52
53       transfer_integer
54       transfer_logical
55       transfer_character
56       transfer_real
57       transfer_complex
58
59     These subroutines do not return status.
60
61     The last call is a call to st_[read|write]_done().  While
62     something can easily go wrong with the initial st_read() or
63     st_write(), an error inhibits any data from actually being
64     transferred.  */
65
66 extern void transfer_integer (st_parameter_dt *, void *, int);
67 export_proto(transfer_integer);
68
69 extern void transfer_real (st_parameter_dt *, void *, int);
70 export_proto(transfer_real);
71
72 extern void transfer_logical (st_parameter_dt *, void *, int);
73 export_proto(transfer_logical);
74
75 extern void transfer_character (st_parameter_dt *, void *, int);
76 export_proto(transfer_character);
77
78 extern void transfer_complex (st_parameter_dt *, void *, int);
79 export_proto(transfer_complex);
80
81 extern void transfer_array (st_parameter_dt *, gfc_array_char *, int,
82                             gfc_charlen_type);
83 export_proto(transfer_array);
84
85 static const st_option advance_opt[] = {
86   {"yes", ADVANCE_YES},
87   {"no", ADVANCE_NO},
88   {NULL, 0}
89 };
90
91
92 typedef enum
93 { FORMATTED_SEQUENTIAL, UNFORMATTED_SEQUENTIAL,
94   FORMATTED_DIRECT, UNFORMATTED_DIRECT
95 }
96 file_mode;
97
98
99 static file_mode
100 current_mode (st_parameter_dt *dtp)
101 {
102   file_mode m;
103
104   if (dtp->u.p.current_unit->flags.access == ACCESS_DIRECT)
105     {
106       m = dtp->u.p.current_unit->flags.form == FORM_FORMATTED ?
107         FORMATTED_DIRECT : UNFORMATTED_DIRECT;
108     }
109   else
110     {
111       m = dtp->u.p.current_unit->flags.form == FORM_FORMATTED ?
112         FORMATTED_SEQUENTIAL : UNFORMATTED_SEQUENTIAL;
113     }
114
115   return m;
116 }
117
118
119 /* Mid level data transfer statements.  These subroutines do reading
120    and writing in the style of salloc_r()/salloc_w() within the
121    current record.  */
122
123 /* When reading sequential formatted records we have a problem.  We
124    don't know how long the line is until we read the trailing newline,
125    and we don't want to read too much.  If we read too much, we might
126    have to do a physical seek backwards depending on how much data is
127    present, and devices like terminals aren't seekable and would cause
128    an I/O error.
129
130    Given this, the solution is to read a byte at a time, stopping if
131    we hit the newline.  For small locations, we use a static buffer.
132    For larger allocations, we are forced to allocate memory on the
133    heap.  Hopefully this won't happen very often.  */
134
135 static char *
136 read_sf (st_parameter_dt *dtp, int *length)
137 {
138   char *base, *p, *q;
139   int n, readlen, crlf;
140   gfc_offset pos;
141
142   if (*length > SCRATCH_SIZE)
143     dtp->u.p.line_buffer = get_mem (*length);
144   p = base = dtp->u.p.line_buffer;
145
146   /* If we have seen an eor previously, return a length of 0.  The
147      caller is responsible for correctly padding the input field.  */
148   if (dtp->u.p.sf_seen_eor)
149     {
150       *length = 0;
151       return base;
152     }
153
154   readlen = 1;
155   n = 0;
156
157   do
158     {
159       if (is_internal_unit (dtp))
160         {
161           /* readlen may be modified inside salloc_r if
162              is_internal_unit (dtp) is true.  */
163           readlen = 1;
164         }
165
166       q = salloc_r (dtp->u.p.current_unit->s, &readlen);
167       if (q == NULL)
168         break;
169
170       /* If we have a line without a terminating \n, drop through to
171          EOR below.  */
172       if (readlen < 1 && n == 0)
173         {
174           generate_error (&dtp->common, ERROR_END, NULL);
175           return NULL;
176         }
177
178       if (readlen < 1 || *q == '\n' || *q == '\r')
179         {
180           /* Unexpected end of line.  */
181
182           /* If we see an EOR during non-advancing I/O, we need to skip
183              the rest of the I/O statement.  Set the corresponding flag.  */
184           if (dtp->u.p.advance_status == ADVANCE_NO || dtp->u.p.seen_dollar)
185             dtp->u.p.eor_condition = 1;
186
187           crlf = 0;
188           /* If we encounter a CR, it might be a CRLF.  */
189           if (*q == '\r') /* Probably a CRLF */
190             {
191               readlen = 1;
192               pos = stream_offset (dtp->u.p.current_unit->s);
193               q = salloc_r (dtp->u.p.current_unit->s, &readlen);
194               if (*q != '\n' && readlen == 1) /* Not a CRLF after all.  */
195                 sseek (dtp->u.p.current_unit->s, pos);
196               else
197                 crlf = 1;
198             }
199
200           /* Without padding, terminate the I/O statement without assigning
201              the value.  With padding, the value still needs to be assigned,
202              so we can just continue with a short read.  */
203           if (dtp->u.p.current_unit->flags.pad == PAD_NO)
204             {
205               generate_error (&dtp->common, ERROR_EOR, NULL);
206               return NULL;
207             }
208
209           *length = n;
210           dtp->u.p.sf_seen_eor = (crlf ? 2 : 1);
211           break;
212         }
213       /*  Short circuit the read if a comma is found during numeric input.
214           The flag is set to zero during character reads so that commas in
215           strings are not ignored  */
216       if (*q == ',')
217         if (dtp->u.p.sf_read_comma == 1)
218           {
219             notify_std (GFC_STD_GNU, "Comma in formatted numeric read.");
220             *length = n;
221             break;
222           }
223
224       n++;
225       *p++ = *q;
226       dtp->u.p.sf_seen_eor = 0;
227     }
228   while (n < *length);
229   dtp->u.p.current_unit->bytes_left -= *length;
230
231   if ((dtp->common.flags & IOPARM_DT_HAS_SIZE) != 0)
232     *dtp->size += *length;
233
234   return base;
235 }
236
237
238 /* Function for reading the next couple of bytes from the current
239    file, advancing the current position.  We return a pointer to a
240    buffer containing the bytes.  We return NULL on end of record or
241    end of file.
242
243    If the read is short, then it is because the current record does not
244    have enough data to satisfy the read request and the file was
245    opened with PAD=YES.  The caller must assume tailing spaces for
246    short reads.  */
247
248 void *
249 read_block (st_parameter_dt *dtp, int *length)
250 {
251   char *source;
252   int nread;
253
254   if (dtp->u.p.current_unit->bytes_left < *length)
255     {
256       if (dtp->u.p.current_unit->flags.pad == PAD_NO)
257         {
258           generate_error (&dtp->common, ERROR_EOR, NULL);
259           /* Not enough data left.  */
260           return NULL;
261         }
262
263       *length = dtp->u.p.current_unit->bytes_left;
264     }
265
266   if (dtp->u.p.current_unit->flags.form == FORM_FORMATTED &&
267       dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL)
268     return read_sf (dtp, length);       /* Special case.  */
269
270   dtp->u.p.current_unit->bytes_left -= *length;
271
272   nread = *length;
273   source = salloc_r (dtp->u.p.current_unit->s, &nread);
274
275   if ((dtp->common.flags & IOPARM_DT_HAS_SIZE) != 0)
276     *dtp->size += nread;
277
278   if (nread != *length)
279     {                           /* Short read, this shouldn't happen.  */
280       if (dtp->u.p.current_unit->flags.pad == PAD_YES)
281         *length = nread;
282       else
283         {
284           generate_error (&dtp->common, ERROR_EOR, NULL);
285           source = NULL;
286         }
287     }
288
289   return source;
290 }
291
292
293 /* Reads a block directly into application data space.  */
294
295 static void
296 read_block_direct (st_parameter_dt *dtp, void *buf, size_t *nbytes)
297 {
298   int *length;
299   void *data;
300   size_t nread;
301
302   if (dtp->u.p.current_unit->bytes_left < *nbytes)
303     {
304       if (dtp->u.p.current_unit->flags.pad == PAD_NO)
305         {
306           /* Not enough data left.  */
307           generate_error (&dtp->common, ERROR_EOR, NULL);
308           return;
309         }
310
311       *nbytes = dtp->u.p.current_unit->bytes_left;
312     }
313
314   if (dtp->u.p.current_unit->flags.form == FORM_FORMATTED &&
315       dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL)
316     {
317       length = (int *) nbytes;
318       data = read_sf (dtp, length);     /* Special case.  */
319       memcpy (buf, data, (size_t) *length);
320       return;
321     }
322
323   dtp->u.p.current_unit->bytes_left -= *nbytes;
324
325   nread = *nbytes;
326   if (sread (dtp->u.p.current_unit->s, buf, &nread) != 0)
327     {
328       generate_error (&dtp->common, ERROR_OS, NULL);
329       return;
330     }
331
332   if ((dtp->common.flags & IOPARM_DT_HAS_SIZE) != 0)
333     *dtp->size += (GFC_INTEGER_4) nread;
334
335   if (nread != *nbytes)
336     {                           /* Short read, e.g. if we hit EOF.  */
337       if (dtp->u.p.current_unit->flags.pad == PAD_YES)
338         {
339           memset (((char *) buf) + nread, ' ', *nbytes - nread);
340           *nbytes = nread;
341         }
342       else
343         generate_error (&dtp->common, ERROR_EOR, NULL);
344     }
345 }
346
347
348 /* Function for writing a block of bytes to the current file at the
349    current position, advancing the file pointer. We are given a length
350    and return a pointer to a buffer that the caller must (completely)
351    fill in.  Returns NULL on error.  */
352
353 void *
354 write_block (st_parameter_dt *dtp, int length)
355 {
356   char *dest;
357   
358   if (dtp->u.p.current_unit->bytes_left < length)
359     {
360       generate_error (&dtp->common, ERROR_EOR, NULL);
361       return NULL;
362     }
363
364   dtp->u.p.current_unit->bytes_left -= (gfc_offset) length;
365   dest = salloc_w (dtp->u.p.current_unit->s, &length);
366   
367   if (dest == NULL)
368     {
369       generate_error (&dtp->common, ERROR_END, NULL);
370       return NULL;
371     }
372
373   if ((dtp->common.flags & IOPARM_DT_HAS_SIZE) != 0)
374     *dtp->size += length;
375
376   return dest;
377 }
378
379
380 /* Writes a block directly without necessarily allocating space in a
381    buffer.  */
382
383 static void
384 write_block_direct (st_parameter_dt *dtp, void *buf, size_t *nbytes)
385 {
386   if (dtp->u.p.current_unit->bytes_left < *nbytes)
387     generate_error (&dtp->common, ERROR_EOR, NULL);
388
389   dtp->u.p.current_unit->bytes_left -= (gfc_offset) *nbytes;
390
391   if (swrite (dtp->u.p.current_unit->s, buf, nbytes) != 0)
392     generate_error (&dtp->common, ERROR_OS, NULL);
393
394   if ((dtp->common.flags & IOPARM_DT_HAS_SIZE) != 0)
395     *dtp->size += (GFC_INTEGER_4) *nbytes;
396 }
397
398
399 /* Master function for unformatted reads.  */
400
401 static void
402 unformatted_read (st_parameter_dt *dtp, bt type,
403                   void *dest, int kind,
404                   size_t size, size_t nelems)
405 {
406   /* Currently, character implies size=1.  */
407   if (dtp->u.p.current_unit->flags.convert == CONVERT_NATIVE
408       || size == 1 || type == BT_CHARACTER)
409     {
410       size *= nelems;
411       read_block_direct (dtp, dest, &size);
412     }
413   else
414     {
415       char buffer[16];
416       char *p;
417       size_t i, sz;
418       
419       /* Break up complex into its constituent reals.  */
420       if (type == BT_COMPLEX)
421         {
422           nelems *= 2;
423           size /= 2;
424         }
425       p = dest;
426       
427       /* By now, all complex variables have been split into their
428          constituent reals.  For types with padding, we only need to
429          read kind bytes.  We don't care about the contents
430          of the padding.  */
431       
432       sz = kind;
433       for (i=0; i<nelems; i++)
434         {
435           read_block_direct (dtp, buffer, &sz);
436           reverse_memcpy (p, buffer, sz);
437           p += size;
438         }
439     }
440 }
441
442
443 /* Master function for unformatted writes.  */
444
445 static void
446 unformatted_write (st_parameter_dt *dtp, bt type,
447                    void *source, int kind,
448                    size_t size, size_t nelems)
449 {
450   if (dtp->u.p.current_unit->flags.convert == CONVERT_NATIVE ||
451       size == 1 || type == BT_CHARACTER)
452     {
453       size *= nelems;
454
455       write_block_direct (dtp, source, &size);
456     }
457   else
458     {
459       char buffer[16];
460       char *p;
461       size_t i, sz;
462   
463       /* Break up complex into its constituent reals.  */
464       if (type == BT_COMPLEX)
465         {
466           nelems *= 2;
467           size /= 2;
468         }      
469
470       p = source;
471
472       /* By now, all complex variables have been split into their
473          constituent reals.  For types with padding, we only need to
474          read kind bytes.  We don't care about the contents
475          of the padding.  */
476
477       sz = kind;
478       for (i=0; i<nelems; i++)
479         {
480           reverse_memcpy(buffer, p, size);
481           p+= size;
482           write_block_direct (dtp, buffer, &sz);
483         }
484     }
485 }
486
487
488 /* Return a pointer to the name of a type.  */
489
490 const char *
491 type_name (bt type)
492 {
493   const char *p;
494
495   switch (type)
496     {
497     case BT_INTEGER:
498       p = "INTEGER";
499       break;
500     case BT_LOGICAL:
501       p = "LOGICAL";
502       break;
503     case BT_CHARACTER:
504       p = "CHARACTER";
505       break;
506     case BT_REAL:
507       p = "REAL";
508       break;
509     case BT_COMPLEX:
510       p = "COMPLEX";
511       break;
512     default:
513       internal_error (NULL, "type_name(): Bad type");
514     }
515
516   return p;
517 }
518
519
520 /* Write a constant string to the output.
521    This is complicated because the string can have doubled delimiters
522    in it.  The length in the format node is the true length.  */
523
524 static void
525 write_constant_string (st_parameter_dt *dtp, const fnode *f)
526 {
527   char c, delimiter, *p, *q;
528   int length;
529
530   length = f->u.string.length;
531   if (length == 0)
532     return;
533
534   p = write_block (dtp, length);
535   if (p == NULL)
536     return;
537
538   q = f->u.string.p;
539   delimiter = q[-1];
540
541   for (; length > 0; length--)
542     {
543       c = *p++ = *q++;
544       if (c == delimiter && c != 'H' && c != 'h')
545         q++;                    /* Skip the doubled delimiter.  */
546     }
547 }
548
549
550 /* Given actual and expected types in a formatted data transfer, make
551    sure they agree.  If not, an error message is generated.  Returns
552    nonzero if something went wrong.  */
553
554 static int
555 require_type (st_parameter_dt *dtp, bt expected, bt actual, const fnode *f)
556 {
557   char buffer[100];
558
559   if (actual == expected)
560     return 0;
561
562   st_sprintf (buffer, "Expected %s for item %d in formatted transfer, got %s",
563               type_name (expected), dtp->u.p.item_count, type_name (actual));
564
565   format_error (dtp, f, buffer);
566   return 1;
567 }
568
569
570 /* This subroutine is the main loop for a formatted data transfer
571    statement.  It would be natural to implement this as a coroutine
572    with the user program, but C makes that awkward.  We loop,
573    processesing format elements.  When we actually have to transfer
574    data instead of just setting flags, we return control to the user
575    program which calls a subroutine that supplies the address and type
576    of the next element, then comes back here to process it.  */
577
578 static void
579 formatted_transfer_scalar (st_parameter_dt *dtp, bt type, void *p, int len,
580                            size_t size)
581 {
582   char scratch[SCRATCH_SIZE];
583   int pos, bytes_used;
584   const fnode *f;
585   format_token t;
586   int n;
587   int consume_data_flag;
588
589   /* Change a complex data item into a pair of reals.  */
590
591   n = (p == NULL) ? 0 : ((type != BT_COMPLEX) ? 1 : 2);
592   if (type == BT_COMPLEX)
593     {
594       type = BT_REAL;
595       size /= 2;
596     }
597
598   /* If there's an EOR condition, we simulate finalizing the transfer
599      by doing nothing.  */
600   if (dtp->u.p.eor_condition)
601     return;
602
603   /* Set this flag so that commas in reads cause the read to complete before
604      the entire field has been read.  The next read field will start right after
605      the comma in the stream.  (Set to 0 for character reads).  */
606   dtp->u.p.sf_read_comma = 1;
607
608   dtp->u.p.line_buffer = scratch;
609   for (;;)
610     {
611       /* If reversion has occurred and there is another real data item,
612          then we have to move to the next record.  */
613       if (dtp->u.p.reversion_flag && n > 0)
614         {
615           dtp->u.p.reversion_flag = 0;
616           next_record (dtp, 0);
617         }
618
619       consume_data_flag = 1 ;
620       if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
621         break;
622
623       f = next_format (dtp);
624       if (f == NULL)
625         return;       /* No data descriptors left (already raised).  */
626
627       /* Now discharge T, TR and X movements to the right.  This is delayed
628          until a data producing format to suppress trailing spaces.  */
629          
630       t = f->format;
631       if (dtp->u.p.mode == WRITING && dtp->u.p.skips != 0
632         && ((n>0 && (  t == FMT_I  || t == FMT_B  || t == FMT_O
633                     || t == FMT_Z  || t == FMT_F  || t == FMT_E
634                     || t == FMT_EN || t == FMT_ES || t == FMT_G
635                     || t == FMT_L  || t == FMT_A  || t == FMT_D))
636             || t == FMT_STRING))
637         {
638           if (dtp->u.p.skips > 0)
639             {
640               write_x (dtp, dtp->u.p.skips, dtp->u.p.pending_spaces);
641               dtp->u.p.max_pos = (int)(dtp->u.p.current_unit->recl
642                                        - dtp->u.p.current_unit->bytes_left);
643             }
644           if (dtp->u.p.skips < 0)
645             {
646               move_pos_offset (dtp->u.p.current_unit->s, dtp->u.p.skips);
647               dtp->u.p.current_unit->bytes_left -= (gfc_offset) dtp->u.p.skips;
648             }
649           dtp->u.p.skips = dtp->u.p.pending_spaces = 0;
650         }
651
652       bytes_used = (int)(dtp->u.p.current_unit->recl - dtp->u.p.current_unit->bytes_left);
653
654       switch (t)
655         {
656         case FMT_I:
657           if (n == 0)
658             goto need_data;
659           if (require_type (dtp, BT_INTEGER, type, f))
660             return;
661
662           if (dtp->u.p.mode == READING)
663             read_decimal (dtp, f, p, len);
664           else
665             write_i (dtp, f, p, len);
666
667           break;
668
669         case FMT_B:
670           if (n == 0)
671             goto need_data;
672           if (require_type (dtp, BT_INTEGER, type, f))
673             return;
674
675           if (dtp->u.p.mode == READING)
676             read_radix (dtp, f, p, len, 2);
677           else
678             write_b (dtp, f, p, len);
679
680           break;
681
682         case FMT_O:
683           if (n == 0)
684             goto need_data;
685
686           if (dtp->u.p.mode == READING)
687             read_radix (dtp, f, p, len, 8);
688           else
689             write_o (dtp, f, p, len);
690
691           break;
692
693         case FMT_Z:
694           if (n == 0)
695             goto need_data;
696
697           if (dtp->u.p.mode == READING)
698             read_radix (dtp, f, p, len, 16);
699           else
700             write_z (dtp, f, p, len);
701
702           break;
703
704         case FMT_A:
705           if (n == 0)
706             goto need_data;
707
708           if (dtp->u.p.mode == READING)
709             read_a (dtp, f, p, len);
710           else
711             write_a (dtp, f, p, len);
712
713           break;
714
715         case FMT_L:
716           if (n == 0)
717             goto need_data;
718
719           if (dtp->u.p.mode == READING)
720             read_l (dtp, f, p, len);
721           else
722             write_l (dtp, f, p, len);
723
724           break;
725
726         case FMT_D:
727           if (n == 0)
728             goto need_data;
729           if (require_type (dtp, BT_REAL, type, f))
730             return;
731
732           if (dtp->u.p.mode == READING)
733             read_f (dtp, f, p, len);
734           else
735             write_d (dtp, f, p, len);
736
737           break;
738
739         case FMT_E:
740           if (n == 0)
741             goto need_data;
742           if (require_type (dtp, BT_REAL, type, f))
743             return;
744
745           if (dtp->u.p.mode == READING)
746             read_f (dtp, f, p, len);
747           else
748             write_e (dtp, f, p, len);
749           break;
750
751         case FMT_EN:
752           if (n == 0)
753             goto need_data;
754           if (require_type (dtp, BT_REAL, type, f))
755             return;
756
757           if (dtp->u.p.mode == READING)
758             read_f (dtp, f, p, len);
759           else
760             write_en (dtp, f, p, len);
761
762           break;
763
764         case FMT_ES:
765           if (n == 0)
766             goto need_data;
767           if (require_type (dtp, BT_REAL, type, f))
768             return;
769
770           if (dtp->u.p.mode == READING)
771             read_f (dtp, f, p, len);
772           else
773             write_es (dtp, f, p, len);
774
775           break;
776
777         case FMT_F:
778           if (n == 0)
779             goto need_data;
780           if (require_type (dtp, BT_REAL, type, f))
781             return;
782
783           if (dtp->u.p.mode == READING)
784             read_f (dtp, f, p, len);
785           else
786             write_f (dtp, f, p, len);
787
788           break;
789
790         case FMT_G:
791           if (n == 0)
792             goto need_data;
793           if (dtp->u.p.mode == READING)
794             switch (type)
795               {
796               case BT_INTEGER:
797                 read_decimal (dtp, f, p, len);
798                 break;
799               case BT_LOGICAL:
800                 read_l (dtp, f, p, len);
801                 break;
802               case BT_CHARACTER:
803                 read_a (dtp, f, p, len);
804                 break;
805               case BT_REAL:
806                 read_f (dtp, f, p, len);
807                 break;
808               default:
809                 goto bad_type;
810               }
811           else
812             switch (type)
813               {
814               case BT_INTEGER:
815                 write_i (dtp, f, p, len);
816                 break;
817               case BT_LOGICAL:
818                 write_l (dtp, f, p, len);
819                 break;
820               case BT_CHARACTER:
821                 write_a (dtp, f, p, len);
822                 break;
823               case BT_REAL:
824                 write_d (dtp, f, p, len);
825                 break;
826               default:
827               bad_type:
828                 internal_error (&dtp->common,
829                                 "formatted_transfer(): Bad type");
830               }
831
832           break;
833
834         case FMT_STRING:
835           consume_data_flag = 0 ;
836           if (dtp->u.p.mode == READING)
837             {
838               format_error (dtp, f, "Constant string in input format");
839               return;
840             }
841           write_constant_string (dtp, f);
842           break;
843
844         /* Format codes that don't transfer data.  */
845         case FMT_X:
846         case FMT_TR:
847           consume_data_flag = 0 ;
848
849           pos = bytes_used + f->u.n + dtp->u.p.skips;
850           dtp->u.p.skips = f->u.n + dtp->u.p.skips;
851           dtp->u.p.pending_spaces = pos - dtp->u.p.max_pos;
852
853           /* Writes occur just before the switch on f->format, above, so
854              that trailing blanks are suppressed, unless we are doing a
855              non-advancing write in which case we want to output the blanks
856              now.  */
857           if (dtp->u.p.mode == WRITING
858               && dtp->u.p.advance_status == ADVANCE_NO)
859             {
860               write_x (dtp, dtp->u.p.skips, dtp->u.p.pending_spaces);
861               dtp->u.p.skips = dtp->u.p.pending_spaces = 0;
862             }
863           if (dtp->u.p.mode == READING)
864             read_x (dtp, f->u.n);
865
866           break;
867
868         case FMT_TL:
869         case FMT_T:
870           if (f->format == FMT_TL)
871             {
872
873               /* Handle the special case when no bytes have been used yet.
874                  Cannot go below zero. */
875               if (bytes_used == 0)
876                 {
877                   dtp->u.p.pending_spaces -= f->u.n;
878                   dtp->u.p.pending_spaces = dtp->u.p.pending_spaces < 0 ? 0
879                                             : dtp->u.p.pending_spaces;
880                   dtp->u.p.skips -= f->u.n;
881                   dtp->u.p.skips = dtp->u.p.skips < 0 ? 0 : dtp->u.p.skips;
882                 }
883
884               pos = bytes_used - f->u.n;
885             }
886           else /* FMT_T */
887             {
888               consume_data_flag = 0;
889               pos = f->u.n - 1;
890             }
891
892           /* Standard 10.6.1.1: excessive left tabbing is reset to the
893              left tab limit.  We do not check if the position has gone
894              beyond the end of record because a subsequent tab could
895              bring us back again.  */
896           pos = pos < 0 ? 0 : pos;
897
898           dtp->u.p.skips = dtp->u.p.skips + pos - bytes_used;
899           dtp->u.p.pending_spaces = dtp->u.p.pending_spaces
900                                     + pos - dtp->u.p.max_pos;
901
902           if (dtp->u.p.skips == 0)
903             break;
904
905           /* Writes occur just before the switch on f->format, above, so that
906              trailing blanks are suppressed.  */
907           if (dtp->u.p.mode == READING)
908             {
909               /* Adjust everything for end-of-record condition */
910               if (dtp->u.p.sf_seen_eor && !is_internal_unit (dtp))
911                 {
912                   if (dtp->u.p.sf_seen_eor == 2)
913                     {
914                       /* The EOR was a CRLF (two bytes wide).  */
915                       dtp->u.p.current_unit->bytes_left -= 2;
916                       dtp->u.p.skips -= 2;
917                     }
918                   else
919                     {
920                       /* The EOR marker was only one byte wide.  */
921                       dtp->u.p.current_unit->bytes_left--;
922                       dtp->u.p.skips--;
923                     }
924                   bytes_used = pos;
925                   dtp->u.p.sf_seen_eor = 0;
926                 }
927               if (dtp->u.p.skips < 0)
928                 {
929                   move_pos_offset (dtp->u.p.current_unit->s, dtp->u.p.skips);
930                   dtp->u.p.current_unit->bytes_left
931                     -= (gfc_offset) dtp->u.p.skips;
932                   dtp->u.p.skips = dtp->u.p.pending_spaces = 0;
933                 }
934               else
935                 read_x (dtp, dtp->u.p.skips);
936             }
937
938           break;
939
940         case FMT_S:
941           consume_data_flag = 0 ;
942           dtp->u.p.sign_status = SIGN_S;
943           break;
944
945         case FMT_SS:
946           consume_data_flag = 0 ;
947           dtp->u.p.sign_status = SIGN_SS;
948           break;
949
950         case FMT_SP:
951           consume_data_flag = 0 ;
952           dtp->u.p.sign_status = SIGN_SP;
953           break;
954
955         case FMT_BN:
956           consume_data_flag = 0 ;
957           dtp->u.p.blank_status = BLANK_NULL;
958           break;
959
960         case FMT_BZ:
961           consume_data_flag = 0 ;
962           dtp->u.p.blank_status = BLANK_ZERO;
963           break;
964
965         case FMT_P:
966           consume_data_flag = 0 ;
967           dtp->u.p.scale_factor = f->u.k;
968           break;
969
970         case FMT_DOLLAR:
971           consume_data_flag = 0 ;
972           dtp->u.p.seen_dollar = 1;
973           break;
974
975         case FMT_SLASH:
976           consume_data_flag = 0 ;
977           dtp->u.p.skips = dtp->u.p.pending_spaces = 0;
978           next_record (dtp, 0);
979           break;
980
981         case FMT_COLON:
982           /* A colon descriptor causes us to exit this loop (in
983              particular preventing another / descriptor from being
984              processed) unless there is another data item to be
985              transferred.  */
986           consume_data_flag = 0 ;
987           if (n == 0)
988             return;
989           break;
990
991         default:
992           internal_error (&dtp->common, "Bad format node");
993         }
994
995       /* Free a buffer that we had to allocate during a sequential
996          formatted read of a block that was larger than the static
997          buffer.  */
998
999       if (dtp->u.p.line_buffer != scratch)
1000         {
1001           free_mem (dtp->u.p.line_buffer);
1002           dtp->u.p.line_buffer = scratch;
1003         }
1004
1005       /* Adjust the item count and data pointer.  */
1006
1007       if ((consume_data_flag > 0) && (n > 0))
1008       {
1009         n--;
1010         p = ((char *) p) + size;
1011       }
1012
1013       if (dtp->u.p.mode == READING)
1014         dtp->u.p.skips = 0;
1015
1016       pos = (int)(dtp->u.p.current_unit->recl - dtp->u.p.current_unit->bytes_left);
1017       dtp->u.p.max_pos = (dtp->u.p.max_pos > pos) ? dtp->u.p.max_pos : pos;
1018
1019     }
1020
1021   return;
1022
1023   /* Come here when we need a data descriptor but don't have one.  We
1024      push the current format node back onto the input, then return and
1025      let the user program call us back with the data.  */
1026  need_data:
1027   unget_format (dtp, f);
1028 }
1029
1030 static void
1031 formatted_transfer (st_parameter_dt *dtp, bt type, void *p, int kind,
1032                     size_t size, size_t nelems)
1033 {
1034   size_t elem;
1035   char *tmp;
1036
1037   tmp = (char *) p;
1038
1039   /* Big loop over all the elements.  */
1040   for (elem = 0; elem < nelems; elem++)
1041     {
1042       dtp->u.p.item_count++;
1043       formatted_transfer_scalar (dtp, type, tmp + size*elem, kind, size);
1044     }
1045 }
1046
1047
1048
1049 /* Data transfer entry points.  The type of the data entity is
1050    implicit in the subroutine call.  This prevents us from having to
1051    share a common enum with the compiler.  */
1052
1053 void
1054 transfer_integer (st_parameter_dt *dtp, void *p, int kind)
1055 {
1056   if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1057     return;
1058   dtp->u.p.transfer (dtp, BT_INTEGER, p, kind, kind, 1);
1059 }
1060
1061
1062 void
1063 transfer_real (st_parameter_dt *dtp, void *p, int kind)
1064 {
1065   size_t size;
1066   if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1067     return;
1068   size = size_from_real_kind (kind);
1069   dtp->u.p.transfer (dtp, BT_REAL, p, kind, size, 1);
1070 }
1071
1072
1073 void
1074 transfer_logical (st_parameter_dt *dtp, void *p, int kind)
1075 {
1076   if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1077     return;
1078   dtp->u.p.transfer (dtp, BT_LOGICAL, p, kind, kind, 1);
1079 }
1080
1081
1082 void
1083 transfer_character (st_parameter_dt *dtp, void *p, int len)
1084 {
1085   if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1086     return;
1087   /* Currently we support only 1 byte chars, and the library is a bit
1088      confused of character kind vs. length, so we kludge it by setting
1089      kind = length.  */
1090   dtp->u.p.transfer (dtp, BT_CHARACTER, p, len, len, 1);
1091 }
1092
1093
1094 void
1095 transfer_complex (st_parameter_dt *dtp, void *p, int kind)
1096 {
1097   size_t size;
1098   if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1099     return;
1100   size = size_from_complex_kind (kind);
1101   dtp->u.p.transfer (dtp, BT_COMPLEX, p, kind, size, 1);
1102 }
1103
1104
1105 void
1106 transfer_array (st_parameter_dt *dtp, gfc_array_char *desc, int kind,
1107                 gfc_charlen_type charlen)
1108 {
1109   index_type count[GFC_MAX_DIMENSIONS];
1110   index_type extent[GFC_MAX_DIMENSIONS];
1111   index_type stride[GFC_MAX_DIMENSIONS];
1112   index_type stride0, rank, size, type, n;
1113   size_t tsize;
1114   char *data;
1115   bt iotype;
1116
1117   if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1118     return;
1119
1120   type = GFC_DESCRIPTOR_TYPE (desc);
1121   size = GFC_DESCRIPTOR_SIZE (desc);
1122
1123   /* FIXME: What a kludge: Array descriptors and the IO library use
1124      different enums for types.  */
1125   switch (type)
1126     {
1127     case GFC_DTYPE_UNKNOWN:
1128       iotype = BT_NULL;  /* Is this correct?  */
1129       break;
1130     case GFC_DTYPE_INTEGER:
1131       iotype = BT_INTEGER;
1132       break;
1133     case GFC_DTYPE_LOGICAL:
1134       iotype = BT_LOGICAL;
1135       break;
1136     case GFC_DTYPE_REAL:
1137       iotype = BT_REAL;
1138       break;
1139     case GFC_DTYPE_COMPLEX:
1140       iotype = BT_COMPLEX;
1141       break;
1142     case GFC_DTYPE_CHARACTER:
1143       iotype = BT_CHARACTER;
1144       /* FIXME: Currently dtype contains the charlen, which is
1145          clobbered if charlen > 2**24. That's why we use a separate
1146          argument for the charlen. However, if we want to support
1147          non-8-bit charsets we need to fix dtype to contain
1148          sizeof(chartype) and fix the code below.  */
1149       size = charlen;
1150       kind = charlen;
1151       break;
1152     case GFC_DTYPE_DERIVED:
1153       internal_error (&dtp->common,
1154                 "Derived type I/O should have been handled via the frontend.");
1155       break;
1156     default:
1157       internal_error (&dtp->common, "transfer_array(): Bad type");
1158     }
1159
1160   if (desc->dim[0].stride == 0)
1161     desc->dim[0].stride = 1;
1162
1163   rank = GFC_DESCRIPTOR_RANK (desc);
1164   for (n = 0; n < rank; n++)
1165     {
1166       count[n] = 0;
1167       stride[n] = desc->dim[n].stride;
1168       extent[n] = desc->dim[n].ubound + 1 - desc->dim[n].lbound;
1169
1170       /* If the extent of even one dimension is zero, then the entire
1171          array section contains zero elements, so we return.  */
1172       if (extent[n] == 0)
1173         return;
1174     }
1175
1176   stride0 = stride[0];
1177
1178   /* If the innermost dimension has stride 1, we can do the transfer
1179      in contiguous chunks.  */
1180   if (stride0 == 1)
1181     tsize = extent[0];
1182   else
1183     tsize = 1;
1184
1185   data = GFC_DESCRIPTOR_DATA (desc);
1186
1187   while (data)
1188     {
1189       dtp->u.p.transfer (dtp, iotype, data, kind, size, tsize);
1190       data += stride0 * size * tsize;
1191       count[0] += tsize;
1192       n = 0;
1193       while (count[n] == extent[n])
1194         {
1195           count[n] = 0;
1196           data -= stride[n] * extent[n] * size;
1197           n++;
1198           if (n == rank)
1199             {
1200               data = NULL;
1201               break;
1202             }
1203           else
1204             {
1205               count[n]++;
1206               data += stride[n] * size;
1207             }
1208         }
1209     }
1210 }
1211
1212
1213 /* Preposition a sequential unformatted file while reading.  */
1214
1215 static void
1216 us_read (st_parameter_dt *dtp)
1217 {
1218   char *p;
1219   int n;
1220   gfc_offset i;
1221
1222   n = sizeof (gfc_offset);
1223   p = salloc_r (dtp->u.p.current_unit->s, &n);
1224
1225   if (n == 0)
1226     return;  /* end of file */
1227
1228   if (p == NULL || n != sizeof (gfc_offset))
1229     {
1230       generate_error (&dtp->common, ERROR_BAD_US, NULL);
1231       return;
1232     }
1233
1234   /* Only CONVERT_NATIVE and CONVERT_SWAP are valid here.  */
1235   if (dtp->u.p.current_unit->flags.convert == CONVERT_NATIVE)
1236     memcpy (&i, p, sizeof (gfc_offset));
1237   else
1238     reverse_memcpy (&i, p, sizeof (gfc_offset));
1239     
1240   dtp->u.p.current_unit->bytes_left = i;
1241 }
1242
1243
1244 /* Preposition a sequential unformatted file while writing.  This
1245    amount to writing a bogus length that will be filled in later.  */
1246
1247 static void
1248 us_write (st_parameter_dt *dtp)
1249 {
1250   char *p;
1251   int length;
1252
1253   length = sizeof (gfc_offset);
1254   p = salloc_w (dtp->u.p.current_unit->s, &length);
1255
1256   if (p == NULL)
1257     {
1258       generate_error (&dtp->common, ERROR_OS, NULL);
1259       return;
1260     }
1261
1262   memset (p, '\0', sizeof (gfc_offset));        /* Bogus value for now.  */
1263   if (sfree (dtp->u.p.current_unit->s) == FAILURE)
1264     generate_error (&dtp->common, ERROR_OS, NULL);
1265
1266   /* For sequential unformatted, we write until we have more bytes than
1267      can fit in the record markers. If disk space runs out first, it will
1268      error on the write.  */
1269   dtp->u.p.current_unit->recl = max_offset;
1270
1271   dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
1272 }
1273
1274
1275 /* Position to the next record prior to transfer.  We are assumed to
1276    be before the next record.  We also calculate the bytes in the next
1277    record.  */
1278
1279 static void
1280 pre_position (st_parameter_dt *dtp)
1281 {
1282   if (dtp->u.p.current_unit->current_record)
1283     return;                     /* Already positioned.  */
1284
1285   switch (current_mode (dtp))
1286     {
1287     case UNFORMATTED_SEQUENTIAL:
1288       if (dtp->u.p.mode == READING)
1289         us_read (dtp);
1290       else
1291         us_write (dtp);
1292
1293       break;
1294
1295     case FORMATTED_SEQUENTIAL:
1296     case FORMATTED_DIRECT:
1297     case UNFORMATTED_DIRECT:
1298       dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
1299       break;
1300     }
1301
1302   dtp->u.p.current_unit->current_record = 1;
1303 }
1304
1305
1306 /* Initialize things for a data transfer.  This code is common for
1307    both reading and writing.  */
1308
1309 static void
1310 data_transfer_init (st_parameter_dt *dtp, int read_flag)
1311 {
1312   unit_flags u_flags;  /* Used for creating a unit if needed.  */
1313   GFC_INTEGER_4 cf = dtp->common.flags;
1314   namelist_info *ionml;
1315
1316   ionml = ((cf & IOPARM_DT_IONML_SET) != 0) ? dtp->u.p.ionml : NULL;
1317   memset (&dtp->u.p, 0, sizeof (dtp->u.p));
1318   dtp->u.p.ionml = ionml;
1319   dtp->u.p.mode = read_flag ? READING : WRITING;
1320
1321   if ((cf & IOPARM_DT_HAS_SIZE) != 0)
1322     *dtp->size = 0;             /* Initialize the count.  */
1323
1324   dtp->u.p.current_unit = get_unit (dtp, 1);
1325   if (dtp->u.p.current_unit->s == NULL)
1326   {  /* Open the unit with some default flags.  */
1327      st_parameter_open opp;
1328      if (dtp->common.unit < 0)
1329      {
1330        close_unit (dtp->u.p.current_unit);
1331        dtp->u.p.current_unit = NULL;
1332        generate_error (&dtp->common, ERROR_BAD_OPTION,
1333                        "Bad unit number in OPEN statement");
1334        return;
1335      }
1336      memset (&u_flags, '\0', sizeof (u_flags));
1337      u_flags.access = ACCESS_SEQUENTIAL;
1338      u_flags.action = ACTION_READWRITE;
1339
1340      /* Is it unformatted?  */
1341      if (!(cf & (IOPARM_DT_HAS_FORMAT | IOPARM_DT_LIST_FORMAT
1342                  | IOPARM_DT_IONML_SET)))
1343        u_flags.form = FORM_UNFORMATTED;
1344      else
1345        u_flags.form = FORM_UNSPECIFIED;
1346
1347      u_flags.delim = DELIM_UNSPECIFIED;
1348      u_flags.blank = BLANK_UNSPECIFIED;
1349      u_flags.pad = PAD_UNSPECIFIED;
1350      u_flags.status = STATUS_UNKNOWN;
1351      opp.common = dtp->common;
1352      opp.common.flags &= IOPARM_COMMON_MASK;
1353      dtp->u.p.current_unit = new_unit (&opp, dtp->u.p.current_unit, &u_flags);
1354      dtp->common.flags &= ~IOPARM_COMMON_MASK;
1355      dtp->common.flags |= (opp.common.flags & IOPARM_COMMON_MASK);
1356      if (dtp->u.p.current_unit == NULL)
1357        return;
1358   }
1359
1360   /* Check the action.  */
1361
1362   if (read_flag && dtp->u.p.current_unit->flags.action == ACTION_WRITE)
1363     generate_error (&dtp->common, ERROR_BAD_ACTION,
1364                     "Cannot read from file opened for WRITE");
1365
1366   if (!read_flag && dtp->u.p.current_unit->flags.action == ACTION_READ)
1367     generate_error (&dtp->common, ERROR_BAD_ACTION,
1368                     "Cannot write to file opened for READ");
1369
1370   if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1371     return;
1372
1373   dtp->u.p.first_item = 1;
1374
1375   /* Check the format.  */
1376
1377   if ((cf & IOPARM_DT_HAS_FORMAT) != 0)
1378     parse_format (dtp);
1379
1380   if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1381     return;
1382
1383   if (dtp->u.p.current_unit->flags.form == FORM_UNFORMATTED
1384       && (cf & (IOPARM_DT_HAS_FORMAT | IOPARM_DT_LIST_FORMAT))
1385          != 0)
1386     generate_error (&dtp->common, ERROR_OPTION_CONFLICT,
1387                     "Format present for UNFORMATTED data transfer");
1388
1389   if ((cf & IOPARM_DT_HAS_NAMELIST_NAME) != 0 && dtp->u.p.ionml != NULL)
1390      {
1391         if ((cf & IOPARM_DT_HAS_FORMAT) != 0)
1392            generate_error (&dtp->common, ERROR_OPTION_CONFLICT,
1393                     "A format cannot be specified with a namelist");
1394      }
1395   else if (dtp->u.p.current_unit->flags.form == FORM_FORMATTED &&
1396            !(cf & (IOPARM_DT_HAS_FORMAT | IOPARM_DT_LIST_FORMAT)))
1397     generate_error (&dtp->common, ERROR_OPTION_CONFLICT,
1398                     "Missing format for FORMATTED data transfer");
1399
1400
1401   if (is_internal_unit (dtp)
1402       && dtp->u.p.current_unit->flags.form == FORM_UNFORMATTED)
1403     generate_error (&dtp->common, ERROR_OPTION_CONFLICT,
1404                     "Internal file cannot be accessed by UNFORMATTED data transfer");
1405
1406   /* Check the record number.  */
1407
1408   if (dtp->u.p.current_unit->flags.access == ACCESS_DIRECT
1409       && (cf & IOPARM_DT_HAS_REC) == 0)
1410     {
1411       generate_error (&dtp->common, ERROR_MISSING_OPTION,
1412                       "Direct access data transfer requires record number");
1413       return;
1414     }
1415
1416   if (dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL
1417       && (cf & IOPARM_DT_HAS_REC) != 0)
1418     {
1419       generate_error (&dtp->common, ERROR_OPTION_CONFLICT,
1420                       "Record number not allowed for sequential access data transfer");
1421       return;
1422     }
1423
1424   /* Process the ADVANCE option.  */
1425
1426   dtp->u.p.advance_status
1427     = !(cf & IOPARM_DT_HAS_ADVANCE) ? ADVANCE_UNSPECIFIED :
1428       find_option (&dtp->common, dtp->advance, dtp->advance_len, advance_opt,
1429                    "Bad ADVANCE parameter in data transfer statement");
1430
1431   if (dtp->u.p.advance_status != ADVANCE_UNSPECIFIED)
1432     {
1433       if (dtp->u.p.current_unit->flags.access == ACCESS_DIRECT)
1434         generate_error (&dtp->common, ERROR_OPTION_CONFLICT,
1435                         "ADVANCE specification conflicts with sequential access");
1436
1437       if (is_internal_unit (dtp))
1438         generate_error (&dtp->common, ERROR_OPTION_CONFLICT,
1439                         "ADVANCE specification conflicts with internal file");
1440
1441       if ((cf & (IOPARM_DT_HAS_FORMAT | IOPARM_DT_LIST_FORMAT))
1442           != IOPARM_DT_HAS_FORMAT)
1443         generate_error (&dtp->common, ERROR_OPTION_CONFLICT,
1444                         "ADVANCE specification requires an explicit format");
1445     }
1446
1447   if (read_flag)
1448     {
1449       if ((cf & IOPARM_EOR) != 0 && dtp->u.p.advance_status != ADVANCE_NO)
1450         generate_error (&dtp->common, ERROR_MISSING_OPTION,
1451                         "EOR specification requires an ADVANCE specification of NO");
1452
1453       if ((cf & IOPARM_DT_HAS_SIZE) != 0 && dtp->u.p.advance_status != ADVANCE_NO)
1454         generate_error (&dtp->common, ERROR_MISSING_OPTION,
1455                         "SIZE specification requires an ADVANCE specification of NO");
1456
1457     }
1458   else
1459     {                           /* Write constraints.  */
1460       if ((cf & IOPARM_END) != 0)
1461         generate_error (&dtp->common, ERROR_OPTION_CONFLICT,
1462                         "END specification cannot appear in a write statement");
1463
1464       if ((cf & IOPARM_EOR) != 0)
1465         generate_error (&dtp->common, ERROR_OPTION_CONFLICT,
1466                         "EOR specification cannot appear in a write statement");
1467
1468       if ((cf & IOPARM_DT_HAS_SIZE) != 0)
1469         generate_error (&dtp->common, ERROR_OPTION_CONFLICT,
1470                         "SIZE specification cannot appear in a write statement");
1471     }
1472
1473   if (dtp->u.p.advance_status == ADVANCE_UNSPECIFIED)
1474     dtp->u.p.advance_status = ADVANCE_YES;
1475   if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1476     return;
1477
1478   /* Sanity checks on the record number.  */
1479
1480   if ((cf & IOPARM_DT_HAS_REC) != 0)
1481     {
1482       if (dtp->rec <= 0)
1483         {
1484           generate_error (&dtp->common, ERROR_BAD_OPTION,
1485                           "Record number must be positive");
1486           return;
1487         }
1488
1489       if (dtp->rec >= dtp->u.p.current_unit->maxrec)
1490         {
1491           generate_error (&dtp->common, ERROR_BAD_OPTION,
1492                           "Record number too large");
1493           return;
1494         }
1495
1496       /* Check to see if we might be reading what we wrote before  */
1497
1498       if (dtp->u.p.mode == READING && dtp->u.p.current_unit->mode  == WRITING)
1499          flush(dtp->u.p.current_unit->s);
1500
1501       /* Check whether the record exists to be read.  Only
1502          a partial record needs to exist.  */
1503
1504       if (dtp->u.p.mode == READING && (dtp->rec -1)
1505           * dtp->u.p.current_unit->recl >= file_length (dtp->u.p.current_unit->s))
1506         {
1507           generate_error (&dtp->common, ERROR_BAD_OPTION,
1508                           "Non-existing record number");
1509           return;
1510         }
1511
1512       /* Position the file.  */
1513       if (sseek (dtp->u.p.current_unit->s,
1514                (dtp->rec - 1) * dtp->u.p.current_unit->recl) == FAILURE)
1515         {
1516           generate_error (&dtp->common, ERROR_OS, NULL);
1517           return;
1518         }
1519     }
1520
1521   /* Overwriting an existing sequential file ?
1522      it is always safe to truncate the file on the first write */
1523   if (dtp->u.p.mode == WRITING
1524       && dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL
1525       && dtp->u.p.current_unit->last_record == 0 && !is_preconnected(dtp->u.p.current_unit->s))
1526         struncate(dtp->u.p.current_unit->s);
1527
1528   /* Bugware for badly written mixed C-Fortran I/O.  */
1529   flush_if_preconnected(dtp->u.p.current_unit->s);
1530
1531   dtp->u.p.current_unit->mode = dtp->u.p.mode;
1532
1533   /* Set the initial value of flags.  */
1534
1535   dtp->u.p.blank_status = dtp->u.p.current_unit->flags.blank;
1536   dtp->u.p.sign_status = SIGN_S;
1537
1538   pre_position (dtp);
1539
1540   /* Set up the subroutine that will handle the transfers.  */
1541
1542   if (read_flag)
1543     {
1544       if (dtp->u.p.current_unit->flags.form == FORM_UNFORMATTED)
1545         dtp->u.p.transfer = unformatted_read;
1546       else
1547         {
1548           if ((cf & IOPARM_DT_LIST_FORMAT) != 0)
1549             dtp->u.p.transfer = list_formatted_read;
1550           else
1551             dtp->u.p.transfer = formatted_transfer;
1552         }
1553     }
1554   else
1555     {
1556       if (dtp->u.p.current_unit->flags.form == FORM_UNFORMATTED)
1557         dtp->u.p.transfer = unformatted_write;
1558       else
1559         {
1560           if ((cf & IOPARM_DT_LIST_FORMAT) != 0)
1561             dtp->u.p.transfer = list_formatted_write;
1562           else
1563             dtp->u.p.transfer = formatted_transfer;
1564         }
1565     }
1566
1567   /* Make sure that we don't do a read after a nonadvancing write.  */
1568
1569   if (read_flag)
1570     {
1571       if (dtp->u.p.current_unit->read_bad)
1572         {
1573           generate_error (&dtp->common, ERROR_BAD_OPTION,
1574                           "Cannot READ after a nonadvancing WRITE");
1575           return;
1576         }
1577     }
1578   else
1579     {
1580       if (dtp->u.p.advance_status == ADVANCE_YES && !dtp->u.p.seen_dollar)
1581         dtp->u.p.current_unit->read_bad = 1;
1582     }
1583
1584   /* Start the data transfer if we are doing a formatted transfer.  */
1585   if (dtp->u.p.current_unit->flags.form == FORM_FORMATTED
1586       && ((cf & (IOPARM_DT_LIST_FORMAT | IOPARM_DT_HAS_NAMELIST_NAME)) == 0)
1587       && dtp->u.p.ionml == NULL)
1588     formatted_transfer (dtp, 0, NULL, 0, 0, 1);
1589 }
1590
1591 /* Initialize an array_loop_spec given the array descriptor.  The function
1592    returns the index of the last element of the array.  */
1593    
1594 gfc_offset
1595 init_loop_spec (gfc_array_char *desc, array_loop_spec *ls)
1596 {
1597   int rank = GFC_DESCRIPTOR_RANK(desc);
1598   int i;
1599   gfc_offset index; 
1600
1601   index = 1;
1602   for (i=0; i<rank; i++)
1603     {
1604       ls[i].idx = 1;
1605       ls[i].start = desc->dim[i].lbound;
1606       ls[i].end = desc->dim[i].ubound;
1607       ls[i].step = desc->dim[i].stride;
1608       
1609       index += (desc->dim[i].ubound - desc->dim[i].lbound)
1610                       * desc->dim[i].stride;
1611     }
1612   return index;
1613 }
1614
1615 /* Determine the index to the next record in an internal unit array by
1616    by incrementing through the array_loop_spec.  TODO:  Implement handling
1617    negative strides. */
1618    
1619 gfc_offset
1620 next_array_record (st_parameter_dt *dtp, array_loop_spec *ls)
1621 {
1622   int i, carry;
1623   gfc_offset index;
1624   
1625   carry = 1;
1626   index = 0;
1627   
1628   for (i = 0; i < dtp->u.p.current_unit->rank; i++)
1629     {
1630       if (carry)
1631         {
1632           ls[i].idx++;
1633           if (ls[i].idx > ls[i].end)
1634             {
1635               ls[i].idx = ls[i].start;
1636               carry = 1;
1637             }
1638           else
1639             carry = 0;
1640         }
1641       index = index + (ls[i].idx - 1) * ls[i].step;
1642     }
1643   return index;
1644 }
1645
1646 /* Space to the next record for read mode.  If the file is not
1647    seekable, we read MAX_READ chunks until we get to the right
1648    position.  */
1649
1650 #define MAX_READ 4096
1651
1652 static void
1653 next_record_r (st_parameter_dt *dtp)
1654 {
1655   gfc_offset new, record;
1656   int bytes_left, rlength, length;
1657   char *p;
1658
1659   switch (current_mode (dtp))
1660     {
1661     case UNFORMATTED_SEQUENTIAL:
1662
1663       /* Skip over tail */
1664       dtp->u.p.current_unit->bytes_left += sizeof (gfc_offset);
1665       
1666       /* Fall through...  */
1667
1668     case FORMATTED_DIRECT:
1669     case UNFORMATTED_DIRECT:
1670       if (dtp->u.p.current_unit->bytes_left == 0)
1671         break;
1672
1673       if (is_seekable (dtp->u.p.current_unit->s))
1674         {
1675           new = file_position (dtp->u.p.current_unit->s)
1676                 + dtp->u.p.current_unit->bytes_left;
1677
1678           /* Direct access files do not generate END conditions,
1679              only I/O errors.  */
1680           if (sseek (dtp->u.p.current_unit->s, new) == FAILURE)
1681             generate_error (&dtp->common, ERROR_OS, NULL);
1682
1683         }
1684       else
1685         {                       /* Seek by reading data.  */
1686           while (dtp->u.p.current_unit->bytes_left > 0)
1687             {
1688               rlength = length = (MAX_READ > dtp->u.p.current_unit->bytes_left) ?
1689                 MAX_READ : dtp->u.p.current_unit->bytes_left;
1690
1691               p = salloc_r (dtp->u.p.current_unit->s, &rlength);
1692               if (p == NULL)
1693                 {
1694                   generate_error (&dtp->common, ERROR_OS, NULL);
1695                   break;
1696                 }
1697
1698               dtp->u.p.current_unit->bytes_left -= length;
1699             }
1700         }
1701       break;
1702
1703     case FORMATTED_SEQUENTIAL:
1704       length = 1;
1705       /* sf_read has already terminated input because of an '\n'  */
1706       if (dtp->u.p.sf_seen_eor)
1707         {
1708           dtp->u.p.sf_seen_eor = 0;
1709           break;
1710         }
1711
1712       if (is_internal_unit (dtp))
1713         {
1714           if (is_array_io (dtp))
1715             {
1716               record = next_array_record (dtp, dtp->u.p.current_unit->ls);
1717
1718               /* Now seek to this record.  */
1719               record = record * dtp->u.p.current_unit->recl;
1720               if (sseek (dtp->u.p.current_unit->s, record) == FAILURE)
1721                 {
1722                   generate_error (&dtp->common, ERROR_INTERNAL_UNIT, NULL);
1723                   break;
1724                 }
1725               dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
1726             }
1727           else  
1728             {
1729               bytes_left = (int) dtp->u.p.current_unit->bytes_left;
1730               p = salloc_r (dtp->u.p.current_unit->s, &bytes_left);
1731               if (p != NULL)
1732                 dtp->u.p.current_unit->bytes_left
1733                   = dtp->u.p.current_unit->recl;
1734             } 
1735           break;
1736         }
1737       else do
1738         {
1739           p = salloc_r (dtp->u.p.current_unit->s, &length);
1740
1741           if (p == NULL)
1742             {
1743               generate_error (&dtp->common, ERROR_OS, NULL);
1744               break;
1745             }
1746
1747           if (length == 0)
1748             {
1749               dtp->u.p.current_unit->endfile = AT_ENDFILE;
1750               break;
1751             }
1752         }
1753       while (*p != '\n');
1754
1755       break;
1756     }
1757
1758   if (dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL)
1759     test_endfile (dtp->u.p.current_unit);
1760 }
1761
1762
1763 /* Position to the next record in write mode.  */
1764
1765 static void
1766 next_record_w (st_parameter_dt *dtp, int done)
1767 {
1768   gfc_offset c, m, record, max_pos;
1769   int length;
1770   char *p;
1771
1772   /* Zero counters for X- and T-editing.  */
1773   max_pos = dtp->u.p.max_pos;
1774   dtp->u.p.max_pos = dtp->u.p.skips = dtp->u.p.pending_spaces = 0;
1775
1776   switch (current_mode (dtp))
1777     {
1778     case FORMATTED_DIRECT:
1779       if (dtp->u.p.current_unit->bytes_left == 0)
1780         break;
1781
1782       length = dtp->u.p.current_unit->bytes_left;
1783       p = salloc_w (dtp->u.p.current_unit->s, &length);
1784
1785       if (p == NULL)
1786         goto io_error;
1787
1788       memset (p, ' ', dtp->u.p.current_unit->bytes_left);
1789       if (sfree (dtp->u.p.current_unit->s) == FAILURE)
1790         goto io_error;
1791       break;
1792
1793     case UNFORMATTED_DIRECT:
1794       if (sfree (dtp->u.p.current_unit->s) == FAILURE)
1795         goto io_error;
1796       break;
1797
1798     case UNFORMATTED_SEQUENTIAL:
1799       /* Bytes written.  */
1800       m = dtp->u.p.current_unit->recl - dtp->u.p.current_unit->bytes_left;
1801       c = file_position (dtp->u.p.current_unit->s);
1802
1803       length = sizeof (gfc_offset);
1804
1805       /* Write the length tail.  */
1806
1807       p = salloc_w (dtp->u.p.current_unit->s, &length);
1808       if (p == NULL)
1809         goto io_error;
1810
1811       /* Only CONVERT_NATIVE and CONVERT_SWAP are valid here.  */
1812       if (dtp->u.p.current_unit->flags.convert == CONVERT_NATIVE)
1813         memcpy (p, &m, sizeof (gfc_offset));
1814       else
1815         reverse_memcpy (p, &m, sizeof (gfc_offset));
1816       
1817       if (sfree (dtp->u.p.current_unit->s) == FAILURE)
1818         goto io_error;
1819
1820       /* Seek to the head and overwrite the bogus length with the real
1821          length.  */
1822
1823       p = salloc_w_at (dtp->u.p.current_unit->s, &length, c - m - length);
1824       if (p == NULL)
1825         generate_error (&dtp->common, ERROR_OS, NULL);
1826
1827       /* Only CONVERT_NATIVE and CONVERT_SWAP are valid here.  */
1828       if (dtp->u.p.current_unit->flags.convert == CONVERT_NATIVE)
1829         memcpy (p, &m, sizeof (gfc_offset));
1830       else
1831         reverse_memcpy (p, &m, sizeof (gfc_offset));
1832         
1833       if (sfree (dtp->u.p.current_unit->s) == FAILURE)
1834         goto io_error;
1835
1836       /* Seek past the end of the current record.  */
1837
1838       if (sseek (dtp->u.p.current_unit->s, c + sizeof (gfc_offset)) == FAILURE)
1839         goto io_error;
1840
1841       break;
1842
1843     case FORMATTED_SEQUENTIAL:
1844
1845       if (dtp->u.p.current_unit->bytes_left == 0)
1846         break;
1847         
1848       if (is_internal_unit (dtp))
1849         {
1850           if (is_array_io (dtp))
1851             {
1852               length = (int) dtp->u.p.current_unit->bytes_left;
1853               
1854               /* If the farthest position reached is greater than current
1855               position, adjust the position and set length to pad out
1856               whats left.  Otherwise just pad whats left.
1857               (for character array unit) */
1858               m = dtp->u.p.current_unit->recl
1859                         - dtp->u.p.current_unit->bytes_left;
1860               if (max_pos > m)
1861                 {
1862                   length = (int) (max_pos - m);
1863                   p = salloc_w (dtp->u.p.current_unit->s, &length);
1864                   length = (int) (dtp->u.p.current_unit->recl - max_pos);
1865                 }
1866
1867               p = salloc_w (dtp->u.p.current_unit->s, &length);
1868               if (p == NULL)
1869                 {
1870                   generate_error (&dtp->common, ERROR_END, NULL);
1871                   return;
1872                 }
1873               memset(p, ' ', length);
1874
1875               /* Now that the current record has been padded out,
1876                  determine where the next record in the array is. */
1877               record = next_array_record (dtp, dtp->u.p.current_unit->ls);
1878
1879               /* Now seek to this record */
1880               record = record * dtp->u.p.current_unit->recl;
1881
1882               if (sseek (dtp->u.p.current_unit->s, record) == FAILURE)
1883                 {
1884                   generate_error (&dtp->common, ERROR_INTERNAL_UNIT, NULL);
1885                   return;
1886                 }
1887
1888               dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
1889             }
1890           else
1891             {
1892               length = 1;
1893
1894               /* If this is the last call to next_record move to the farthest
1895                  position reached and set length to pad out the remainder
1896                  of the record. (for character scaler unit) */
1897               if (done)
1898                 {
1899                   m = dtp->u.p.current_unit->recl
1900                         - dtp->u.p.current_unit->bytes_left;
1901                   if (max_pos > m)
1902                     {
1903                       length = (int) (max_pos - m);
1904                       p = salloc_w (dtp->u.p.current_unit->s, &length);
1905                       length = (int) (dtp->u.p.current_unit->recl - max_pos);
1906                     }
1907                   else
1908                     length = (int) dtp->u.p.current_unit->bytes_left;
1909                 }
1910               p = salloc_w (dtp->u.p.current_unit->s, &length);
1911               if (p == NULL)
1912                 {
1913                   generate_error (&dtp->common, ERROR_END, NULL);
1914                   return;
1915                 }
1916               memset (p, ' ', length);
1917             }
1918         }
1919       else
1920         {
1921           /* If this is the last call to next_record move to the farthest
1922           position reached in preparation for completing the record.
1923           (for file unit) */
1924           if (done)
1925             {
1926               m = dtp->u.p.current_unit->recl -
1927                         dtp->u.p.current_unit->bytes_left;
1928               if (max_pos > m)
1929                 {
1930                   length = (int) (max_pos - m);
1931                   p = salloc_w (dtp->u.p.current_unit->s, &length);
1932                 }
1933             }
1934 #ifdef HAVE_CRLF
1935           length = 2;
1936 #else
1937           length = 1;
1938 #endif
1939           p = salloc_w (dtp->u.p.current_unit->s, &length);
1940           if (p)
1941             {  /* No new line for internal writes.  */
1942 #ifdef HAVE_CRLF
1943               p[0] = '\r';
1944               p[1] = '\n';
1945 #else
1946               *p = '\n';
1947 #endif
1948             }
1949           else
1950             goto io_error;
1951         }
1952
1953       break;
1954
1955     io_error:
1956       generate_error (&dtp->common, ERROR_OS, NULL);
1957       break;
1958     }
1959 }
1960
1961 /* Position to the next record, which means moving to the end of the
1962    current record.  This can happen under several different
1963    conditions.  If the done flag is not set, we get ready to process
1964    the next record.  */
1965
1966 void
1967 next_record (st_parameter_dt *dtp, int done)
1968 {
1969   gfc_offset fp; /* File position.  */
1970
1971   dtp->u.p.current_unit->read_bad = 0;
1972
1973   if (dtp->u.p.mode == READING)
1974     next_record_r (dtp);
1975   else
1976     next_record_w (dtp, done);
1977
1978   /* keep position up to date for INQUIRE */
1979   dtp->u.p.current_unit->flags.position = POSITION_ASIS;
1980
1981   dtp->u.p.current_unit->current_record = 0;
1982   if (dtp->u.p.current_unit->flags.access == ACCESS_DIRECT)
1983    {
1984     fp = file_position (dtp->u.p.current_unit->s);
1985     /* Calculate next record, rounding up partial records.  */
1986     dtp->u.p.current_unit->last_record = (fp + dtp->u.p.current_unit->recl - 1)
1987                                 / dtp->u.p.current_unit->recl;
1988    }
1989   else
1990     dtp->u.p.current_unit->last_record++;
1991
1992   if (!done)
1993     pre_position (dtp);
1994 }
1995
1996
1997 /* Finalize the current data transfer.  For a nonadvancing transfer,
1998    this means advancing to the next record.  For internal units close the
1999    stream associated with the unit.  */
2000
2001 static void
2002 finalize_transfer (st_parameter_dt *dtp)
2003 {
2004   jmp_buf eof_jump;
2005   GFC_INTEGER_4 cf = dtp->common.flags;
2006
2007   if (dtp->u.p.eor_condition)
2008     {
2009       generate_error (&dtp->common, ERROR_EOR, NULL);
2010       return;
2011     }
2012
2013   if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
2014     return;
2015
2016   if ((dtp->u.p.ionml != NULL)
2017       && (cf & IOPARM_DT_HAS_NAMELIST_NAME) != 0)
2018     {
2019        if ((cf & IOPARM_DT_NAMELIST_READ_MODE) != 0)
2020          namelist_read (dtp);
2021        else
2022          namelist_write (dtp);
2023     }
2024
2025   dtp->u.p.transfer = NULL;
2026   if (dtp->u.p.current_unit == NULL)
2027     return;
2028
2029   dtp->u.p.eof_jump = &eof_jump;
2030   if (setjmp (eof_jump))
2031     {
2032       generate_error (&dtp->common, ERROR_END, NULL);
2033       return;
2034     }
2035
2036   if ((cf & IOPARM_DT_LIST_FORMAT) != 0 && dtp->u.p.mode == READING)
2037     finish_list_read (dtp);
2038   else
2039     {
2040       dtp->u.p.current_unit->current_record = 0;
2041       if (dtp->u.p.advance_status == ADVANCE_NO || dtp->u.p.seen_dollar)
2042         {
2043           /* Most systems buffer lines, so force the partial record
2044              to be written out.  */
2045           flush (dtp->u.p.current_unit->s);
2046           dtp->u.p.seen_dollar = 0;
2047           return;
2048         }
2049
2050       next_record (dtp, 1);
2051     }
2052
2053   sfree (dtp->u.p.current_unit->s);
2054
2055   if (is_internal_unit (dtp))
2056     {
2057       if (is_array_io (dtp) && dtp->u.p.current_unit->ls != NULL)
2058         free_mem (dtp->u.p.current_unit->ls);
2059       sclose (dtp->u.p.current_unit->s);
2060     }
2061 }
2062
2063
2064 /* Transfer function for IOLENGTH. It doesn't actually do any
2065    data transfer, it just updates the length counter.  */
2066
2067 static void
2068 iolength_transfer (st_parameter_dt *dtp, bt type __attribute__((unused)), 
2069                    void *dest __attribute__ ((unused)),
2070                    int kind __attribute__((unused)), 
2071                    size_t size, size_t nelems)
2072 {
2073   if ((dtp->common.flags & IOPARM_DT_HAS_IOLENGTH) != 0)
2074     *dtp->iolength += (GFC_INTEGER_4) size * nelems;
2075 }
2076
2077
2078 /* Initialize the IOLENGTH data transfer. This function is in essence
2079    a very much simplified version of data_transfer_init(), because it
2080    doesn't have to deal with units at all.  */
2081
2082 static void
2083 iolength_transfer_init (st_parameter_dt *dtp)
2084 {
2085   if ((dtp->common.flags & IOPARM_DT_HAS_IOLENGTH) != 0)
2086     *dtp->iolength = 0;
2087
2088   memset (&dtp->u.p, 0, sizeof (dtp->u.p));
2089
2090   /* Set up the subroutine that will handle the transfers.  */
2091
2092   dtp->u.p.transfer = iolength_transfer;
2093 }
2094
2095
2096 /* Library entry point for the IOLENGTH form of the INQUIRE
2097    statement. The IOLENGTH form requires no I/O to be performed, but
2098    it must still be a runtime library call so that we can determine
2099    the iolength for dynamic arrays and such.  */
2100
2101 extern void st_iolength (st_parameter_dt *);
2102 export_proto(st_iolength);
2103
2104 void
2105 st_iolength (st_parameter_dt *dtp)
2106 {
2107   library_start (&dtp->common);
2108   iolength_transfer_init (dtp);
2109 }
2110
2111 extern void st_iolength_done (st_parameter_dt *);
2112 export_proto(st_iolength_done);
2113
2114 void
2115 st_iolength_done (st_parameter_dt *dtp __attribute__((unused)))
2116 {
2117   free_ionml (dtp);
2118   if (dtp->u.p.scratch != NULL)
2119     free_mem (dtp->u.p.scratch);
2120   library_end ();
2121 }
2122
2123
2124 /* The READ statement.  */
2125
2126 extern void st_read (st_parameter_dt *);
2127 export_proto(st_read);
2128
2129 void
2130 st_read (st_parameter_dt *dtp)
2131 {
2132
2133   library_start (&dtp->common);
2134
2135   data_transfer_init (dtp, 1);
2136
2137   /* Handle complications dealing with the endfile record.  It is
2138      significant that this is the only place where ERROR_END is
2139      generated.  Reading an end of file elsewhere is either end of
2140      record or an I/O error. */
2141
2142   if (dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL)
2143     switch (dtp->u.p.current_unit->endfile)
2144       {
2145       case NO_ENDFILE:
2146         break;
2147
2148       case AT_ENDFILE:
2149         if (!is_internal_unit (dtp))
2150           {
2151             generate_error (&dtp->common, ERROR_END, NULL);
2152             dtp->u.p.current_unit->endfile = AFTER_ENDFILE;
2153             dtp->u.p.current_unit->current_record = 0;
2154           }
2155         break;
2156
2157       case AFTER_ENDFILE:
2158         generate_error (&dtp->common, ERROR_ENDFILE, NULL);
2159         dtp->u.p.current_unit->current_record = 0;
2160         break;
2161       }
2162 }
2163
2164 extern void st_read_done (st_parameter_dt *);
2165 export_proto(st_read_done);
2166
2167 void
2168 st_read_done (st_parameter_dt *dtp)
2169 {
2170   finalize_transfer (dtp);
2171   free_format_data (dtp);
2172   free_ionml (dtp);
2173   if (dtp->u.p.scratch != NULL)
2174     free_mem (dtp->u.p.scratch);
2175   if (dtp->u.p.current_unit != NULL)
2176     unlock_unit (dtp->u.p.current_unit);
2177   library_end ();
2178 }
2179
2180 extern void st_write (st_parameter_dt *);
2181 export_proto(st_write);
2182
2183 void
2184 st_write (st_parameter_dt *dtp)
2185 {
2186   library_start (&dtp->common);
2187   data_transfer_init (dtp, 0);
2188 }
2189
2190 extern void st_write_done (st_parameter_dt *);
2191 export_proto(st_write_done);
2192
2193 void
2194 st_write_done (st_parameter_dt *dtp)
2195 {
2196   finalize_transfer (dtp);
2197
2198   /* Deal with endfile conditions associated with sequential files.  */
2199
2200   if (dtp->u.p.current_unit != NULL && dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL)
2201     switch (dtp->u.p.current_unit->endfile)
2202       {
2203       case AT_ENDFILE:          /* Remain at the endfile record.  */
2204         break;
2205
2206       case AFTER_ENDFILE:
2207         dtp->u.p.current_unit->endfile = AT_ENDFILE;    /* Just at it now.  */
2208         break;
2209
2210       case NO_ENDFILE:
2211         if (dtp->u.p.current_unit->current_record > dtp->u.p.current_unit->last_record)
2212           {
2213             /* Get rid of whatever is after this record.  */
2214             if (struncate (dtp->u.p.current_unit->s) == FAILURE)
2215               generate_error (&dtp->common, ERROR_OS, NULL);
2216           }
2217
2218         dtp->u.p.current_unit->endfile = AT_ENDFILE;
2219         break;
2220       }
2221
2222   free_format_data (dtp);
2223   free_ionml (dtp);
2224   if (dtp->u.p.scratch != NULL)
2225     free_mem (dtp->u.p.scratch);
2226   if (dtp->u.p.current_unit != NULL)
2227     unlock_unit (dtp->u.p.current_unit);
2228   library_end ();
2229 }
2230
2231 /* Receives the scalar information for namelist objects and stores it
2232    in a linked list of namelist_info types.  */
2233
2234 extern void st_set_nml_var (st_parameter_dt *dtp, void *, char *,
2235                             GFC_INTEGER_4, gfc_charlen_type, GFC_INTEGER_4);
2236 export_proto(st_set_nml_var);
2237
2238
2239 void
2240 st_set_nml_var (st_parameter_dt *dtp, void * var_addr, char * var_name,
2241                 GFC_INTEGER_4 len, gfc_charlen_type string_length,
2242                 GFC_INTEGER_4 dtype)
2243 {
2244   namelist_info *t1 = NULL;
2245   namelist_info *nml;
2246
2247   nml = (namelist_info*) get_mem (sizeof (namelist_info));
2248
2249   nml->mem_pos = var_addr;
2250
2251   nml->var_name = (char*) get_mem (strlen (var_name) + 1);
2252   strcpy (nml->var_name, var_name);
2253
2254   nml->len = (int) len;
2255   nml->string_length = (index_type) string_length;
2256
2257   nml->var_rank = (int) (dtype & GFC_DTYPE_RANK_MASK);
2258   nml->size = (index_type) (dtype >> GFC_DTYPE_SIZE_SHIFT);
2259   nml->type = (bt) ((dtype & GFC_DTYPE_TYPE_MASK) >> GFC_DTYPE_TYPE_SHIFT);
2260
2261   if (nml->var_rank > 0)
2262     {
2263       nml->dim = (descriptor_dimension*)
2264                    get_mem (nml->var_rank * sizeof (descriptor_dimension));
2265       nml->ls = (array_loop_spec*)
2266                   get_mem (nml->var_rank * sizeof (array_loop_spec));
2267     }
2268   else
2269     {
2270       nml->dim = NULL;
2271       nml->ls = NULL;
2272     }
2273
2274   nml->next = NULL;
2275
2276   if ((dtp->common.flags & IOPARM_DT_IONML_SET) == 0)
2277     {
2278       dtp->common.flags |= IOPARM_DT_IONML_SET;
2279       dtp->u.p.ionml = nml;
2280     }
2281   else
2282     {
2283       for (t1 = dtp->u.p.ionml; t1->next; t1 = t1->next);
2284       t1->next = nml;
2285     }
2286 }
2287
2288 /* Store the dimensional information for the namelist object.  */
2289 extern void st_set_nml_var_dim (st_parameter_dt *, GFC_INTEGER_4,
2290                                 GFC_INTEGER_4, GFC_INTEGER_4,
2291                                 GFC_INTEGER_4);
2292 export_proto(st_set_nml_var_dim);
2293
2294 void
2295 st_set_nml_var_dim (st_parameter_dt *dtp, GFC_INTEGER_4 n_dim,
2296                     GFC_INTEGER_4 stride, GFC_INTEGER_4 lbound,
2297                     GFC_INTEGER_4 ubound)
2298 {
2299   namelist_info * nml;
2300   int n;
2301
2302   n = (int)n_dim;
2303
2304   for (nml = dtp->u.p.ionml; nml->next; nml = nml->next);
2305
2306   nml->dim[n].stride = (ssize_t)stride;
2307   nml->dim[n].lbound = (ssize_t)lbound;
2308   nml->dim[n].ubound = (ssize_t)ubound;
2309 }
2310
2311 /* Reverse memcpy - used for byte swapping.  */
2312
2313 void reverse_memcpy (void *dest, const void *src, size_t n)
2314 {
2315   char *d, *s;
2316   size_t i;
2317
2318   d = (char *) dest;
2319   s = (char *) src + n - 1;
2320
2321   /* Write with ascending order - this is likely faster
2322      on modern architectures because of write combining.  */
2323   for (i=0; i<n; i++)
2324       *(d++) = *(s--);
2325 }