re PR fortran/38398 (g0.w edit descriptor: Update for F2008 Tokyo meeting changes)
[gcc.git] / libgfortran / io / transfer.c
1 /* Copyright (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008
2 Free Software Foundation, Inc.
3 Contributed by Andy Vaught
4 Namelist transfer functions contributed by Paul Thomas
5 F2003 I/O support contributed by Jerry DeLisle
6
7 This file is part of the GNU Fortran 95 runtime library (libgfortran).
8
9 Libgfortran is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2, or (at your option)
12 any later version.
13
14 In addition to the permissions in the GNU General Public License, the
15 Free Software Foundation gives you unlimited permission to link the
16 compiled version of this file into combinations with other programs,
17 and to distribute those combinations without any restriction coming
18 from the use of this file. (The General Public License restrictions
19 do apply in other respects; for example, they cover modification of
20 the file, and distribution when not linked into a combine
21 executable.)
22
23 Libgfortran is distributed in the hope that it will be useful,
24 but WITHOUT ANY WARRANTY; without even the implied warranty of
25 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
26 GNU General Public License for more details.
27
28 You should have received a copy of the GNU General Public License
29 along with Libgfortran; see the file COPYING. If not, write to
30 the Free Software Foundation, 51 Franklin Street, Fifth Floor,
31 Boston, MA 02110-1301, USA. */
32
33
34 /* transfer.c -- Top level handling of data transfer statements. */
35
36 #include "io.h"
37 #include <string.h>
38 #include <assert.h>
39 #include <stdlib.h>
40
41
42 /* Calling conventions: Data transfer statements are unlike other
43 library calls in that they extend over several calls.
44
45 The first call is always a call to st_read() or st_write(). These
46 subroutines return no status unless a namelist read or write is
47 being done, in which case there is the usual status. No further
48 calls are necessary in this case.
49
50 For other sorts of data transfer, there are zero or more data
51 transfer statement that depend on the format of the data transfer
52 statement.
53
54 transfer_integer
55 transfer_logical
56 transfer_character
57 transfer_character_wide
58 transfer_real
59 transfer_complex
60
61 These subroutines do not return status.
62
63 The last call is a call to st_[read|write]_done(). While
64 something can easily go wrong with the initial st_read() or
65 st_write(), an error inhibits any data from actually being
66 transferred. */
67
68 extern void transfer_integer (st_parameter_dt *, void *, int);
69 export_proto(transfer_integer);
70
71 extern void transfer_real (st_parameter_dt *, void *, int);
72 export_proto(transfer_real);
73
74 extern void transfer_logical (st_parameter_dt *, void *, int);
75 export_proto(transfer_logical);
76
77 extern void transfer_character (st_parameter_dt *, void *, int);
78 export_proto(transfer_character);
79
80 extern void transfer_character_wide (st_parameter_dt *, void *, int, int);
81 export_proto(transfer_character_wide);
82
83 extern void transfer_complex (st_parameter_dt *, void *, int);
84 export_proto(transfer_complex);
85
86 extern void transfer_array (st_parameter_dt *, gfc_array_char *, int,
87 gfc_charlen_type);
88 export_proto(transfer_array);
89
90 static void us_read (st_parameter_dt *, int);
91 static void us_write (st_parameter_dt *, int);
92 static void next_record_r_unf (st_parameter_dt *, int);
93 static void next_record_w_unf (st_parameter_dt *, int);
94
95 static const st_option advance_opt[] = {
96 {"yes", ADVANCE_YES},
97 {"no", ADVANCE_NO},
98 {NULL, 0}
99 };
100
101
102 static const st_option decimal_opt[] = {
103 {"point", DECIMAL_POINT},
104 {"comma", DECIMAL_COMMA},
105 {NULL, 0}
106 };
107
108
109 static const st_option sign_opt[] = {
110 {"plus", SIGN_SP},
111 {"suppress", SIGN_SS},
112 {"processor_defined", SIGN_S},
113 {NULL, 0}
114 };
115
116 static const st_option blank_opt[] = {
117 {"null", BLANK_NULL},
118 {"zero", BLANK_ZERO},
119 {NULL, 0}
120 };
121
122 static const st_option delim_opt[] = {
123 {"apostrophe", DELIM_APOSTROPHE},
124 {"quote", DELIM_QUOTE},
125 {"none", DELIM_NONE},
126 {NULL, 0}
127 };
128
129 static const st_option pad_opt[] = {
130 {"yes", PAD_YES},
131 {"no", PAD_NO},
132 {NULL, 0}
133 };
134
135 typedef enum
136 { FORMATTED_SEQUENTIAL, UNFORMATTED_SEQUENTIAL,
137 FORMATTED_DIRECT, UNFORMATTED_DIRECT, FORMATTED_STREAM, UNFORMATTED_STREAM
138 }
139 file_mode;
140
141
142 static file_mode
143 current_mode (st_parameter_dt *dtp)
144 {
145 file_mode m;
146
147 m = FORM_UNSPECIFIED;
148
149 if (dtp->u.p.current_unit->flags.access == ACCESS_DIRECT)
150 {
151 m = dtp->u.p.current_unit->flags.form == FORM_FORMATTED ?
152 FORMATTED_DIRECT : UNFORMATTED_DIRECT;
153 }
154 else if (dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL)
155 {
156 m = dtp->u.p.current_unit->flags.form == FORM_FORMATTED ?
157 FORMATTED_SEQUENTIAL : UNFORMATTED_SEQUENTIAL;
158 }
159 else if (dtp->u.p.current_unit->flags.access == ACCESS_STREAM)
160 {
161 m = dtp->u.p.current_unit->flags.form == FORM_FORMATTED ?
162 FORMATTED_STREAM : UNFORMATTED_STREAM;
163 }
164
165 return m;
166 }
167
168
169 /* Mid level data transfer statements. These subroutines do reading
170 and writing in the style of salloc_r()/salloc_w() within the
171 current record. */
172
173 /* When reading sequential formatted records we have a problem. We
174 don't know how long the line is until we read the trailing newline,
175 and we don't want to read too much. If we read too much, we might
176 have to do a physical seek backwards depending on how much data is
177 present, and devices like terminals aren't seekable and would cause
178 an I/O error.
179
180 Given this, the solution is to read a byte at a time, stopping if
181 we hit the newline. For small allocations, we use a static buffer.
182 For larger allocations, we are forced to allocate memory on the
183 heap. Hopefully this won't happen very often. */
184
185 char *
186 read_sf (st_parameter_dt *dtp, int *length, int no_error)
187 {
188 char *base, *p, q;
189 int n, crlf;
190 gfc_offset pos;
191 size_t readlen;
192
193 if (*length > SCRATCH_SIZE)
194 dtp->u.p.line_buffer = get_mem (*length);
195 p = base = dtp->u.p.line_buffer;
196
197 /* If we have seen an eor previously, return a length of 0. The
198 caller is responsible for correctly padding the input field. */
199 if (dtp->u.p.sf_seen_eor)
200 {
201 *length = 0;
202 return base;
203 }
204
205 if (is_internal_unit (dtp))
206 {
207 readlen = *length;
208 if (unlikely (sread (dtp->u.p.current_unit->s, p, &readlen) != 0
209 || readlen < (size_t) *length))
210 {
211 generate_error (&dtp->common, LIBERROR_END, NULL);
212 return NULL;
213 }
214
215 goto done;
216 }
217
218 readlen = 1;
219 n = 0;
220
221 do
222 {
223 if (unlikely (sread (dtp->u.p.current_unit->s, &q, &readlen) != 0))
224 {
225 generate_error (&dtp->common, LIBERROR_END, NULL);
226 return NULL;
227 }
228
229 /* If we have a line without a terminating \n, drop through to
230 EOR below. */
231 if (readlen < 1 && n == 0)
232 {
233 if (likely (no_error))
234 break;
235 generate_error (&dtp->common, LIBERROR_END, NULL);
236 return NULL;
237 }
238
239 if (readlen < 1 || q == '\n' || q == '\r')
240 {
241 /* Unexpected end of line. */
242
243 /* If we see an EOR during non-advancing I/O, we need to skip
244 the rest of the I/O statement. Set the corresponding flag. */
245 if (dtp->u.p.advance_status == ADVANCE_NO || dtp->u.p.seen_dollar)
246 dtp->u.p.eor_condition = 1;
247
248 crlf = 0;
249 /* If we encounter a CR, it might be a CRLF. */
250 if (q == '\r') /* Probably a CRLF */
251 {
252 readlen = 1;
253 pos = stream_offset (dtp->u.p.current_unit->s);
254 if (unlikely (sread (dtp->u.p.current_unit->s, &q, &readlen)
255 != 0))
256 {
257 generate_error (&dtp->common, LIBERROR_END, NULL);
258 return NULL;
259 }
260 if (q != '\n' && readlen == 1) /* Not a CRLF after all. */
261 sseek (dtp->u.p.current_unit->s, pos);
262 else
263 crlf = 1;
264 }
265
266 /* Without padding, terminate the I/O statement without assigning
267 the value. With padding, the value still needs to be assigned,
268 so we can just continue with a short read. */
269 if (dtp->u.p.current_unit->pad_status == PAD_NO)
270 {
271 if (likely (no_error))
272 break;
273 generate_error (&dtp->common, LIBERROR_EOR, NULL);
274 return NULL;
275 }
276
277 *length = n;
278 dtp->u.p.sf_seen_eor = (crlf ? 2 : 1);
279 break;
280 }
281 /* Short circuit the read if a comma is found during numeric input.
282 The flag is set to zero during character reads so that commas in
283 strings are not ignored */
284 if (q == ',')
285 if (dtp->u.p.sf_read_comma == 1)
286 {
287 notify_std (&dtp->common, GFC_STD_GNU,
288 "Comma in formatted numeric read.");
289 *length = n;
290 break;
291 }
292
293 n++;
294 *p++ = q;
295 dtp->u.p.sf_seen_eor = 0;
296 }
297 while (n < *length);
298
299 done:
300 dtp->u.p.current_unit->bytes_left -= *length;
301
302 if ((dtp->common.flags & IOPARM_DT_HAS_SIZE) != 0)
303 dtp->u.p.size_used += (GFC_IO_INT) *length;
304
305 return base;
306 }
307
308
309 /* Function for reading the next couple of bytes from the current
310 file, advancing the current position. We return FAILURE on end of record or
311 end of file. This function is only for formatted I/O, unformatted uses
312 read_block_direct.
313
314 If the read is short, then it is because the current record does not
315 have enough data to satisfy the read request and the file was
316 opened with PAD=YES. The caller must assume tailing spaces for
317 short reads. */
318
319 try
320 read_block_form (st_parameter_dt *dtp, void *buf, size_t *nbytes)
321 {
322 char *source;
323 size_t nread;
324 int nb;
325
326 if (!is_stream_io (dtp))
327 {
328 if (dtp->u.p.current_unit->bytes_left < (gfc_offset) *nbytes)
329 {
330 /* For preconnected units with default record length, set bytes left
331 to unit record length and proceed, otherwise error. */
332 if (dtp->u.p.current_unit->unit_number == options.stdin_unit
333 && dtp->u.p.current_unit->recl == DEFAULT_RECL)
334 dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
335 else
336 {
337 if (unlikely (dtp->u.p.current_unit->pad_status == PAD_NO))
338 {
339 /* Not enough data left. */
340 generate_error (&dtp->common, LIBERROR_EOR, NULL);
341 return FAILURE;
342 }
343 }
344
345 if (unlikely (dtp->u.p.current_unit->bytes_left == 0))
346 {
347 dtp->u.p.current_unit->endfile = AT_ENDFILE;
348 generate_error (&dtp->common, LIBERROR_END, NULL);
349 return FAILURE;
350 }
351
352 *nbytes = dtp->u.p.current_unit->bytes_left;
353 }
354 }
355
356 if (dtp->u.p.current_unit->flags.form == FORM_FORMATTED &&
357 (dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL ||
358 dtp->u.p.current_unit->flags.access == ACCESS_STREAM))
359 {
360 nb = *nbytes;
361 source = read_sf (dtp, &nb, 0);
362 *nbytes = nb;
363 dtp->u.p.current_unit->strm_pos +=
364 (gfc_offset) (*nbytes + dtp->u.p.sf_seen_eor);
365 if (source == NULL)
366 return FAILURE;
367 memcpy (buf, source, *nbytes);
368 return SUCCESS;
369 }
370 dtp->u.p.current_unit->bytes_left -= (gfc_offset) *nbytes;
371
372 nread = *nbytes;
373 if (unlikely (sread (dtp->u.p.current_unit->s, buf, &nread) != 0))
374 {
375 generate_error (&dtp->common, LIBERROR_OS, NULL);
376 return FAILURE;
377 }
378
379 if ((dtp->common.flags & IOPARM_DT_HAS_SIZE) != 0)
380 dtp->u.p.size_used += (GFC_IO_INT) nread;
381
382 if (nread != *nbytes)
383 { /* Short read, this shouldn't happen. */
384 if (likely (dtp->u.p.current_unit->pad_status == PAD_YES))
385 *nbytes = nread;
386 else
387 {
388 generate_error (&dtp->common, LIBERROR_EOR, NULL);
389 source = NULL;
390 }
391 }
392
393 dtp->u.p.current_unit->strm_pos += (gfc_offset) nread;
394
395 return SUCCESS;
396 }
397
398
399 /* Reads a block directly into application data space. This is for
400 unformatted files. */
401
402 static void
403 read_block_direct (st_parameter_dt *dtp, void *buf, size_t *nbytes)
404 {
405 size_t to_read_record;
406 size_t have_read_record;
407 size_t to_read_subrecord;
408 size_t have_read_subrecord;
409 int short_record;
410
411 if (is_stream_io (dtp))
412 {
413 to_read_record = *nbytes;
414 have_read_record = to_read_record;
415 if (unlikely (sread (dtp->u.p.current_unit->s, buf, &have_read_record)
416 != 0))
417 {
418 generate_error (&dtp->common, LIBERROR_OS, NULL);
419 return;
420 }
421
422 dtp->u.p.current_unit->strm_pos += (gfc_offset) have_read_record;
423
424 if (unlikely (to_read_record != have_read_record))
425 {
426 /* Short read, e.g. if we hit EOF. For stream files,
427 we have to set the end-of-file condition. */
428 generate_error (&dtp->common, LIBERROR_END, NULL);
429 return;
430 }
431 return;
432 }
433
434 if (dtp->u.p.current_unit->flags.access == ACCESS_DIRECT)
435 {
436 if (dtp->u.p.current_unit->bytes_left < (gfc_offset) *nbytes)
437 {
438 short_record = 1;
439 to_read_record = (size_t) dtp->u.p.current_unit->bytes_left;
440 *nbytes = to_read_record;
441 }
442
443 else
444 {
445 short_record = 0;
446 to_read_record = *nbytes;
447 }
448
449 dtp->u.p.current_unit->bytes_left -= to_read_record;
450
451 if (unlikely (sread (dtp->u.p.current_unit->s, buf, &to_read_record)
452 != 0))
453 {
454 generate_error (&dtp->common, LIBERROR_OS, NULL);
455 return;
456 }
457
458 if (to_read_record != *nbytes)
459 {
460 /* Short read, e.g. if we hit EOF. Apparently, we read
461 more than was written to the last record. */
462 *nbytes = to_read_record;
463 return;
464 }
465
466 if (unlikely (short_record))
467 {
468 generate_error (&dtp->common, LIBERROR_SHORT_RECORD, NULL);
469 return;
470 }
471 return;
472 }
473
474 /* Unformatted sequential. We loop over the subrecords, reading
475 until the request has been fulfilled or the record has run out
476 of continuation subrecords. */
477
478 if (unlikely (dtp->u.p.current_unit->endfile == AT_ENDFILE))
479 {
480 generate_error (&dtp->common, LIBERROR_END, NULL);
481 return;
482 }
483
484 /* Check whether we exceed the total record length. */
485
486 if (dtp->u.p.current_unit->flags.has_recl
487 && (*nbytes > (size_t) dtp->u.p.current_unit->bytes_left))
488 {
489 to_read_record = (size_t) dtp->u.p.current_unit->bytes_left;
490 short_record = 1;
491 }
492 else
493 {
494 to_read_record = *nbytes;
495 short_record = 0;
496 }
497 have_read_record = 0;
498
499 while(1)
500 {
501 if (dtp->u.p.current_unit->bytes_left_subrecord
502 < (gfc_offset) to_read_record)
503 {
504 to_read_subrecord = (size_t) dtp->u.p.current_unit->bytes_left_subrecord;
505 to_read_record -= to_read_subrecord;
506 }
507 else
508 {
509 to_read_subrecord = to_read_record;
510 to_read_record = 0;
511 }
512
513 dtp->u.p.current_unit->bytes_left_subrecord -= to_read_subrecord;
514
515 have_read_subrecord = to_read_subrecord;
516 if (unlikely (sread (dtp->u.p.current_unit->s, buf + have_read_record,
517 &have_read_subrecord) != 0))
518 {
519 generate_error (&dtp->common, LIBERROR_OS, NULL);
520 return;
521 }
522
523 have_read_record += have_read_subrecord;
524
525 if (unlikely (to_read_subrecord != have_read_subrecord))
526
527 {
528 /* Short read, e.g. if we hit EOF. This means the record
529 structure has been corrupted, or the trailing record
530 marker would still be present. */
531
532 *nbytes = have_read_record;
533 generate_error (&dtp->common, LIBERROR_CORRUPT_FILE, NULL);
534 return;
535 }
536
537 if (to_read_record > 0)
538 {
539 if (likely (dtp->u.p.current_unit->continued))
540 {
541 next_record_r_unf (dtp, 0);
542 us_read (dtp, 1);
543 }
544 else
545 {
546 /* Let's make sure the file position is correctly pre-positioned
547 for the next read statement. */
548
549 dtp->u.p.current_unit->current_record = 0;
550 next_record_r_unf (dtp, 0);
551 generate_error (&dtp->common, LIBERROR_SHORT_RECORD, NULL);
552 return;
553 }
554 }
555 else
556 {
557 /* Normal exit, the read request has been fulfilled. */
558 break;
559 }
560 }
561
562 dtp->u.p.current_unit->bytes_left -= have_read_record;
563 if (unlikely (short_record))
564 {
565 generate_error (&dtp->common, LIBERROR_SHORT_RECORD, NULL);
566 return;
567 }
568 return;
569 }
570
571
572 /* Function for writing a block of bytes to the current file at the
573 current position, advancing the file pointer. We are given a length
574 and return a pointer to a buffer that the caller must (completely)
575 fill in. Returns NULL on error. */
576
577 void *
578 write_block (st_parameter_dt *dtp, int length)
579 {
580 char *dest;
581
582 if (!is_stream_io (dtp))
583 {
584 if (dtp->u.p.current_unit->bytes_left < (gfc_offset) length)
585 {
586 /* For preconnected units with default record length, set bytes left
587 to unit record length and proceed, otherwise error. */
588 if (likely ((dtp->u.p.current_unit->unit_number
589 == options.stdout_unit
590 || dtp->u.p.current_unit->unit_number
591 == options.stderr_unit)
592 && dtp->u.p.current_unit->recl == DEFAULT_RECL))
593 dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
594 else
595 {
596 generate_error (&dtp->common, LIBERROR_EOR, NULL);
597 return NULL;
598 }
599 }
600
601 dtp->u.p.current_unit->bytes_left -= (gfc_offset) length;
602 }
603
604 if (is_internal_unit (dtp))
605 {
606 dest = salloc_w (dtp->u.p.current_unit->s, &length);
607
608 if (dest == NULL)
609 {
610 generate_error (&dtp->common, LIBERROR_END, NULL);
611 return NULL;
612 }
613
614 if (unlikely (dtp->u.p.current_unit->endfile == AT_ENDFILE))
615 generate_error (&dtp->common, LIBERROR_END, NULL);
616 }
617 else
618 {
619 dest = fbuf_alloc (dtp->u.p.current_unit, length);
620 if (dest == NULL)
621 {
622 generate_error (&dtp->common, LIBERROR_OS, NULL);
623 return NULL;
624 }
625 }
626
627 if ((dtp->common.flags & IOPARM_DT_HAS_SIZE) != 0)
628 dtp->u.p.size_used += (GFC_IO_INT) length;
629
630 dtp->u.p.current_unit->strm_pos += (gfc_offset) length;
631
632 return dest;
633 }
634
635
636 /* High level interface to swrite(), taking care of errors. This is only
637 called for unformatted files. There are three cases to consider:
638 Stream I/O, unformatted direct, unformatted sequential. */
639
640 static try
641 write_buf (st_parameter_dt *dtp, void *buf, size_t nbytes)
642 {
643
644 size_t have_written, to_write_subrecord;
645 int short_record;
646
647 /* Stream I/O. */
648
649 if (is_stream_io (dtp))
650 {
651 if (unlikely (swrite (dtp->u.p.current_unit->s, buf, &nbytes) != 0))
652 {
653 generate_error (&dtp->common, LIBERROR_OS, NULL);
654 return FAILURE;
655 }
656
657 dtp->u.p.current_unit->strm_pos += (gfc_offset) nbytes;
658
659 return SUCCESS;
660 }
661
662 /* Unformatted direct access. */
663
664 if (dtp->u.p.current_unit->flags.access == ACCESS_DIRECT)
665 {
666 if (unlikely (dtp->u.p.current_unit->bytes_left < (gfc_offset) nbytes))
667 {
668 generate_error (&dtp->common, LIBERROR_DIRECT_EOR, NULL);
669 return FAILURE;
670 }
671
672 if (buf == NULL && nbytes == 0)
673 return SUCCESS;
674
675 if (unlikely (swrite (dtp->u.p.current_unit->s, buf, &nbytes) != 0))
676 {
677 generate_error (&dtp->common, LIBERROR_OS, NULL);
678 return FAILURE;
679 }
680
681 dtp->u.p.current_unit->strm_pos += (gfc_offset) nbytes;
682 dtp->u.p.current_unit->bytes_left -= (gfc_offset) nbytes;
683
684 return SUCCESS;
685 }
686
687 /* Unformatted sequential. */
688
689 have_written = 0;
690
691 if (dtp->u.p.current_unit->flags.has_recl
692 && (gfc_offset) nbytes > dtp->u.p.current_unit->bytes_left)
693 {
694 nbytes = dtp->u.p.current_unit->bytes_left;
695 short_record = 1;
696 }
697 else
698 {
699 short_record = 0;
700 }
701
702 while (1)
703 {
704
705 to_write_subrecord =
706 (size_t) dtp->u.p.current_unit->bytes_left_subrecord < nbytes ?
707 (size_t) dtp->u.p.current_unit->bytes_left_subrecord : nbytes;
708
709 dtp->u.p.current_unit->bytes_left_subrecord -=
710 (gfc_offset) to_write_subrecord;
711
712 if (unlikely (swrite (dtp->u.p.current_unit->s, buf + have_written,
713 &to_write_subrecord) != 0))
714 {
715 generate_error (&dtp->common, LIBERROR_OS, NULL);
716 return FAILURE;
717 }
718
719 dtp->u.p.current_unit->strm_pos += (gfc_offset) to_write_subrecord;
720 nbytes -= to_write_subrecord;
721 have_written += to_write_subrecord;
722
723 if (nbytes == 0)
724 break;
725
726 next_record_w_unf (dtp, 1);
727 us_write (dtp, 1);
728 }
729 dtp->u.p.current_unit->bytes_left -= have_written;
730 if (unlikely (short_record))
731 {
732 generate_error (&dtp->common, LIBERROR_SHORT_RECORD, NULL);
733 return FAILURE;
734 }
735 return SUCCESS;
736 }
737
738
739 /* Master function for unformatted reads. */
740
741 static void
742 unformatted_read (st_parameter_dt *dtp, bt type,
743 void *dest, int kind, size_t size, size_t nelems)
744 {
745 size_t i, sz;
746
747 if (likely (dtp->u.p.current_unit->flags.convert == GFC_CONVERT_NATIVE)
748 || kind == 1)
749 {
750 sz = size * nelems;
751 if (type == BT_CHARACTER)
752 sz *= GFC_SIZE_OF_CHAR_KIND(kind);
753 read_block_direct (dtp, dest, &sz);
754 }
755 else
756 {
757 char buffer[16];
758 char *p;
759
760 p = dest;
761
762 /* Handle wide chracters. */
763 if (type == BT_CHARACTER && kind != 1)
764 {
765 nelems *= size;
766 size = kind;
767 }
768
769 /* Break up complex into its constituent reals. */
770 if (type == BT_COMPLEX)
771 {
772 nelems *= 2;
773 size /= 2;
774 }
775
776 /* By now, all complex variables have been split into their
777 constituent reals. */
778
779 for (i = 0; i < nelems; i++)
780 {
781 read_block_direct (dtp, buffer, &size);
782 reverse_memcpy (p, buffer, size);
783 p += size;
784 }
785 }
786 }
787
788
789 /* Master function for unformatted writes. NOTE: For kind=10 the size is 16
790 bytes on 64 bit machines. The unused bytes are not initialized and never
791 used, which can show an error with memory checking analyzers like
792 valgrind. */
793
794 static void
795 unformatted_write (st_parameter_dt *dtp, bt type,
796 void *source, int kind, size_t size, size_t nelems)
797 {
798 if (likely (dtp->u.p.current_unit->flags.convert == GFC_CONVERT_NATIVE)
799 || kind == 1)
800 {
801 size_t stride = type == BT_CHARACTER ?
802 size * GFC_SIZE_OF_CHAR_KIND(kind) : size;
803
804 write_buf (dtp, source, stride * nelems);
805 }
806 else
807 {
808 char buffer[16];
809 char *p;
810 size_t i;
811
812 p = source;
813
814 /* Handle wide chracters. */
815 if (type == BT_CHARACTER && kind != 1)
816 {
817 nelems *= size;
818 size = kind;
819 }
820
821 /* Break up complex into its constituent reals. */
822 if (type == BT_COMPLEX)
823 {
824 nelems *= 2;
825 size /= 2;
826 }
827
828 /* By now, all complex variables have been split into their
829 constituent reals. */
830
831 for (i = 0; i < nelems; i++)
832 {
833 reverse_memcpy(buffer, p, size);
834 p += size;
835 write_buf (dtp, buffer, size);
836 }
837 }
838 }
839
840
841 /* Return a pointer to the name of a type. */
842
843 const char *
844 type_name (bt type)
845 {
846 const char *p;
847
848 switch (type)
849 {
850 case BT_INTEGER:
851 p = "INTEGER";
852 break;
853 case BT_LOGICAL:
854 p = "LOGICAL";
855 break;
856 case BT_CHARACTER:
857 p = "CHARACTER";
858 break;
859 case BT_REAL:
860 p = "REAL";
861 break;
862 case BT_COMPLEX:
863 p = "COMPLEX";
864 break;
865 default:
866 internal_error (NULL, "type_name(): Bad type");
867 }
868
869 return p;
870 }
871
872
873 /* Write a constant string to the output.
874 This is complicated because the string can have doubled delimiters
875 in it. The length in the format node is the true length. */
876
877 static void
878 write_constant_string (st_parameter_dt *dtp, const fnode *f)
879 {
880 char c, delimiter, *p, *q;
881 int length;
882
883 length = f->u.string.length;
884 if (length == 0)
885 return;
886
887 p = write_block (dtp, length);
888 if (p == NULL)
889 return;
890
891 q = f->u.string.p;
892 delimiter = q[-1];
893
894 for (; length > 0; length--)
895 {
896 c = *p++ = *q++;
897 if (c == delimiter && c != 'H' && c != 'h')
898 q++; /* Skip the doubled delimiter. */
899 }
900 }
901
902
903 /* Given actual and expected types in a formatted data transfer, make
904 sure they agree. If not, an error message is generated. Returns
905 nonzero if something went wrong. */
906
907 static int
908 require_type (st_parameter_dt *dtp, bt expected, bt actual, const fnode *f)
909 {
910 char buffer[100];
911
912 if (actual == expected)
913 return 0;
914
915 sprintf (buffer, "Expected %s for item %d in formatted transfer, got %s",
916 type_name (expected), dtp->u.p.item_count, type_name (actual));
917
918 format_error (dtp, f, buffer);
919 return 1;
920 }
921
922
923 /* This subroutine is the main loop for a formatted data transfer
924 statement. It would be natural to implement this as a coroutine
925 with the user program, but C makes that awkward. We loop,
926 processing format elements. When we actually have to transfer
927 data instead of just setting flags, we return control to the user
928 program which calls a subroutine that supplies the address and type
929 of the next element, then comes back here to process it. */
930
931 static void
932 formatted_transfer_scalar (st_parameter_dt *dtp, bt type, void *p, int kind,
933 size_t size)
934 {
935 char scratch[SCRATCH_SIZE];
936 int pos, bytes_used;
937 const fnode *f;
938 format_token t;
939 int n;
940 int consume_data_flag;
941
942 /* Change a complex data item into a pair of reals. */
943
944 n = (p == NULL) ? 0 : ((type != BT_COMPLEX) ? 1 : 2);
945 if (type == BT_COMPLEX)
946 {
947 type = BT_REAL;
948 size /= 2;
949 }
950
951 /* If there's an EOR condition, we simulate finalizing the transfer
952 by doing nothing. */
953 if (dtp->u.p.eor_condition)
954 return;
955
956 /* Set this flag so that commas in reads cause the read to complete before
957 the entire field has been read. The next read field will start right after
958 the comma in the stream. (Set to 0 for character reads). */
959 dtp->u.p.sf_read_comma =
960 dtp->u.p.current_unit->decimal_status == DECIMAL_COMMA ? 0 : 1;
961
962 dtp->u.p.line_buffer = scratch;
963
964 for (;;)
965 {
966 /* If reversion has occurred and there is another real data item,
967 then we have to move to the next record. */
968 if (dtp->u.p.reversion_flag && n > 0)
969 {
970 dtp->u.p.reversion_flag = 0;
971 next_record (dtp, 0);
972 }
973
974 consume_data_flag = 1;
975 if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
976 break;
977
978 f = next_format (dtp);
979 if (f == NULL)
980 {
981 /* No data descriptors left. */
982 if (unlikely (n > 0))
983 generate_error (&dtp->common, LIBERROR_FORMAT,
984 "Insufficient data descriptors in format after reversion");
985 return;
986 }
987
988 /* Now discharge T, TR and X movements to the right. This is delayed
989 until a data producing format to suppress trailing spaces. */
990
991 t = f->format;
992 if (dtp->u.p.mode == WRITING && dtp->u.p.skips != 0
993 && ((n>0 && ( t == FMT_I || t == FMT_B || t == FMT_O
994 || t == FMT_Z || t == FMT_F || t == FMT_E
995 || t == FMT_EN || t == FMT_ES || t == FMT_G
996 || t == FMT_L || t == FMT_A || t == FMT_D))
997 || t == FMT_STRING))
998 {
999 if (dtp->u.p.skips > 0)
1000 {
1001 int tmp;
1002 write_x (dtp, dtp->u.p.skips, dtp->u.p.pending_spaces);
1003 tmp = (int)(dtp->u.p.current_unit->recl
1004 - dtp->u.p.current_unit->bytes_left);
1005 dtp->u.p.max_pos =
1006 dtp->u.p.max_pos > tmp ? dtp->u.p.max_pos : tmp;
1007 }
1008 if (dtp->u.p.skips < 0)
1009 {
1010 if (is_internal_unit (dtp))
1011 move_pos_offset (dtp->u.p.current_unit->s, dtp->u.p.skips);
1012 else
1013 fbuf_seek (dtp->u.p.current_unit, dtp->u.p.skips);
1014 dtp->u.p.current_unit->bytes_left -= (gfc_offset) dtp->u.p.skips;
1015 }
1016 dtp->u.p.skips = dtp->u.p.pending_spaces = 0;
1017 }
1018
1019 bytes_used = (int)(dtp->u.p.current_unit->recl
1020 - dtp->u.p.current_unit->bytes_left);
1021
1022 if (is_stream_io(dtp))
1023 bytes_used = 0;
1024
1025 switch (t)
1026 {
1027 case FMT_I:
1028 if (n == 0)
1029 goto need_data;
1030 if (require_type (dtp, BT_INTEGER, type, f))
1031 return;
1032
1033 if (dtp->u.p.mode == READING)
1034 read_decimal (dtp, f, p, kind);
1035 else
1036 write_i (dtp, f, p, kind);
1037
1038 break;
1039
1040 case FMT_B:
1041 if (n == 0)
1042 goto need_data;
1043
1044 if (compile_options.allow_std < GFC_STD_GNU
1045 && require_type (dtp, BT_INTEGER, type, f))
1046 return;
1047
1048 if (dtp->u.p.mode == READING)
1049 read_radix (dtp, f, p, kind, 2);
1050 else
1051 write_b (dtp, f, p, kind);
1052
1053 break;
1054
1055 case FMT_O:
1056 if (n == 0)
1057 goto need_data;
1058
1059 if (compile_options.allow_std < GFC_STD_GNU
1060 && require_type (dtp, BT_INTEGER, type, f))
1061 return;
1062
1063 if (dtp->u.p.mode == READING)
1064 read_radix (dtp, f, p, kind, 8);
1065 else
1066 write_o (dtp, f, p, kind);
1067
1068 break;
1069
1070 case FMT_Z:
1071 if (n == 0)
1072 goto need_data;
1073
1074 if (compile_options.allow_std < GFC_STD_GNU
1075 && require_type (dtp, BT_INTEGER, type, f))
1076 return;
1077
1078 if (dtp->u.p.mode == READING)
1079 read_radix (dtp, f, p, kind, 16);
1080 else
1081 write_z (dtp, f, p, kind);
1082
1083 break;
1084
1085 case FMT_A:
1086 if (n == 0)
1087 goto need_data;
1088
1089 /* It is possible to have FMT_A with something not BT_CHARACTER such
1090 as when writing out hollerith strings, so check both type
1091 and kind before calling wide character routines. */
1092 if (dtp->u.p.mode == READING)
1093 {
1094 if (type == BT_CHARACTER && kind == 4)
1095 read_a_char4 (dtp, f, p, size);
1096 else
1097 read_a (dtp, f, p, size);
1098 }
1099 else
1100 {
1101 if (type == BT_CHARACTER && kind == 4)
1102 write_a_char4 (dtp, f, p, size);
1103 else
1104 write_a (dtp, f, p, size);
1105 }
1106 break;
1107
1108 case FMT_L:
1109 if (n == 0)
1110 goto need_data;
1111
1112 if (dtp->u.p.mode == READING)
1113 read_l (dtp, f, p, kind);
1114 else
1115 write_l (dtp, f, p, kind);
1116
1117 break;
1118
1119 case FMT_D:
1120 if (n == 0)
1121 goto need_data;
1122 if (require_type (dtp, BT_REAL, type, f))
1123 return;
1124
1125 if (dtp->u.p.mode == READING)
1126 read_f (dtp, f, p, kind);
1127 else
1128 write_d (dtp, f, p, kind);
1129
1130 break;
1131
1132 case FMT_E:
1133 if (n == 0)
1134 goto need_data;
1135 if (require_type (dtp, BT_REAL, type, f))
1136 return;
1137
1138 if (dtp->u.p.mode == READING)
1139 read_f (dtp, f, p, kind);
1140 else
1141 write_e (dtp, f, p, kind);
1142 break;
1143
1144 case FMT_EN:
1145 if (n == 0)
1146 goto need_data;
1147 if (require_type (dtp, BT_REAL, type, f))
1148 return;
1149
1150 if (dtp->u.p.mode == READING)
1151 read_f (dtp, f, p, kind);
1152 else
1153 write_en (dtp, f, p, kind);
1154
1155 break;
1156
1157 case FMT_ES:
1158 if (n == 0)
1159 goto need_data;
1160 if (require_type (dtp, BT_REAL, type, f))
1161 return;
1162
1163 if (dtp->u.p.mode == READING)
1164 read_f (dtp, f, p, kind);
1165 else
1166 write_es (dtp, f, p, kind);
1167
1168 break;
1169
1170 case FMT_F:
1171 if (n == 0)
1172 goto need_data;
1173 if (require_type (dtp, BT_REAL, type, f))
1174 return;
1175
1176 if (dtp->u.p.mode == READING)
1177 read_f (dtp, f, p, kind);
1178 else
1179 write_f (dtp, f, p, kind);
1180
1181 break;
1182
1183 case FMT_G:
1184 if (n == 0)
1185 goto need_data;
1186 if (dtp->u.p.mode == READING)
1187 switch (type)
1188 {
1189 case BT_INTEGER:
1190 read_decimal (dtp, f, p, kind);
1191 break;
1192 case BT_LOGICAL:
1193 read_l (dtp, f, p, kind);
1194 break;
1195 case BT_CHARACTER:
1196 if (kind == 4)
1197 read_a_char4 (dtp, f, p, size);
1198 else
1199 read_a (dtp, f, p, size);
1200 break;
1201 case BT_REAL:
1202 read_f (dtp, f, p, kind);
1203 break;
1204 default:
1205 goto bad_type;
1206 }
1207 else
1208 switch (type)
1209 {
1210 case BT_INTEGER:
1211 write_i (dtp, f, p, kind);
1212 break;
1213 case BT_LOGICAL:
1214 write_l (dtp, f, p, kind);
1215 break;
1216 case BT_CHARACTER:
1217 if (kind == 4)
1218 write_a_char4 (dtp, f, p, size);
1219 else
1220 write_a (dtp, f, p, size);
1221 break;
1222 case BT_REAL:
1223 if (f->u.real.w == 0)
1224 write_real_g0 (dtp, p, kind, f->u.real.d);
1225 else
1226 write_d (dtp, f, p, kind);
1227 break;
1228 default:
1229 bad_type:
1230 internal_error (&dtp->common,
1231 "formatted_transfer(): Bad type");
1232 }
1233
1234 break;
1235
1236 case FMT_STRING:
1237 consume_data_flag = 0;
1238 if (dtp->u.p.mode == READING)
1239 {
1240 format_error (dtp, f, "Constant string in input format");
1241 return;
1242 }
1243 write_constant_string (dtp, f);
1244 break;
1245
1246 /* Format codes that don't transfer data. */
1247 case FMT_X:
1248 case FMT_TR:
1249 consume_data_flag = 0;
1250
1251 dtp->u.p.skips += f->u.n;
1252 pos = bytes_used + dtp->u.p.skips - 1;
1253 dtp->u.p.pending_spaces = pos - dtp->u.p.max_pos + 1;
1254
1255 /* Writes occur just before the switch on f->format, above, so
1256 that trailing blanks are suppressed, unless we are doing a
1257 non-advancing write in which case we want to output the blanks
1258 now. */
1259 if (dtp->u.p.mode == WRITING
1260 && dtp->u.p.advance_status == ADVANCE_NO)
1261 {
1262 write_x (dtp, dtp->u.p.skips, dtp->u.p.pending_spaces);
1263 dtp->u.p.skips = dtp->u.p.pending_spaces = 0;
1264 }
1265
1266 if (dtp->u.p.mode == READING)
1267 read_x (dtp, f->u.n);
1268
1269 break;
1270
1271 case FMT_TL:
1272 case FMT_T:
1273 consume_data_flag = 0;
1274
1275 if (f->format == FMT_TL)
1276 {
1277
1278 /* Handle the special case when no bytes have been used yet.
1279 Cannot go below zero. */
1280 if (bytes_used == 0)
1281 {
1282 dtp->u.p.pending_spaces -= f->u.n;
1283 dtp->u.p.skips -= f->u.n;
1284 dtp->u.p.skips = dtp->u.p.skips < 0 ? 0 : dtp->u.p.skips;
1285 }
1286
1287 pos = bytes_used - f->u.n;
1288 }
1289 else /* FMT_T */
1290 {
1291 if (dtp->u.p.mode == READING)
1292 pos = f->u.n - 1;
1293 else
1294 pos = f->u.n - dtp->u.p.pending_spaces - 1;
1295 }
1296
1297 /* Standard 10.6.1.1: excessive left tabbing is reset to the
1298 left tab limit. We do not check if the position has gone
1299 beyond the end of record because a subsequent tab could
1300 bring us back again. */
1301 pos = pos < 0 ? 0 : pos;
1302
1303 dtp->u.p.skips = dtp->u.p.skips + pos - bytes_used;
1304 dtp->u.p.pending_spaces = dtp->u.p.pending_spaces
1305 + pos - dtp->u.p.max_pos;
1306 dtp->u.p.pending_spaces = dtp->u.p.pending_spaces < 0
1307 ? 0 : dtp->u.p.pending_spaces;
1308
1309 if (dtp->u.p.skips == 0)
1310 break;
1311
1312 /* Writes occur just before the switch on f->format, above, so that
1313 trailing blanks are suppressed. */
1314 if (dtp->u.p.mode == READING)
1315 {
1316 /* Adjust everything for end-of-record condition */
1317 if (dtp->u.p.sf_seen_eor && !is_internal_unit (dtp))
1318 {
1319 if (dtp->u.p.sf_seen_eor == 2)
1320 {
1321 /* The EOR was a CRLF (two bytes wide). */
1322 dtp->u.p.current_unit->bytes_left -= 2;
1323 dtp->u.p.skips -= 2;
1324 }
1325 else
1326 {
1327 /* The EOR marker was only one byte wide. */
1328 dtp->u.p.current_unit->bytes_left--;
1329 dtp->u.p.skips--;
1330 }
1331 bytes_used = pos;
1332 dtp->u.p.sf_seen_eor = 0;
1333 }
1334 if (dtp->u.p.skips < 0)
1335 {
1336 move_pos_offset (dtp->u.p.current_unit->s, dtp->u.p.skips);
1337 dtp->u.p.current_unit->bytes_left
1338 -= (gfc_offset) dtp->u.p.skips;
1339 dtp->u.p.skips = dtp->u.p.pending_spaces = 0;
1340 }
1341 else
1342 read_x (dtp, dtp->u.p.skips);
1343 }
1344
1345 break;
1346
1347 case FMT_S:
1348 consume_data_flag = 0;
1349 dtp->u.p.sign_status = SIGN_S;
1350 break;
1351
1352 case FMT_SS:
1353 consume_data_flag = 0;
1354 dtp->u.p.sign_status = SIGN_SS;
1355 break;
1356
1357 case FMT_SP:
1358 consume_data_flag = 0;
1359 dtp->u.p.sign_status = SIGN_SP;
1360 break;
1361
1362 case FMT_BN:
1363 consume_data_flag = 0 ;
1364 dtp->u.p.blank_status = BLANK_NULL;
1365 break;
1366
1367 case FMT_BZ:
1368 consume_data_flag = 0;
1369 dtp->u.p.blank_status = BLANK_ZERO;
1370 break;
1371
1372 case FMT_DC:
1373 consume_data_flag = 0;
1374 dtp->u.p.current_unit->decimal_status = DECIMAL_COMMA;
1375 break;
1376
1377 case FMT_DP:
1378 consume_data_flag = 0;
1379 dtp->u.p.current_unit->decimal_status = DECIMAL_POINT;
1380 break;
1381
1382 case FMT_P:
1383 consume_data_flag = 0;
1384 dtp->u.p.scale_factor = f->u.k;
1385 break;
1386
1387 case FMT_DOLLAR:
1388 consume_data_flag = 0;
1389 dtp->u.p.seen_dollar = 1;
1390 break;
1391
1392 case FMT_SLASH:
1393 consume_data_flag = 0;
1394 dtp->u.p.skips = dtp->u.p.pending_spaces = 0;
1395 next_record (dtp, 0);
1396 break;
1397
1398 case FMT_COLON:
1399 /* A colon descriptor causes us to exit this loop (in
1400 particular preventing another / descriptor from being
1401 processed) unless there is another data item to be
1402 transferred. */
1403 consume_data_flag = 0;
1404 if (n == 0)
1405 return;
1406 break;
1407
1408 default:
1409 internal_error (&dtp->common, "Bad format node");
1410 }
1411
1412 /* Free a buffer that we had to allocate during a sequential
1413 formatted read of a block that was larger than the static
1414 buffer. */
1415
1416 if (dtp->u.p.line_buffer != scratch)
1417 {
1418 free_mem (dtp->u.p.line_buffer);
1419 dtp->u.p.line_buffer = scratch;
1420 }
1421
1422 /* Adjust the item count and data pointer. */
1423
1424 if ((consume_data_flag > 0) && (n > 0))
1425 {
1426 n--;
1427 p = ((char *) p) + size;
1428 }
1429
1430 if (dtp->u.p.mode == READING)
1431 dtp->u.p.skips = 0;
1432
1433 pos = (int)(dtp->u.p.current_unit->recl - dtp->u.p.current_unit->bytes_left);
1434 dtp->u.p.max_pos = (dtp->u.p.max_pos > pos) ? dtp->u.p.max_pos : pos;
1435
1436 }
1437
1438 return;
1439
1440 /* Come here when we need a data descriptor but don't have one. We
1441 push the current format node back onto the input, then return and
1442 let the user program call us back with the data. */
1443 need_data:
1444 unget_format (dtp, f);
1445 }
1446
1447 static void
1448 formatted_transfer (st_parameter_dt *dtp, bt type, void *p, int kind,
1449 size_t size, size_t nelems)
1450 {
1451 size_t elem;
1452 char *tmp;
1453
1454 tmp = (char *) p;
1455 size_t stride = type == BT_CHARACTER ?
1456 size * GFC_SIZE_OF_CHAR_KIND(kind) : size;
1457 /* Big loop over all the elements. */
1458 for (elem = 0; elem < nelems; elem++)
1459 {
1460 dtp->u.p.item_count++;
1461 formatted_transfer_scalar (dtp, type, tmp + stride*elem, kind, size);
1462 }
1463 }
1464
1465
1466
1467 /* Data transfer entry points. The type of the data entity is
1468 implicit in the subroutine call. This prevents us from having to
1469 share a common enum with the compiler. */
1470
1471 void
1472 transfer_integer (st_parameter_dt *dtp, void *p, int kind)
1473 {
1474 if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1475 return;
1476 dtp->u.p.transfer (dtp, BT_INTEGER, p, kind, kind, 1);
1477 }
1478
1479
1480 void
1481 transfer_real (st_parameter_dt *dtp, void *p, int kind)
1482 {
1483 size_t size;
1484 if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1485 return;
1486 size = size_from_real_kind (kind);
1487 dtp->u.p.transfer (dtp, BT_REAL, p, kind, size, 1);
1488 }
1489
1490
1491 void
1492 transfer_logical (st_parameter_dt *dtp, void *p, int kind)
1493 {
1494 if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1495 return;
1496 dtp->u.p.transfer (dtp, BT_LOGICAL, p, kind, kind, 1);
1497 }
1498
1499
1500 void
1501 transfer_character (st_parameter_dt *dtp, void *p, int len)
1502 {
1503 static char *empty_string[0];
1504
1505 if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1506 return;
1507
1508 /* Strings of zero length can have p == NULL, which confuses the
1509 transfer routines into thinking we need more data elements. To avoid
1510 this, we give them a nice pointer. */
1511 if (len == 0 && p == NULL)
1512 p = empty_string;
1513
1514 /* Set kind here to 1. */
1515 dtp->u.p.transfer (dtp, BT_CHARACTER, p, 1, len, 1);
1516 }
1517
1518 void
1519 transfer_character_wide (st_parameter_dt *dtp, void *p, int len, int kind)
1520 {
1521 static char *empty_string[0];
1522
1523 if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1524 return;
1525
1526 /* Strings of zero length can have p == NULL, which confuses the
1527 transfer routines into thinking we need more data elements. To avoid
1528 this, we give them a nice pointer. */
1529 if (len == 0 && p == NULL)
1530 p = empty_string;
1531
1532 /* Here we pass the actual kind value. */
1533 dtp->u.p.transfer (dtp, BT_CHARACTER, p, kind, len, 1);
1534 }
1535
1536
1537 void
1538 transfer_complex (st_parameter_dt *dtp, void *p, int kind)
1539 {
1540 size_t size;
1541 if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1542 return;
1543 size = size_from_complex_kind (kind);
1544 dtp->u.p.transfer (dtp, BT_COMPLEX, p, kind, size, 1);
1545 }
1546
1547
1548 void
1549 transfer_array (st_parameter_dt *dtp, gfc_array_char *desc, int kind,
1550 gfc_charlen_type charlen)
1551 {
1552 index_type count[GFC_MAX_DIMENSIONS];
1553 index_type extent[GFC_MAX_DIMENSIONS];
1554 index_type stride[GFC_MAX_DIMENSIONS];
1555 index_type stride0, rank, size, type, n;
1556 size_t tsize;
1557 char *data;
1558 bt iotype;
1559
1560 if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1561 return;
1562
1563 type = GFC_DESCRIPTOR_TYPE (desc);
1564 size = GFC_DESCRIPTOR_SIZE (desc);
1565
1566 /* FIXME: What a kludge: Array descriptors and the IO library use
1567 different enums for types. */
1568 switch (type)
1569 {
1570 case GFC_DTYPE_UNKNOWN:
1571 iotype = BT_NULL; /* Is this correct? */
1572 break;
1573 case GFC_DTYPE_INTEGER:
1574 iotype = BT_INTEGER;
1575 break;
1576 case GFC_DTYPE_LOGICAL:
1577 iotype = BT_LOGICAL;
1578 break;
1579 case GFC_DTYPE_REAL:
1580 iotype = BT_REAL;
1581 break;
1582 case GFC_DTYPE_COMPLEX:
1583 iotype = BT_COMPLEX;
1584 break;
1585 case GFC_DTYPE_CHARACTER:
1586 iotype = BT_CHARACTER;
1587 size = charlen;
1588 break;
1589 case GFC_DTYPE_DERIVED:
1590 internal_error (&dtp->common,
1591 "Derived type I/O should have been handled via the frontend.");
1592 break;
1593 default:
1594 internal_error (&dtp->common, "transfer_array(): Bad type");
1595 }
1596
1597 rank = GFC_DESCRIPTOR_RANK (desc);
1598 for (n = 0; n < rank; n++)
1599 {
1600 count[n] = 0;
1601 stride[n] = iotype == BT_CHARACTER ?
1602 desc->dim[n].stride * GFC_SIZE_OF_CHAR_KIND(kind) :
1603 desc->dim[n].stride;
1604 extent[n] = desc->dim[n].ubound + 1 - desc->dim[n].lbound;
1605
1606 /* If the extent of even one dimension is zero, then the entire
1607 array section contains zero elements, so we return after writing
1608 a zero array record. */
1609 if (extent[n] <= 0)
1610 {
1611 data = NULL;
1612 tsize = 0;
1613 dtp->u.p.transfer (dtp, iotype, data, kind, size, tsize);
1614 return;
1615 }
1616 }
1617
1618 stride0 = stride[0];
1619
1620 /* If the innermost dimension has stride 1, we can do the transfer
1621 in contiguous chunks. */
1622 if (stride0 == 1)
1623 tsize = extent[0];
1624 else
1625 tsize = 1;
1626
1627 data = GFC_DESCRIPTOR_DATA (desc);
1628
1629 while (data)
1630 {
1631 dtp->u.p.transfer (dtp, iotype, data, kind, size, tsize);
1632 data += stride0 * size * tsize;
1633 count[0] += tsize;
1634 n = 0;
1635 while (count[n] == extent[n])
1636 {
1637 count[n] = 0;
1638 data -= stride[n] * extent[n] * size;
1639 n++;
1640 if (n == rank)
1641 {
1642 data = NULL;
1643 break;
1644 }
1645 else
1646 {
1647 count[n]++;
1648 data += stride[n] * size;
1649 }
1650 }
1651 }
1652 }
1653
1654
1655 /* Preposition a sequential unformatted file while reading. */
1656
1657 static void
1658 us_read (st_parameter_dt *dtp, int continued)
1659 {
1660 size_t n, nr;
1661 GFC_INTEGER_4 i4;
1662 GFC_INTEGER_8 i8;
1663 gfc_offset i;
1664
1665 if (dtp->u.p.current_unit->endfile == AT_ENDFILE)
1666 return;
1667
1668 if (compile_options.record_marker == 0)
1669 n = sizeof (GFC_INTEGER_4);
1670 else
1671 n = compile_options.record_marker;
1672
1673 nr = n;
1674
1675 if (unlikely (sread (dtp->u.p.current_unit->s, &i, &n) != 0))
1676 {
1677 generate_error (&dtp->common, LIBERROR_BAD_US, NULL);
1678 return;
1679 }
1680
1681 if (n == 0)
1682 {
1683 dtp->u.p.current_unit->endfile = AT_ENDFILE;
1684 return; /* end of file */
1685 }
1686
1687 if (unlikely (n != nr))
1688 {
1689 generate_error (&dtp->common, LIBERROR_BAD_US, NULL);
1690 return;
1691 }
1692
1693 /* Only GFC_CONVERT_NATIVE and GFC_CONVERT_SWAP are valid here. */
1694 if (likely (dtp->u.p.current_unit->flags.convert == GFC_CONVERT_NATIVE))
1695 {
1696 switch (nr)
1697 {
1698 case sizeof(GFC_INTEGER_4):
1699 memcpy (&i4, &i, sizeof (i4));
1700 i = i4;
1701 break;
1702
1703 case sizeof(GFC_INTEGER_8):
1704 memcpy (&i8, &i, sizeof (i8));
1705 i = i8;
1706 break;
1707
1708 default:
1709 runtime_error ("Illegal value for record marker");
1710 break;
1711 }
1712 }
1713 else
1714 switch (nr)
1715 {
1716 case sizeof(GFC_INTEGER_4):
1717 reverse_memcpy (&i4, &i, sizeof (i4));
1718 i = i4;
1719 break;
1720
1721 case sizeof(GFC_INTEGER_8):
1722 reverse_memcpy (&i8, &i, sizeof (i8));
1723 i = i8;
1724 break;
1725
1726 default:
1727 runtime_error ("Illegal value for record marker");
1728 break;
1729 }
1730
1731 if (i >= 0)
1732 {
1733 dtp->u.p.current_unit->bytes_left_subrecord = i;
1734 dtp->u.p.current_unit->continued = 0;
1735 }
1736 else
1737 {
1738 dtp->u.p.current_unit->bytes_left_subrecord = -i;
1739 dtp->u.p.current_unit->continued = 1;
1740 }
1741
1742 if (! continued)
1743 dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
1744 }
1745
1746
1747 /* Preposition a sequential unformatted file while writing. This
1748 amount to writing a bogus length that will be filled in later. */
1749
1750 static void
1751 us_write (st_parameter_dt *dtp, int continued)
1752 {
1753 size_t nbytes;
1754 gfc_offset dummy;
1755
1756 dummy = 0;
1757
1758 if (compile_options.record_marker == 0)
1759 nbytes = sizeof (GFC_INTEGER_4);
1760 else
1761 nbytes = compile_options.record_marker ;
1762
1763 if (swrite (dtp->u.p.current_unit->s, &dummy, &nbytes) != 0)
1764 generate_error (&dtp->common, LIBERROR_OS, NULL);
1765
1766 /* For sequential unformatted, if RECL= was not specified in the OPEN
1767 we write until we have more bytes than can fit in the subrecord
1768 markers, then we write a new subrecord. */
1769
1770 dtp->u.p.current_unit->bytes_left_subrecord =
1771 dtp->u.p.current_unit->recl_subrecord;
1772 dtp->u.p.current_unit->continued = continued;
1773 }
1774
1775
1776 /* Position to the next record prior to transfer. We are assumed to
1777 be before the next record. We also calculate the bytes in the next
1778 record. */
1779
1780 static void
1781 pre_position (st_parameter_dt *dtp)
1782 {
1783 if (dtp->u.p.current_unit->current_record)
1784 return; /* Already positioned. */
1785
1786 switch (current_mode (dtp))
1787 {
1788 case FORMATTED_STREAM:
1789 case UNFORMATTED_STREAM:
1790 /* There are no records with stream I/O. If the position was specified
1791 data_transfer_init has already positioned the file. If no position
1792 was specified, we continue from where we last left off. I.e.
1793 there is nothing to do here. */
1794 break;
1795
1796 case UNFORMATTED_SEQUENTIAL:
1797 if (dtp->u.p.mode == READING)
1798 us_read (dtp, 0);
1799 else
1800 us_write (dtp, 0);
1801
1802 break;
1803
1804 case FORMATTED_SEQUENTIAL:
1805 case FORMATTED_DIRECT:
1806 case UNFORMATTED_DIRECT:
1807 dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
1808 break;
1809 }
1810
1811 dtp->u.p.current_unit->current_record = 1;
1812 }
1813
1814
1815 /* Initialize things for a data transfer. This code is common for
1816 both reading and writing. */
1817
1818 static void
1819 data_transfer_init (st_parameter_dt *dtp, int read_flag)
1820 {
1821 unit_flags u_flags; /* Used for creating a unit if needed. */
1822 GFC_INTEGER_4 cf = dtp->common.flags;
1823 namelist_info *ionml;
1824
1825 ionml = ((cf & IOPARM_DT_IONML_SET) != 0) ? dtp->u.p.ionml : NULL;
1826
1827 memset (&dtp->u.p, 0, sizeof (dtp->u.p));
1828
1829 dtp->u.p.ionml = ionml;
1830 dtp->u.p.mode = read_flag ? READING : WRITING;
1831
1832 if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
1833 return;
1834
1835 if ((cf & IOPARM_DT_HAS_SIZE) != 0)
1836 dtp->u.p.size_used = 0; /* Initialize the count. */
1837
1838 dtp->u.p.current_unit = get_unit (dtp, 1);
1839 if (dtp->u.p.current_unit->s == NULL)
1840 { /* Open the unit with some default flags. */
1841 st_parameter_open opp;
1842 unit_convert conv;
1843
1844 if (dtp->common.unit < 0)
1845 {
1846 close_unit (dtp->u.p.current_unit);
1847 dtp->u.p.current_unit = NULL;
1848 generate_error (&dtp->common, LIBERROR_BAD_OPTION,
1849 "Bad unit number in OPEN statement");
1850 return;
1851 }
1852 memset (&u_flags, '\0', sizeof (u_flags));
1853 u_flags.access = ACCESS_SEQUENTIAL;
1854 u_flags.action = ACTION_READWRITE;
1855
1856 /* Is it unformatted? */
1857 if (!(cf & (IOPARM_DT_HAS_FORMAT | IOPARM_DT_LIST_FORMAT
1858 | IOPARM_DT_IONML_SET)))
1859 u_flags.form = FORM_UNFORMATTED;
1860 else
1861 u_flags.form = FORM_UNSPECIFIED;
1862
1863 u_flags.delim = DELIM_UNSPECIFIED;
1864 u_flags.blank = BLANK_UNSPECIFIED;
1865 u_flags.pad = PAD_UNSPECIFIED;
1866 u_flags.decimal = DECIMAL_UNSPECIFIED;
1867 u_flags.encoding = ENCODING_UNSPECIFIED;
1868 u_flags.async = ASYNC_UNSPECIFIED;
1869 u_flags.round = ROUND_UNSPECIFIED;
1870 u_flags.sign = SIGN_UNSPECIFIED;
1871
1872 u_flags.status = STATUS_UNKNOWN;
1873
1874 conv = get_unformatted_convert (dtp->common.unit);
1875
1876 if (conv == GFC_CONVERT_NONE)
1877 conv = compile_options.convert;
1878
1879 /* We use big_endian, which is 0 on little-endian machines
1880 and 1 on big-endian machines. */
1881 switch (conv)
1882 {
1883 case GFC_CONVERT_NATIVE:
1884 case GFC_CONVERT_SWAP:
1885 break;
1886
1887 case GFC_CONVERT_BIG:
1888 conv = big_endian ? GFC_CONVERT_NATIVE : GFC_CONVERT_SWAP;
1889 break;
1890
1891 case GFC_CONVERT_LITTLE:
1892 conv = big_endian ? GFC_CONVERT_SWAP : GFC_CONVERT_NATIVE;
1893 break;
1894
1895 default:
1896 internal_error (&opp.common, "Illegal value for CONVERT");
1897 break;
1898 }
1899
1900 u_flags.convert = conv;
1901
1902 opp.common = dtp->common;
1903 opp.common.flags &= IOPARM_COMMON_MASK;
1904 dtp->u.p.current_unit = new_unit (&opp, dtp->u.p.current_unit, &u_flags);
1905 dtp->common.flags &= ~IOPARM_COMMON_MASK;
1906 dtp->common.flags |= (opp.common.flags & IOPARM_COMMON_MASK);
1907 if (dtp->u.p.current_unit == NULL)
1908 return;
1909 }
1910
1911 /* Check the action. */
1912
1913 if (read_flag && dtp->u.p.current_unit->flags.action == ACTION_WRITE)
1914 {
1915 generate_error (&dtp->common, LIBERROR_BAD_ACTION,
1916 "Cannot read from file opened for WRITE");
1917 return;
1918 }
1919
1920 if (!read_flag && dtp->u.p.current_unit->flags.action == ACTION_READ)
1921 {
1922 generate_error (&dtp->common, LIBERROR_BAD_ACTION,
1923 "Cannot write to file opened for READ");
1924 return;
1925 }
1926
1927 dtp->u.p.first_item = 1;
1928
1929 /* Check the format. */
1930
1931 if ((cf & IOPARM_DT_HAS_FORMAT) != 0)
1932 parse_format (dtp);
1933
1934 if (dtp->u.p.current_unit->flags.form == FORM_UNFORMATTED
1935 && (cf & (IOPARM_DT_HAS_FORMAT | IOPARM_DT_LIST_FORMAT))
1936 != 0)
1937 {
1938 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
1939 "Format present for UNFORMATTED data transfer");
1940 return;
1941 }
1942
1943 if ((cf & IOPARM_DT_HAS_NAMELIST_NAME) != 0 && dtp->u.p.ionml != NULL)
1944 {
1945 if ((cf & IOPARM_DT_HAS_FORMAT) != 0)
1946 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
1947 "A format cannot be specified with a namelist");
1948 }
1949 else if (dtp->u.p.current_unit->flags.form == FORM_FORMATTED &&
1950 !(cf & (IOPARM_DT_HAS_FORMAT | IOPARM_DT_LIST_FORMAT)))
1951 {
1952 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
1953 "Missing format for FORMATTED data transfer");
1954 }
1955
1956 if (is_internal_unit (dtp)
1957 && dtp->u.p.current_unit->flags.form == FORM_UNFORMATTED)
1958 {
1959 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
1960 "Internal file cannot be accessed by UNFORMATTED "
1961 "data transfer");
1962 return;
1963 }
1964
1965 /* Check the record number. */
1966
1967 if (dtp->u.p.current_unit->flags.access == ACCESS_DIRECT
1968 && (cf & IOPARM_DT_HAS_REC) == 0)
1969 {
1970 generate_error (&dtp->common, LIBERROR_MISSING_OPTION,
1971 "Direct access data transfer requires record number");
1972 return;
1973 }
1974
1975 if (dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL
1976 && (cf & IOPARM_DT_HAS_REC) != 0)
1977 {
1978 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
1979 "Record number not allowed for sequential access "
1980 "data transfer");
1981 return;
1982 }
1983
1984 /* Process the ADVANCE option. */
1985
1986 dtp->u.p.advance_status
1987 = !(cf & IOPARM_DT_HAS_ADVANCE) ? ADVANCE_UNSPECIFIED :
1988 find_option (&dtp->common, dtp->advance, dtp->advance_len, advance_opt,
1989 "Bad ADVANCE parameter in data transfer statement");
1990
1991 if (dtp->u.p.advance_status != ADVANCE_UNSPECIFIED)
1992 {
1993 if (dtp->u.p.current_unit->flags.access == ACCESS_DIRECT)
1994 {
1995 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
1996 "ADVANCE specification conflicts with sequential "
1997 "access");
1998 return;
1999 }
2000
2001 if (is_internal_unit (dtp))
2002 {
2003 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
2004 "ADVANCE specification conflicts with internal file");
2005 return;
2006 }
2007
2008 if ((cf & (IOPARM_DT_HAS_FORMAT | IOPARM_DT_LIST_FORMAT))
2009 != IOPARM_DT_HAS_FORMAT)
2010 {
2011 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
2012 "ADVANCE specification requires an explicit format");
2013 return;
2014 }
2015 }
2016
2017 if (read_flag)
2018 {
2019 dtp->u.p.current_unit->previous_nonadvancing_write = 0;
2020
2021 if ((cf & IOPARM_EOR) != 0 && dtp->u.p.advance_status != ADVANCE_NO)
2022 {
2023 generate_error (&dtp->common, LIBERROR_MISSING_OPTION,
2024 "EOR specification requires an ADVANCE specification "
2025 "of NO");
2026 return;
2027 }
2028
2029 if ((cf & IOPARM_DT_HAS_SIZE) != 0
2030 && dtp->u.p.advance_status != ADVANCE_NO)
2031 {
2032 generate_error (&dtp->common, LIBERROR_MISSING_OPTION,
2033 "SIZE specification requires an ADVANCE "
2034 "specification of NO");
2035 return;
2036 }
2037 }
2038 else
2039 { /* Write constraints. */
2040 if ((cf & IOPARM_END) != 0)
2041 {
2042 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
2043 "END specification cannot appear in a write "
2044 "statement");
2045 return;
2046 }
2047
2048 if ((cf & IOPARM_EOR) != 0)
2049 {
2050 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
2051 "EOR specification cannot appear in a write "
2052 "statement");
2053 return;
2054 }
2055
2056 if ((cf & IOPARM_DT_HAS_SIZE) != 0)
2057 {
2058 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
2059 "SIZE specification cannot appear in a write "
2060 "statement");
2061 return;
2062 }
2063 }
2064
2065 if (dtp->u.p.advance_status == ADVANCE_UNSPECIFIED)
2066 dtp->u.p.advance_status = ADVANCE_YES;
2067
2068 /* Check the decimal mode. */
2069 dtp->u.p.current_unit->decimal_status
2070 = !(cf & IOPARM_DT_HAS_DECIMAL) ? DECIMAL_UNSPECIFIED :
2071 find_option (&dtp->common, dtp->decimal, dtp->decimal_len,
2072 decimal_opt, "Bad DECIMAL parameter in data transfer "
2073 "statement");
2074
2075 if (dtp->u.p.current_unit->decimal_status == DECIMAL_UNSPECIFIED)
2076 dtp->u.p.current_unit->decimal_status = dtp->u.p.current_unit->flags.decimal;
2077
2078 /* Check the sign mode. */
2079 dtp->u.p.sign_status
2080 = !(cf & IOPARM_DT_HAS_SIGN) ? SIGN_UNSPECIFIED :
2081 find_option (&dtp->common, dtp->sign, dtp->sign_len, sign_opt,
2082 "Bad SIGN parameter in data transfer statement");
2083
2084 if (dtp->u.p.sign_status == SIGN_UNSPECIFIED)
2085 dtp->u.p.sign_status = dtp->u.p.current_unit->flags.sign;
2086
2087 /* Check the blank mode. */
2088 dtp->u.p.blank_status
2089 = !(cf & IOPARM_DT_HAS_BLANK) ? BLANK_UNSPECIFIED :
2090 find_option (&dtp->common, dtp->blank, dtp->blank_len,
2091 blank_opt,
2092 "Bad BLANK parameter in data transfer statement");
2093
2094 if (dtp->u.p.blank_status == BLANK_UNSPECIFIED)
2095 dtp->u.p.blank_status = dtp->u.p.current_unit->flags.blank;
2096
2097 /* Check the delim mode. */
2098 dtp->u.p.current_unit->delim_status
2099 = !(cf & IOPARM_DT_HAS_DELIM) ? DELIM_UNSPECIFIED :
2100 find_option (&dtp->common, dtp->delim, dtp->delim_len,
2101 delim_opt, "Bad DELIM parameter in data transfer statement");
2102
2103 if (dtp->u.p.current_unit->delim_status == DELIM_UNSPECIFIED)
2104 dtp->u.p.current_unit->delim_status = dtp->u.p.current_unit->flags.delim;
2105
2106 /* Check the pad mode. */
2107 dtp->u.p.current_unit->pad_status
2108 = !(cf & IOPARM_DT_HAS_PAD) ? PAD_UNSPECIFIED :
2109 find_option (&dtp->common, dtp->pad, dtp->pad_len, pad_opt,
2110 "Bad PAD parameter in data transfer statement");
2111
2112 if (dtp->u.p.current_unit->pad_status == PAD_UNSPECIFIED)
2113 dtp->u.p.current_unit->pad_status = dtp->u.p.current_unit->flags.pad;
2114
2115 /* Check the POS= specifier: that it is in range and that it is used with a
2116 unit that has been connected for STREAM access. F2003 9.5.1.10. */
2117
2118 if (((cf & IOPARM_DT_HAS_POS) != 0))
2119 {
2120 if (is_stream_io (dtp))
2121 {
2122
2123 if (dtp->pos <= 0)
2124 {
2125 generate_error (&dtp->common, LIBERROR_BAD_OPTION,
2126 "POS=specifier must be positive");
2127 return;
2128 }
2129
2130 if (dtp->pos >= dtp->u.p.current_unit->maxrec)
2131 {
2132 generate_error (&dtp->common, LIBERROR_BAD_OPTION,
2133 "POS=specifier too large");
2134 return;
2135 }
2136
2137 dtp->rec = dtp->pos;
2138
2139 if (dtp->u.p.mode == READING)
2140 {
2141 /* Required for compatibility between 4.3 and 4.4 runtime. Check
2142 to see if we might be reading what we wrote before */
2143 if (dtp->u.p.current_unit->mode == WRITING)
2144 {
2145 fbuf_flush (dtp->u.p.current_unit, 1);
2146 flush(dtp->u.p.current_unit->s);
2147 }
2148
2149 if (dtp->pos < file_length (dtp->u.p.current_unit->s))
2150 dtp->u.p.current_unit->endfile = NO_ENDFILE;
2151 }
2152
2153 if (dtp->pos != dtp->u.p.current_unit->strm_pos)
2154 {
2155 fbuf_flush (dtp->u.p.current_unit, 1);
2156 flush (dtp->u.p.current_unit->s);
2157 if (sseek (dtp->u.p.current_unit->s, dtp->pos - 1) == FAILURE)
2158 {
2159 generate_error (&dtp->common, LIBERROR_OS, NULL);
2160 return;
2161 }
2162 dtp->u.p.current_unit->strm_pos = dtp->pos;
2163 }
2164 }
2165 else
2166 {
2167 generate_error (&dtp->common, LIBERROR_BAD_OPTION,
2168 "POS=specifier not allowed, "
2169 "Try OPEN with ACCESS='stream'");
2170 return;
2171 }
2172 }
2173
2174 /* Sanity checks on the record number. */
2175 if ((cf & IOPARM_DT_HAS_REC) != 0)
2176 {
2177 if (dtp->rec <= 0)
2178 {
2179 generate_error (&dtp->common, LIBERROR_BAD_OPTION,
2180 "Record number must be positive");
2181 return;
2182 }
2183
2184 if (dtp->rec >= dtp->u.p.current_unit->maxrec)
2185 {
2186 generate_error (&dtp->common, LIBERROR_BAD_OPTION,
2187 "Record number too large");
2188 return;
2189 }
2190
2191 /* Check to see if we might be reading what we wrote before */
2192
2193 if (dtp->u.p.mode == READING
2194 && dtp->u.p.current_unit->mode == WRITING
2195 && !is_internal_unit (dtp))
2196 {
2197 fbuf_flush (dtp->u.p.current_unit, 1);
2198 flush(dtp->u.p.current_unit->s);
2199 }
2200
2201 /* Check whether the record exists to be read. Only
2202 a partial record needs to exist. */
2203
2204 if (dtp->u.p.mode == READING && (dtp->rec - 1)
2205 * dtp->u.p.current_unit->recl >= file_length (dtp->u.p.current_unit->s))
2206 {
2207 generate_error (&dtp->common, LIBERROR_BAD_OPTION,
2208 "Non-existing record number");
2209 return;
2210 }
2211
2212 /* Position the file. */
2213 if (sseek (dtp->u.p.current_unit->s, (gfc_offset) (dtp->rec - 1)
2214 * dtp->u.p.current_unit->recl) == FAILURE)
2215 {
2216 generate_error (&dtp->common, LIBERROR_OS, NULL);
2217 return;
2218 }
2219
2220 /* TODO: This is required to maintain compatibility between
2221 4.3 and 4.4 runtime. Remove when ABI changes from 4.3 */
2222
2223 if (is_stream_io (dtp))
2224 dtp->u.p.current_unit->strm_pos = dtp->rec;
2225
2226 /* TODO: Un-comment this code when ABI changes from 4.3.
2227 if (dtp->u.p.current_unit->flags.access == ACCESS_STREAM)
2228 {
2229 generate_error (&dtp->common, LIBERROR_OPTION_CONFLICT,
2230 "Record number not allowed for stream access "
2231 "data transfer");
2232 return;
2233 } */
2234
2235 }
2236
2237 /* Overwriting an existing sequential file ?
2238 it is always safe to truncate the file on the first write */
2239 if (dtp->u.p.mode == WRITING
2240 && dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL
2241 && dtp->u.p.current_unit->last_record == 0
2242 && !is_preconnected(dtp->u.p.current_unit->s))
2243 struncate(dtp->u.p.current_unit->s);
2244
2245 /* Bugware for badly written mixed C-Fortran I/O. */
2246 flush_if_preconnected(dtp->u.p.current_unit->s);
2247
2248 dtp->u.p.current_unit->mode = dtp->u.p.mode;
2249
2250 /* Set the maximum position reached from the previous I/O operation. This
2251 could be greater than zero from a previous non-advancing write. */
2252 dtp->u.p.max_pos = dtp->u.p.current_unit->saved_pos;
2253
2254 pre_position (dtp);
2255
2256
2257 /* Set up the subroutine that will handle the transfers. */
2258
2259 if (read_flag)
2260 {
2261 if (dtp->u.p.current_unit->flags.form == FORM_UNFORMATTED)
2262 dtp->u.p.transfer = unformatted_read;
2263 else
2264 {
2265 if ((cf & IOPARM_DT_LIST_FORMAT) != 0)
2266 dtp->u.p.transfer = list_formatted_read;
2267 else
2268 dtp->u.p.transfer = formatted_transfer;
2269 }
2270 }
2271 else
2272 {
2273 if (dtp->u.p.current_unit->flags.form == FORM_UNFORMATTED)
2274 dtp->u.p.transfer = unformatted_write;
2275 else
2276 {
2277 if ((cf & IOPARM_DT_LIST_FORMAT) != 0)
2278 dtp->u.p.transfer = list_formatted_write;
2279 else
2280 dtp->u.p.transfer = formatted_transfer;
2281 }
2282 }
2283
2284 /* Make sure that we don't do a read after a nonadvancing write. */
2285
2286 if (read_flag)
2287 {
2288 if (dtp->u.p.current_unit->read_bad && !is_stream_io (dtp))
2289 {
2290 generate_error (&dtp->common, LIBERROR_BAD_OPTION,
2291 "Cannot READ after a nonadvancing WRITE");
2292 return;
2293 }
2294 }
2295 else
2296 {
2297 if (dtp->u.p.advance_status == ADVANCE_YES && !dtp->u.p.seen_dollar)
2298 dtp->u.p.current_unit->read_bad = 1;
2299 }
2300
2301 /* Start the data transfer if we are doing a formatted transfer. */
2302 if (dtp->u.p.current_unit->flags.form == FORM_FORMATTED
2303 && ((cf & (IOPARM_DT_LIST_FORMAT | IOPARM_DT_HAS_NAMELIST_NAME)) == 0)
2304 && dtp->u.p.ionml == NULL)
2305 formatted_transfer (dtp, 0, NULL, 0, 0, 1);
2306 }
2307
2308 /* Initialize an array_loop_spec given the array descriptor. The function
2309 returns the index of the last element of the array, and also returns
2310 starting record, where the first I/O goes to (necessary in case of
2311 negative strides). */
2312
2313 gfc_offset
2314 init_loop_spec (gfc_array_char *desc, array_loop_spec *ls,
2315 gfc_offset *start_record)
2316 {
2317 int rank = GFC_DESCRIPTOR_RANK(desc);
2318 int i;
2319 gfc_offset index;
2320 int empty;
2321
2322 empty = 0;
2323 index = 1;
2324 *start_record = 0;
2325
2326 for (i=0; i<rank; i++)
2327 {
2328 ls[i].idx = desc->dim[i].lbound;
2329 ls[i].start = desc->dim[i].lbound;
2330 ls[i].end = desc->dim[i].ubound;
2331 ls[i].step = desc->dim[i].stride;
2332 empty = empty || (desc->dim[i].ubound < desc->dim[i].lbound);
2333
2334 if (desc->dim[i].stride > 0)
2335 {
2336 index += (desc->dim[i].ubound - desc->dim[i].lbound)
2337 * desc->dim[i].stride;
2338 }
2339 else
2340 {
2341 index -= (desc->dim[i].ubound - desc->dim[i].lbound)
2342 * desc->dim[i].stride;
2343 *start_record -= (desc->dim[i].ubound - desc->dim[i].lbound)
2344 * desc->dim[i].stride;
2345 }
2346 }
2347
2348 if (empty)
2349 return 0;
2350 else
2351 return index;
2352 }
2353
2354 /* Determine the index to the next record in an internal unit array by
2355 by incrementing through the array_loop_spec. */
2356
2357 gfc_offset
2358 next_array_record (st_parameter_dt *dtp, array_loop_spec *ls, int *finished)
2359 {
2360 int i, carry;
2361 gfc_offset index;
2362
2363 carry = 1;
2364 index = 0;
2365
2366 for (i = 0; i < dtp->u.p.current_unit->rank; i++)
2367 {
2368 if (carry)
2369 {
2370 ls[i].idx++;
2371 if (ls[i].idx > ls[i].end)
2372 {
2373 ls[i].idx = ls[i].start;
2374 carry = 1;
2375 }
2376 else
2377 carry = 0;
2378 }
2379 index = index + (ls[i].idx - ls[i].start) * ls[i].step;
2380 }
2381
2382 *finished = carry;
2383
2384 return index;
2385 }
2386
2387
2388
2389 /* Skip to the end of the current record, taking care of an optional
2390 record marker of size bytes. If the file is not seekable, we
2391 read chunks of size MAX_READ until we get to the right
2392 position. */
2393
2394 static void
2395 skip_record (st_parameter_dt *dtp, size_t bytes)
2396 {
2397 gfc_offset new;
2398 size_t rlength;
2399 static const size_t MAX_READ = 4096;
2400 char p[MAX_READ];
2401
2402 dtp->u.p.current_unit->bytes_left_subrecord += bytes;
2403 if (dtp->u.p.current_unit->bytes_left_subrecord == 0)
2404 return;
2405
2406 if (is_seekable (dtp->u.p.current_unit->s))
2407 {
2408 new = file_position (dtp->u.p.current_unit->s)
2409 + dtp->u.p.current_unit->bytes_left_subrecord;
2410
2411 /* Direct access files do not generate END conditions,
2412 only I/O errors. */
2413 if (sseek (dtp->u.p.current_unit->s, new) == FAILURE)
2414 generate_error (&dtp->common, LIBERROR_OS, NULL);
2415 }
2416 else
2417 { /* Seek by reading data. */
2418 while (dtp->u.p.current_unit->bytes_left_subrecord > 0)
2419 {
2420 rlength =
2421 (MAX_READ > (size_t) dtp->u.p.current_unit->bytes_left_subrecord) ?
2422 MAX_READ : (size_t) dtp->u.p.current_unit->bytes_left_subrecord;
2423
2424 if (sread (dtp->u.p.current_unit->s, p, &rlength) != 0)
2425 {
2426 generate_error (&dtp->common, LIBERROR_OS, NULL);
2427 return;
2428 }
2429
2430 dtp->u.p.current_unit->bytes_left_subrecord -= rlength;
2431 }
2432 }
2433
2434 }
2435
2436
2437 /* Advance to the next record reading unformatted files, taking
2438 care of subrecords. If complete_record is nonzero, we loop
2439 until all subrecords are cleared. */
2440
2441 static void
2442 next_record_r_unf (st_parameter_dt *dtp, int complete_record)
2443 {
2444 size_t bytes;
2445
2446 bytes = compile_options.record_marker == 0 ?
2447 sizeof (GFC_INTEGER_4) : compile_options.record_marker;
2448
2449 while(1)
2450 {
2451
2452 /* Skip over tail */
2453
2454 skip_record (dtp, bytes);
2455
2456 if ( ! (complete_record && dtp->u.p.current_unit->continued))
2457 return;
2458
2459 us_read (dtp, 1);
2460 }
2461 }
2462
2463
2464 static inline gfc_offset
2465 min_off (gfc_offset a, gfc_offset b)
2466 {
2467 return (a < b ? a : b);
2468 }
2469
2470
2471 /* Space to the next record for read mode. */
2472
2473 static void
2474 next_record_r (st_parameter_dt *dtp)
2475 {
2476 gfc_offset record;
2477 int bytes_left;
2478 size_t length;
2479 char p;
2480
2481 switch (current_mode (dtp))
2482 {
2483 /* No records in unformatted STREAM I/O. */
2484 case UNFORMATTED_STREAM:
2485 return;
2486
2487 case UNFORMATTED_SEQUENTIAL:
2488 next_record_r_unf (dtp, 1);
2489 dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
2490 break;
2491
2492 case FORMATTED_DIRECT:
2493 case UNFORMATTED_DIRECT:
2494 skip_record (dtp, 0);
2495 break;
2496
2497 case FORMATTED_STREAM:
2498 case FORMATTED_SEQUENTIAL:
2499 length = 1;
2500 /* sf_read has already terminated input because of an '\n' */
2501 if (dtp->u.p.sf_seen_eor)
2502 {
2503 dtp->u.p.sf_seen_eor = 0;
2504 break;
2505 }
2506
2507 if (is_internal_unit (dtp))
2508 {
2509 if (is_array_io (dtp))
2510 {
2511 int finished;
2512
2513 record = next_array_record (dtp, dtp->u.p.current_unit->ls,
2514 &finished);
2515
2516 /* Now seek to this record. */
2517 record = record * dtp->u.p.current_unit->recl;
2518 if (sseek (dtp->u.p.current_unit->s, record) == FAILURE)
2519 {
2520 generate_error (&dtp->common, LIBERROR_INTERNAL_UNIT, NULL);
2521 break;
2522 }
2523 dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
2524 }
2525 else
2526 {
2527 bytes_left = (int) dtp->u.p.current_unit->bytes_left;
2528 bytes_left = min_off (bytes_left,
2529 file_length (dtp->u.p.current_unit->s)
2530 - file_position (dtp->u.p.current_unit->s));
2531 if (sseek (dtp->u.p.current_unit->s,
2532 file_position (dtp->u.p.current_unit->s)
2533 + bytes_left) == FAILURE)
2534 {
2535 generate_error (&dtp->common, LIBERROR_INTERNAL_UNIT, NULL);
2536 break;
2537 }
2538 dtp->u.p.current_unit->bytes_left
2539 = dtp->u.p.current_unit->recl;
2540 }
2541 break;
2542 }
2543 else do
2544 {
2545 if (sread (dtp->u.p.current_unit->s, &p, &length) != 0)
2546 {
2547 generate_error (&dtp->common, LIBERROR_OS, NULL);
2548 break;
2549 }
2550
2551 if (length == 0)
2552 {
2553 dtp->u.p.current_unit->endfile = AT_ENDFILE;
2554 break;
2555 }
2556
2557 if (is_stream_io (dtp))
2558 dtp->u.p.current_unit->strm_pos++;
2559 }
2560 while (p != '\n');
2561
2562 break;
2563 }
2564
2565 if (dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL
2566 && !dtp->u.p.namelist_mode
2567 && dtp->u.p.current_unit->endfile == NO_ENDFILE
2568 && (file_length (dtp->u.p.current_unit->s) ==
2569 file_position (dtp->u.p.current_unit->s)))
2570 dtp->u.p.current_unit->endfile = AT_ENDFILE;
2571
2572 }
2573
2574
2575 /* Small utility function to write a record marker, taking care of
2576 byte swapping and of choosing the correct size. */
2577
2578 inline static int
2579 write_us_marker (st_parameter_dt *dtp, const gfc_offset buf)
2580 {
2581 size_t len;
2582 GFC_INTEGER_4 buf4;
2583 GFC_INTEGER_8 buf8;
2584 char p[sizeof (GFC_INTEGER_8)];
2585
2586 if (compile_options.record_marker == 0)
2587 len = sizeof (GFC_INTEGER_4);
2588 else
2589 len = compile_options.record_marker;
2590
2591 /* Only GFC_CONVERT_NATIVE and GFC_CONVERT_SWAP are valid here. */
2592 if (likely (dtp->u.p.current_unit->flags.convert == GFC_CONVERT_NATIVE))
2593 {
2594 switch (len)
2595 {
2596 case sizeof (GFC_INTEGER_4):
2597 buf4 = buf;
2598 return swrite (dtp->u.p.current_unit->s, &buf4, &len);
2599 break;
2600
2601 case sizeof (GFC_INTEGER_8):
2602 buf8 = buf;
2603 return swrite (dtp->u.p.current_unit->s, &buf8, &len);
2604 break;
2605
2606 default:
2607 runtime_error ("Illegal value for record marker");
2608 break;
2609 }
2610 }
2611 else
2612 {
2613 switch (len)
2614 {
2615 case sizeof (GFC_INTEGER_4):
2616 buf4 = buf;
2617 reverse_memcpy (p, &buf4, sizeof (GFC_INTEGER_4));
2618 return swrite (dtp->u.p.current_unit->s, p, &len);
2619 break;
2620
2621 case sizeof (GFC_INTEGER_8):
2622 buf8 = buf;
2623 reverse_memcpy (p, &buf8, sizeof (GFC_INTEGER_8));
2624 return swrite (dtp->u.p.current_unit->s, p, &len);
2625 break;
2626
2627 default:
2628 runtime_error ("Illegal value for record marker");
2629 break;
2630 }
2631 }
2632
2633 }
2634
2635 /* Position to the next (sub)record in write mode for
2636 unformatted sequential files. */
2637
2638 static void
2639 next_record_w_unf (st_parameter_dt *dtp, int next_subrecord)
2640 {
2641 gfc_offset c, m, m_write;
2642 size_t record_marker;
2643
2644 /* Bytes written. */
2645 m = dtp->u.p.current_unit->recl_subrecord
2646 - dtp->u.p.current_unit->bytes_left_subrecord;
2647 c = file_position (dtp->u.p.current_unit->s);
2648
2649 /* Write the length tail. If we finish a record containing
2650 subrecords, we write out the negative length. */
2651
2652 if (dtp->u.p.current_unit->continued)
2653 m_write = -m;
2654 else
2655 m_write = m;
2656
2657 if (unlikely (write_us_marker (dtp, m_write) != 0))
2658 goto io_error;
2659
2660 if (compile_options.record_marker == 0)
2661 record_marker = sizeof (GFC_INTEGER_4);
2662 else
2663 record_marker = compile_options.record_marker;
2664
2665 /* Seek to the head and overwrite the bogus length with the real
2666 length. */
2667
2668 if (unlikely (sseek (dtp->u.p.current_unit->s, c - m - record_marker)
2669 == FAILURE))
2670 goto io_error;
2671
2672 if (next_subrecord)
2673 m_write = -m;
2674 else
2675 m_write = m;
2676
2677 if (unlikely (write_us_marker (dtp, m_write) != 0))
2678 goto io_error;
2679
2680 /* Seek past the end of the current record. */
2681
2682 if (unlikely (sseek (dtp->u.p.current_unit->s, c + record_marker)
2683 == FAILURE))
2684 goto io_error;
2685
2686 return;
2687
2688 io_error:
2689 generate_error (&dtp->common, LIBERROR_OS, NULL);
2690 return;
2691
2692 }
2693
2694 /* Position to the next record in write mode. */
2695
2696 static void
2697 next_record_w (st_parameter_dt *dtp, int done)
2698 {
2699 gfc_offset m, record, max_pos;
2700 int length;
2701
2702 /* Flush and reset the format buffer. */
2703 fbuf_flush (dtp->u.p.current_unit, 1);
2704
2705 /* Zero counters for X- and T-editing. */
2706 max_pos = dtp->u.p.max_pos;
2707 dtp->u.p.max_pos = dtp->u.p.skips = dtp->u.p.pending_spaces = 0;
2708
2709 switch (current_mode (dtp))
2710 {
2711 /* No records in unformatted STREAM I/O. */
2712 case UNFORMATTED_STREAM:
2713 return;
2714
2715 case FORMATTED_DIRECT:
2716 if (dtp->u.p.current_unit->bytes_left == 0)
2717 break;
2718
2719 if (sset (dtp->u.p.current_unit->s, ' ',
2720 dtp->u.p.current_unit->bytes_left) == FAILURE)
2721 goto io_error;
2722
2723 break;
2724
2725 case UNFORMATTED_DIRECT:
2726 if (dtp->u.p.current_unit->bytes_left > 0)
2727 {
2728 length = (int) dtp->u.p.current_unit->bytes_left;
2729 if (sset (dtp->u.p.current_unit->s, 0, length) == FAILURE)
2730 goto io_error;
2731 }
2732 break;
2733
2734 case UNFORMATTED_SEQUENTIAL:
2735 next_record_w_unf (dtp, 0);
2736 dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
2737 break;
2738
2739 case FORMATTED_STREAM:
2740 case FORMATTED_SEQUENTIAL:
2741
2742 if (is_internal_unit (dtp))
2743 {
2744 if (is_array_io (dtp))
2745 {
2746 int finished;
2747
2748 length = (int) dtp->u.p.current_unit->bytes_left;
2749
2750 /* If the farthest position reached is greater than current
2751 position, adjust the position and set length to pad out
2752 whats left. Otherwise just pad whats left.
2753 (for character array unit) */
2754 m = dtp->u.p.current_unit->recl
2755 - dtp->u.p.current_unit->bytes_left;
2756 if (max_pos > m)
2757 {
2758 length = (int) (max_pos - m);
2759 if (sseek (dtp->u.p.current_unit->s,
2760 file_position (dtp->u.p.current_unit->s)
2761 + length) == FAILURE)
2762 {
2763 generate_error (&dtp->common, LIBERROR_INTERNAL_UNIT, NULL);
2764 return;
2765 }
2766 length = (int) (dtp->u.p.current_unit->recl - max_pos);
2767 }
2768
2769 if (sset (dtp->u.p.current_unit->s, ' ', length) == FAILURE)
2770 {
2771 generate_error (&dtp->common, LIBERROR_END, NULL);
2772 return;
2773 }
2774
2775 /* Now that the current record has been padded out,
2776 determine where the next record in the array is. */
2777 record = next_array_record (dtp, dtp->u.p.current_unit->ls,
2778 &finished);
2779 if (finished)
2780 dtp->u.p.current_unit->endfile = AT_ENDFILE;
2781
2782 /* Now seek to this record */
2783 record = record * dtp->u.p.current_unit->recl;
2784
2785 if (sseek (dtp->u.p.current_unit->s, record) == FAILURE)
2786 {
2787 generate_error (&dtp->common, LIBERROR_INTERNAL_UNIT, NULL);
2788 return;
2789 }
2790
2791 dtp->u.p.current_unit->bytes_left = dtp->u.p.current_unit->recl;
2792 }
2793 else
2794 {
2795 length = 1;
2796
2797 /* If this is the last call to next_record move to the farthest
2798 position reached and set length to pad out the remainder
2799 of the record. (for character scaler unit) */
2800 if (done)
2801 {
2802 m = dtp->u.p.current_unit->recl
2803 - dtp->u.p.current_unit->bytes_left;
2804 if (max_pos > m)
2805 {
2806 length = (int) (max_pos - m);
2807 if (sseek (dtp->u.p.current_unit->s,
2808 file_position (dtp->u.p.current_unit->s)
2809 + length) == FAILURE)
2810 {
2811 generate_error (&dtp->common, LIBERROR_INTERNAL_UNIT, NULL);
2812 return;
2813 }
2814 length = (int) (dtp->u.p.current_unit->recl - max_pos);
2815 }
2816 else
2817 length = (int) dtp->u.p.current_unit->bytes_left;
2818 }
2819
2820 if (sset (dtp->u.p.current_unit->s, ' ', length) == FAILURE)
2821 {
2822 generate_error (&dtp->common, LIBERROR_END, NULL);
2823 return;
2824 }
2825 }
2826 }
2827 else
2828 {
2829 size_t len;
2830 const char crlf[] = "\r\n";
2831
2832 #ifdef HAVE_CRLF
2833 len = 2;
2834 #else
2835 len = 1;
2836 #endif
2837 if (swrite (dtp->u.p.current_unit->s, &crlf[2-len], &len) != 0)
2838 goto io_error;
2839
2840 if (is_stream_io (dtp))
2841 {
2842 dtp->u.p.current_unit->strm_pos += len;
2843 if (dtp->u.p.current_unit->strm_pos
2844 < file_length (dtp->u.p.current_unit->s))
2845 struncate (dtp->u.p.current_unit->s);
2846 }
2847 }
2848
2849 break;
2850
2851 io_error:
2852 generate_error (&dtp->common, LIBERROR_OS, NULL);
2853 break;
2854 }
2855 }
2856
2857 /* Position to the next record, which means moving to the end of the
2858 current record. This can happen under several different
2859 conditions. If the done flag is not set, we get ready to process
2860 the next record. */
2861
2862 void
2863 next_record (st_parameter_dt *dtp, int done)
2864 {
2865 gfc_offset fp; /* File position. */
2866
2867 dtp->u.p.current_unit->read_bad = 0;
2868
2869 if (dtp->u.p.mode == READING)
2870 next_record_r (dtp);
2871 else
2872 next_record_w (dtp, done);
2873
2874 if (!is_stream_io (dtp))
2875 {
2876 /* Keep position up to date for INQUIRE */
2877 if (done)
2878 update_position (dtp->u.p.current_unit);
2879
2880 dtp->u.p.current_unit->current_record = 0;
2881 if (dtp->u.p.current_unit->flags.access == ACCESS_DIRECT)
2882 {
2883 fp = file_position (dtp->u.p.current_unit->s);
2884 /* Calculate next record, rounding up partial records. */
2885 dtp->u.p.current_unit->last_record =
2886 (fp + dtp->u.p.current_unit->recl - 1) /
2887 dtp->u.p.current_unit->recl;
2888 }
2889 else
2890 dtp->u.p.current_unit->last_record++;
2891 }
2892
2893 if (!done)
2894 pre_position (dtp);
2895 }
2896
2897
2898 /* Finalize the current data transfer. For a nonadvancing transfer,
2899 this means advancing to the next record. For internal units close the
2900 stream associated with the unit. */
2901
2902 static void
2903 finalize_transfer (st_parameter_dt *dtp)
2904 {
2905 jmp_buf eof_jump;
2906 GFC_INTEGER_4 cf = dtp->common.flags;
2907
2908 if ((dtp->common.flags & IOPARM_DT_HAS_SIZE) != 0)
2909 *dtp->size = dtp->u.p.size_used;
2910
2911 if (dtp->u.p.eor_condition)
2912 {
2913 generate_error (&dtp->common, LIBERROR_EOR, NULL);
2914 return;
2915 }
2916
2917 if ((dtp->common.flags & IOPARM_LIBRETURN_MASK) != IOPARM_LIBRETURN_OK)
2918 return;
2919
2920 if ((dtp->u.p.ionml != NULL)
2921 && (cf & IOPARM_DT_HAS_NAMELIST_NAME) != 0)
2922 {
2923 if ((cf & IOPARM_DT_NAMELIST_READ_MODE) != 0)
2924 namelist_read (dtp);
2925 else
2926 namelist_write (dtp);
2927 }
2928
2929 dtp->u.p.transfer = NULL;
2930 if (dtp->u.p.current_unit == NULL)
2931 return;
2932
2933 dtp->u.p.eof_jump = &eof_jump;
2934 if (setjmp (eof_jump))
2935 {
2936 generate_error (&dtp->common, LIBERROR_END, NULL);
2937 return;
2938 }
2939
2940 if ((cf & IOPARM_DT_LIST_FORMAT) != 0 && dtp->u.p.mode == READING)
2941 {
2942 finish_list_read (dtp);
2943 sfree (dtp->u.p.current_unit->s);
2944 return;
2945 }
2946
2947 if (dtp->u.p.mode == WRITING)
2948 dtp->u.p.current_unit->previous_nonadvancing_write
2949 = dtp->u.p.advance_status == ADVANCE_NO;
2950
2951 if (is_stream_io (dtp))
2952 {
2953 if (dtp->u.p.current_unit->flags.form == FORM_FORMATTED
2954 && dtp->u.p.advance_status != ADVANCE_NO)
2955 next_record (dtp, 1);
2956
2957 if (dtp->u.p.current_unit->flags.form == FORM_UNFORMATTED
2958 && file_position (dtp->u.p.current_unit->s) >= dtp->rec)
2959 {
2960 flush (dtp->u.p.current_unit->s);
2961 sfree (dtp->u.p.current_unit->s);
2962 }
2963 return;
2964 }
2965
2966 dtp->u.p.current_unit->current_record = 0;
2967
2968 if (!is_internal_unit (dtp) && dtp->u.p.seen_dollar)
2969 {
2970 dtp->u.p.seen_dollar = 0;
2971 fbuf_flush (dtp->u.p.current_unit, 1);
2972 sfree (dtp->u.p.current_unit->s);
2973 return;
2974 }
2975
2976 /* For non-advancing I/O, save the current maximum position for use in the
2977 next I/O operation if needed. */
2978 if (dtp->u.p.advance_status == ADVANCE_NO)
2979 {
2980 int bytes_written = (int) (dtp->u.p.current_unit->recl
2981 - dtp->u.p.current_unit->bytes_left);
2982 dtp->u.p.current_unit->saved_pos =
2983 dtp->u.p.max_pos > 0 ? dtp->u.p.max_pos - bytes_written : 0;
2984 fbuf_flush (dtp->u.p.current_unit, 0);
2985 flush (dtp->u.p.current_unit->s);
2986 return;
2987 }
2988
2989 dtp->u.p.current_unit->saved_pos = 0;
2990
2991 next_record (dtp, 1);
2992 sfree (dtp->u.p.current_unit->s);
2993 }
2994
2995 /* Transfer function for IOLENGTH. It doesn't actually do any
2996 data transfer, it just updates the length counter. */
2997
2998 static void
2999 iolength_transfer (st_parameter_dt *dtp, bt type __attribute__((unused)),
3000 void *dest __attribute__ ((unused)),
3001 int kind __attribute__((unused)),
3002 size_t size, size_t nelems)
3003 {
3004 if ((dtp->common.flags & IOPARM_DT_HAS_IOLENGTH) != 0)
3005 *dtp->iolength += (GFC_IO_INT) size * nelems;
3006 }
3007
3008
3009 /* Initialize the IOLENGTH data transfer. This function is in essence
3010 a very much simplified version of data_transfer_init(), because it
3011 doesn't have to deal with units at all. */
3012
3013 static void
3014 iolength_transfer_init (st_parameter_dt *dtp)
3015 {
3016 if ((dtp->common.flags & IOPARM_DT_HAS_IOLENGTH) != 0)
3017 *dtp->iolength = 0;
3018
3019 memset (&dtp->u.p, 0, sizeof (dtp->u.p));
3020
3021 /* Set up the subroutine that will handle the transfers. */
3022
3023 dtp->u.p.transfer = iolength_transfer;
3024 }
3025
3026
3027 /* Library entry point for the IOLENGTH form of the INQUIRE
3028 statement. The IOLENGTH form requires no I/O to be performed, but
3029 it must still be a runtime library call so that we can determine
3030 the iolength for dynamic arrays and such. */
3031
3032 extern void st_iolength (st_parameter_dt *);
3033 export_proto(st_iolength);
3034
3035 void
3036 st_iolength (st_parameter_dt *dtp)
3037 {
3038 library_start (&dtp->common);
3039 iolength_transfer_init (dtp);
3040 }
3041
3042 extern void st_iolength_done (st_parameter_dt *);
3043 export_proto(st_iolength_done);
3044
3045 void
3046 st_iolength_done (st_parameter_dt *dtp __attribute__((unused)))
3047 {
3048 free_ionml (dtp);
3049 if (dtp->u.p.scratch != NULL)
3050 free_mem (dtp->u.p.scratch);
3051 library_end ();
3052 }
3053
3054
3055 /* The READ statement. */
3056
3057 extern void st_read (st_parameter_dt *);
3058 export_proto(st_read);
3059
3060 void
3061 st_read (st_parameter_dt *dtp)
3062 {
3063 library_start (&dtp->common);
3064
3065 data_transfer_init (dtp, 1);
3066
3067 /* Handle complications dealing with the endfile record. */
3068
3069 if (dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL)
3070 switch (dtp->u.p.current_unit->endfile)
3071 {
3072 case NO_ENDFILE:
3073 break;
3074
3075 case AT_ENDFILE:
3076 if (!is_internal_unit (dtp))
3077 {
3078 generate_error (&dtp->common, LIBERROR_END, NULL);
3079 dtp->u.p.current_unit->endfile = AFTER_ENDFILE;
3080 dtp->u.p.current_unit->current_record = 0;
3081 }
3082 break;
3083
3084 case AFTER_ENDFILE:
3085 generate_error (&dtp->common, LIBERROR_ENDFILE, NULL);
3086 dtp->u.p.current_unit->current_record = 0;
3087 break;
3088 }
3089 }
3090
3091 extern void st_read_done (st_parameter_dt *);
3092 export_proto(st_read_done);
3093
3094 void
3095 st_read_done (st_parameter_dt *dtp)
3096 {
3097 finalize_transfer (dtp);
3098 free_format_data (dtp);
3099 free_ionml (dtp);
3100 if (dtp->u.p.scratch != NULL)
3101 free_mem (dtp->u.p.scratch);
3102 if (dtp->u.p.current_unit != NULL)
3103 unlock_unit (dtp->u.p.current_unit);
3104
3105 free_internal_unit (dtp);
3106
3107 library_end ();
3108 }
3109
3110 extern void st_write (st_parameter_dt *);
3111 export_proto(st_write);
3112
3113 void
3114 st_write (st_parameter_dt *dtp)
3115 {
3116 library_start (&dtp->common);
3117 data_transfer_init (dtp, 0);
3118 }
3119
3120 extern void st_write_done (st_parameter_dt *);
3121 export_proto(st_write_done);
3122
3123 void
3124 st_write_done (st_parameter_dt *dtp)
3125 {
3126 finalize_transfer (dtp);
3127
3128 /* Deal with endfile conditions associated with sequential files. */
3129
3130 if (dtp->u.p.current_unit != NULL
3131 && dtp->u.p.current_unit->flags.access == ACCESS_SEQUENTIAL)
3132 switch (dtp->u.p.current_unit->endfile)
3133 {
3134 case AT_ENDFILE: /* Remain at the endfile record. */
3135 break;
3136
3137 case AFTER_ENDFILE:
3138 dtp->u.p.current_unit->endfile = AT_ENDFILE; /* Just at it now. */
3139 break;
3140
3141 case NO_ENDFILE:
3142 /* Get rid of whatever is after this record. */
3143 if (!is_internal_unit (dtp))
3144 {
3145 flush (dtp->u.p.current_unit->s);
3146 if (struncate (dtp->u.p.current_unit->s) == FAILURE)
3147 generate_error (&dtp->common, LIBERROR_OS, NULL);
3148 }
3149 dtp->u.p.current_unit->endfile = AT_ENDFILE;
3150 break;
3151 }
3152
3153 free_format_data (dtp);
3154 free_ionml (dtp);
3155 if (dtp->u.p.scratch != NULL)
3156 free_mem (dtp->u.p.scratch);
3157 if (dtp->u.p.current_unit != NULL)
3158 unlock_unit (dtp->u.p.current_unit);
3159
3160 free_internal_unit (dtp);
3161
3162 library_end ();
3163 }
3164
3165
3166 /* F2003: This is a stub for the runtime portion of the WAIT statement. */
3167 void
3168 st_wait (st_parameter_wait *wtp __attribute__((unused)))
3169 {
3170 }
3171
3172
3173 /* Receives the scalar information for namelist objects and stores it
3174 in a linked list of namelist_info types. */
3175
3176 extern void st_set_nml_var (st_parameter_dt *dtp, void *, char *,
3177 GFC_INTEGER_4, gfc_charlen_type, GFC_INTEGER_4);
3178 export_proto(st_set_nml_var);
3179
3180
3181 void
3182 st_set_nml_var (st_parameter_dt *dtp, void * var_addr, char * var_name,
3183 GFC_INTEGER_4 len, gfc_charlen_type string_length,
3184 GFC_INTEGER_4 dtype)
3185 {
3186 namelist_info *t1 = NULL;
3187 namelist_info *nml;
3188 size_t var_name_len = strlen (var_name);
3189
3190 nml = (namelist_info*) get_mem (sizeof (namelist_info));
3191
3192 nml->mem_pos = var_addr;
3193
3194 nml->var_name = (char*) get_mem (var_name_len + 1);
3195 memcpy (nml->var_name, var_name, var_name_len);
3196 nml->var_name[var_name_len] = '\0';
3197
3198 nml->len = (int) len;
3199 nml->string_length = (index_type) string_length;
3200
3201 nml->var_rank = (int) (dtype & GFC_DTYPE_RANK_MASK);
3202 nml->size = (index_type) (dtype >> GFC_DTYPE_SIZE_SHIFT);
3203 nml->type = (bt) ((dtype & GFC_DTYPE_TYPE_MASK) >> GFC_DTYPE_TYPE_SHIFT);
3204
3205 if (nml->var_rank > 0)
3206 {
3207 nml->dim = (descriptor_dimension*)
3208 get_mem (nml->var_rank * sizeof (descriptor_dimension));
3209 nml->ls = (array_loop_spec*)
3210 get_mem (nml->var_rank * sizeof (array_loop_spec));
3211 }
3212 else
3213 {
3214 nml->dim = NULL;
3215 nml->ls = NULL;
3216 }
3217
3218 nml->next = NULL;
3219
3220 if ((dtp->common.flags & IOPARM_DT_IONML_SET) == 0)
3221 {
3222 dtp->common.flags |= IOPARM_DT_IONML_SET;
3223 dtp->u.p.ionml = nml;
3224 }
3225 else
3226 {
3227 for (t1 = dtp->u.p.ionml; t1->next; t1 = t1->next);
3228 t1->next = nml;
3229 }
3230 }
3231
3232 /* Store the dimensional information for the namelist object. */
3233 extern void st_set_nml_var_dim (st_parameter_dt *, GFC_INTEGER_4,
3234 index_type, index_type,
3235 index_type);
3236 export_proto(st_set_nml_var_dim);
3237
3238 void
3239 st_set_nml_var_dim (st_parameter_dt *dtp, GFC_INTEGER_4 n_dim,
3240 index_type stride, index_type lbound,
3241 index_type ubound)
3242 {
3243 namelist_info * nml;
3244 int n;
3245
3246 n = (int)n_dim;
3247
3248 for (nml = dtp->u.p.ionml; nml->next; nml = nml->next);
3249
3250 nml->dim[n].stride = stride;
3251 nml->dim[n].lbound = lbound;
3252 nml->dim[n].ubound = ubound;
3253 }
3254
3255 /* Reverse memcpy - used for byte swapping. */
3256
3257 void reverse_memcpy (void *dest, const void *src, size_t n)
3258 {
3259 char *d, *s;
3260 size_t i;
3261
3262 d = (char *) dest;
3263 s = (char *) src + n - 1;
3264
3265 /* Write with ascending order - this is likely faster
3266 on modern architectures because of write combining. */
3267 for (i=0; i<n; i++)
3268 *(d++) = *(s--);
3269 }