   This file documents the GNU C library.

   This is Edition 0.06 DRAFT, last updated 24 October 1994, of `The
GNU C Library Reference Manual', for Version 1.09 Beta.

   Copyright (C) 1993, 1994 Free Software Foundation, Inc.

   Permission is granted to make and distribute verbatim copies of this
manual provided the copyright notice and this permission notice are
preserved on all copies.

   Permission is granted to copy and distribute modified versions of
this manual under the conditions for verbatim copying, provided also
that the section entitled "GNU Library General Public License" is
included exactly as in the original, and provided that the entire
resulting derived work is distributed under the terms of a permission
notice identical to this one.

   Permission is granted to copy and distribute translations of this
manual into another language, under the above conditions for modified
versions, except that the text of the translations of the section
entitled "GNU Library General Public License" must be approved for
accuracy by the Foundation.

Controlling Which Kind of Buffering
-----------------------------------

   After opening a stream (but before any other operations have been
performed on it), you can explicitly specify what kind of buffering you
want it to have using the `setvbuf' function.

   The facilities listed in this section are declared in the header
file `stdio.h'.

 - Function: int setvbuf (FILE *STREAM, char *BUF, int MODE, size_t
          SIZE)
     This function is used to specify that the stream STREAM should
     have the buffering mode MODE, which can be either `_IOFBF' (for
     full buffering), `_IOLBF' (for line buffering), or `_IONBF' (for
     unbuffered input/output).

     If you specify a null pointer as the BUF argument, then `setvbuf'
     allocates a buffer itself using `malloc'.  This buffer will be
     freed when you close the stream.

     Otherwise, BUF should be a character array that can hold at least
     SIZE characters.  You should not free the space for this array as
     long as the stream remains open and this array remains its buffer.
     You should usually either allocate it statically, or `malloc'
     (see Unconstrained Allocation.) the buffer.  Using an
     automatic array is not a good idea unless you close the file
     before exiting the block that declares the array.

     While the array remains a stream buffer, the stream I/O functions
     will use the buffer for their internal purposes.  You shouldn't
     try to access the values in the array directly while the stream is
     using it for buffering.

     The `setvbuf' function returns zero on success, or a nonzero value
     if the value of MODE is not valid or if the request could not be
     honored.

 - Macro: int _IOFBF
     The value of this macro is an integer constant expression that can
     be used as the MODE argument to the `setvbuf' function to specify
     that the stream should be fully buffered.

 - Macro: int _IOLBF
     The value of this macro is an integer constant expression that can
     be used as the MODE argument to the `setvbuf' function to specify
     that the stream should be line buffered.

 - Macro: int _IONBF
     The value of this macro is an integer constant expression that can
     be used as the MODE argument to the `setvbuf' function to specify
     that the stream should be unbuffered.

 - Macro: int BUFSIZ
     The value of this macro is an integer constant expression that is
     good to use for the SIZE argument to `setvbuf'.  This value is
     guaranteed to be at least `256'.

     The value of `BUFSIZ' is chosen on each system so as to make stream
     I/O efficient.  So it is a good idea to use `BUFSIZ' as the size
     for the buffer when you call `setvbuf'.

     Actually, you can get an even better value to use for the buffer
     size by means of the `fstat' system call: it is found in the
     `st_blksize' field of the file attributes.  See Attribute Meanings.

     Sometimes people also use `BUFSIZ' as the allocation size of
     buffers used for related purposes, such as strings used to receive
     a line of input with `fgets' (see Character Input.).  There is
     no particular reason to use `BUFSIZ' for this instead of any other
     integer, except that it might lead to doing I/O in chunks of an
     efficient size.

 - Function: void setbuf (FILE *STREAM, char *BUF)
     If BUF is a null pointer, the effect of this function is
     equivalent to calling `setvbuf' with a MODE argument of `_IONBF'.
     Otherwise, it is equivalent to calling `setvbuf' with BUF, and a
     MODE of `_IOFBF' and a SIZE argument of `BUFSIZ'.

     The `setbuf' function is provided for compatibility with old code;
     use `setvbuf' in all new programs.

 - Function: void setbuffer (FILE *STREAM, char *BUF, size_t SIZE)
     If BUF is a null pointer, this function makes STREAM unbuffered.
     Otherwise, it makes STREAM fully buffered using BUF as the buffer.
     The SIZE argument specifies the length of BUF.

     This function is provided for compatibility with old BSD code.  Use
     `setvbuf' instead.

 - Function: void setlinebuf (FILE *STREAM)
     This function makes STREAM be line buffered, and allocates the
     buffer for you.

     This function is provided for compatibility with old BSD code.  Use
     `setvbuf' instead.

