Developer Guide and Reference

ID 767251
Date 10/31/2024
Public
Document Table of Contents

Logical Devices

Every file, internal or external, is associated with a logical device. You identify the logical device associated with a file by using Unit Specifier (UNIT=). The unit specifier for an internal file is the name of the character variable associated with it. The unit specifier for an external file is one of the following:

  • A number you assign with the OPEN statement

  • A number assigned by the Intel® Fortran runtime library with the OPEN specifier NEWUNIT=

  • A number preconnected as a unit specifier to a device

  • An asterisk (*)

The OPEN statement connects a unit number with an external file and allows you to explicitly specify file attributes and runtime options using OPEN statement specifiers. External unit specifiers that are preconnected to certain devices do not have to be opened. External units that you connect are disconnected when program execution terminates or when the unit is closed by a CLOSE statement.

A unit must not be connected to more than one file at a time, and a file must not be connected to more than one unit at a time. You can OPEN an already opened file but only to change some of the I/O options for the connection, not to connect an already opened file or unit to a different unit or file.

You must use a unit specifier for all I/O statements except in the following cases:

  • ACCEPT, which always reads from standard input unless the FOR_ACCEPT environment variable is defined.

  • INQUIRE by file, which specifies the filename rather than the unit with which the file is associated.

  • PRINT, which always writes to standard output unless the FOR_PRINT environment variable is defined.

  • READ statements that contain only an I/O list and format specifier, which read from standard input (UNIT=5) unless the FOR_READ environment variable is defined.

  • WRITE statements that contain only an I/O list and format specifier, which write to standard output unless the FOR_WRITE environment variable is defined.

  • TYPE, which always writes to standard output unless the FOR_TYPE environment variable is defined.

External Files

A unit specifier associated with an external file must be either an integer expression or an asterisk (*). The integer expression must be in the range 0 (zero) to a maximum value of 2,147,483,640. (The predefined parameters FOR_K_PRINT_UNITNO, FOR_K_TYPE_UNITNO, FOR_K_ACCEPT_UNITNO, and FOR_K_READ_UNITNO may not be in that range. For more information, see the Language Reference.)

The following example connects the external file UNDAMP.DAT to unit 10 and writes to it:

OPEN (UNIT = 10, FILE = 'UNDAMP.DAT')
WRITE (10, '(A18,\)') ' Undamped Motion:'

The asterisk (*) unit specifier specifies the keyboard when reading and the screen when writing. The following example uses the asterisk specifier to write to the screen:

WRITE (*, '(1X, A30,\)') ' Write this to the screen.'

Intel Fortran has four units preconnected to external files (devices), as shown in the following table:

External Unit Specifier

Environment Variable

Description

Asterisk (*)

None

Always represents the keyboard and screen (unless the appropriate environment variable is defined, such as FOR_READ).

0

FORT0

Initially represents the screen (unless FORT0 is explicitly defined)

5

FORT5

Initially represents the keyboard (unless FORT5 is explicitly defined)

6

FORT6

Initially represents the screen (unless FORT6 is explicitly defined)

The asterisk (*) specifier is the only unit specifier that cannot be reconnected to another file; attempting to close such a unit causes a compile-time error. Units 0, 5, and 6 can be connected to any file with the OPEN statement; if you close one of those units, the file is automatically reconnected to its preconnected device the next time an I/O statement attempts to use that unit.

Intel® Fortran does not support buffering to stdin, and does not buffer to stdout by default unless the assume buffered_stdout option is specified. All I/O to units * and 6 use line buffering by default. Therefore, C and Fortran output to stdout should work well as long as the C code is not performing buffering. If the C code is performing buffering, the C code will have to flush the buffers after each write. For more information on stdout and stdin, see Assigning Files to Logical Units.

You can change these preconnected files by doing one of the following:

  • Using an OPEN statement to open unit 5, 6, or 0. When you explicitly OPEN a file for unit 5, 6, or 0, the OPEN statement keywords specify the file-related information to be used instead of the preconnected standard I/O file.

  • Setting the appropriate environment variable (FORTn) to redirect I/O to an external file.

