OSDN Git Service

PR libfortran/35293
[pf3gnuchains/gcc-fork.git] / libgfortran / io / unix.c
1 /* Copyright (C) 2002, 2003, 2004, 2005, 2006, 2007
2    Free Software Foundation, Inc.
3    Contributed by Andy Vaught
4
5 This file is part of the GNU Fortran 95 runtime library (libgfortran).
6
7 Libgfortran is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
10 any later version.
11
12 In addition to the permissions in the GNU General Public License, the
13 Free Software Foundation gives you unlimited permission to link the
14 compiled version of this file into combinations with other programs,
15 and to distribute those combinations without any restriction coming
16 from the use of this file.  (The General Public License restrictions
17 do apply in other respects; for example, they cover modification of
18 the file, and distribution when not linked into a combine
19 executable.)
20
21 Libgfortran is distributed in the hope that it will be useful,
22 but WITHOUT ANY WARRANTY; without even the implied warranty of
23 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
24 GNU General Public License for more details.
25
26 You should have received a copy of the GNU General Public License
27 along with Libgfortran; see the file COPYING.  If not, write to
28 the Free Software Foundation, 51 Franklin Street, Fifth Floor,
29 Boston, MA 02110-1301, USA.  */
30
31 /* Unix stream I/O module */
32
33 #include "io.h"
34 #include <stdlib.h>
35 #include <limits.h>
36
37 #include <unistd.h>
38 #include <sys/stat.h>
39 #include <fcntl.h>
40 #include <assert.h>
41
42 #include <string.h>
43 #include <errno.h>
44
45
46 /* For mingw, we don't identify files by their inode number, but by a
47    64-bit identifier created from a BY_HANDLE_FILE_INFORMATION. */
48 #if defined(__MINGW32__) && !HAVE_WORKING_STAT
49
50 #define WIN32_LEAN_AND_MEAN
51 #include <windows.h>
52
53 static uint64_t
54 id_from_handle (HANDLE hFile)
55 {
56   BY_HANDLE_FILE_INFORMATION FileInformation;
57
58   if (hFile == INVALID_HANDLE_VALUE)
59       return 0;
60
61   memset (&FileInformation, 0, sizeof(FileInformation));
62   if (!GetFileInformationByHandle (hFile, &FileInformation))
63     return 0;
64
65   return ((uint64_t) FileInformation.nFileIndexLow)
66          | (((uint64_t) FileInformation.nFileIndexHigh) << 32);
67 }
68
69
70 static uint64_t
71 id_from_path (const char *path)
72 {
73   HANDLE hFile;
74   uint64_t res;
75
76   if (!path || !*path || access (path, F_OK))
77     return (uint64_t) -1;
78
79   hFile = CreateFile (path, 0, 0, NULL, OPEN_EXISTING,
80                       FILE_FLAG_BACKUP_SEMANTICS | FILE_ATTRIBUTE_READONLY,
81                       NULL);
82   res = id_from_handle (hFile);
83   CloseHandle (hFile);
84   return res;
85 }
86
87
88 static uint64_t
89 id_from_fd (const int fd)
90 {
91   return id_from_handle ((HANDLE) _get_osfhandle (fd));
92 }
93
94 #endif
95
96
97
98 #ifndef SSIZE_MAX
99 #define SSIZE_MAX SHRT_MAX
100 #endif
101
102 #ifndef PATH_MAX
103 #define PATH_MAX 1024
104 #endif
105
106 #ifndef PROT_READ
107 #define PROT_READ 1
108 #endif
109
110 #ifndef PROT_WRITE
111 #define PROT_WRITE 2
112 #endif
113
114 /* These flags aren't defined on all targets (mingw32), so provide them
115    here.  */
116 #ifndef S_IRGRP
117 #define S_IRGRP 0
118 #endif
119
120 #ifndef S_IWGRP
121 #define S_IWGRP 0
122 #endif
123
124 #ifndef S_IROTH
125 #define S_IROTH 0
126 #endif
127
128 #ifndef S_IWOTH
129 #define S_IWOTH 0
130 #endif
131
132
133 /* Unix stream I/O module */
134
135 #define BUFFER_SIZE 8192
136
137 typedef struct
138 {
139   stream st;
140
141   int fd;
142   gfc_offset buffer_offset;     /* File offset of the start of the buffer */
143   gfc_offset physical_offset;   /* Current physical file offset */
144   gfc_offset logical_offset;    /* Current logical file offset */
145   gfc_offset dirty_offset;      /* Start of modified bytes in buffer */
146   gfc_offset file_length;       /* Length of the file, -1 if not seekable. */
147
148   int len;                      /* Physical length of the current buffer */
149   int active;                   /* Length of valid bytes in the buffer */
150
151   int prot;
152   int ndirty;                   /* Dirty bytes starting at dirty_offset */
153
154   int special_file;             /* =1 if the fd refers to a special file */
155
156   int unbuffered;               /* =1 if the stream is not buffered */
157
158   char *buffer;
159   char small_buffer[BUFFER_SIZE];
160 }
161 unix_stream;
162
163
164 /* Stream structure for internal files. Fields must be kept in sync
165    with unix_stream above, except for the buffer. For internal files
166    we point the buffer pointer directly at the destination memory.  */
167
168 typedef struct
169 {
170   stream st;
171
172   int fd;
173   gfc_offset buffer_offset;     /* File offset of the start of the buffer */
174   gfc_offset physical_offset;   /* Current physical file offset */
175   gfc_offset logical_offset;    /* Current logical file offset */
176   gfc_offset dirty_offset;      /* Start of modified bytes in buffer */
177   gfc_offset file_length;       /* Length of the file, -1 if not seekable. */
178
179   int len;                      /* Physical length of the current buffer */
180   int active;                   /* Length of valid bytes in the buffer */
181
182   int prot;
183   int ndirty;                   /* Dirty bytes starting at dirty_offset */
184
185   int special_file;             /* =1 if the fd refers to a special file */
186
187   int unbuffered;               /* =1 if the stream is not buffered */
188
189   char *buffer;
190 }
191 int_stream;
192
193 /* This implementation of stream I/O is based on the paper:
194  *
195  *  "Exploiting the advantages of mapped files for stream I/O",
196  *  O. Krieger, M. Stumm and R. Umrau, "Proceedings of the 1992 Winter
197  *  USENIX conference", p. 27-42.
198  *
199  * It differs in a number of ways from the version described in the
200  * paper.  First of all, threads are not an issue during I/O and we
201  * also don't have to worry about having multiple regions, since
202  * fortran's I/O model only allows you to be one place at a time.
203  *
204  * On the other hand, we have to be able to writing at the end of a
205  * stream, read from the start of a stream or read and write blocks of
206  * bytes from an arbitrary position.  After opening a file, a pointer
207  * to a stream structure is returned, which is used to handle file
208  * accesses until the file is closed.
209  *
210  * salloc_at_r(stream, len, where)-- Given a stream pointer, return a
211  * pointer to a block of memory that mirror the file at position
212  * 'where' that is 'len' bytes long.  The len integer is updated to
213  * reflect how many bytes were actually read.  The only reason for a
214  * short read is end of file.  The file pointer is updated.  The
215  * pointer is valid until the next call to salloc_*.
216  *
217  * salloc_at_w(stream, len, where)-- Given the stream pointer, returns
218  * a pointer to a block of memory that is updated to reflect the state
219  * of the file.  The length of the buffer is always equal to that
220  * requested.  The buffer must be completely set by the caller.  When
221  * data has been written, the sfree() function must be called to
222  * indicate that the caller is done writing data to the buffer.  This
223  * may or may not cause a physical write.
224  *
225  * Short forms of these are salloc_r() and salloc_w() which drop the
226  * 'where' parameter and use the current file pointer. */
227
228
229 /*move_pos_offset()--  Move the record pointer right or left
230  *relative to current position */
231
232 int
233 move_pos_offset (stream* st, int pos_off)
234 {
235   unix_stream * str = (unix_stream*)st;
236   if (pos_off < 0)
237     {
238       str->logical_offset += pos_off;
239
240       if (str->dirty_offset + str->ndirty > str->logical_offset)
241         {
242           if (str->ndirty + pos_off > 0)
243             str->ndirty += pos_off;
244           else
245             {
246               str->dirty_offset +=  pos_off + pos_off;
247               str->ndirty = 0;
248             }
249         }
250
251     return pos_off;
252   }
253   return 0;
254 }
255
256
257 /* fix_fd()-- Given a file descriptor, make sure it is not one of the
258  * standard descriptors, returning a non-standard descriptor.  If the
259  * user specifies that system errors should go to standard output,
260  * then closes standard output, we don't want the system errors to a
261  * file that has been given file descriptor 1 or 0.  We want to send
262  * the error to the invalid descriptor. */
263
264 static int
265 fix_fd (int fd)
266 {
267 #ifdef HAVE_DUP
268   int input, output, error;
269
270   input = output = error = 0;
271
272   /* Unix allocates the lowest descriptors first, so a loop is not
273      required, but this order is. */
274   if (fd == STDIN_FILENO)
275     {
276       fd = dup (fd);
277       input = 1;
278     }
279   if (fd == STDOUT_FILENO)
280     {
281       fd = dup (fd);
282       output = 1;
283     }
284   if (fd == STDERR_FILENO)
285     {
286       fd = dup (fd);
287       error = 1;
288     }
289
290   if (input)
291     close (STDIN_FILENO);
292   if (output)
293     close (STDOUT_FILENO);
294   if (error)
295     close (STDERR_FILENO);
296 #endif
297
298   return fd;
299 }
300
301 int
302 is_preconnected (stream * s)
303 {
304   int fd;
305
306   fd = ((unix_stream *) s)->fd;
307   if (fd == STDIN_FILENO || fd == STDOUT_FILENO || fd == STDERR_FILENO)
308     return 1;
309   else
310     return 0;
311 }
312
313 /* If the stream corresponds to a preconnected unit, we flush the
314    corresponding C stream.  This is bugware for mixed C-Fortran codes
315    where the C code doesn't flush I/O before returning.  */
316 void
317 flush_if_preconnected (stream * s)
318 {
319   int fd;
320
321   fd = ((unix_stream *) s)->fd;
322   if (fd == STDIN_FILENO)
323     fflush (stdin);
324   else if (fd == STDOUT_FILENO)
325     fflush (stdout);
326   else if (fd == STDERR_FILENO)
327     fflush (stderr);
328 }
329
330
331 /* Reset a stream after reading/writing. Assumes that the buffers have
332    been flushed.  */
333
334 inline static void
335 reset_stream (unix_stream * s, size_t bytes_rw)
336 {
337   s->physical_offset += bytes_rw;
338   s->logical_offset = s->physical_offset;
339   if (s->file_length != -1 && s->physical_offset > s->file_length)
340     s->file_length = s->physical_offset;
341 }
342
343
344 /* Read bytes into a buffer, allowing for short reads.  If the nbytes
345  * argument is less on return than on entry, it is because we've hit
346  * the end of file. */
347
348 static int
349 do_read (unix_stream * s, void * buf, size_t * nbytes)
350 {
351   ssize_t trans;
352   size_t bytes_left;
353   char *buf_st;
354   int status;
355
356   status = 0;
357   bytes_left = *nbytes;
358   buf_st = (char *) buf;
359
360   /* We must read in a loop since some systems don't restart system
361      calls in case of a signal.  */
362   while (bytes_left > 0)
363     {
364       /* Requests between SSIZE_MAX and SIZE_MAX are undefined by SUSv3,
365          so we must read in chunks smaller than SSIZE_MAX.  */
366       trans = (bytes_left < SSIZE_MAX) ? bytes_left : SSIZE_MAX;
367       trans = read (s->fd, buf_st, trans);
368       if (trans < 0)
369         {
370           if (errno == EINTR)
371             continue;
372           else
373             {
374               status = errno;
375               break;
376             }
377         }
378       else if (trans == 0) /* We hit EOF.  */
379         break;
380       buf_st += trans;
381       bytes_left -= trans;
382     }
383
384   *nbytes -= bytes_left;
385   return status;
386 }
387
388
389 /* Write a buffer to a stream, allowing for short writes.  */
390
391 static int
392 do_write (unix_stream * s, const void * buf, size_t * nbytes)
393 {
394   ssize_t trans;
395   size_t bytes_left;
396   char *buf_st;
397   int status;
398
399   status = 0;
400   bytes_left = *nbytes;
401   buf_st = (char *) buf;
402
403   /* We must write in a loop since some systems don't restart system
404      calls in case of a signal.  */
405   while (bytes_left > 0)
406     {
407       /* Requests between SSIZE_MAX and SIZE_MAX are undefined by SUSv3,
408          so we must write in chunks smaller than SSIZE_MAX.  */
409       trans = (bytes_left < SSIZE_MAX) ? bytes_left : SSIZE_MAX;
410       trans = write (s->fd, buf_st, trans);
411       if (trans < 0)
412         {
413           if (errno == EINTR)
414             continue;
415           else
416             {
417               status = errno;
418               break;
419             }
420         }
421       buf_st += trans;
422       bytes_left -= trans;
423     }
424
425   *nbytes -= bytes_left;
426   return status;
427 }
428
429
430 /* get_oserror()-- Get the most recent operating system error.  For
431  * unix, this is errno. */
432
433 const char *
434 get_oserror (void)
435 {
436   return strerror (errno);
437 }
438
439
440 /*********************************************************************
441     File descriptor stream functions
442 *********************************************************************/
443
444
445 /* fd_flush()-- Write bytes that need to be written */
446
447 static try
448 fd_flush (unix_stream * s)
449 {
450   size_t writelen;
451
452   if (s->ndirty == 0)
453     return SUCCESS;
454   
455   if (s->file_length != -1 && s->physical_offset != s->dirty_offset &&
456       lseek (s->fd, s->dirty_offset, SEEK_SET) < 0)
457     return FAILURE;
458
459   writelen = s->ndirty;
460   if (do_write (s, s->buffer + (s->dirty_offset - s->buffer_offset),
461                 &writelen) != 0)
462     return FAILURE;
463
464   s->physical_offset = s->dirty_offset + writelen;
465
466   /* don't increment file_length if the file is non-seekable */
467   if (s->file_length != -1 && s->physical_offset > s->file_length)
468       s->file_length = s->physical_offset; 
469
470   s->ndirty -= writelen;
471   if (s->ndirty != 0)
472     return FAILURE;
473
474   return SUCCESS;
475 }
476
477
478 /* fd_alloc()-- Arrange a buffer such that the salloc() request can be
479  * satisfied.  This subroutine gets the buffer ready for whatever is
480  * to come next. */
481
482 static void
483 fd_alloc (unix_stream * s, gfc_offset where,
484           int *len __attribute__ ((unused)))
485 {
486   char *new_buffer;
487   int n, read_len;
488
489   if (*len <= BUFFER_SIZE)
490     {
491       new_buffer = s->small_buffer;
492       read_len = BUFFER_SIZE;
493     }
494   else
495     {
496       new_buffer = get_mem (*len);
497       read_len = *len;
498     }
499
500   /* Salvage bytes currently within the buffer.  This is important for
501    * devices that cannot seek. */
502
503   if (s->buffer != NULL && s->buffer_offset <= where &&
504       where <= s->buffer_offset + s->active)
505     {
506
507       n = s->active - (where - s->buffer_offset);
508       memmove (new_buffer, s->buffer + (where - s->buffer_offset), n);
509
510       s->active = n;
511     }
512   else
513     {                           /* new buffer starts off empty */
514       s->active = 0;
515     }
516
517   s->buffer_offset = where;
518
519   /* free the old buffer if necessary */
520
521   if (s->buffer != NULL && s->buffer != s->small_buffer)
522     free_mem (s->buffer);
523
524   s->buffer = new_buffer;
525   s->len = read_len;
526 }
527
528
529 /* fd_alloc_r_at()-- Allocate a stream buffer for reading.  Either
530  * we've already buffered the data or we need to load it.  Returns
531  * NULL on I/O error. */
532
533 static char *
534 fd_alloc_r_at (unix_stream * s, int *len, gfc_offset where)
535 {
536   gfc_offset m;
537
538   if (where == -1)
539     where = s->logical_offset;
540
541   if (s->buffer != NULL && s->buffer_offset <= where &&
542       where + *len <= s->buffer_offset + s->active)
543     {
544
545       /* Return a position within the current buffer */
546
547       s->logical_offset = where + *len;
548       return s->buffer + where - s->buffer_offset;
549     }
550
551   fd_alloc (s, where, len);
552
553   m = where + s->active;
554
555   if (s->physical_offset != m && lseek (s->fd, m, SEEK_SET) < 0)
556     return NULL;
557
558   /* do_read() hangs on read from terminals for *BSD-systems.  Only
559      use read() in that case.  */
560
561   if (s->special_file)
562     {
563       ssize_t n;
564
565       n = read (s->fd, s->buffer + s->active, s->len - s->active);
566       if (n < 0)
567         return NULL;
568
569       s->physical_offset = m + n;
570       s->active += n;
571     }
572   else
573     {
574       size_t n;
575
576       n = s->len - s->active;
577       if (do_read (s, s->buffer + s->active, &n) != 0)
578         return NULL;
579
580       s->physical_offset = m + n;
581       s->active += n;
582     }
583
584   if (s->active < *len)
585     *len = s->active;           /* Bytes actually available */
586
587   s->logical_offset = where + *len;
588
589   return s->buffer;
590 }
591
592
593 /* fd_alloc_w_at()-- Allocate a stream buffer for writing.  Either
594  * we've already buffered the data or we need to load it. */
595
596 static char *
597 fd_alloc_w_at (unix_stream * s, int *len, gfc_offset where)
598 {
599   gfc_offset n;
600
601   if (where == -1)
602     where = s->logical_offset;
603
604   if (s->buffer == NULL || s->buffer_offset > where ||
605       where + *len > s->buffer_offset + s->len)
606     {
607
608       if (fd_flush (s) == FAILURE)
609         return NULL;
610       fd_alloc (s, where, len);
611     }
612
613   /* Return a position within the current buffer */
614   if (s->ndirty == 0 
615       || where > s->dirty_offset + s->ndirty    
616       || s->dirty_offset > where + *len)
617     {  /* Discontiguous blocks, start with a clean buffer.  */  
618         /* Flush the buffer.  */  
619        if (s->ndirty != 0)    
620          fd_flush (s);  
621        s->dirty_offset = where;  
622        s->ndirty = *len;
623     }
624   else
625     {  
626       gfc_offset start;  /* Merge with the existing data.  */  
627       if (where < s->dirty_offset)    
628         start = where;  
629       else    
630         start = s->dirty_offset;  
631       if (where + *len > s->dirty_offset + s->ndirty)    
632         s->ndirty = where + *len - start;  
633       else    
634         s->ndirty = s->dirty_offset + s->ndirty - start;  
635       s->dirty_offset = start;
636     }
637
638   s->logical_offset = where + *len;
639
640   /* Don't increment file_length if the file is non-seekable.  */
641
642   if (s->file_length != -1 && s->logical_offset > s->file_length)
643      s->file_length = s->logical_offset;
644
645   n = s->logical_offset - s->buffer_offset;
646   if (n > s->active)
647     s->active = n;
648
649   return s->buffer + where - s->buffer_offset;
650 }
651
652
653 static try
654 fd_sfree (unix_stream * s)
655 {
656   if (s->ndirty != 0 &&
657       (s->buffer != s->small_buffer || options.all_unbuffered ||
658        s->unbuffered))
659     return fd_flush (s);
660
661   return SUCCESS;
662 }
663
664
665 static try
666 fd_seek (unix_stream * s, gfc_offset offset)
667 {
668
669   if (s->file_length == -1)
670     return SUCCESS;
671
672   if (s->physical_offset == offset) /* Are we lucky and avoid syscall?  */
673     {
674       s->logical_offset = offset;
675       return SUCCESS;
676     }
677
678   if (lseek (s->fd, offset, SEEK_SET) >= 0)
679     {
680       s->physical_offset = s->logical_offset = offset;
681       s->active = 0;
682       return SUCCESS;
683     }
684
685   return FAILURE;
686 }
687
688
689 /* truncate_file()-- Given a unit, truncate the file at the current
690  * position.  Sets the physical location to the new end of the file.
691  * Returns nonzero on error. */
692
693 static try
694 fd_truncate (unix_stream * s)
695 {
696   /* Non-seekable files, like terminals and fifo's fail the lseek so just
697      return success, there is nothing to truncate.  If its not a pipe there
698      is a real problem.  */
699   if (lseek (s->fd, s->logical_offset, SEEK_SET) == -1)
700     {
701       if (errno == ESPIPE)
702         return SUCCESS;
703       else
704         return FAILURE;
705     }
706
707   /* Using ftruncate on a seekable special file (like /dev/null)
708      is undefined, so we treat it as if the ftruncate succeeded.  */
709   if (!s->special_file
710       && (
711 #ifdef HAVE_FTRUNCATE
712           ftruncate (s->fd, s->logical_offset) != 0
713 #elif defined HAVE_CHSIZE
714           chsize (s->fd, s->logical_offset) != 0
715 #else
716           /* If we have neither, always fail and exit, noisily.  */
717           runtime_error ("required ftruncate or chsize support not present"), 1
718 #endif
719           ))
720     {
721       /* The truncation failed and we need to handle this gracefully.
722          The file length remains the same, but the file-descriptor
723          offset needs adjustment per the successful lseek above.
724          (Similarly, the contents of the buffer isn't valid anymore.)
725          A ftruncate call does not affect the physical (file-descriptor)
726          offset, according to the ftruncate manual, so neither should a
727          failed call.  */
728       s->physical_offset = s->logical_offset;
729       s->active = 0;
730       return FAILURE;
731     }
732
733   s->physical_offset = s->file_length = s->logical_offset;
734   s->active = 0;
735   return SUCCESS;
736 }
737
738
739 /* Similar to memset(), but operating on a stream instead of a string.
740    Takes care of not using too much memory.  */
741
742 static try
743 fd_sset (unix_stream * s, int c, size_t n)
744 {
745   size_t bytes_left;
746   int trans;
747   void *p;
748
749   bytes_left = n;
750
751   while (bytes_left > 0)
752     {
753       /* memset() in chunks of BUFFER_SIZE.  */
754       trans = (bytes_left < BUFFER_SIZE) ? bytes_left : BUFFER_SIZE;
755
756       p = fd_alloc_w_at (s, &trans, -1);
757       if (p)
758           memset (p, c, trans);
759       else
760         return FAILURE;
761
762       bytes_left -= trans;
763     }
764
765   return SUCCESS;
766 }
767
768
769 /* Stream read function. Avoids using a buffer for big reads. The
770    interface is like POSIX read(), but the nbytes argument is a
771    pointer; on return it contains the number of bytes written. The
772    function return value is the status indicator (0 for success).  */
773
774 static int
775 fd_read (unix_stream * s, void * buf, size_t * nbytes)
776 {
777   void *p;
778   int tmp, status;
779
780   if (*nbytes < BUFFER_SIZE && !s->unbuffered)
781     {
782       tmp = *nbytes;
783       p = fd_alloc_r_at (s, &tmp, -1);
784       if (p)
785         {
786           *nbytes = tmp;
787           memcpy (buf, p, *nbytes);
788           return 0;
789         }
790       else
791         {
792           *nbytes = 0;
793           return errno;
794         }
795     }
796
797   /* If the request is bigger than BUFFER_SIZE we flush the buffers
798      and read directly.  */
799   if (fd_flush (s) == FAILURE)
800     {
801       *nbytes = 0;
802       return errno;
803     }
804
805   if (is_seekable ((stream *) s) && fd_seek (s, s->logical_offset) == FAILURE)
806     {
807       *nbytes = 0;
808       return errno;
809     }
810
811   status = do_read (s, buf, nbytes);
812   reset_stream (s, *nbytes);
813   return status;
814 }
815
816
817 /* Stream write function. Avoids using a buffer for big writes. The
818    interface is like POSIX write(), but the nbytes argument is a
819    pointer; on return it contains the number of bytes written. The
820    function return value is the status indicator (0 for success).  */
821
822 static int
823 fd_write (unix_stream * s, const void * buf, size_t * nbytes)
824 {
825   void *p;
826   int tmp, status;
827
828   if (*nbytes < BUFFER_SIZE && !s->unbuffered)
829     {
830       tmp = *nbytes;
831       p = fd_alloc_w_at (s, &tmp, -1);
832       if (p)
833         {
834           *nbytes = tmp;
835           memcpy (p, buf, *nbytes);
836           return 0;
837         }
838       else
839         {
840           *nbytes = 0;
841           return errno;
842         }
843     }
844
845   /* If the request is bigger than BUFFER_SIZE we flush the buffers
846      and write directly.  */
847   if (fd_flush (s) == FAILURE)
848     {
849       *nbytes = 0;
850       return errno;
851     }
852
853   if (is_seekable ((stream *) s) && fd_seek (s, s->logical_offset) == FAILURE)
854     {
855       *nbytes = 0;
856       return errno;
857     }
858
859   status =  do_write (s, buf, nbytes);
860   reset_stream (s, *nbytes);
861   return status;
862 }
863
864
865 static try
866 fd_close (unix_stream * s)
867 {
868   if (fd_flush (s) == FAILURE)
869     return FAILURE;
870
871   if (s->buffer != NULL && s->buffer != s->small_buffer)
872     free_mem (s->buffer);
873
874   if (s->fd != STDOUT_FILENO && s->fd != STDERR_FILENO)
875     {
876       if (close (s->fd) < 0)
877         return FAILURE;
878     }
879
880   free_mem (s);
881
882   return SUCCESS;
883 }
884
885
886 static void
887 fd_open (unix_stream * s)
888 {
889   if (isatty (s->fd))
890     s->unbuffered = 1;
891
892   s->st.alloc_r_at = (void *) fd_alloc_r_at;
893   s->st.alloc_w_at = (void *) fd_alloc_w_at;
894   s->st.sfree = (void *) fd_sfree;
895   s->st.close = (void *) fd_close;
896   s->st.seek = (void *) fd_seek;
897   s->st.trunc = (void *) fd_truncate;
898   s->st.read = (void *) fd_read;
899   s->st.write = (void *) fd_write;
900   s->st.set = (void *) fd_sset;
901
902   s->buffer = NULL;
903 }
904
905
906
907
908 /*********************************************************************
909   memory stream functions - These are used for internal files
910
911   The idea here is that a single stream structure is created and all
912   requests must be satisfied from it.  The location and size of the
913   buffer is the character variable supplied to the READ or WRITE
914   statement.
915
916 *********************************************************************/
917
918
919 static char *
920 mem_alloc_r_at (int_stream * s, int *len, gfc_offset where)
921 {
922   gfc_offset n;
923
924   if (where == -1)
925     where = s->logical_offset;
926
927   if (where < s->buffer_offset || where > s->buffer_offset + s->active)
928     return NULL;
929
930   s->logical_offset = where + *len;
931
932   n = s->buffer_offset + s->active - where;
933   if (*len > n)
934     *len = n;
935
936   return s->buffer + (where - s->buffer_offset);
937 }
938
939
940 static char *
941 mem_alloc_w_at (int_stream * s, int *len, gfc_offset where)
942 {
943   gfc_offset m;
944
945   assert (*len >= 0);  /* Negative values not allowed. */
946   
947   if (where == -1)
948     where = s->logical_offset;
949
950   m = where + *len;
951
952   if (where < s->buffer_offset)
953     return NULL;
954
955   if (m > s->file_length)
956     return NULL;
957
958   s->logical_offset = m;
959
960   return s->buffer + (where - s->buffer_offset);
961 }
962
963
964 /* Stream read function for internal units. This is not actually used
965    at the moment, as all internal IO is formatted and the formatted IO
966    routines use mem_alloc_r_at.  */
967
968 static int
969 mem_read (int_stream * s, void * buf, size_t * nbytes)
970 {
971   void *p;
972   int tmp;
973
974   tmp = *nbytes;
975   p = mem_alloc_r_at (s, &tmp, -1);
976   if (p)
977     {
978       *nbytes = tmp;
979       memcpy (buf, p, *nbytes);
980       return 0;
981     }
982   else
983     {
984       *nbytes = 0;
985       return errno;
986     }
987 }
988
989
990 /* Stream write function for internal units. This is not actually used
991    at the moment, as all internal IO is formatted and the formatted IO
992    routines use mem_alloc_w_at.  */
993
994 static int
995 mem_write (int_stream * s, const void * buf, size_t * nbytes)
996 {
997   void *p;
998   int tmp;
999
1000   errno = 0;
1001
1002   tmp = *nbytes;
1003   p = mem_alloc_w_at (s, &tmp, -1);
1004   if (p)
1005     {
1006       *nbytes = tmp;
1007       memcpy (p, buf, *nbytes);
1008       return 0;
1009     }
1010   else
1011     {
1012       *nbytes = 0;
1013       return errno;
1014     }
1015 }
1016
1017
1018 static int
1019 mem_seek (int_stream * s, gfc_offset offset)
1020 {
1021   if (offset > s->file_length)
1022     {
1023       errno = ESPIPE;
1024       return FAILURE;
1025     }
1026
1027   s->logical_offset = offset;
1028   return SUCCESS;
1029 }
1030
1031
1032 static try
1033 mem_set (int_stream * s, int c, size_t n)
1034 {
1035   void *p;
1036   int len;
1037
1038   len = n;
1039   
1040   p = mem_alloc_w_at (s, &len, -1);
1041   if (p)
1042     {
1043       memset (p, c, len);
1044       return SUCCESS;
1045     }
1046   else
1047     return FAILURE;
1048 }
1049
1050
1051 static int
1052 mem_truncate (int_stream * s __attribute__ ((unused)))
1053 {
1054   return SUCCESS;
1055 }
1056
1057
1058 static try
1059 mem_close (int_stream * s)
1060 {
1061   if (s != NULL)
1062     free_mem (s);
1063
1064   return SUCCESS;
1065 }
1066
1067
1068 static try
1069 mem_sfree (int_stream * s __attribute__ ((unused)))
1070 {
1071   return SUCCESS;
1072 }
1073
1074
1075
1076 /*********************************************************************
1077   Public functions -- A reimplementation of this module needs to
1078   define functional equivalents of the following.
1079 *********************************************************************/
1080
1081 /* empty_internal_buffer()-- Zero the buffer of Internal file */
1082
1083 void
1084 empty_internal_buffer(stream *strm)
1085 {
1086   int_stream * s = (int_stream *) strm;
1087   memset(s->buffer, ' ', s->file_length);
1088 }
1089
1090 /* open_internal()-- Returns a stream structure from an internal file */
1091
1092 stream *
1093 open_internal (char *base, int length, gfc_offset offset)
1094 {
1095   int_stream *s;
1096
1097   s = get_mem (sizeof (int_stream));
1098   memset (s, '\0', sizeof (int_stream));
1099
1100   s->buffer = base;
1101   s->buffer_offset = offset;
1102
1103   s->logical_offset = 0;
1104   s->active = s->file_length = length;
1105
1106   s->st.alloc_r_at = (void *) mem_alloc_r_at;
1107   s->st.alloc_w_at = (void *) mem_alloc_w_at;
1108   s->st.sfree = (void *) mem_sfree;
1109   s->st.close = (void *) mem_close;
1110   s->st.seek = (void *) mem_seek;
1111   s->st.trunc = (void *) mem_truncate;
1112   s->st.read = (void *) mem_read;
1113   s->st.write = (void *) mem_write;
1114   s->st.set = (void *) mem_set;
1115
1116   return (stream *) s;
1117 }
1118
1119
1120 /* fd_to_stream()-- Given an open file descriptor, build a stream
1121  * around it. */
1122
1123 static stream *
1124 fd_to_stream (int fd, int prot)
1125 {
1126   struct stat statbuf;
1127   unix_stream *s;
1128
1129   s = get_mem (sizeof (unix_stream));
1130   memset (s, '\0', sizeof (unix_stream));
1131
1132   s->fd = fd;
1133   s->buffer_offset = 0;
1134   s->physical_offset = 0;
1135   s->logical_offset = 0;
1136   s->prot = prot;
1137
1138   /* Get the current length of the file. */
1139
1140   fstat (fd, &statbuf);
1141
1142   if (lseek (fd, 0, SEEK_CUR) == (off_t) -1)
1143     s->file_length = -1;
1144   else
1145     s->file_length = S_ISREG (statbuf.st_mode) ? statbuf.st_size : -1;
1146
1147   s->special_file = !S_ISREG (statbuf.st_mode);
1148
1149   fd_open (s);
1150
1151   return (stream *) s;
1152 }
1153
1154
1155 /* Given the Fortran unit number, convert it to a C file descriptor.  */
1156
1157 int
1158 unit_to_fd (int unit)
1159 {
1160   gfc_unit *us;
1161   int fd;
1162
1163   us = find_unit (unit);
1164   if (us == NULL)
1165     return -1;
1166
1167   fd = ((unix_stream *) us->s)->fd;
1168   unlock_unit (us);
1169   return fd;
1170 }
1171
1172
1173 /* unpack_filename()-- Given a fortran string and a pointer to a
1174  * buffer that is PATH_MAX characters, convert the fortran string to a
1175  * C string in the buffer.  Returns nonzero if this is not possible.  */
1176
1177 int
1178 unpack_filename (char *cstring, const char *fstring, int len)
1179 {
1180   len = fstrlen (fstring, len);
1181   if (len >= PATH_MAX)
1182     return 1;
1183
1184   memmove (cstring, fstring, len);
1185   cstring[len] = '\0';
1186
1187   return 0;
1188 }
1189
1190
1191 /* tempfile()-- Generate a temporary filename for a scratch file and
1192  * open it.  mkstemp() opens the file for reading and writing, but the
1193  * library mode prevents anything that is not allowed.  The descriptor
1194  * is returned, which is -1 on error.  The template is pointed to by 
1195  * opp->file, which is copied into the unit structure
1196  * and freed later. */
1197
1198 static int
1199 tempfile (st_parameter_open *opp)
1200 {
1201   const char *tempdir;
1202   char *template;
1203   int fd;
1204
1205   tempdir = getenv ("GFORTRAN_TMPDIR");
1206   if (tempdir == NULL)
1207     tempdir = getenv ("TMP");
1208   if (tempdir == NULL)
1209     tempdir = getenv ("TEMP");
1210   if (tempdir == NULL)
1211     tempdir = DEFAULT_TEMPDIR;
1212
1213   template = get_mem (strlen (tempdir) + 20);
1214
1215   sprintf (template, "%s/gfortrantmpXXXXXX", tempdir);
1216
1217 #ifdef HAVE_MKSTEMP
1218
1219   fd = mkstemp (template);
1220
1221 #else /* HAVE_MKSTEMP */
1222
1223   if (mktemp (template))
1224     do
1225 #if defined(HAVE_CRLF) && defined(O_BINARY)
1226       fd = open (template, O_RDWR | O_CREAT | O_EXCL | O_BINARY,
1227                  S_IREAD | S_IWRITE);
1228 #else
1229       fd = open (template, O_RDWR | O_CREAT | O_EXCL, S_IREAD | S_IWRITE);
1230 #endif
1231     while (!(fd == -1 && errno == EEXIST) && mktemp (template));
1232   else
1233     fd = -1;
1234
1235 #endif /* HAVE_MKSTEMP */
1236
1237   if (fd < 0)
1238     free_mem (template);
1239   else
1240     {
1241       opp->file = template;
1242       opp->file_len = strlen (template);        /* Don't include trailing nul */
1243     }
1244
1245   return fd;
1246 }
1247
1248
1249 /* regular_file()-- Open a regular file.
1250  * Change flags->action if it is ACTION_UNSPECIFIED on entry,
1251  * unless an error occurs.
1252  * Returns the descriptor, which is less than zero on error. */
1253
1254 static int
1255 regular_file (st_parameter_open *opp, unit_flags *flags)
1256 {
1257   char path[PATH_MAX + 1];
1258   int mode;
1259   int rwflag;
1260   int crflag;
1261   int fd;
1262
1263   if (unpack_filename (path, opp->file, opp->file_len))
1264     {
1265       errno = ENOENT;           /* Fake an OS error */
1266       return -1;
1267     }
1268
1269   rwflag = 0;
1270
1271   switch (flags->action)
1272     {
1273     case ACTION_READ:
1274       rwflag = O_RDONLY;
1275       break;
1276
1277     case ACTION_WRITE:
1278       rwflag = O_WRONLY;
1279       break;
1280
1281     case ACTION_READWRITE:
1282     case ACTION_UNSPECIFIED:
1283       rwflag = O_RDWR;
1284       break;
1285
1286     default:
1287       internal_error (&opp->common, "regular_file(): Bad action");
1288     }
1289
1290   switch (flags->status)
1291     {
1292     case STATUS_NEW:
1293       crflag = O_CREAT | O_EXCL;
1294       break;
1295
1296     case STATUS_OLD:            /* open will fail if the file does not exist*/
1297       crflag = 0;
1298       break;
1299
1300     case STATUS_UNKNOWN:
1301     case STATUS_SCRATCH:
1302       crflag = O_CREAT;
1303       break;
1304
1305     case STATUS_REPLACE:
1306       crflag = O_CREAT | O_TRUNC;
1307       break;
1308
1309     default:
1310       internal_error (&opp->common, "regular_file(): Bad status");
1311     }
1312
1313   /* rwflag |= O_LARGEFILE; */
1314
1315 #if defined(HAVE_CRLF) && defined(O_BINARY)
1316   crflag |= O_BINARY;
1317 #endif
1318
1319   mode = S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH;
1320   fd = open (path, rwflag | crflag, mode);
1321   if (flags->action != ACTION_UNSPECIFIED)
1322     return fd;
1323
1324   if (fd >= 0)
1325     {
1326       flags->action = ACTION_READWRITE;
1327       return fd;
1328     }
1329   if (errno != EACCES && errno != EROFS)
1330      return fd;
1331
1332   /* retry for read-only access */
1333   rwflag = O_RDONLY;
1334   fd = open (path, rwflag | crflag, mode);
1335   if (fd >=0)
1336     {
1337       flags->action = ACTION_READ;
1338       return fd;               /* success */
1339     }
1340   
1341   if (errno != EACCES)
1342     return fd;                 /* failure */
1343
1344   /* retry for write-only access */
1345   rwflag = O_WRONLY;
1346   fd = open (path, rwflag | crflag, mode);
1347   if (fd >=0)
1348     {
1349       flags->action = ACTION_WRITE;
1350       return fd;               /* success */
1351     }
1352   return fd;                   /* failure */
1353 }
1354
1355
1356 /* open_external()-- Open an external file, unix specific version.
1357  * Change flags->action if it is ACTION_UNSPECIFIED on entry.
1358  * Returns NULL on operating system error. */
1359
1360 stream *
1361 open_external (st_parameter_open *opp, unit_flags *flags)
1362 {
1363   int fd, prot;
1364
1365   if (flags->status == STATUS_SCRATCH)
1366     {
1367       fd = tempfile (opp);
1368       if (flags->action == ACTION_UNSPECIFIED)
1369         flags->action = ACTION_READWRITE;
1370
1371 #if HAVE_UNLINK_OPEN_FILE
1372       /* We can unlink scratch files now and it will go away when closed. */
1373       if (fd >= 0)
1374         unlink (opp->file);
1375 #endif
1376     }
1377   else
1378     {
1379       /* regular_file resets flags->action if it is ACTION_UNSPECIFIED and
1380        * if it succeeds */
1381       fd = regular_file (opp, flags);
1382     }
1383
1384   if (fd < 0)
1385     return NULL;
1386   fd = fix_fd (fd);
1387
1388   switch (flags->action)
1389     {
1390     case ACTION_READ:
1391       prot = PROT_READ;
1392       break;
1393
1394     case ACTION_WRITE:
1395       prot = PROT_WRITE;
1396       break;
1397
1398     case ACTION_READWRITE:
1399       prot = PROT_READ | PROT_WRITE;
1400       break;
1401
1402     default:
1403       internal_error (&opp->common, "open_external(): Bad action");
1404     }
1405
1406   return fd_to_stream (fd, prot);
1407 }
1408
1409
1410 /* input_stream()-- Return a stream pointer to the default input stream.
1411  * Called on initialization. */
1412
1413 stream *
1414 input_stream (void)
1415 {
1416   return fd_to_stream (STDIN_FILENO, PROT_READ);
1417 }
1418
1419
1420 /* output_stream()-- Return a stream pointer to the default output stream.
1421  * Called on initialization. */
1422
1423 stream *
1424 output_stream (void)
1425 {
1426   stream * s;
1427
1428 #if defined(HAVE_CRLF) && defined(HAVE_SETMODE)
1429   setmode (STDOUT_FILENO, O_BINARY);
1430 #endif
1431
1432   s = fd_to_stream (STDOUT_FILENO, PROT_WRITE);
1433   if (options.unbuffered_preconnected)
1434     ((unix_stream *) s)->unbuffered = 1;
1435   return s;
1436 }
1437
1438
1439 /* error_stream()-- Return a stream pointer to the default error stream.
1440  * Called on initialization. */
1441
1442 stream *
1443 error_stream (void)
1444 {
1445   stream * s;
1446
1447 #if defined(HAVE_CRLF) && defined(HAVE_SETMODE)
1448   setmode (STDERR_FILENO, O_BINARY);
1449 #endif
1450
1451   s = fd_to_stream (STDERR_FILENO, PROT_WRITE);
1452   if (options.unbuffered_preconnected)
1453     ((unix_stream *) s)->unbuffered = 1;
1454   return s;
1455 }
1456
1457
1458 /* st_vprintf()-- vprintf function for error output.  To avoid buffer
1459    overruns, we limit the length of the buffer to ST_VPRINTF_SIZE.  2k
1460    is big enough to completely fill a 80x25 terminal, so it shuld be
1461    OK.  We use a direct write() because it is simpler and least likely
1462    to be clobbered by memory corruption.  Writing an error message
1463    longer than that is an error.  */
1464
1465 #define ST_VPRINTF_SIZE 2048
1466
1467 int
1468 st_vprintf (const char *format, va_list ap)
1469 {
1470   static char buffer[ST_VPRINTF_SIZE];
1471   int written;
1472   int fd;
1473
1474   fd = options.use_stderr ? STDERR_FILENO : STDOUT_FILENO;
1475 #ifdef HAVE_VSNPRINTF
1476   written = vsnprintf(buffer, ST_VPRINTF_SIZE, format, ap);
1477 #else
1478   written = vsprintf(buffer, format, ap);
1479
1480   if (written >= ST_VPRINTF_SIZE-1)
1481     {
1482       /* The error message was longer than our buffer.  Ouch.  Because
1483          we may have messed up things badly, report the error and
1484          quit.  */
1485 #define ERROR_MESSAGE "Internal error: buffer overrun in st_vprintf()\n"
1486       write (fd, buffer, ST_VPRINTF_SIZE-1);
1487       write (fd, ERROR_MESSAGE, strlen(ERROR_MESSAGE));
1488       sys_exit(2);
1489 #undef ERROR_MESSAGE
1490
1491     }
1492 #endif
1493
1494   written = write (fd, buffer, written);
1495   return written;
1496 }
1497
1498 /* st_printf()-- printf() function for error output.  This just calls
1499    st_vprintf() to do the actual work.  */
1500
1501 int
1502 st_printf (const char *format, ...)
1503 {
1504   int written;
1505   va_list ap;
1506   va_start (ap, format);
1507   written = st_vprintf(format, ap);
1508   va_end (ap);
1509   return written;
1510 }
1511
1512
1513 /* compare_file_filename()-- Given an open stream and a fortran string
1514  * that is a filename, figure out if the file is the same as the
1515  * filename. */
1516
1517 int
1518 compare_file_filename (gfc_unit *u, const char *name, int len)
1519 {
1520   char path[PATH_MAX + 1];
1521   struct stat st1;
1522 #ifdef HAVE_WORKING_STAT
1523   struct stat st2;
1524 #else
1525 # ifdef __MINGW32__
1526   uint64_t id1, id2;
1527 # endif
1528 #endif
1529
1530   if (unpack_filename (path, name, len))
1531     return 0;                   /* Can't be the same */
1532
1533   /* If the filename doesn't exist, then there is no match with the
1534    * existing file. */
1535
1536   if (stat (path, &st1) < 0)
1537     return 0;
1538
1539 #ifdef HAVE_WORKING_STAT
1540   fstat (((unix_stream *) (u->s))->fd, &st2);
1541   return (st1.st_dev == st2.st_dev) && (st1.st_ino == st2.st_ino);
1542 #else
1543
1544 # ifdef __MINGW32__
1545   /* We try to match files by a unique ID.  On some filesystems (network
1546      fs and FAT), we can't generate this unique ID, and will simply compare
1547      filenames.  */
1548   id1 = id_from_path (path);
1549   id2 = id_from_fd (((unix_stream *) (u->s))->fd);
1550   if (id1 || id2)
1551     return (id1 == id2);
1552 # endif
1553
1554   if (len != u->file_len)
1555     return 0;
1556   return (memcmp(path, u->file, len) == 0);
1557 #endif
1558 }
1559
1560
1561 #ifdef HAVE_WORKING_STAT
1562 # define FIND_FILE0_DECL struct stat *st
1563 # define FIND_FILE0_ARGS st
1564 #else
1565 # define FIND_FILE0_DECL uint64_t id, const char *file, gfc_charlen_type file_len
1566 # define FIND_FILE0_ARGS id, file, file_len
1567 #endif
1568
1569 /* find_file0()-- Recursive work function for find_file() */
1570
1571 static gfc_unit *
1572 find_file0 (gfc_unit *u, FIND_FILE0_DECL)
1573 {
1574   gfc_unit *v;
1575 #if defined(__MINGW32__) && !HAVE_WORKING_STAT
1576   uint64_t id1;
1577 #endif
1578
1579   if (u == NULL)
1580     return NULL;
1581
1582 #ifdef HAVE_WORKING_STAT
1583   if (u->s != NULL
1584       && fstat (((unix_stream *) u->s)->fd, &st[1]) >= 0 &&
1585       st[0].st_dev == st[1].st_dev && st[0].st_ino == st[1].st_ino)
1586     return u;
1587 #else
1588 # ifdef __MINGW32__ 
1589   if (u->s && ((id1 = id_from_fd (((unix_stream *) u->s)->fd)) || id1))
1590     {
1591       if (id == id1)
1592         return u;
1593     }
1594   else
1595 # endif
1596     if (compare_string (u->file_len, u->file, file_len, file) == 0)
1597       return u;
1598 #endif
1599
1600   v = find_file0 (u->left, FIND_FILE0_ARGS);
1601   if (v != NULL)
1602     return v;
1603
1604   v = find_file0 (u->right, FIND_FILE0_ARGS);
1605   if (v != NULL)
1606     return v;
1607
1608   return NULL;
1609 }
1610
1611
1612 /* find_file()-- Take the current filename and see if there is a unit
1613  * that has the file already open.  Returns a pointer to the unit if so. */
1614
1615 gfc_unit *
1616 find_file (const char *file, gfc_charlen_type file_len)
1617 {
1618   char path[PATH_MAX + 1];
1619   struct stat st[2];
1620   gfc_unit *u;
1621   uint64_t id;
1622
1623   if (unpack_filename (path, file, file_len))
1624     return NULL;
1625
1626   if (stat (path, &st[0]) < 0)
1627     return NULL;
1628
1629 #if defined(__MINGW32__) && !HAVE_WORKING_STAT
1630   id = id_from_path (path);
1631 #else
1632   id = 0;
1633 #endif
1634
1635   __gthread_mutex_lock (&unit_lock);
1636 retry:
1637   u = find_file0 (unit_root, FIND_FILE0_ARGS);
1638   if (u != NULL)
1639     {
1640       /* Fast path.  */
1641       if (! __gthread_mutex_trylock (&u->lock))
1642         {
1643           /* assert (u->closed == 0); */
1644           __gthread_mutex_unlock (&unit_lock);
1645           return u;
1646         }
1647
1648       inc_waiting_locked (u);
1649     }
1650   __gthread_mutex_unlock (&unit_lock);
1651   if (u != NULL)
1652     {
1653       __gthread_mutex_lock (&u->lock);
1654       if (u->closed)
1655         {
1656           __gthread_mutex_lock (&unit_lock);
1657           __gthread_mutex_unlock (&u->lock);
1658           if (predec_waiting_locked (u) == 0)
1659             free_mem (u);
1660           goto retry;
1661         }
1662
1663       dec_waiting_unlocked (u);
1664     }
1665   return u;
1666 }
1667
1668 static gfc_unit *
1669 flush_all_units_1 (gfc_unit *u, int min_unit)
1670 {
1671   while (u != NULL)
1672     {
1673       if (u->unit_number > min_unit)
1674         {
1675           gfc_unit *r = flush_all_units_1 (u->left, min_unit);
1676           if (r != NULL)
1677             return r;
1678         }
1679       if (u->unit_number >= min_unit)
1680         {
1681           if (__gthread_mutex_trylock (&u->lock))
1682             return u;
1683           if (u->s)
1684             flush (u->s);
1685           __gthread_mutex_unlock (&u->lock);
1686         }
1687       u = u->right;
1688     }
1689   return NULL;
1690 }
1691
1692 void
1693 flush_all_units (void)
1694 {
1695   gfc_unit *u;
1696   int min_unit = 0;
1697
1698   __gthread_mutex_lock (&unit_lock);
1699   do
1700     {
1701       u = flush_all_units_1 (unit_root, min_unit);
1702       if (u != NULL)
1703         inc_waiting_locked (u);
1704       __gthread_mutex_unlock (&unit_lock);
1705       if (u == NULL)
1706         return;
1707
1708       __gthread_mutex_lock (&u->lock);
1709
1710       min_unit = u->unit_number + 1;
1711
1712       if (u->closed == 0)
1713         {
1714           flush (u->s);
1715           __gthread_mutex_lock (&unit_lock);
1716           __gthread_mutex_unlock (&u->lock);
1717           (void) predec_waiting_locked (u);
1718         }
1719       else
1720         {
1721           __gthread_mutex_lock (&unit_lock);
1722           __gthread_mutex_unlock (&u->lock);
1723           if (predec_waiting_locked (u) == 0)
1724             free_mem (u);
1725         }
1726     }
1727   while (1);
1728 }
1729
1730
1731 /* stream_at_bof()-- Returns nonzero if the stream is at the beginning
1732  * of the file. */
1733
1734 int
1735 stream_at_bof (stream * s)
1736 {
1737   unix_stream *us;
1738
1739   if (!is_seekable (s))
1740     return 0;
1741
1742   us = (unix_stream *) s;
1743
1744   return us->logical_offset == 0;
1745 }
1746
1747
1748 /* stream_at_eof()-- Returns nonzero if the stream is at the end
1749  * of the file. */
1750
1751 int
1752 stream_at_eof (stream * s)
1753 {
1754   unix_stream *us;
1755
1756   if (!is_seekable (s))
1757     return 0;
1758
1759   us = (unix_stream *) s;
1760
1761   return us->logical_offset == us->dirty_offset;
1762 }
1763
1764
1765 /* delete_file()-- Given a unit structure, delete the file associated
1766  * with the unit.  Returns nonzero if something went wrong. */
1767
1768 int
1769 delete_file (gfc_unit * u)
1770 {
1771   char path[PATH_MAX + 1];
1772
1773   if (unpack_filename (path, u->file, u->file_len))
1774     {                           /* Shouldn't be possible */
1775       errno = ENOENT;
1776       return 1;
1777     }
1778
1779   return unlink (path);
1780 }
1781
1782
1783 /* file_exists()-- Returns nonzero if the current filename exists on
1784  * the system */
1785
1786 int
1787 file_exists (const char *file, gfc_charlen_type file_len)
1788 {
1789   char path[PATH_MAX + 1];
1790   struct stat statbuf;
1791
1792   if (unpack_filename (path, file, file_len))
1793     return 0;
1794
1795   if (stat (path, &statbuf) < 0)
1796     return 0;
1797
1798   return 1;
1799 }
1800
1801
1802
1803 static const char yes[] = "YES", no[] = "NO", unknown[] = "UNKNOWN";
1804
1805 /* inquire_sequential()-- Given a fortran string, determine if the
1806  * file is suitable for sequential access.  Returns a C-style
1807  * string. */
1808
1809 const char *
1810 inquire_sequential (const char *string, int len)
1811 {
1812   char path[PATH_MAX + 1];
1813   struct stat statbuf;
1814
1815   if (string == NULL ||
1816       unpack_filename (path, string, len) || stat (path, &statbuf) < 0)
1817     return unknown;
1818
1819   if (S_ISREG (statbuf.st_mode) ||
1820       S_ISCHR (statbuf.st_mode) || S_ISFIFO (statbuf.st_mode))
1821     return unknown;
1822
1823   if (S_ISDIR (statbuf.st_mode) || S_ISBLK (statbuf.st_mode))
1824     return no;
1825
1826   return unknown;
1827 }
1828
1829
1830 /* inquire_direct()-- Given a fortran string, determine if the file is
1831  * suitable for direct access.  Returns a C-style string. */
1832
1833 const char *
1834 inquire_direct (const char *string, int len)
1835 {
1836   char path[PATH_MAX + 1];
1837   struct stat statbuf;
1838
1839   if (string == NULL ||
1840       unpack_filename (path, string, len) || stat (path, &statbuf) < 0)
1841     return unknown;
1842
1843   if (S_ISREG (statbuf.st_mode) || S_ISBLK (statbuf.st_mode))
1844     return unknown;
1845
1846   if (S_ISDIR (statbuf.st_mode) ||
1847       S_ISCHR (statbuf.st_mode) || S_ISFIFO (statbuf.st_mode))
1848     return no;
1849
1850   return unknown;
1851 }
1852
1853
1854 /* inquire_formatted()-- Given a fortran string, determine if the file
1855  * is suitable for formatted form.  Returns a C-style string. */
1856
1857 const char *
1858 inquire_formatted (const char *string, int len)
1859 {
1860   char path[PATH_MAX + 1];
1861   struct stat statbuf;
1862
1863   if (string == NULL ||
1864       unpack_filename (path, string, len) || stat (path, &statbuf) < 0)
1865     return unknown;
1866
1867   if (S_ISREG (statbuf.st_mode) ||
1868       S_ISBLK (statbuf.st_mode) ||
1869       S_ISCHR (statbuf.st_mode) || S_ISFIFO (statbuf.st_mode))
1870     return unknown;
1871
1872   if (S_ISDIR (statbuf.st_mode))
1873     return no;
1874
1875   return unknown;
1876 }
1877
1878
1879 /* inquire_unformatted()-- Given a fortran string, determine if the file
1880  * is suitable for unformatted form.  Returns a C-style string. */
1881
1882 const char *
1883 inquire_unformatted (const char *string, int len)
1884 {
1885   return inquire_formatted (string, len);
1886 }
1887
1888
1889 #ifndef HAVE_ACCESS
1890
1891 #ifndef W_OK
1892 #define W_OK 2
1893 #endif
1894
1895 #ifndef R_OK
1896 #define R_OK 4
1897 #endif
1898
1899 /* Fallback implementation of access() on systems that don't have it.
1900    Only modes R_OK and W_OK are used in this file.  */
1901
1902 static int
1903 fallback_access (const char *path, int mode)
1904 {
1905   if ((mode & R_OK) && open (path, O_RDONLY) < 0)
1906     return -1;
1907
1908   if ((mode & W_OK) && open (path, O_WRONLY) < 0)
1909     return -1;
1910
1911   return 0;
1912 }
1913
1914 #undef access
1915 #define access fallback_access
1916 #endif
1917
1918
1919 /* inquire_access()-- Given a fortran string, determine if the file is
1920  * suitable for access. */
1921
1922 static const char *
1923 inquire_access (const char *string, int len, int mode)
1924 {
1925   char path[PATH_MAX + 1];
1926
1927   if (string == NULL || unpack_filename (path, string, len) ||
1928       access (path, mode) < 0)
1929     return no;
1930
1931   return yes;
1932 }
1933
1934
1935 /* inquire_read()-- Given a fortran string, determine if the file is
1936  * suitable for READ access. */
1937
1938 const char *
1939 inquire_read (const char *string, int len)
1940 {
1941   return inquire_access (string, len, R_OK);
1942 }
1943
1944
1945 /* inquire_write()-- Given a fortran string, determine if the file is
1946  * suitable for READ access. */
1947
1948 const char *
1949 inquire_write (const char *string, int len)
1950 {
1951   return inquire_access (string, len, W_OK);
1952 }
1953
1954
1955 /* inquire_readwrite()-- Given a fortran string, determine if the file is
1956  * suitable for read and write access. */
1957
1958 const char *
1959 inquire_readwrite (const char *string, int len)
1960 {
1961   return inquire_access (string, len, R_OK | W_OK);
1962 }
1963
1964
1965 /* file_length()-- Return the file length in bytes, -1 if unknown */
1966
1967 gfc_offset
1968 file_length (stream * s)
1969 {
1970   return ((unix_stream *) s)->file_length;
1971 }
1972
1973
1974 /* file_position()-- Return the current position of the file */
1975
1976 gfc_offset
1977 file_position (stream *s)
1978 {
1979   return ((unix_stream *) s)->logical_offset;
1980 }
1981
1982
1983 /* is_seekable()-- Return nonzero if the stream is seekable, zero if
1984  * it is not */
1985
1986 int
1987 is_seekable (stream *s)
1988 {
1989   /* By convention, if file_length == -1, the file is not
1990      seekable.  */
1991   return ((unix_stream *) s)->file_length!=-1;
1992 }
1993
1994
1995 /* is_special()-- Return nonzero if the stream is not a regular file.  */
1996
1997 int
1998 is_special (stream *s)
1999 {
2000   return ((unix_stream *) s)->special_file;
2001 }
2002
2003
2004 try
2005 flush (stream *s)
2006 {
2007   return fd_flush( (unix_stream *) s);
2008 }
2009
2010 int
2011 stream_isatty (stream *s)
2012 {
2013   return isatty (((unix_stream *) s)->fd);
2014 }
2015
2016 char *
2017 stream_ttyname (stream *s __attribute__ ((unused)))
2018 {
2019 #ifdef HAVE_TTYNAME
2020   return ttyname (((unix_stream *) s)->fd);
2021 #else
2022   return NULL;
2023 #endif
2024 }
2025
2026 gfc_offset
2027 stream_offset (stream *s)
2028 {
2029   return (((unix_stream *) s)->logical_offset);
2030 }
2031
2032
2033 /* How files are stored:  This is an operating-system specific issue,
2034    and therefore belongs here.  There are three cases to consider.
2035
2036    Direct Access:
2037       Records are written as block of bytes corresponding to the record
2038       length of the file.  This goes for both formatted and unformatted
2039       records.  Positioning is done explicitly for each data transfer,
2040       so positioning is not much of an issue.
2041
2042    Sequential Formatted:
2043       Records are separated by newline characters.  The newline character
2044       is prohibited from appearing in a string.  If it does, this will be
2045       messed up on the next read.  End of file is also the end of a record.
2046
2047    Sequential Unformatted:
2048       In this case, we are merely copying bytes to and from main storage,
2049       yet we need to keep track of varying record lengths.  We adopt
2050       the solution used by f2c.  Each record contains a pair of length
2051       markers:
2052
2053         Length of record n in bytes
2054         Data of record n
2055         Length of record n in bytes
2056
2057         Length of record n+1 in bytes
2058         Data of record n+1
2059         Length of record n+1 in bytes
2060
2061      The length is stored at the end of a record to allow backspacing to the
2062      previous record.  Between data transfer statements, the file pointer
2063      is left pointing to the first length of the current record.
2064
2065      ENDFILE records are never explicitly stored.
2066
2067 */