Other Kinds of Streams
======================

   The GNU library provides ways for you to define additional kinds of
streams that do not necessarily correspond to an open file.

   One such type of stream takes input from or writes output to a
string.  These kinds of streams are used internally to implement the
`sprintf' and `sscanf' functions.  You can also create such a stream
explicitly, using the functions described in String Streams.

   More generally, you can define streams that do input/output to
arbitrary objects using functions supplied by your program.  This
protocol is discussed in Custom Streams.

   *Portability Note:* The facilities described in this section are
specific to GNU.  Other systems or C implementations might or might not
provide equivalent functionality.

String Streams
--------------

   The `fmemopen' and `open_memstream' functions allow you to do I/O to
a string or memory buffer.  These facilities are declared in `stdio.h'.

 - Function: FILE * fmemopen (void *BUF, size_t SIZE, const char
          *OPENTYPE)
     This function opens a stream that allows the access specified by
     the OPENTYPE argument, that reads from or writes to the buffer
     specified by the argument BUF.  This array must be at least SIZE
     bytes long.

     If you specify a null pointer as the BUF argument, `fmemopen'
     dynamically allocates (as with `malloc'; see Unconstrained Allocation.)
     an array SIZE bytes long.  This is really only
     useful if you are going to write things to the buffer and then
     read them back in again, because you have no way of actually
     getting a pointer to the buffer (for this, try `open_memstream',
     below).  The buffer is freed when the stream is open.

     The argument OPENTYPE is the same as in `fopen' (see Opening Streams).
     If the OPENTYPE specifies append mode, then the
     initial file position is set to the first null character in the
     buffer.  Otherwise the initial file position is at the beginning
     of the buffer.

     When a stream open for writing is flushed or closed, a null
     character (zero byte) is written at the end of the buffer if it
     fits.  You should add an extra byte to the SIZE argument to
     account for this.  Attempts to write more than SIZE bytes to the
     buffer result in an error.

     For a stream open for reading, null characters (zero bytes) in the
     buffer do not count as "end of file".  Read operations indicate
     end of file only when the file position advances past SIZE bytes.
     So, if you want to read characters from a null-terminated string,
     you should supply the length of the string as the SIZE argument.

   Here is an example of using `fmemopen' to create a stream for
reading from a string:

     #include <stdio.h>

     static char buffer[] = "foobar";

     int
     main (void)
     {
       int ch;
       FILE *stream;

       stream = fmemopen (buffer, strlen (buffer), "r");
       while ((ch = fgetc (stream)) != EOF)
         printf ("Got %c\n", ch);
       fclose (stream);

       return 0;
     }

   This program produces the following output:

     Got f
     Got o
     Got o
     Got b
     Got a
     Got r

 - Function: FILE * open_memstream (char **PTR, size_t *SIZELOC)
     This function opens a stream for writing to a buffer.  The buffer
     is allocated dynamically (as with `malloc'; see Unconstrained Allocation.)
     and grown as necessary.

     When the stream is closed with `fclose' or flushed with `fflush',
     the locations PTR and SIZELOC are updated to contain the pointer
     to the buffer and its size.  The values thus stored remain valid
     only as long as no further output on the stream takes place.  If
     you do more output, you must flush the stream again to store new
     values before you use them again.

     A null character is written at the end of the buffer.  This null
     character is *not* included in the size value stored at SIZELOC.

     You can move the stream's file position with `fseek' (see File Positioning.).
     Moving the file position past the end of the data
     already written fills the intervening space with zeroes.

   Here is an example of using `open_memstream':

     #include <stdio.h>

     int
     main (void)
     {
       char *bp;
       size_t size;
       FILE *stream;

       stream = open_memstream (&bp, &size);
       fprintf (stream, "hello");
       fflush (stream);
       printf ("buf = `%s', size = %d\n", bp, size);
       fprintf (stream, ", world");
       fclose (stream);
       printf ("buf = `%s', size = %d\n", bp, size);

       return 0;
     }

   This program produces the following output:

     buf = `hello', size = 5
     buf = `hello, world', size = 12

