]> git.ipfire.org Git - thirdparty/gcc.git/blob - libgfortran/io/unix.c
re PR libfortran/39664 (Revision 145571 breaks stdio)
[thirdparty/gcc.git] / libgfortran / io / unix.c
1 /* Copyright (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008
2 Free Software Foundation, Inc.
3 Contributed by Andy Vaught
4 F2003 I/O support contributed by Jerry DeLisle
5
6 This file is part of the GNU Fortran 95 runtime library (libgfortran).
7
8 Libgfortran is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2, or (at your option)
11 any later version.
12
13 In addition to the permissions in the GNU General Public License, the
14 Free Software Foundation gives you unlimited permission to link the
15 compiled version of this file into combinations with other programs,
16 and to distribute those combinations without any restriction coming
17 from the use of this file. (The General Public License restrictions
18 do apply in other respects; for example, they cover modification of
19 the file, and distribution when not linked into a combine
20 executable.)
21
22 Libgfortran is distributed in the hope that it will be useful,
23 but WITHOUT ANY WARRANTY; without even the implied warranty of
24 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
25 GNU General Public License for more details.
26
27 You should have received a copy of the GNU General Public License
28 along with Libgfortran; see the file COPYING. If not, write to
29 the Free Software Foundation, 51 Franklin Street, Fifth Floor,
30 Boston, MA 02110-1301, USA. */
31
32 /* Unix stream I/O module */
33
34 #include "io.h"
35 #include <stdlib.h>
36 #include <limits.h>
37
38 #include <unistd.h>
39 #include <sys/stat.h>
40 #include <fcntl.h>
41 #include <assert.h>
42
43 #include <string.h>
44 #include <errno.h>
45
46
47 /* For mingw, we don't identify files by their inode number, but by a
48 64-bit identifier created from a BY_HANDLE_FILE_INFORMATION. */
49 #if defined(__MINGW32__) && !HAVE_WORKING_STAT
50
51 #define WIN32_LEAN_AND_MEAN
52 #include <windows.h>
53
54 static uint64_t
55 id_from_handle (HANDLE hFile)
56 {
57 BY_HANDLE_FILE_INFORMATION FileInformation;
58
59 if (hFile == INVALID_HANDLE_VALUE)
60 return 0;
61
62 memset (&FileInformation, 0, sizeof(FileInformation));
63 if (!GetFileInformationByHandle (hFile, &FileInformation))
64 return 0;
65
66 return ((uint64_t) FileInformation.nFileIndexLow)
67 | (((uint64_t) FileInformation.nFileIndexHigh) << 32);
68 }
69
70
71 static uint64_t
72 id_from_path (const char *path)
73 {
74 HANDLE hFile;
75 uint64_t res;
76
77 if (!path || !*path || access (path, F_OK))
78 return (uint64_t) -1;
79
80 hFile = CreateFile (path, 0, 0, NULL, OPEN_EXISTING,
81 FILE_FLAG_BACKUP_SEMANTICS | FILE_ATTRIBUTE_READONLY,
82 NULL);
83 res = id_from_handle (hFile);
84 CloseHandle (hFile);
85 return res;
86 }
87
88
89 static uint64_t
90 id_from_fd (const int fd)
91 {
92 return id_from_handle ((HANDLE) _get_osfhandle (fd));
93 }
94
95 #endif
96
97 #ifndef PATH_MAX
98 #define PATH_MAX 1024
99 #endif
100
101 #ifndef PROT_READ
102 #define PROT_READ 1
103 #endif
104
105 #ifndef PROT_WRITE
106 #define PROT_WRITE 2
107 #endif
108
109 /* These flags aren't defined on all targets (mingw32), so provide them
110 here. */
111 #ifndef S_IRGRP
112 #define S_IRGRP 0
113 #endif
114
115 #ifndef S_IWGRP
116 #define S_IWGRP 0
117 #endif
118
119 #ifndef S_IROTH
120 #define S_IROTH 0
121 #endif
122
123 #ifndef S_IWOTH
124 #define S_IWOTH 0
125 #endif
126
127
128 /* Unix and internal stream I/O module */
129
130 static const int BUFFER_SIZE = 8192;
131
132 typedef struct
133 {
134 stream st;
135
136 gfc_offset buffer_offset; /* File offset of the start of the buffer */
137 gfc_offset physical_offset; /* Current physical file offset */
138 gfc_offset logical_offset; /* Current logical file offset */
139 gfc_offset file_length; /* Length of the file, -1 if not seekable. */
140
141 char *buffer; /* Pointer to the buffer. */
142 int fd; /* The POSIX file descriptor. */
143
144 int active; /* Length of valid bytes in the buffer */
145
146 int prot;
147 int ndirty; /* Dirty bytes starting at buffer_offset */
148
149 int special_file; /* =1 if the fd refers to a special file */
150 }
151 unix_stream;
152
153
154 /*move_pos_offset()-- Move the record pointer right or left
155 *relative to current position */
156
157 int
158 move_pos_offset (stream* st, int pos_off)
159 {
160 unix_stream * str = (unix_stream*)st;
161 if (pos_off < 0)
162 {
163 str->logical_offset += pos_off;
164
165 if (str->ndirty > str->logical_offset)
166 {
167 if (str->ndirty + pos_off > 0)
168 str->ndirty += pos_off;
169 else
170 str->ndirty = 0;
171 }
172
173 return pos_off;
174 }
175 return 0;
176 }
177
178
179 /* fix_fd()-- Given a file descriptor, make sure it is not one of the
180 * standard descriptors, returning a non-standard descriptor. If the
181 * user specifies that system errors should go to standard output,
182 * then closes standard output, we don't want the system errors to a
183 * file that has been given file descriptor 1 or 0. We want to send
184 * the error to the invalid descriptor. */
185
186 static int
187 fix_fd (int fd)
188 {
189 #ifdef HAVE_DUP
190 int input, output, error;
191
192 input = output = error = 0;
193
194 /* Unix allocates the lowest descriptors first, so a loop is not
195 required, but this order is. */
196 if (fd == STDIN_FILENO)
197 {
198 fd = dup (fd);
199 input = 1;
200 }
201 if (fd == STDOUT_FILENO)
202 {
203 fd = dup (fd);
204 output = 1;
205 }
206 if (fd == STDERR_FILENO)
207 {
208 fd = dup (fd);
209 error = 1;
210 }
211
212 if (input)
213 close (STDIN_FILENO);
214 if (output)
215 close (STDOUT_FILENO);
216 if (error)
217 close (STDERR_FILENO);
218 #endif
219
220 return fd;
221 }
222
223 int
224 is_preconnected (stream * s)
225 {
226 int fd;
227
228 fd = ((unix_stream *) s)->fd;
229 if (fd == STDIN_FILENO || fd == STDOUT_FILENO || fd == STDERR_FILENO)
230 return 1;
231 else
232 return 0;
233 }
234
235 /* If the stream corresponds to a preconnected unit, we flush the
236 corresponding C stream. This is bugware for mixed C-Fortran codes
237 where the C code doesn't flush I/O before returning. */
238 void
239 flush_if_preconnected (stream * s)
240 {
241 int fd;
242
243 fd = ((unix_stream *) s)->fd;
244 if (fd == STDIN_FILENO)
245 fflush (stdin);
246 else if (fd == STDOUT_FILENO)
247 fflush (stdout);
248 else if (fd == STDERR_FILENO)
249 fflush (stderr);
250 }
251
252
253 /* get_oserror()-- Get the most recent operating system error. For
254 * unix, this is errno. */
255
256 const char *
257 get_oserror (void)
258 {
259 return strerror (errno);
260 }
261
262
263 /********************************************************************
264 Raw I/O functions (read, write, seek, tell, truncate, close).
265
266 These functions wrap the basic POSIX I/O syscalls. Any deviation in
267 semantics is a bug, except the following: write restarts in case
268 of being interrupted by a signal, and as the first argument the
269 functions take the unix_stream struct rather than an integer file
270 descriptor. Also, for POSIX read() and write() a nbyte argument larger
271 than SSIZE_MAX is undefined; here the type of nbyte is ssize_t rather
272 than size_t as for POSIX read/write.
273 *********************************************************************/
274
275 static int
276 raw_flush (unix_stream * s __attribute__ ((unused)))
277 {
278 return 0;
279 }
280
281 static ssize_t
282 raw_read (unix_stream * s, void * buf, ssize_t nbyte)
283 {
284 /* For read we can't do I/O in a loop like raw_write does, because
285 that will break applications that wait for interactive I/O. */
286 return read (s->fd, buf, nbyte);
287 }
288
289 static ssize_t
290 raw_write (unix_stream * s, const void * buf, ssize_t nbyte)
291 {
292 ssize_t trans, bytes_left;
293 char *buf_st;
294
295 bytes_left = nbyte;
296 buf_st = (char *) buf;
297
298 /* We must write in a loop since some systems don't restart system
299 calls in case of a signal. */
300 while (bytes_left > 0)
301 {
302 trans = write (s->fd, buf_st, bytes_left);
303 if (trans < 0)
304 {
305 if (errno == EINTR)
306 continue;
307 else
308 return trans;
309 }
310 buf_st += trans;
311 bytes_left -= trans;
312 }
313
314 return nbyte - bytes_left;
315 }
316
317 static off_t
318 raw_seek (unix_stream * s, off_t offset, int whence)
319 {
320 return lseek (s->fd, offset, whence);
321 }
322
323 static off_t
324 raw_tell (unix_stream * s)
325 {
326 return lseek (s->fd, 0, SEEK_CUR);
327 }
328
329 static int
330 raw_truncate (unix_stream * s, off_t length)
331 {
332 #ifdef HAVE_FTRUNCATE
333 return ftruncate (s->fd, length);
334 #elif defined HAVE_CHSIZE
335 return chsize (s->fd, length);
336 #else
337 runtime_error ("required ftruncate or chsize support not present");
338 return -1;
339 #endif
340 }
341
342 static int
343 raw_close (unix_stream * s)
344 {
345 int retval;
346
347 if (s->fd != STDOUT_FILENO
348 && s->fd != STDERR_FILENO
349 && s->fd != STDIN_FILENO)
350 retval = close (s->fd);
351 else
352 retval = SUCCESS;
353 free_mem (s);
354 return retval;
355 }
356
357 static int
358 raw_init (unix_stream * s)
359 {
360 s->st.read = (void *) raw_read;
361 s->st.write = (void *) raw_write;
362 s->st.seek = (void *) raw_seek;
363 s->st.tell = (void *) raw_tell;
364 s->st.trunc = (void *) raw_truncate;
365 s->st.close = (void *) raw_close;
366 s->st.flush = (void *) raw_flush;
367
368 s->buffer = NULL;
369 return 0;
370 }
371
372
373 /*********************************************************************
374 Buffered I/O functions. These functions have the same semantics as the
375 raw I/O functions above, except that they are buffered in order to
376 improve performance. The buffer must be flushed when switching from
377 reading to writing and vice versa.
378 *********************************************************************/
379
380 static int
381 buf_flush (unix_stream * s)
382 {
383 int writelen;
384
385 /* Flushing in read mode means discarding read bytes. */
386 s->active = 0;
387
388 if (s->ndirty == 0)
389 return 0;
390
391 if (s->file_length != -1 && s->physical_offset != s->buffer_offset
392 && lseek (s->fd, s->buffer_offset, SEEK_SET) < 0)
393 return -1;
394
395 writelen = raw_write (s, s->buffer, s->ndirty);
396
397 s->physical_offset = s->buffer_offset + writelen;
398
399 /* Don't increment file_length if the file is non-seekable. */
400 if (s->file_length != -1 && s->physical_offset > s->file_length)
401 s->file_length = s->physical_offset;
402
403 s->ndirty -= writelen;
404 if (s->ndirty != 0)
405 return -1;
406
407 return 0;
408 }
409
410 static ssize_t
411 buf_read (unix_stream * s, void * buf, ssize_t nbyte)
412 {
413 if (s->active == 0)
414 s->buffer_offset = s->logical_offset;
415
416 /* Is the data we want in the buffer? */
417 if (s->logical_offset + nbyte <= s->buffer_offset + s->active
418 && s->buffer_offset <= s->logical_offset)
419 memcpy (buf, s->buffer + (s->logical_offset - s->buffer_offset), nbyte);
420 else
421 {
422 /* First copy the active bytes if applicable, then read the rest
423 either directly or filling the buffer. */
424 char *p;
425 int nread = 0;
426 ssize_t to_read, did_read;
427 gfc_offset new_logical;
428
429 p = (char *) buf;
430 if (s->logical_offset >= s->buffer_offset
431 && s->buffer_offset + s->active >= s->logical_offset)
432 {
433 nread = s->active - (s->logical_offset - s->buffer_offset);
434 memcpy (buf, s->buffer + (s->logical_offset - s->buffer_offset),
435 nread);
436 p += nread;
437 }
438 /* At this point we consider all bytes in the buffer discarded. */
439 to_read = nbyte - nread;
440 new_logical = s->logical_offset + nread;
441 if (s->file_length != -1 && s->physical_offset != new_logical
442 && lseek (s->fd, new_logical, SEEK_SET) < 0)
443 return -1;
444 s->buffer_offset = s->physical_offset = new_logical;
445 if (to_read <= BUFFER_SIZE/2)
446 {
447 did_read = raw_read (s, s->buffer, BUFFER_SIZE);
448 s->physical_offset += did_read;
449 s->active = did_read;
450 did_read = (did_read > to_read) ? to_read : did_read;
451 memcpy (p, s->buffer, did_read);
452 }
453 else
454 {
455 did_read = raw_read (s, p, to_read);
456 s->physical_offset += did_read;
457 s->active = 0;
458 }
459 nbyte = did_read + nread;
460 }
461 s->logical_offset += nbyte;
462 return nbyte;
463 }
464
465 static ssize_t
466 buf_write (unix_stream * s, const void * buf, ssize_t nbyte)
467 {
468 if (s->ndirty == 0)
469 s->buffer_offset = s->logical_offset;
470
471 /* Does the data fit into the buffer? As a special case, if the
472 buffer is empty and the request is bigger than BUFFER_SIZE/2,
473 write directly. This avoids the case where the buffer would have
474 to be flushed at every write. */
475 if (!(s->ndirty == 0 && nbyte > BUFFER_SIZE/2)
476 && s->logical_offset + nbyte <= s->buffer_offset + BUFFER_SIZE
477 && s->buffer_offset <= s->logical_offset
478 && s->buffer_offset + s->ndirty >= s->logical_offset)
479 {
480 memcpy (s->buffer + (s->logical_offset - s->buffer_offset), buf, nbyte);
481 int nd = (s->logical_offset - s->buffer_offset) + nbyte;
482 if (nd > s->ndirty)
483 s->ndirty = nd;
484 }
485 else
486 {
487 /* Flush, and either fill the buffer with the new data, or if
488 the request is bigger than the buffer size, write directly
489 bypassing the buffer. */
490 buf_flush (s);
491 if (nbyte <= BUFFER_SIZE/2)
492 {
493 memcpy (s->buffer, buf, nbyte);
494 s->buffer_offset = s->logical_offset;
495 s->ndirty += nbyte;
496 }
497 else
498 {
499 if (s->file_length != -1 && s->physical_offset != s->logical_offset
500 && lseek (s->fd, s->logical_offset, SEEK_SET) < 0)
501 return -1;
502 nbyte = raw_write (s, buf, nbyte);
503 s->physical_offset += nbyte;
504 }
505 }
506 s->logical_offset += nbyte;
507 /* Don't increment file_length if the file is non-seekable. */
508 if (s->file_length != -1 && s->logical_offset > s->file_length)
509 s->file_length = s->logical_offset;
510 return nbyte;
511 }
512
513 static off_t
514 buf_seek (unix_stream * s, off_t offset, int whence)
515 {
516 switch (whence)
517 {
518 case SEEK_SET:
519 break;
520 case SEEK_CUR:
521 offset += s->logical_offset;
522 break;
523 case SEEK_END:
524 offset += s->file_length;
525 break;
526 default:
527 return -1;
528 }
529 if (offset < 0)
530 {
531 errno = EINVAL;
532 return -1;
533 }
534 s->logical_offset = offset;
535 return offset;
536 }
537
538 static off_t
539 buf_tell (unix_stream * s)
540 {
541 return s->logical_offset;
542 }
543
544 static int
545 buf_truncate (unix_stream * s, off_t length)
546 {
547 int r;
548
549 if (buf_flush (s) != 0)
550 return -1;
551 r = raw_truncate (s, length);
552 if (r == 0)
553 s->file_length = length;
554 return r;
555 }
556
557 static int
558 buf_close (unix_stream * s)
559 {
560 if (buf_flush (s) != 0)
561 return -1;
562 free_mem (s->buffer);
563 return raw_close (s);
564 }
565
566 static int
567 buf_init (unix_stream * s)
568 {
569 s->st.read = (void *) buf_read;
570 s->st.write = (void *) buf_write;
571 s->st.seek = (void *) buf_seek;
572 s->st.tell = (void *) buf_tell;
573 s->st.trunc = (void *) buf_truncate;
574 s->st.close = (void *) buf_close;
575 s->st.flush = (void *) buf_flush;
576
577 s->buffer = get_mem (BUFFER_SIZE);
578 return 0;
579 }
580
581
582 /*********************************************************************
583 memory stream functions - These are used for internal files
584
585 The idea here is that a single stream structure is created and all
586 requests must be satisfied from it. The location and size of the
587 buffer is the character variable supplied to the READ or WRITE
588 statement.
589
590 *********************************************************************/
591
592
593 char *
594 mem_alloc_r (stream * strm, int * len)
595 {
596 unix_stream * s = (unix_stream *) strm;
597 gfc_offset n;
598 gfc_offset where = s->logical_offset;
599
600 if (where < s->buffer_offset || where > s->buffer_offset + s->active)
601 return NULL;
602
603 n = s->buffer_offset + s->active - where;
604 if (*len > n)
605 *len = n;
606
607 s->logical_offset = where + *len;
608
609 return s->buffer + (where - s->buffer_offset);
610 }
611
612
613 char *
614 mem_alloc_w (stream * strm, int * len)
615 {
616 unix_stream * s = (unix_stream *) strm;
617 gfc_offset m;
618 gfc_offset where = s->logical_offset;
619
620 m = where + *len;
621
622 if (where < s->buffer_offset)
623 return NULL;
624
625 if (m > s->file_length)
626 return NULL;
627
628 s->logical_offset = m;
629
630 return s->buffer + (where - s->buffer_offset);
631 }
632
633
634 /* Stream read function for internal units. */
635
636 static ssize_t
637 mem_read (stream * s, void * buf, ssize_t nbytes)
638 {
639 void *p;
640 int nb = nbytes;
641
642 p = mem_alloc_r (s, &nb);
643 if (p)
644 {
645 memcpy (buf, p, nb);
646 return (ssize_t) nb;
647 }
648 else
649 return 0;
650 }
651
652
653 /* Stream write function for internal units. This is not actually used
654 at the moment, as all internal IO is formatted and the formatted IO
655 routines use mem_alloc_w_at. */
656
657 static ssize_t
658 mem_write (stream * s, const void * buf, ssize_t nbytes)
659 {
660 void *p;
661 int nb = nbytes;
662
663 p = mem_alloc_w (s, &nb);
664 if (p)
665 {
666 memcpy (p, buf, nb);
667 return (ssize_t) nb;
668 }
669 else
670 return 0;
671 }
672
673
674 static off_t
675 mem_seek (stream * strm, off_t offset, int whence)
676 {
677 unix_stream * s = (unix_stream *) strm;
678 switch (whence)
679 {
680 case SEEK_SET:
681 break;
682 case SEEK_CUR:
683 offset += s->logical_offset;
684 break;
685 case SEEK_END:
686 offset += s->file_length;
687 break;
688 default:
689 return -1;
690 }
691
692 /* Note that for internal array I/O it's actually possible to have a
693 negative offset, so don't check for that. */
694 if (offset > s->file_length)
695 {
696 errno = EINVAL;
697 return -1;
698 }
699
700 s->logical_offset = offset;
701
702 /* Returning < 0 is the error indicator for sseek(), so return 0 if
703 offset is negative. Thus if the return value is 0, the caller
704 has to use stell() to get the real value of logical_offset. */
705 if (offset >= 0)
706 return offset;
707 return 0;
708 }
709
710
711 static off_t
712 mem_tell (stream * s)
713 {
714 return ((unix_stream *)s)->logical_offset;
715 }
716
717
718 static int
719 mem_truncate (unix_stream * s __attribute__ ((unused)),
720 off_t length __attribute__ ((unused)))
721 {
722 return 0;
723 }
724
725
726 static int
727 mem_flush (unix_stream * s __attribute__ ((unused)))
728 {
729 return 0;
730 }
731
732
733 static int
734 mem_close (unix_stream * s)
735 {
736 if (s != NULL)
737 free_mem (s);
738
739 return 0;
740 }
741
742
743 /*********************************************************************
744 Public functions -- A reimplementation of this module needs to
745 define functional equivalents of the following.
746 *********************************************************************/
747
748 /* empty_internal_buffer()-- Zero the buffer of Internal file */
749
750 void
751 empty_internal_buffer(stream *strm)
752 {
753 unix_stream * s = (unix_stream *) strm;
754 memset(s->buffer, ' ', s->file_length);
755 }
756
757 /* open_internal()-- Returns a stream structure from an internal file */
758
759 stream *
760 open_internal (char *base, int length, gfc_offset offset)
761 {
762 unix_stream *s;
763
764 s = get_mem (sizeof (unix_stream));
765 memset (s, '\0', sizeof (unix_stream));
766
767 s->buffer = base;
768 s->buffer_offset = offset;
769
770 s->logical_offset = 0;
771 s->active = s->file_length = length;
772
773 s->st.close = (void *) mem_close;
774 s->st.seek = (void *) mem_seek;
775 s->st.tell = (void *) mem_tell;
776 s->st.trunc = (void *) mem_truncate;
777 s->st.read = (void *) mem_read;
778 s->st.write = (void *) mem_write;
779 s->st.flush = (void *) mem_flush;
780
781 return (stream *) s;
782 }
783
784
785 /* fd_to_stream()-- Given an open file descriptor, build a stream
786 * around it. */
787
788 static stream *
789 fd_to_stream (int fd, int prot)
790 {
791 struct stat statbuf;
792 unix_stream *s;
793
794 s = get_mem (sizeof (unix_stream));
795 memset (s, '\0', sizeof (unix_stream));
796
797 s->fd = fd;
798 s->buffer_offset = 0;
799 s->physical_offset = 0;
800 s->logical_offset = 0;
801 s->prot = prot;
802
803 /* Get the current length of the file. */
804
805 fstat (fd, &statbuf);
806
807 if (lseek (fd, 0, SEEK_CUR) == (off_t) -1)
808 s->file_length = -1;
809 else
810 s->file_length = S_ISREG (statbuf.st_mode) ? statbuf.st_size : -1;
811
812 s->special_file = !S_ISREG (statbuf.st_mode);
813
814 if (isatty (s->fd) || options.all_unbuffered
815 ||(options.unbuffered_preconnected &&
816 (s->fd == STDIN_FILENO
817 || s->fd == STDOUT_FILENO
818 || s->fd == STDERR_FILENO)))
819 raw_init (s);
820 else
821 buf_init (s);
822
823 return (stream *) s;
824 }
825
826
827 /* Given the Fortran unit number, convert it to a C file descriptor. */
828
829 int
830 unit_to_fd (int unit)
831 {
832 gfc_unit *us;
833 int fd;
834
835 us = find_unit (unit);
836 if (us == NULL)
837 return -1;
838
839 fd = ((unix_stream *) us->s)->fd;
840 unlock_unit (us);
841 return fd;
842 }
843
844
845 /* unpack_filename()-- Given a fortran string and a pointer to a
846 * buffer that is PATH_MAX characters, convert the fortran string to a
847 * C string in the buffer. Returns nonzero if this is not possible. */
848
849 int
850 unpack_filename (char *cstring, const char *fstring, int len)
851 {
852 len = fstrlen (fstring, len);
853 if (len >= PATH_MAX)
854 return 1;
855
856 memmove (cstring, fstring, len);
857 cstring[len] = '\0';
858
859 return 0;
860 }
861
862
863 /* tempfile()-- Generate a temporary filename for a scratch file and
864 * open it. mkstemp() opens the file for reading and writing, but the
865 * library mode prevents anything that is not allowed. The descriptor
866 * is returned, which is -1 on error. The template is pointed to by
867 * opp->file, which is copied into the unit structure
868 * and freed later. */
869
870 static int
871 tempfile (st_parameter_open *opp)
872 {
873 const char *tempdir;
874 char *template;
875 int fd;
876
877 tempdir = getenv ("GFORTRAN_TMPDIR");
878 if (tempdir == NULL)
879 tempdir = getenv ("TMP");
880 if (tempdir == NULL)
881 tempdir = getenv ("TEMP");
882 if (tempdir == NULL)
883 tempdir = DEFAULT_TEMPDIR;
884
885 template = get_mem (strlen (tempdir) + 20);
886
887 sprintf (template, "%s/gfortrantmpXXXXXX", tempdir);
888
889 #ifdef HAVE_MKSTEMP
890
891 fd = mkstemp (template);
892
893 #else /* HAVE_MKSTEMP */
894
895 if (mktemp (template))
896 do
897 #if defined(HAVE_CRLF) && defined(O_BINARY)
898 fd = open (template, O_RDWR | O_CREAT | O_EXCL | O_BINARY,
899 S_IREAD | S_IWRITE);
900 #else
901 fd = open (template, O_RDWR | O_CREAT | O_EXCL, S_IREAD | S_IWRITE);
902 #endif
903 while (!(fd == -1 && errno == EEXIST) && mktemp (template));
904 else
905 fd = -1;
906
907 #endif /* HAVE_MKSTEMP */
908
909 if (fd < 0)
910 free_mem (template);
911 else
912 {
913 opp->file = template;
914 opp->file_len = strlen (template); /* Don't include trailing nul */
915 }
916
917 return fd;
918 }
919
920
921 /* regular_file()-- Open a regular file.
922 * Change flags->action if it is ACTION_UNSPECIFIED on entry,
923 * unless an error occurs.
924 * Returns the descriptor, which is less than zero on error. */
925
926 static int
927 regular_file (st_parameter_open *opp, unit_flags *flags)
928 {
929 char path[PATH_MAX + 1];
930 int mode;
931 int rwflag;
932 int crflag;
933 int fd;
934
935 if (unpack_filename (path, opp->file, opp->file_len))
936 {
937 errno = ENOENT; /* Fake an OS error */
938 return -1;
939 }
940
941 rwflag = 0;
942
943 switch (flags->action)
944 {
945 case ACTION_READ:
946 rwflag = O_RDONLY;
947 break;
948
949 case ACTION_WRITE:
950 rwflag = O_WRONLY;
951 break;
952
953 case ACTION_READWRITE:
954 case ACTION_UNSPECIFIED:
955 rwflag = O_RDWR;
956 break;
957
958 default:
959 internal_error (&opp->common, "regular_file(): Bad action");
960 }
961
962 switch (flags->status)
963 {
964 case STATUS_NEW:
965 crflag = O_CREAT | O_EXCL;
966 break;
967
968 case STATUS_OLD: /* open will fail if the file does not exist*/
969 crflag = 0;
970 break;
971
972 case STATUS_UNKNOWN:
973 case STATUS_SCRATCH:
974 crflag = O_CREAT;
975 break;
976
977 case STATUS_REPLACE:
978 crflag = O_CREAT | O_TRUNC;
979 break;
980
981 default:
982 internal_error (&opp->common, "regular_file(): Bad status");
983 }
984
985 /* rwflag |= O_LARGEFILE; */
986
987 #if defined(HAVE_CRLF) && defined(O_BINARY)
988 crflag |= O_BINARY;
989 #endif
990
991 mode = S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH;
992 fd = open (path, rwflag | crflag, mode);
993 if (flags->action != ACTION_UNSPECIFIED)
994 return fd;
995
996 if (fd >= 0)
997 {
998 flags->action = ACTION_READWRITE;
999 return fd;
1000 }
1001 if (errno != EACCES && errno != EROFS)
1002 return fd;
1003
1004 /* retry for read-only access */
1005 rwflag = O_RDONLY;
1006 fd = open (path, rwflag | crflag, mode);
1007 if (fd >=0)
1008 {
1009 flags->action = ACTION_READ;
1010 return fd; /* success */
1011 }
1012
1013 if (errno != EACCES)
1014 return fd; /* failure */
1015
1016 /* retry for write-only access */
1017 rwflag = O_WRONLY;
1018 fd = open (path, rwflag | crflag, mode);
1019 if (fd >=0)
1020 {
1021 flags->action = ACTION_WRITE;
1022 return fd; /* success */
1023 }
1024 return fd; /* failure */
1025 }
1026
1027
1028 /* open_external()-- Open an external file, unix specific version.
1029 * Change flags->action if it is ACTION_UNSPECIFIED on entry.
1030 * Returns NULL on operating system error. */
1031
1032 stream *
1033 open_external (st_parameter_open *opp, unit_flags *flags)
1034 {
1035 int fd, prot;
1036
1037 if (flags->status == STATUS_SCRATCH)
1038 {
1039 fd = tempfile (opp);
1040 if (flags->action == ACTION_UNSPECIFIED)
1041 flags->action = ACTION_READWRITE;
1042
1043 #if HAVE_UNLINK_OPEN_FILE
1044 /* We can unlink scratch files now and it will go away when closed. */
1045 if (fd >= 0)
1046 unlink (opp->file);
1047 #endif
1048 }
1049 else
1050 {
1051 /* regular_file resets flags->action if it is ACTION_UNSPECIFIED and
1052 * if it succeeds */
1053 fd = regular_file (opp, flags);
1054 }
1055
1056 if (fd < 0)
1057 return NULL;
1058 fd = fix_fd (fd);
1059
1060 switch (flags->action)
1061 {
1062 case ACTION_READ:
1063 prot = PROT_READ;
1064 break;
1065
1066 case ACTION_WRITE:
1067 prot = PROT_WRITE;
1068 break;
1069
1070 case ACTION_READWRITE:
1071 prot = PROT_READ | PROT_WRITE;
1072 break;
1073
1074 default:
1075 internal_error (&opp->common, "open_external(): Bad action");
1076 }
1077
1078 return fd_to_stream (fd, prot);
1079 }
1080
1081
1082 /* input_stream()-- Return a stream pointer to the default input stream.
1083 * Called on initialization. */
1084
1085 stream *
1086 input_stream (void)
1087 {
1088 return fd_to_stream (STDIN_FILENO, PROT_READ);
1089 }
1090
1091
1092 /* output_stream()-- Return a stream pointer to the default output stream.
1093 * Called on initialization. */
1094
1095 stream *
1096 output_stream (void)
1097 {
1098 stream * s;
1099
1100 #if defined(HAVE_CRLF) && defined(HAVE_SETMODE)
1101 setmode (STDOUT_FILENO, O_BINARY);
1102 #endif
1103
1104 s = fd_to_stream (STDOUT_FILENO, PROT_WRITE);
1105 return s;
1106 }
1107
1108
1109 /* error_stream()-- Return a stream pointer to the default error stream.
1110 * Called on initialization. */
1111
1112 stream *
1113 error_stream (void)
1114 {
1115 stream * s;
1116
1117 #if defined(HAVE_CRLF) && defined(HAVE_SETMODE)
1118 setmode (STDERR_FILENO, O_BINARY);
1119 #endif
1120
1121 s = fd_to_stream (STDERR_FILENO, PROT_WRITE);
1122 return s;
1123 }
1124
1125
1126 /* st_vprintf()-- vprintf function for error output. To avoid buffer
1127 overruns, we limit the length of the buffer to ST_VPRINTF_SIZE. 2k
1128 is big enough to completely fill a 80x25 terminal, so it shuld be
1129 OK. We use a direct write() because it is simpler and least likely
1130 to be clobbered by memory corruption. Writing an error message
1131 longer than that is an error. */
1132
1133 #define ST_VPRINTF_SIZE 2048
1134
1135 int
1136 st_vprintf (const char *format, va_list ap)
1137 {
1138 static char buffer[ST_VPRINTF_SIZE];
1139 int written;
1140 int fd;
1141
1142 fd = options.use_stderr ? STDERR_FILENO : STDOUT_FILENO;
1143 #ifdef HAVE_VSNPRINTF
1144 written = vsnprintf(buffer, ST_VPRINTF_SIZE, format, ap);
1145 #else
1146 written = vsprintf(buffer, format, ap);
1147
1148 if (written >= ST_VPRINTF_SIZE-1)
1149 {
1150 /* The error message was longer than our buffer. Ouch. Because
1151 we may have messed up things badly, report the error and
1152 quit. */
1153 #define ERROR_MESSAGE "Internal error: buffer overrun in st_vprintf()\n"
1154 write (fd, buffer, ST_VPRINTF_SIZE-1);
1155 write (fd, ERROR_MESSAGE, strlen(ERROR_MESSAGE));
1156 sys_exit(2);
1157 #undef ERROR_MESSAGE
1158
1159 }
1160 #endif
1161
1162 written = write (fd, buffer, written);
1163 return written;
1164 }
1165
1166 /* st_printf()-- printf() function for error output. This just calls
1167 st_vprintf() to do the actual work. */
1168
1169 int
1170 st_printf (const char *format, ...)
1171 {
1172 int written;
1173 va_list ap;
1174 va_start (ap, format);
1175 written = st_vprintf(format, ap);
1176 va_end (ap);
1177 return written;
1178 }
1179
1180
1181 /* compare_file_filename()-- Given an open stream and a fortran string
1182 * that is a filename, figure out if the file is the same as the
1183 * filename. */
1184
1185 int
1186 compare_file_filename (gfc_unit *u, const char *name, int len)
1187 {
1188 char path[PATH_MAX + 1];
1189 struct stat st1;
1190 #ifdef HAVE_WORKING_STAT
1191 struct stat st2;
1192 #else
1193 # ifdef __MINGW32__
1194 uint64_t id1, id2;
1195 # endif
1196 #endif
1197
1198 if (unpack_filename (path, name, len))
1199 return 0; /* Can't be the same */
1200
1201 /* If the filename doesn't exist, then there is no match with the
1202 * existing file. */
1203
1204 if (stat (path, &st1) < 0)
1205 return 0;
1206
1207 #ifdef HAVE_WORKING_STAT
1208 fstat (((unix_stream *) (u->s))->fd, &st2);
1209 return (st1.st_dev == st2.st_dev) && (st1.st_ino == st2.st_ino);
1210 #else
1211
1212 # ifdef __MINGW32__
1213 /* We try to match files by a unique ID. On some filesystems (network
1214 fs and FAT), we can't generate this unique ID, and will simply compare
1215 filenames. */
1216 id1 = id_from_path (path);
1217 id2 = id_from_fd (((unix_stream *) (u->s))->fd);
1218 if (id1 || id2)
1219 return (id1 == id2);
1220 # endif
1221
1222 if (len != u->file_len)
1223 return 0;
1224 return (memcmp(path, u->file, len) == 0);
1225 #endif
1226 }
1227
1228
1229 #ifdef HAVE_WORKING_STAT
1230 # define FIND_FILE0_DECL struct stat *st
1231 # define FIND_FILE0_ARGS st
1232 #else
1233 # define FIND_FILE0_DECL uint64_t id, const char *file, gfc_charlen_type file_len
1234 # define FIND_FILE0_ARGS id, file, file_len
1235 #endif
1236
1237 /* find_file0()-- Recursive work function for find_file() */
1238
1239 static gfc_unit *
1240 find_file0 (gfc_unit *u, FIND_FILE0_DECL)
1241 {
1242 gfc_unit *v;
1243 #if defined(__MINGW32__) && !HAVE_WORKING_STAT
1244 uint64_t id1;
1245 #endif
1246
1247 if (u == NULL)
1248 return NULL;
1249
1250 #ifdef HAVE_WORKING_STAT
1251 if (u->s != NULL
1252 && fstat (((unix_stream *) u->s)->fd, &st[1]) >= 0 &&
1253 st[0].st_dev == st[1].st_dev && st[0].st_ino == st[1].st_ino)
1254 return u;
1255 #else
1256 # ifdef __MINGW32__
1257 if (u->s && ((id1 = id_from_fd (((unix_stream *) u->s)->fd)) || id1))
1258 {
1259 if (id == id1)
1260 return u;
1261 }
1262 else
1263 # endif
1264 if (compare_string (u->file_len, u->file, file_len, file) == 0)
1265 return u;
1266 #endif
1267
1268 v = find_file0 (u->left, FIND_FILE0_ARGS);
1269 if (v != NULL)
1270 return v;
1271
1272 v = find_file0 (u->right, FIND_FILE0_ARGS);
1273 if (v != NULL)
1274 return v;
1275
1276 return NULL;
1277 }
1278
1279
1280 /* find_file()-- Take the current filename and see if there is a unit
1281 * that has the file already open. Returns a pointer to the unit if so. */
1282
1283 gfc_unit *
1284 find_file (const char *file, gfc_charlen_type file_len)
1285 {
1286 char path[PATH_MAX + 1];
1287 struct stat st[2];
1288 gfc_unit *u;
1289 uint64_t id;
1290
1291 if (unpack_filename (path, file, file_len))
1292 return NULL;
1293
1294 if (stat (path, &st[0]) < 0)
1295 return NULL;
1296
1297 #if defined(__MINGW32__) && !HAVE_WORKING_STAT
1298 id = id_from_path (path);
1299 #else
1300 id = 0;
1301 #endif
1302
1303 __gthread_mutex_lock (&unit_lock);
1304 retry:
1305 u = find_file0 (unit_root, FIND_FILE0_ARGS);
1306 if (u != NULL)
1307 {
1308 /* Fast path. */
1309 if (! __gthread_mutex_trylock (&u->lock))
1310 {
1311 /* assert (u->closed == 0); */
1312 __gthread_mutex_unlock (&unit_lock);
1313 return u;
1314 }
1315
1316 inc_waiting_locked (u);
1317 }
1318 __gthread_mutex_unlock (&unit_lock);
1319 if (u != NULL)
1320 {
1321 __gthread_mutex_lock (&u->lock);
1322 if (u->closed)
1323 {
1324 __gthread_mutex_lock (&unit_lock);
1325 __gthread_mutex_unlock (&u->lock);
1326 if (predec_waiting_locked (u) == 0)
1327 free_mem (u);
1328 goto retry;
1329 }
1330
1331 dec_waiting_unlocked (u);
1332 }
1333 return u;
1334 }
1335
1336 static gfc_unit *
1337 flush_all_units_1 (gfc_unit *u, int min_unit)
1338 {
1339 while (u != NULL)
1340 {
1341 if (u->unit_number > min_unit)
1342 {
1343 gfc_unit *r = flush_all_units_1 (u->left, min_unit);
1344 if (r != NULL)
1345 return r;
1346 }
1347 if (u->unit_number >= min_unit)
1348 {
1349 if (__gthread_mutex_trylock (&u->lock))
1350 return u;
1351 if (u->s)
1352 sflush (u->s);
1353 __gthread_mutex_unlock (&u->lock);
1354 }
1355 u = u->right;
1356 }
1357 return NULL;
1358 }
1359
1360 void
1361 flush_all_units (void)
1362 {
1363 gfc_unit *u;
1364 int min_unit = 0;
1365
1366 __gthread_mutex_lock (&unit_lock);
1367 do
1368 {
1369 u = flush_all_units_1 (unit_root, min_unit);
1370 if (u != NULL)
1371 inc_waiting_locked (u);
1372 __gthread_mutex_unlock (&unit_lock);
1373 if (u == NULL)
1374 return;
1375
1376 __gthread_mutex_lock (&u->lock);
1377
1378 min_unit = u->unit_number + 1;
1379
1380 if (u->closed == 0)
1381 {
1382 sflush (u->s);
1383 __gthread_mutex_lock (&unit_lock);
1384 __gthread_mutex_unlock (&u->lock);
1385 (void) predec_waiting_locked (u);
1386 }
1387 else
1388 {
1389 __gthread_mutex_lock (&unit_lock);
1390 __gthread_mutex_unlock (&u->lock);
1391 if (predec_waiting_locked (u) == 0)
1392 free_mem (u);
1393 }
1394 }
1395 while (1);
1396 }
1397
1398
1399 /* delete_file()-- Given a unit structure, delete the file associated
1400 * with the unit. Returns nonzero if something went wrong. */
1401
1402 int
1403 delete_file (gfc_unit * u)
1404 {
1405 char path[PATH_MAX + 1];
1406
1407 if (unpack_filename (path, u->file, u->file_len))
1408 { /* Shouldn't be possible */
1409 errno = ENOENT;
1410 return 1;
1411 }
1412
1413 return unlink (path);
1414 }
1415
1416
1417 /* file_exists()-- Returns nonzero if the current filename exists on
1418 * the system */
1419
1420 int
1421 file_exists (const char *file, gfc_charlen_type file_len)
1422 {
1423 char path[PATH_MAX + 1];
1424 struct stat statbuf;
1425
1426 if (unpack_filename (path, file, file_len))
1427 return 0;
1428
1429 if (stat (path, &statbuf) < 0)
1430 return 0;
1431
1432 return 1;
1433 }
1434
1435
1436
1437 static const char yes[] = "YES", no[] = "NO", unknown[] = "UNKNOWN";
1438
1439 /* inquire_sequential()-- Given a fortran string, determine if the
1440 * file is suitable for sequential access. Returns a C-style
1441 * string. */
1442
1443 const char *
1444 inquire_sequential (const char *string, int len)
1445 {
1446 char path[PATH_MAX + 1];
1447 struct stat statbuf;
1448
1449 if (string == NULL ||
1450 unpack_filename (path, string, len) || stat (path, &statbuf) < 0)
1451 return unknown;
1452
1453 if (S_ISREG (statbuf.st_mode) ||
1454 S_ISCHR (statbuf.st_mode) || S_ISFIFO (statbuf.st_mode))
1455 return unknown;
1456
1457 if (S_ISDIR (statbuf.st_mode) || S_ISBLK (statbuf.st_mode))
1458 return no;
1459
1460 return unknown;
1461 }
1462
1463
1464 /* inquire_direct()-- Given a fortran string, determine if the file is
1465 * suitable for direct access. Returns a C-style string. */
1466
1467 const char *
1468 inquire_direct (const char *string, int len)
1469 {
1470 char path[PATH_MAX + 1];
1471 struct stat statbuf;
1472
1473 if (string == NULL ||
1474 unpack_filename (path, string, len) || stat (path, &statbuf) < 0)
1475 return unknown;
1476
1477 if (S_ISREG (statbuf.st_mode) || S_ISBLK (statbuf.st_mode))
1478 return unknown;
1479
1480 if (S_ISDIR (statbuf.st_mode) ||
1481 S_ISCHR (statbuf.st_mode) || S_ISFIFO (statbuf.st_mode))
1482 return no;
1483
1484 return unknown;
1485 }
1486
1487
1488 /* inquire_formatted()-- Given a fortran string, determine if the file
1489 * is suitable for formatted form. Returns a C-style string. */
1490
1491 const char *
1492 inquire_formatted (const char *string, int len)
1493 {
1494 char path[PATH_MAX + 1];
1495 struct stat statbuf;
1496
1497 if (string == NULL ||
1498 unpack_filename (path, string, len) || stat (path, &statbuf) < 0)
1499 return unknown;
1500
1501 if (S_ISREG (statbuf.st_mode) ||
1502 S_ISBLK (statbuf.st_mode) ||
1503 S_ISCHR (statbuf.st_mode) || S_ISFIFO (statbuf.st_mode))
1504 return unknown;
1505
1506 if (S_ISDIR (statbuf.st_mode))
1507 return no;
1508
1509 return unknown;
1510 }
1511
1512
1513 /* inquire_unformatted()-- Given a fortran string, determine if the file
1514 * is suitable for unformatted form. Returns a C-style string. */
1515
1516 const char *
1517 inquire_unformatted (const char *string, int len)
1518 {
1519 return inquire_formatted (string, len);
1520 }
1521
1522
1523 #ifndef HAVE_ACCESS
1524
1525 #ifndef W_OK
1526 #define W_OK 2
1527 #endif
1528
1529 #ifndef R_OK
1530 #define R_OK 4
1531 #endif
1532
1533 /* Fallback implementation of access() on systems that don't have it.
1534 Only modes R_OK and W_OK are used in this file. */
1535
1536 static int
1537 fallback_access (const char *path, int mode)
1538 {
1539 if ((mode & R_OK) && open (path, O_RDONLY) < 0)
1540 return -1;
1541
1542 if ((mode & W_OK) && open (path, O_WRONLY) < 0)
1543 return -1;
1544
1545 return 0;
1546 }
1547
1548 #undef access
1549 #define access fallback_access
1550 #endif
1551
1552
1553 /* inquire_access()-- Given a fortran string, determine if the file is
1554 * suitable for access. */
1555
1556 static const char *
1557 inquire_access (const char *string, int len, int mode)
1558 {
1559 char path[PATH_MAX + 1];
1560
1561 if (string == NULL || unpack_filename (path, string, len) ||
1562 access (path, mode) < 0)
1563 return no;
1564
1565 return yes;
1566 }
1567
1568
1569 /* inquire_read()-- Given a fortran string, determine if the file is
1570 * suitable for READ access. */
1571
1572 const char *
1573 inquire_read (const char *string, int len)
1574 {
1575 return inquire_access (string, len, R_OK);
1576 }
1577
1578
1579 /* inquire_write()-- Given a fortran string, determine if the file is
1580 * suitable for READ access. */
1581
1582 const char *
1583 inquire_write (const char *string, int len)
1584 {
1585 return inquire_access (string, len, W_OK);
1586 }
1587
1588
1589 /* inquire_readwrite()-- Given a fortran string, determine if the file is
1590 * suitable for read and write access. */
1591
1592 const char *
1593 inquire_readwrite (const char *string, int len)
1594 {
1595 return inquire_access (string, len, R_OK | W_OK);
1596 }
1597
1598
1599 /* file_length()-- Return the file length in bytes, -1 if unknown */
1600
1601 gfc_offset
1602 file_length (stream * s)
1603 {
1604 off_t curr, end;
1605 if (!is_seekable (s))
1606 return -1;
1607 curr = stell (s);
1608 if (curr == -1)
1609 return curr;
1610 end = sseek (s, 0, SEEK_END);
1611 sseek (s, curr, SEEK_SET);
1612 return end;
1613 }
1614
1615
1616 /* is_seekable()-- Return nonzero if the stream is seekable, zero if
1617 * it is not */
1618
1619 int
1620 is_seekable (stream *s)
1621 {
1622 /* By convention, if file_length == -1, the file is not
1623 seekable. */
1624 return ((unix_stream *) s)->file_length!=-1;
1625 }
1626
1627
1628 /* is_special()-- Return nonzero if the stream is not a regular file. */
1629
1630 int
1631 is_special (stream *s)
1632 {
1633 return ((unix_stream *) s)->special_file;
1634 }
1635
1636
1637 int
1638 stream_isatty (stream *s)
1639 {
1640 return isatty (((unix_stream *) s)->fd);
1641 }
1642
1643 char *
1644 stream_ttyname (stream *s __attribute__ ((unused)))
1645 {
1646 #ifdef HAVE_TTYNAME
1647 return ttyname (((unix_stream *) s)->fd);
1648 #else
1649 return NULL;
1650 #endif
1651 }
1652
1653
1654 /* How files are stored: This is an operating-system specific issue,
1655 and therefore belongs here. There are three cases to consider.
1656
1657 Direct Access:
1658 Records are written as block of bytes corresponding to the record
1659 length of the file. This goes for both formatted and unformatted
1660 records. Positioning is done explicitly for each data transfer,
1661 so positioning is not much of an issue.
1662
1663 Sequential Formatted:
1664 Records are separated by newline characters. The newline character
1665 is prohibited from appearing in a string. If it does, this will be
1666 messed up on the next read. End of file is also the end of a record.
1667
1668 Sequential Unformatted:
1669 In this case, we are merely copying bytes to and from main storage,
1670 yet we need to keep track of varying record lengths. We adopt
1671 the solution used by f2c. Each record contains a pair of length
1672 markers:
1673
1674 Length of record n in bytes
1675 Data of record n
1676 Length of record n in bytes
1677
1678 Length of record n+1 in bytes
1679 Data of record n+1
1680 Length of record n+1 in bytes
1681
1682 The length is stored at the end of a record to allow backspacing to the
1683 previous record. Between data transfer statements, the file pointer
1684 is left pointing to the first length of the current record.
1685
1686 ENDFILE records are never explicitly stored.
1687
1688 */