To redirect input or output from the standard preconnected files at runtime, you can set the appropriate environment variable or use the appropriate shell redirection character in a pipe (such as > or <).

When you omit the file name in the OPEN statement or use an implicit OPEN, you can define the environment variable FORTn to specify the file name for a particular unit number n. An exception to this is when the fpscomp filesfromcmd compiler option is specified.

For example, if you want unit 6 to write to a file instead of standard output, set the environment variable FORT6 to the path and filename to be used before you run the program. If the appropriate environment variable is not defined, a default filename is used, in the form fort.n where n is the logical unit number.

The following example writes to the preconnected unit 6 (the screen), then reconnects unit 6 to an external file and writes to it, and finally reconnects unit 6 to the screen and writes to it:

PROGRAM Cosines
    implicit none
    INTEGER, PARAMETER :: dp = selected_real_kind(15, 307)
    integer,parameter :: k15 = selected_int_kind(15)
    INTEGER(kind=k15) k
    real(kind = dp) :: a, b,c

    !Write to the screen (preconnected unit 6).
    WRITE (6, '('' This is unit 6'')')
    ! Use the OPEN statement to connect unit 6
    ! to an external file named 'COSINES'.
    OPEN (UNIT = 6, FILE = 'COSINES', STATUS = 'UNKNOWN')
    DO k = 1, 63, 1
        c = real (k)
        a = c / 10.0
        b = COS(a)
        ! Write to the file 'COSINES'.
        WRITE (6, 100) a, b
        WRITE (*, 101) k, a, b
100     FORMAT (F3.1, '   ', F5.2)
101     FORMAT (I4, '   ', F3.1,'   ', F5.2)
    END DO
    ! Close it.
    CLOSE (6)
    ! Reconnect unit 6 to the screen, by writing to it.
    WRITE (6,' ('' Cosines completed'')')
END PROGRAM Cosines

Internal Files

The unit specifier associated with an internal file is a scalar or array character variable:

  • If the internal file is a scalar character variable, the file has only one record; its length is equal to that of the variable.

  • If the internal file is an array character variable, the file has a record for each element in the array; each record's length is equal to one array element.

Follow these rules when using internal files:

  • Use only formatted I/O, including I/O formatted with a format specification, namelist, and list-directed I/O. (List-directed and namelist I/O are treated as sequential formatted I/O.)

  • If the character variable is an allocatable array or array part of an allocatable array, the array must be allocated before use as an internal file. If the character variable is a pointer, it must be associated with a target.

  • Use only READ and WRITE statements. You cannot use file connection (OPEN, CLOSE), file positioning (REWIND, BACKSPACE), or file inquiry (INQUIRE) statements with internal files.

You can read and write internal files with FORMAT I/O statements, namelist I/O statements, or list-directed I/O statements exactly as you can external files. Before an I/O statement is executed, internal files are positioned at the beginning of the variable, before the first record.

With internal files, you can use the formatting capabilities of the I/O system to convert values between external character representations and Fortran internal memory representations. Reading from an internal file converts the ASCII representations into numeric, logical, or character representations, and writing to an internal file converts these representations into their ASCII representations.

This feature makes it possible to read a string of characters without knowing its exact format, examine the string, and interpret its contents. It also makes it possible, as in dialog boxes, for the user to enter a string and for your application to interpret it as a number.

If less than an entire record is written to an internal file, the rest of the record is filled with blanks.

In the following example, str and fname specify internal files:

PROGRAM INTERNALFILES 
    implicit none
    integer,parameter :: k15 = selected_int_kind(15)
    CHARACTER(10) str, fname
    INTEGER(kind=k15) i, n1, n2, n3
    str = " 1 2 3"
    ! List-directed READ sets n1 = 1, n2 = 2, n3 = 3.
    READ(str, *) n1, n2, n3
    i = 4
    ! Formatted WRITE sets fname = 'FM004.DAT'.
    WRITE (fname, 200) i
200 FORMAT ('FM', I3.3, '.DAT')
    write(*,*)fname
END PROGRAM

See Also