Obstack Streams
---------------

   You can open an output stream that puts it data in an obstack.
See Obstacks.

 - Function: FILE * open_obstack_stream (struct obstack *OBSTACK)
     This function opens a stream for writing data into the obstack
     OBSTACK.  This starts an object in the obstack and makes it grow
     as data is written (see Growing Objects.).

     Calling `fflush' on this stream updates the current size of the
     object to match the amount of data that has been written.  After a
     call to `fflush', you can examine the object temporarily.

     You can move the file position of an obstack stream with `fseek'
     (see File Positioning.).  Moving the file position past the
     end of the data written fills the intervening space with zeros.

     To make the object permanent, update the obstack with `fflush', and
     then use `obstack_finish' to finalize the object and get its
     address.  The following write to the stream starts a new object in
     the obstack, and later writes add to that object until you do
     another `fflush' and `obstack_finish'.

     But how do you find out how long the object is?  You can get the
     length in bytes by calling `obstack_object_size' (see Status of an Obstack.),
     or you can null-terminate the object like this:

          obstack_1grow (OBSTACK, 0);

     Whichever one you do, you must do it *before* calling
     `obstack_finish'.  (You can do both if you wish.)

   Here is a sample function that uses `open_obstack_stream':

     char *
     make_message_string (const char *a, int b)
     {
       FILE *stream = open_obstack_stream (&message_obstack);
       output_task (stream);
       fprintf (stream, ": ");
       fprintf (stream, a, b);
       fprintf (stream, "\n");
       fclose (stream);
       obstack_1grow (&message_obstack, 0);
       return obstack_finish (&message_obstack);
     }

Programming Your Own Custom Streams
-----------------------------------

   This section describes how you can make a stream that gets input
from an arbitrary data source or writes output to an arbitrary data sink
programmed by you.  We call these "custom streams".

Custom Streams and Cookies
..........................

   Inside every custom stream is a special object called the "cookie".
This is an object supplied by you which records where to fetch or store
the data read or written.  It is up to you to define a data type to use
for the cookie.  The stream functions in the library never refer
directly to its contents, and they don't even know what the type is;
they record its address with type `void *'.

   To implement a custom stream, you must specify *how* to fetch or
store the data in the specified place.  You do this by defining "hook
functions" to read, write, change "file position", and close the
stream.  All four of these functions will be passed the stream's cookie
so they can tell where to fetch or store the data.  The library
functions don't know what's inside the cookie, but your functions will
know.

   When you create a custom stream, you must specify the cookie pointer,
and also the four hook functions stored in a structure of type
`cookie_io_functions_t'.

   These facilities are declared in `stdio.h'.

 - Data Type: cookie_io_functions_t
     This is a structure type that holds the functions that define the
     communications protocol between the stream and its cookie.  It has
     the following members:

    `cookie_read_function_t *read'
          This is the function that reads data from the cookie.  If the
          value is a null pointer instead of a function, then read
          operations on ths stream always return `EOF'.

    `cookie_write_function_t *write'
          This is the function that writes data to the cookie.  If the
          value is a null pointer instead of a function, then data
          written to the stream is discarded.

    `cookie_seek_function_t *seek'
          This is the function that performs the equivalent of file
          positioning on the cookie.  If the value is a null pointer
          instead of a function, calls to `fseek' on this stream can
          only seek to locations within the buffer; any attempt to seek
          outside the buffer will return an `ESPIPE' error.

    `cookie_close_function_t *close'
          This function performs any appropriate cleanup on the cookie
          when closing the stream.  If the value is a null pointer
          instead of a function, nothing special is done to close the
          cookie when the stream is closed.

 - Function: FILE * fopencookie (void *COOKIE, const char *OPENTYPE,
          cookie_io_functions_t IO-FUNCTIONS)
     This function actually creates the stream for communicating with
     the COOKIE using the functions in the IO-FUNCTIONS argument.  The
     OPENTYPE argument is interpreted as for `fopen'; see Opening Streams.
     (But note that the "truncate on open" option is
     ignored.)  The new stream is fully buffered.

     The `fopencookie' function returns the newly created stream, or a
     null pointer in case of an error.

Custom Stream Hook Functions
............................

   Here are more details on how you should define the four hook
functions that a custom stream needs.

   You should define the function to read data from the cookie as:

     ssize_t READER (void *COOKIE, void *BUFFER, size_t SIZE)

   This is very similar to the `read' function; see I/O Primitives.
