HP OpenVMS Systems Documentation |
HP Fortran for OpenVMS
|
Previous | Contents | Index |
This chapter describes:
You specify the floating-point format in memory with the /FLOAT qualifier. HP Fortran supports the following little endian floating-point formats in memory (default is /FLOAT=G_FLOAT):
Floating-Point Size | /FLOAT=IEEE_FLOAT | /FLOAT=D_FLOAT | /FLOAT=G_FLOAT |
---|---|---|---|
KIND=4 | S_float | F_float | F_float |
KIND=8 | T_float | D_float | G_float |
KIND=16 | X_float | X_float | X_float |
If your program needs to read or write unformatted data files containing a floating-point format that differs from the format in memory for that data size, you can request that the unformatted data be converted.
For example, if your program primarily uses IEEE little endian floating-point data, specify /FLOAT=IEEE_FLOAT to specify use of the S_float, T_float, and X_float formats in memory. If your program needs to read a data file containing a different format (VAX or big endian), you need to specify which VAX or big endian floating-point format to use for conversion into the native IEEE memory format for that file.
Converting unformatted data is generally faster than converting
formatted data and is less likely to lose precision for floating-point
numbers.
9.2 Endian Order of Numeric Formats
Data storage in different computers use a convention of either little endian or big endian storage. The storage convention generally applies to numeric values that span multiple bytes, as follows:
Figure 9-1 shows the difference between the two byte-ordering schemes.
Figure 9-1 Little and Big Endian Storage of an INTEGER Value
Moving data files between big endian and little endian computers
requires that the data be converted.
9.3 Native and Supported Nonnative Numeric Formats
HP Fortran provides the capability for programs to read and write unformatted data (originally written using unformatted I/O statements) in several nonnative floating-point formats and in big endian INTEGER or floating-point format.
When reading a nonnative unformatted format, the nonnative format on disk must be converted to native format in memory. Similarly, native data in memory can be written to a nonnative unformatted format. If a converted nonnative value is outside the range of the native data type, a run-time message appears (listed in Section 7.2).
Supported native and nonnative floating-point formats include:
The native memory format uses little endian integers and little endian floating-point formats, as follows:
Table 9-1 lists the keywords for the supported unformatted file data formats. Use the appropriate keyword after the /CONVERT qualifier (such as /CONVERT=CRAY) or as an logical name value (see Section 9.5).
Recognized Keyword | Description |
---|---|
BIG_ENDIAN | Big endian integer data of the appropriate INTEGER size (one, two, or four bytes) and big endian IEEE floating-point formats for REAL and COMPLEX single- and double-precision numbers. INTEGER (KIND=1) or INTEGER*1 data is the same for little endian and big endian. |
CRAY | Big endian integer data of the appropriate INTEGER size (one, two, four, or eight bytes) and big endian CRAY proprietary floating-point format for REAL and COMPLEX single- and double-precision numbers. |
IBM | Big endian integer data of the appropriate INTEGER size (one, two, or four bytes) and big endian IBM proprietary floating-point format for REAL and COMPLEX single- and double-precision numbers. |
FDX |
Native little endian integers of the appropriate INTEGER size (one,
two, four, or eight bytes) and the following native little endian
proprietary floating-point formats:
F_float for REAL (KIND=4) and COMPLEX (KIND=4) For information on these native OpenVMS formats, see Table 8-1 and Section 8.4. |
FGX |
Native little endian integers of the appropriate INTEGER size (one,
two, four, or eight bytes) and the following native little endian
proprietary floating-point formats:
F_float for REAL (KIND=4) and COMPLEX (KIND=4) For information on these native OpenVMS formats, see Table 8-1 and Section 8.4. |
LITTLE_ENDIAN |
Little endian integers of the appropriate INTEGER size (one, two, four,
or eight bytes) and the following native little endian IEEE
floating-point formats:
S_float for REAL (KIND=4) and COMPLEX (KIND=4) For information on these native OpenVMS formats, see Table 8-1 and Section 8.4. |
NATIVE | No conversion occurs between memory and disk. This is the default for unformatted files. |
VAXD |
Native little endian integers of the appropriate INTEGER size (one,
two, four, or eight bytes) and the following little endian VAX
proprietary floating-point formats:
F_float for REAL (KIND=4) and COMPLEX (KIND=4) For information on the F_float and D_float formats, see Table 8-1 and Section 8.4. For information on the H_float format (available only on VAX systems), see Section B.8. |
VAXG |
Native little endian integers of the appropriate INTEGER size (one,
two, four, or eight bytes) and the following little endian VAX
proprietary floating-point formats:
F_float format for REAL (KIND=4) and COMPLEX (KIND=4) For information on the F_float and D_float formats, see Table 8-1 and Section 8.4. For information on the H_float format (available only on VAX systems), see Section B.8. |
While this solution is not expected to fulfill all floating-point conversion needs, it provides the capability to read and write various types of unformatted nonnative floating-point data.
1 IEEE floating-point formats are defined in the IEEE Standard for Binary Floating-Point Arithmetic, ANSI/IEEE Standard 754-1985, Institute of Electrical and Electronics Engineers, August 1985. |
9.4 Limitations of Numeric Conversion
The HP Fortran floating-point conversion solution is not expected to fulfill all floating-point conversion needs.
Data (variables) in record structures (specified in a STRUCTURE statement) and data components of derived types (TYPE statement) are not converted. When variables are later examined as separate fields by the program, they will remain in the binary format they were stored in on disk, unless the program is modified.
If a program reads an I/O record containing multiple floating-point fields into an integer array (instead of their respective variables), the fields will not be converted. When they are later examined as separate fields by the program, they will remain in the binary format they were stored in on disk, unless the program is modified. To convert floating-point formats for individual fields, consider using the CVT$CONVERT_FLOAT routine (see Example B-1).
With EQUIVALENCE statements, the data type of the variable named in the
I/O statement is used.
9.5 Methods of Specifying the Unformatted Numeric Format
The methods you can use to specify the type of numeric floating-point format are as follows:
If you specify more than one method, the order of precedence when you open a file with unformatted data is:
If none of these methods are specified, no conversion occurs between disk and memory. Data should therefore be in the native memory format (little endian integer and little endian IEEE or VAX format) or otherwise translated by the application program.
Any keyword listed in Table 9-1 can be used with any of these
methods.
9.5.1 Logical Name FOR$CONVERTnnn Method
You can use the logical name method to specify multiple formats in a single program, usually one format for each unit number. You specify the numeric format at run time by setting the appropriate logical name before you open that unit number. For unit numbers that contain fewer than three digits, use leading zeros.
For example, to specify the numeric format for unit 9, set logical name FOR$CONVERT009 to the appropriate value (such as BIG_ENDIAN) before you run the program. For unit 125, set the logical name FOR$CONVERT125 before you run the program.
When you open the file, the logical name is always used, since this method takes precedence over the FORTRAN command qualifier methods. For instance, you might use this method to specify that different unformatted numeric formats for different unit numbers (perhaps in a command procedure that sets the logical name before running the program).
For example, assume you have a previously compiled program that reads numeric data from unit 28 and writes it to unit 29 using unformatted I/O statements. You want the program to read nonnative big endian (IEEE floating-point) format from unit 28 and write that data in native little endian format to unit 29.
In this case, the data is converted from big endian IEEE format to native little endian IEEE memory format (S_float and T_float) when read from unit 28, and then written without conversion in native little endian IEEE format to unit 29. The FORTRAN command qualifier /FLOAT specifies the IEEE floating-point format in memory and the LINK command creates the executable program:
$ FORTRAN/FLOAT=IEEE_FLOAT CONV_IEEE $ LINK CONV_IEEE |
Without requiring source code modification of recompilation of this program, the following DCL command sequence sets the appropriate logical name and then runs the program CONV_IEEE.EXE:
$ DEFINE FOR$CONVERT028 BIG_ENDIAN $ DEFINE FOR$CONVERT029 NATIVE $ RUN CONV_IEEE |
Figure 9-2 shows the data formats used on disk and in memory when the example file conv_ieee.exe is run after the logical names are set with DCL commands.
Figure 9-2 Sample Unformatted File Conversion
For information on the DCL commands you can use to define and deassign
logical names, see Appendix D.
9.5.2 Logical Name FOR$CONVERT.ext (and FOR$CONVERT_ext) Method
You can use this method to specify formats in a single program, usually one format for each specified file name extension (suffix). You specify the numeric format at run time by setting the appropriate logical name before an implicit or explicit OPEN statement to one or more unformatted files.
For example, assume you have a previously compiled program that reads floating-point numeric data from one file and writes to another file using unformatted I/O statements. You want the program to read nonnative big endian (IEEE floating-point) format from a file with a .dat file extension suffix and write that data in native little endian format to a file with a suffix of .data. You would DEFINE FOR$CONVERT.DAT BIG_ENDIAN.
In this case, the data is converted from big endian IEEE format to native little endian IEEE memory format when read from file.dat, and then written without conversion in native little endian IEEE format to the file with a suffix of .data, assuming that logical names FOR$CONVERT.DATA and FOR$CONVERTnnn (for that unit number) are not defined.
The FOR$CONVERTnnn method takes precedence over this method. When the appropriate logical name is set when you open the file, the FOR$CONVERT.ext logical name is used if a FOR$CONVERTnnn logical name is not set for the unit number.
The FOR$CONVERTnnn and FOR$CONVERT.ext (or FOR$CONVERT_ext) logical name methods take precedence over the other methods. For instance, you might use this method to specify that a unit number will use a particular format instead of the format specified in the program (perhaps for a one-time file conversion).
See Example 9-1.
Example 9-1 Example Showing the Use of the FOR$CONVERT.ext Method |
---|
Source program: program p integer i real r open( file='convert_in.txt', unit=10) open( file='convert_out.big', unit=11, form="unformatted") open( file='convert_out.dat', unit=12, form="unformatted") do i = 1, 10 read(10,*) r ! In text type *,r write(11) r ! In BIG_ENDIAN write(12) r ! In NATIVE enddo close(10) close(11) close(12) end |
Assume the following data in the file convert_in.txt :
1 2 3 4 5 6 7 8 9 10 |
Define the following symbols:
$ def for$convert.big big_endian $ def for$convert.dat native |
Then after you run the compiled source program, you get the following output:
1.000000 2.000000 3.000000 4.000000 5.000000 6.000000 7.000000 8.000000 9.000000 10.00000 |
And the following data in the big endian output file convert_out.big :
? @ @@ @ @ @À @à A A A |
And the following data in the native output file convert_out.dat :
@ A @A A A ÀA àA B B B |
You can use the OPEN statement method to specify multiple formats in a single program, usually one format for each specified unit number. This method requires an explicit file OPEN statement to specify the numeric format of the file for that unit number.
This method takes precedence over the /CONVERT=keyword method (see Section 9.5.5), but has a lower precedence than the logical name method.
The following source code shows an OPEN statement coded for unformatted VAXD numeric data (read from unit 15), and an OPEN statement coded for unformatted native little endian format (written to unit 20). The absence of the CONVERT specifier (in the second OPEN statement) or logical name FOR$CONVERT020 indicates native little endian data for unit 20:
OPEN (CONVERT='VAXD', FILE='graph3.dat', FORM='UNFORMATTED', UNIT=15) . . . OPEN (FILE='graph3_ieee.dat', FORM='UNFORMATTED', UNIT=20) |
A hard-coded OPEN statement CONVERT specifier keyword value cannot be changed after compile time. However, to allow selection of a particular format at run time, you can equate the CONVERT specifier to a variable and provide the user with a menu that allows selection of the appropriate format (menu choice sets the variable) before the OPEN occurs.
You can also select a particular format for a unit number at run time by using the logical name method (see Section 9.5.1), which takes precedence over the OPEN statement CONVERT specifier method.
You can issue an INQUIRE statement (by unit number) to an opened file to obtain the current CONVERT method in use.
Previous | Next | Contents | Index |