Your function should transfer up to SIZE bytes into the
BUFFER, and return the number of bytes read, or zero to indicate
end-of-file.  You can return a value of `-1' to indicate an error.

   You should define the function to write data to the cookie as:

     ssize_t WRITER (void *COOKIE, const void *BUFFER, size_t SIZE)

   This is very similar to the `write' function; see I/O Primitives.
Your function should transfer up to SIZE bytes from the
buffer, and return the number of bytes written.  You can return a value
of `-1' to indicate an error.

   You should define the function to perform seek operations on the
cookie as:

     int SEEKER (void *COOKIE, fpos_t *POSITION, int WHENCE)

   For this function, the POSITION and WHENCE arguments are interpreted
as for `fgetpos'; see Portable Positioning.  In the GNU
library, `fpos_t' is equivalent to `off_t' or `long int', and simply
represents the number of bytes from the beginning of the file.

   After doing the seek operation, your function should store the
resulting file position relative to the beginning of the file in
POSITION.  Your function should return a value of `0' on success and
`-1' to indicate an error.

   You should define the function to do cleanup operations on the cookie
appropriate for closing the stream as:

     int CLEANER (void *COOKIE)

   Your function should return `-1' to indicate an error, and `0'
otherwise.

 - Data Type: cookie_read_function
     This is the data type that the read function for a custom stream
     should have.  If you declare the function as shown above, this is
     the type it will have.

 - Data Type: cookie_write_function
     The data type of the write function for a custom stream.

 - Data Type: cookie_seek_function
     The data type of the seek function for a custom stream.

 - Data Type: cookie_close_function
     The data type of the close function for a custom stream.

Low-Level Input/Output
**********************

   This chapter describes functions for performing low-level
input/output operations on file descriptors.  These functions include
the primitives for the higher-level I/O functions described in
I/O on Streams, as well as functions for performing low-level control
operations for which there are no equivalents on streams.

   Stream-level I/O is more flexible and usually more convenient;
therefore, programmers generally use the descriptor-level functions only
when necessary.  These are some of the usual reasons:

   * For reading binary files in large chunks.

   * For reading an entire file into core before parsing it.

   * To perform operations other than data transfer, which can only be
     done with a descriptor.  (You can use `fileno' to get the
     descriptor corresponding to a stream.)

   * To pass descriptors to a child process.  (The child can create its
     own stream to use a descriptor that it inherits, but cannot
     inherit a stream directly.)

Opening and Closing Files
=========================

   This section describes the primitives for opening and closing files
using file descriptors.  The `open' and `creat' functions are declared
in the header file `fcntl.h', while `close' is declared in `unistd.h'.

 - Function: int open (const char *FILENAME, int FLAGS[, mode_t MODE])
     The `open' function creates and returns a new file descriptor for
     the file named by FILENAME.  Initially, the file position
     indicator for the file is at the beginning of the file.  The
     argument MODE is used only when a file is created, but it doesn't
     hurt to supply the argument in any case.

     The FLAGS argument controls how the file is to be opened.  This is
     a bit mask; you create the value by the bitwise OR of the
     appropriate parameters (using the `|' operator in C).  See File Status Flags,
     for the parameters available.

     The normal return value from `open' is a non-negative integer file
     descriptor.  In the case of an error, a value of `-1' is returned
     instead.  In addition to the usual file name syntax errors (see
     File Name Errors.), the following `errno' error conditions are
     defined for this function:

    `EACCES'
          The file exists but is not readable/writable as requested by
          the FLAGS argument.

    `EEXIST'
          Both `O_CREAT' and `O_EXCL' are set, and the named file
          already exists.

    `EINTR'
          The `open' operation was interrupted by a signal.  See
          Interrupted Primitives.

    `EISDIR'
          The FLAGS argument specified write access, and the file is a
          directory.

    `EMFILE'
          The process has too many files open.

    `ENFILE'
          The entire system, or perhaps the file system which contains
          the directory, cannot support any additional open files at
          the moment.  (This problem cannot happen on the GNU system.)

    `ENOENT'
          The named file does not exist, and `O_CREAT' is not specified.

    `ENOSPC'
          The directory or file system that would contain the new file
          cannot be extended, because there is no disk space left.

    `ENXIO'
          `O_NONBLOCK' and `O_WRONLY' are both set in the FLAGS
          argument, the file named by FILENAME is a FIFO (see Pipes and FIFOs.),
          and no process has the file open for reading.

    `EROFS'
          The file resides on a read-only file system and any of
          `O_WRONLY', `O_RDWR', and `O_TRUNC' are set in the FLAGS
          argument, or `O_CREAT' is set and the file does not already
          exist.

     The `open' function is the underlying primitive for the `fopen'
     and `freopen' functions, that create streams.

 - Obsolete function: int creat (const char *FILENAME, mode_t MODE)
     This function is obsolete.  The call:

          creat (FILENAME, MODE)

     is equivalent to:

          open (FILENAME, O_WRONLY | O_CREAT | O_TRUNC, MODE)

 - Function: int close (int FILEDES)
     The function `close' closes the file descriptor FILEDES.  Closing
     a file has the following consequences:

        * The file descriptor is deallocated.

        * Any record locks owned by the process on the file are
          unlocked.

        * When all file descriptors associated with a pipe or FIFO have
          been closed, any unread data is discarded.

     The normal return value from `close' is `0'; a value of `-1' is
     returned in case of failure.  The following `errno' error
     conditions are defined for this function:

    `EBADF'
          The FILEDES argument is not a valid file descriptor.

    `EINTR'
          The `close' call was interrupted by a signal.  See
          Interrupted Primitives.  Here is an example of how to
          handle `EINTR' properly:

               TEMP_FAILURE_RETRY (close (desc));

   To close a stream, call `fclose' (see Closing Streams.) instead
of trying to close its underlying file descriptor with `close'.  This
flushes any buffered output and updates the stream object to indicate
that it is closed.

Input and Output Primitives
===========================

   This section describes the functions for performing primitive input
and output operations on file descriptors: `read', `write', and
`lseek'.  These functions are declared in the header file `unistd.h'.

 - Data Type: ssize_t
     This data type is used to represent the sizes of blocks that can be
     read or written in a single operation.  It is similar to `size_t',
     but must be a signed type.

 - Function: ssize_t read (int FILEDES, void *BUFFER, size_t SIZE)
     The `read' function reads up to SIZE bytes from the file with
     descriptor FILEDES, storing the results in the BUFFER.  (This is
     not necessarily a character string and there is no terminating
     null character added.)

     The return value is the number of bytes actually read.  This might
     be less than SIZE; for example, if there aren't that many bytes
     left in the file or if there aren't that many bytes immediately
     available.  The exact behavior depends on what kind of file it is.
     Note that reading less than SIZE bytes is not an error.

     A value of zero indicates end-of-file (except if the value of the
     SIZE argument is also zero).  This is not considered an error.  If
     you keep calling `read' while at end-of-file, it will keep
     returning zero and doing nothing else.

     If `read' returns at least one character, there is no way you can
     tell whether end-of-file was reached.  But if you did reach the
     end, the next read will return zero.

     In case of an error, `read' returns `-1'.  The following `errno'
     error conditions are defined for this function:

    `EAGAIN'
          Normally, when no input is immediately available, `read'
          waits for some input.  But if the `O_NONBLOCK' flag is set
          for the file (see File Status Flags.), `read' returns
          immediately without reading any data, and reports this error.

          *Compatibility Note:* Most versions of BSD Unix use a
          different error code for this: `EWOULDBLOCK'.  In the GNU
          library, `EWOULDBLOCK' is an alias for `EAGAIN', so it
          doesn't matter which name you use.

          On some systems, reading a large amount of data from a
          character special file can also fail with `EAGAIN' if the
          kernel cannot find enough physical memory to lock down the
          user's pages.  This is limited to devices that transfer with
          direct memory access into the user's memory, which means it
          does not include terminals, since they always use separate
          buffers inside the kernel.

          Any condition that could result in `EAGAIN' can instead
          result in a successful `read' which returns fewer bytes than
          requested.  Calling `read' again immediately would result in
          `EAGAIN'.

    `EBADF'
          The FILEDES argument is not a valid file descriptor.

    `EINTR'
          `read' was interrupted by a signal while it was waiting for
          input.  See Interrupted Primitives.

    `EIO'
          For many devices, and for disk files, this error code
          indicates a hardware error.

          `EIO' also occurs when a background process tries to read
          from the controlling terminal, and the normal action of
          stopping the process by sending it a `SIGTTIN' signal isn't
          working.  This might happen if signal is being blocked or
          ignored, or because the process group is orphaned.  See Job Control,
          for more information about job control, and
          Signal Handling, for information about signals.

     The `read' function is the underlying primitive for all of the
     functions that read from streams, such as `fgetc'.

 - Function: ssize_t write (int FILEDES, const void *BUFFER, size_t
          SIZE)
     The `write' function writes up to SIZE bytes from BUFFER to the
     file with descriptor FILEDES.  The data in BUFFER is not
     necessarily a character string and a null character is output like
     any other character.

     The return value is the number of bytes actually written.  This is
     normally the same as SIZE, but might be less (for example, if the
     physical media being written to fills up).

     In the case of an error, `write' returns `-1'.  The following
     `errno' error conditions are defined for this function:

    `EAGAIN'
          Normally, `write' blocks until the write operation is
          complete.  But if the `O_NONBLOCK' flag is set for the file
          (see Control Operations.), it returns immediately without
          writing any data, and reports this error.  An example of a
          situation that might cause the process to block on output is
          writing to a terminal device that supports flow control,
          where output has been suspended by receipt of a STOP
          character.

          *Compatibility Note:* Most versions of BSD Unix use a
          different error code for this: `EWOULDBLOCK'.  In the GNU
          library, `EWOULDBLOCK' is an alias for `EAGAIN', so it
          doesn't matter which name you use.

          On some systems, writing a large amount of data from a
          character special file can also fail with `EAGAIN' if the
          kernel cannot find enough physical memory to lock down the
          user's pages.  This is limited to devices that transfer with
          direct memory access into the user's memory, which means it
          does not include terminals, since they always use separate
          buffers inside the kernel.

    `EBADF'
          The FILEDES argument is not a valid file descriptor.

    `EFBIG'
          The size of the file is larger than the implementation can
          support.

    `EINTR'
          The `write' operation was interrupted by a signal while it was
          blocked waiting for completion.  See Interrupted Primitives.

    `EIO'
          For many devices, and for disk files, this error code
          indicates a hardware error.

    `ENOSPC'
          The device is full.

    `EPIPE'
          This error is returned when you try to write to a pipe or
          FIFO that isn't open for reading by any process.  When this
          happens, a `SIGPIPE' signal is also sent to the process; see
          Signal Handling.

     Unless you have arranged to prevent `EINTR' failures, you should
     check `errno' after each failing call to `write', and if the error
     was `EINTR', you should simply repeat the call.  See Interrupted Primitives.
     The easy way to do this is with the macro
     `TEMP_FAILURE_RETRY', as follows:

          nbytes = TEMP_FAILURE_RETRY (write (desc, buffer, count));

     The `write' function is the underlying primitive for all of the
     functions that write to streams, such as `fputc'.

Setting the File Position of a Descriptor
=========================================

   Just as you can set the file position of a stream with `fseek', you
can set the file position of a descriptor with `lseek'.  This specifies
the position in the file for the next `read' or `write' operation.
See File Positioning, for more information on the file position and
what it means.

   To read the current file position value from a descriptor, use
`lseek (DESC, 0, SEEK_CUR)'.

 - Function: off_t lseek (int FILEDES, off_t OFFSET, int WHENCE)
     The `lseek' function is used to change the file position of the
     file with descriptor FILEDES.

     The WHENCE argument specifies how the OFFSET should be interpreted
     in the same way as for the `fseek' function, and can be one of the
     symbolic constants `SEEK_SET', `SEEK_CUR', or `SEEK_END'.

    `SEEK_SET'
          Specifies that WHENCE is a count of characters from the
          beginning of the file.

    `SEEK_CUR'
          Specifies that WHENCE is a count of characters from the
          current file position.  This count may be positive or
          negative.

    `SEEK_END'
          Specifies that WHENCE is a count of characters from the end of
          the file.  A negative count specifies a position within the
          current extent of the file; a positive count specifies a
          position past the current end.  If you set the position past
          the current end, and actually write data, you will extend the
          file with zeros up to that position.

     The return value from `lseek' is normally the resulting file
     position, measured in bytes from the beginning of the file.  You
     can use this feature together with `SEEK_CUR' to read the current
     file position.

     You can set the file position past the current end of the file.
     This does not by itself make the file longer; `lseek' never
     changes the file.  But subsequent output at that position will
     extend the file.  Characters between the previous end of file and
     the new position are filled with zeros.

     If the file position cannot be changed, or the operation is in
     some way invalid, `lseek' returns a value of `-1'.  The following
     `errno' error conditions are defined for this function:

    `EBADF'
          The FILEDES is not a valid file descriptor.

    `EINVAL'
          The WHENCE argument value is not valid, or the resulting file
          offset is not valid.

    `ESPIPE'
          The FILEDES corresponds to a pipe or FIFO, which cannot be
          positioned.  (There may be other kinds of files that cannot
          be positioned either, but the behavior is not specified in
          those cases.)

     The `lseek' function is the underlying primitive for the `fseek',
     `ftell' and `rewind' functions, which operate on streams instead
     of file descriptors.

   You can have multiple descriptors for the same file if you open the
file more than once, or if you duplicate a descriptor with `dup'.
Descriptors that come from separate calls to `open' have independent
file positions; using `lseek' on one descriptor has no effect on the
other.  For example,

     {
       int d1, d2;
       char buf[4];
       d1 = open ("foo", O_RDONLY);
       d2 = open ("foo", O_RDONLY);
       lseek (d1, 1024, SEEK_SET);
       read (d2, buf, 4);
     }

will read the first four characters of the file `foo'.  (The
error-checking code necessary for a real program has been omitted here
for brevity.)

   By contrast, descriptors made by duplication share a common file
position with the original descriptor that was duplicated.  Anything
which alters the file position of one of the duplicates, including
reading or writing data, affects all of them alike.  Thus, for example,

     {
       int d1, d2, d3;
       char buf1[4], buf2[4];
       d1 = open ("foo", O_RDONLY);
       d2 = dup (d1);
       d3 = dup (d2);
       lseek (d3, 1024, SEEK_SET);
       read (d1, buf1, 4);
       read (d2, buf2, 4);
     }

will read four characters starting with the 1024'th character of `foo',
and then four more characters starting with the 1028'th character.

 - Data Type: off_t
     This is an arithmetic data type used to represent file sizes.  In
     the GNU system, this is equivalent to `fpos_t' or `long int'.

   These aliases for the `SEEK_...' constants exist for the sake of
compatibility with older BSD systems.  They are defined in two
different header files: `fcntl.h' and `sys/file.h'.

`L_SET'
     An alias for `SEEK_SET'.

`L_INCR'
     An alias for `SEEK_CUR'.

`L_XTND'
     An alias for `SEEK_END'.

Descriptors and Streams
=======================

   Given an open file descriptor, you can create a stream for it with
the `fdopen' function.  You can get the underlying file descriptor for
an existing stream with the `fileno' function.  These functions are
declared in the header file `stdio.h'.

 - Function: FILE * fdopen (int FILEDES, const char *OPENTYPE)
     The `fdopen' function returns a new stream for the file descriptor
     FILEDES.

     The OPENTYPE argument is interpreted in the same way as for the
     `fopen' function (see Opening Streams.), except that the `b'
     option is not permitted; this is because GNU makes no distinction
     between text and binary files.  Also, `"w"' and `"w+"' do not
     cause truncation of the file; these have affect only when opening
     a file, and in this case the file has already been opened.  You
     must make sure that the OPENTYPE argument matches the actual mode
     of the open file descriptor.

     The return value is the new stream.  If the stream cannot be
     created (for example, if the modes for the file indicated by the
     file descriptor do not permit the access specified by the OPENTYPE
     argument), a null pointer is returned instead.

   For an example showing the use of the `fdopen' function, see
Creating a Pipe.

 - Function: int fileno (FILE *STREAM)
     This function returns the file descriptor associated with the
     stream STREAM.  If an error is detected (for example, if the STREAM
     is not valid) or if STREAM does not do I/O to a file, `fileno'
     returns `-1'.

   There are also symbolic constants defined in `unistd.h' for the file
descriptors belonging to the standard streams `stdin', `stdout', and
`stderr'; see Standard Streams.

`STDIN_FILENO'
     This macro has value `0', which is the file descriptor for
     standard input.

`STDOUT_FILENO'
     This macro has value `1', which is the file descriptor for
     standard output.

`STDERR_FILENO'
     This macro has value `2', which is the file descriptor for
     standard error output.

Dangers of Mixing Streams and Descriptors
=========================================

   You can have multiple file descriptors and streams (let's call both
streams and descriptors "channels" for short) connected to the same
file, but you must take care to avoid confusion between channels.  There
are two cases to consider: "linked" channels that share a single file
position value, and "independent" channels that have their own file
positions.

   It's best to use just one channel in your program for actual data
transfer to any given file, except when all the access is for input.
For example, if you open a pipe (something you can only do at the file
descriptor level), either do all I/O with the descriptor, or construct a
stream from the descriptor with `fdopen' and then do all I/O with the
stream.

Linked Channels
---------------

   Channels that come from a single opening share the same file
position; we call them "linked" channels.  Linked channels result when
you make a stream from a descriptor using `fdopen', when you get a
descriptor from a stream with `fileno', and when you copy a descriptor
with `dup' or `dup2'.  For files that don't support random access, such
as terminals and pipes, *all* channels are effectively linked.  On
random-access files, all append-type output streams are effectively
linked to each other.

   If you have been using a stream for I/O, and you want to do I/O using
another channel (either a stream or a descriptor) that is linked to it,
you must first "clean up" the stream that you have been using.  See
Cleaning Streams.

   Terminating a process, or executing a new program in the process,
destroys all the streams in the process.  If descriptors linked to these
streams persist in other processes, their file positions become
undefined as a result.  To prevent this, you must clean up the streams
before destroying them.

Independent Channels
--------------------

   When you open channels (streams or descriptors) separately on a
seekable file, each channel has its own file position.  These are called
"independent channels".

   The system handles each channel independently.  Most of the time,
this is quite predictable and natural (especially for input): each
channel can read or write sequentially at its own place in the file.
However, if some of the channels are streams, you must take these
precautions:

   * You should clean an output stream after use, before doing anything
     else that might read or write from the same part of the file.

   * You should clean an input stream before reading data that may have
     been modified using an independent channel.  Otherwise, you might
     read obsolete data that had been in the stream's buffer.

   If you do output to one channel at the end of the file, this will
certainly leave the other independent channels positioned somewhere
before the new end.  If you want them to output at the end, you must set
their file positions to end of file, first.  (This is not necessary if
you use an append-type descriptor or stream; they always output at the
current end of the file.)  In order to make the end-of-file position
accurate, you must clean the output channel you were using, if it is a
stream.  (This is necessary even if you plan to use an append-type
channel next.)

   It's impossible for two channels to have separate file pointers for a
file that doesn't support random access.  Thus, channels for reading or
writing such files are always linked, never independent.  Append-type
channels are also always linked.  For these channels, follow the rules
for linked channels; see Linked Channels.

Cleaning Streams
----------------

   On the GNU system, you can clean up any stream with `fclean':

 - Function: int fclean (FILE *STREAM)
     Clean up the stream STREAM so that its buffer is empty.  If STREAM
     is doing output, force it out.  If STREAM is doing input, give the
     data in the buffer back to the system, arranging to reread it.

   On other systems, you can use `fflush' to clean a stream in most
cases.

   You can skip the `fclean' or `fflush' if you know the stream is
already clean.  A stream is clean whenever its buffer is empty.  For
example, an unbuffered stream is always clean.  An input stream that is
at end-of-file is clean.  A line-buffered stream is clean when the last
character output was a newline.

   There is one case in which cleaning a stream is impossible on most
systems.  This is when the stream is doing input from a file that is not
random-access.  Such streams typically read ahead, and when the file is
not random access, there is no way to give back the excess data already
read.  When an input stream reads from a random-access file, `fflush'
does clean the stream, but leaves the file pointer at an unpredictable
place; you must set the file pointer before doing any further I/O.  On
the GNU system, using `fclean' avoids both of these problems.

   Closing an output-only stream also does `fflush', so this is a valid
way of cleaning an output stream.  On the GNU system, closing an input
stream does `fclean'.

   You need not clean a stream before using its descriptor for control
operations such as setting terminal modes; these operations don't affect
the file position and are not affected by it.  You can use any
descriptor for these operations, and all channels are affected
simultaneously.  However, text already "output" to a stream but still
buffered by the stream will be subject to the new terminal modes when
subsequently flushed.  To make sure "past" output is covered by the
terminal settings that were in effect at the time, flush the output
streams for that terminal before setting the modes.  See Terminal Modes.