To: The Public Review Commentor
cc: J3 Members - For Information
Date: 2008 August 18
From: Dan Nagle, J3 Chair
Subject: J3's Response to the Public Review of ISO/IEC CD 1539-1, Information technology - Programming languages - Fortran.
Thank you for your public review comments on ISO/IEC CD 1539-1, Information technology - Programming languages - Fortran.
This is J3's response to your comments.
In J3's response, J3 describes ISO/IEC CD 1539-1, Information technology - Programming languages - Fortran as the draft. Various other terms were used in comments, including CD, 08-007r2, and N1723. J3 believes that this variety of terms, while each is correct, may be confusing.
Once again, thank you for your interest in the ISO/IEC CD 1539-1, Information technology - Programming languages - Fortran draft standard.
Public Review Comment J32001 from Jerry DeLisle
commentor's Subject was "Comments on F2008 - 08-007r2:2008/03/11"
I have the following comments:
126.96.36.199 NEWUNIT= specifier in the OPEN statement:
Paragraph 2 needs some clarification. Is it really intended that the NEWUNIT unit number be negative? I presume this is intended to avoid conflicts with legacy codes.
Also, the wording of the paragraph reads as if this is a set of constraints or restrictions. I suggest the sentence be broken into at least two sentences to clarify. The first sentence should make the assertion that the unit be a negative number (if that is indeed the case). The second sentence should then state what the unit number shall not be.
2 A NEWUNIT value is a negative number. A NEWUNIT value shall not be; equal to -1, any of the named constants ERROR_UNIT, INPUT_UNIT, or OUTPUT_UNIT from the intrinsic module ISO FORTRAN ENV (13.8.2), any value used by the processor for the unit argument to a defined input/output procedure, nor any previous NEWUNIT value that identifies a file that is currently connected.
10.7.2.3.3 E and D editing:
Please explicitly state that the d precision specifier in Ew.d can not be zero. Currently we are deducing this from the relation given in sub-part 8:
-d < k <= 0
For any value of k, d can not be zero and have this relation satisfied. This is a rather obscure way to come to the conclusion that d can not be zero. The standard could be improved by being more specific and just stating "d shall not be zero"
J3 Response to point 1
J3 agrees that the language could be clarified and proposes the following edit to the draft.
In the draft at 188.8.131.52, second paragraph, on page 205, replace the paragraph with:
"A NEWUNIT value is a negative number. A NEWUNIT value shall not be: equal to -1, any of the named constants ERROR_UNIT, INPUT_UNIT, or OUTPUT_UNIT from the intrinsic module ISO FORTRAN ENV (13.8.2), any value used by the processor for the unit argument to a defined input/output procedure, nor any previous NEWUNIT value that identifies a file that is currently connected."
J3 Response to point 2
For input, E, EN, ES and D are all equivalent to the F edit descriptor and a zero value for d is valid for F. Therefore, it would be incorrect to place such a restriction into the standard. Since it is possible to deduce from the current text that d cannot be zero on output, J3 prefers to leave the text as it is.
Public Review Comment J32002 from François-Xavier Coudert
commentor's Subject was "Fortran 2008 comment".
The Fortran 2008 standard provides intrinsic procedures for conversion between different kinds of logical, integer, real and complex types It does not, however, provide such functionality for characters. As conversion between different character kinds is allowed in assignment statements, the way it happens is already specified and little work is required to add an conversion intrinsic. Such a conversion intrinsic would be useful, especially in a number of cases where it allows for a more compact coding style, compared to having an extra variable and using an assignment statement. Some examples of this, reported by GNU Fortran users who tested the recently added UCS-4 support, include converting a wide character string when passing it to a routine (such as error-reporting routine, or informational argument to a library routine) that expects a character argument of the default kind; this is particularly interesting in the case where the user has no control over the library function.
To add such an intrinsic, I suggest adding the following text to section 13.6:
CHARACTER (STRING [, KIND])
Description. Conversion between kinds of characters.
Class. Elemental function.
STRING shall be of type character.
KIND (optional) shall be a scalar integer initialization expression.
Result Characteristics. Character. If KIND is present, the kind type parameter is that specified by the value of KIND; otherwise, the kind type parameter is that of default character type. The length of the result is the same as the length of STRING.
Result Value. The result is the conversion of STRING to the result kind type parameter, under the same rules as character intrinsic assignment. Each character of the result is equal to ACHAR(IACHAR(c) [, KIND]), where c is the character at the same position in STRING.
Example. On a processor where SELECTED_CHAR_KIND("ISO_10646") has the value 4, CHARACTER ("ABC", 4) has the value 4_"ABC".
The following line should also be added to Table 13.1 (section 13.5): Procedure: CHARACTER Arguments: (STRING [, KIND]) Class: E Description: Conversion between kinds of characters.
Unfortunately, the premise that intrinsic assignement between character variables of different kind is allowed is wrong. See table 7.10 on page 152 of the draft: "Type conformance for the intrinsic assignment". Character assignments are only allowed for "the same kind type parameter". J3 believes the mapping between characters of different kind is difficult to define. Consequently, J3 declines to make this addition.
Public Review Comment J32003 from Tobias Burnus
commentor's Subject was "F2008 comment to BESSEL_YN/BESSEL_JN"
Fortran 2008 adds the BESSEL_YN and BESSEL_JN intrinsic procedures. These are special in so far that they belong into two classes:
Having a procedure of dual nature is confusing and conceptually inconsistent. Furthermore, it increases the implementation burden for the compiler vendor.
Additionally, I do not not see the need for the transformational function; the same functionality can easily gained by using the elemental function.
I therefore strongly prefer to make BESSEL_YN and BESSEL_JN only elemental functions. If a burning need is seen for a BESSEL_*N(N1,N2,X) function (which I do not see), one should add a new intrinsic with a different name.
Bessel functions of order greater than one are usually computed via recursion relations. Frequently, values of several consecutive orders of the same argument are needed. This requirement does not match the usual implementation of elemental procedures. Therefore, there is an efficiency gain by providing the transformational form. Generic resolution in this case will work as usual without undue confusion. Also, using the same names for both forms reduces the number of new names added to the intrinsic library. Therefore, J3 declines to make this change.
Public Review Comment J32004 from Richard Maine
commentor's Subject was "F2008 too early"
This is a public comment on the f2008 CD. While I have perused the CD, I have no detailed technical comments at the moment. My only comment is the general one that it is simply too early to be processing the next Fortran standard. I realize that the processing was already somewhat delayed, but insufficiently so in my opinion.
To my knowledge, there are no f2003 compilers currently publicly available. I certainly have access to none that implement even a substantial portion of the f2003 standard. I do not think it appropriate to be reviewing a CD for a proposed follow-on standard until there have been multiple f2003 compilers available to the general public for at least a year. A single compiler would provide breadth, both in terms of implementation and user experience. With less than a year of compilers being in user's hands, users have insufficient basis for evaluating what weaknesses in f2003 might need addressing.
If the current process continues as scheduled, it appears plausible that there might never be a standard-conforming f2003 compiler during the time frame when the f2003 standard was a current standard. I would interpret that as implying that the f2003 standard was a failure. If so, then it behooves the committee to evaluate the reasons for the failure in order to address them rather than just continuing down the same failed path, adding more features when the existing ones haven't yet been implemented.
Even if an f2003 compiler is released between now and the final approval of f2008, I maintain that it would provide insufficient basis for users to evaluate a proposed follow-on language, particularly when that evaluation is required now. Suggesting that user comments can be submitted on the FCD is not, in my opinion adequate response. The FCD is too late in the process for significant decisions about feature selection to be made. Such decisions are more appropriate during preparation and review of the CD.
It seems to me that the possible interpretations of the current lack of f2003 compilers fall into one of the following two major categories:
1. The f2003 standard is a failure. In that case the committee should be studying and addressing the reasons for the failure instead of just pressing on.
2. It is just too early to expect full implementations of something as large as f2003. In that case, it is also too early to be proposing a follow-on standard.
Both of those possibilities lead to a common conclusion that this is not an appropriate time to be reviewing a CD for a follow-on standard. I don't think a few months delate will change things either, given my guideline of a year of availability of multiple compilers. I might guess that about 2 years from now might be a more sensible time - for a CD, not for final approval of the standard.
The schedule and work list for this revision of the Fortran standard were established in 2005; that was the time for suggestions. J3 declines to change the schedule or to substantially change the work list at this time.
Public Review Comment J32005 from Robert Corbett
commentor's Subject was "Coarrays should be optional"
The Fortran 2008 draft should not be approved unless coarrays are made optional.
Coarrays are too new to belong in Fortran 2008. Many models for parallel programming have been developed. Coarrays are not clearly superior to these other models. Making coarrays optional would allow further development of coarrays without creating problems if other models of parallel programming prove more successful.
Coarrays have been implemented in commercially available compilers for a decade, which is longer than the typical lifetime of a Fortran standard. The SPMD programming model implemented in Fortran with coarrays is that used by MPI, which is the most successful parallel programming model available. Previous experience with optional parts of the standard is that they are not widely implemented. Since the most often voiced complaint about coarrays is that they are not widely available, this is not an appropriate course of action. The status of coarrays in the proposed Fortran standard has been extensively debated and balloted, and J3 believes the outcome should not be changed.
Public Review Comment J32006 from Robert Corbett
commentor's Subject was "Restore the restrictions on internal procedures"
The Fortran 2008 draft allows internal procedures to be pointer targets and dummy arguments. The only practical implementation of the functionality as specified in the current draft requires the use of self-modifying code. Self-modifying code has long been established to be a security problem. Some secure operating systems, such as SELinux and Trusted Debian, can be built in ways that do not allow self-modifying code. Recent versions of Mac OS require users to mark executables that allow self-modifying code.
The functionality could be provided in ways that do not require self-modifying code. Traditionally, pointers to internal procedures have been implemented as two parts: the address of the entry point of the internal procedure and the context in which the procedure is to be executed. In modern languages, such pointers are called "closures." Adding a way to declare closures would permit the functionality of pointers to internal procedures without putting security at risk.
There are existing implementations of this feature that do not fall afoul of the operating system restrictions noted. Given this, as well as the popularity of this feature with the Fortran community, J3 declines to remove the feature from the language.
Public Review Comment J32007 from Robert Corbett
commentor's Subject was "the official interpretations should be examined"
The Fortran standard should be written in such a manner that a reader who is not a member of the committee should be able to understand it without needing to read the interpretations issued against Fortran 90, Fortran 95, and Fortran 2003.
The committee should examine the interpretations issued against the previous Fortran standards to see that those interpretations are reflected in the text of the new standard. Many of those interpretations were requested by senior members of the committee, a succession of interpretations were considered and rejected before the final interpretation was issued, and yet the text of the standard was left unchanged. Given that the unmodified text raised questions in the minds of members of the committee, that text can reasonably be supposed to be confusing to readers who are not members of the committee.
When an interpretation is agreed upon and includes edits, the edits are published in a Corrigendum. It is J3's policy always to include edits from the published Corrigenda in the immediately following standard.
J3 will endeavor to capture the sense of agreed-upon interpretations in the following standard even when they do not result in edits.
Public Review Comment J32008 from Robert Corbett
commentor's Subject was "generic resolution"
Consider the program
PROGRAM MAIN INTERFACE COS REAL FUNCTION MYCOS(X) END FUNCTION END INTERFACE CALL SUBR CONTAINS SUBROUTINE SUBR INTRINSIC COS PRINT *, COS(0.0) END SUBROUTINE END REAL FUNCTION MYCOS(X) MYCOS = 2.0 END
When compiled using the compilers provided by Sun, Cray, Intel, HP, and PathScale, the program prints 2.0. When compiled using the compilers provided by IBM, NAG, and GCC, the program prints 1.0. Interpretations 90/000082 and 90/000086 require the latter interpretation. Text should be added to the standard itself clarifying this point.
Neither interpretation F90/000082 nor F90/000086, at least according to
184.108.40.206 paragraph 1 and 220.127.116.11 paragraph 2 do not apply because the generic interface block is not (defined) in the internal subroutine. Although neither paragraph includes the word "defined", the fact that host association is mentioned in 18.104.22.168 paragraph 4 makes it clear that the generic name is not accessed from the host scoping unit, notwithstanding 22.214.171.124 paragraphs 2 and 3. The relationship between 126.96.36.199 and 188.8.131.52 should perhaps be clarified at a later time.
The program should print 1.0 because 184.108.40.206 paragraph 3 specifies that the intrinsic COS is referenced when 220.127.116.11 paragraphs 1 and 2 do not apply, and they do not apply in this case.
An edit is supplied to clarify this.
At subclause 18.104.22.168 paragraphs 1 and 2,
Public Review Comment J32009 from Robert Corbett
commentor's Subject was "File position and the left tab limit"
[...] filed request for interpretation 95/000027. The interpretation issued by the committee is clear, but it is not reflected in the text of the standard. The standard does not clearly state that the character position within the current record is part of the file position. Questions regarding the character position have been asked about Fortran 90, Fortran 95, and Fortran 2003.
Paragraph 3 of Section 22.214.171.124 should state that if a record file is positioned within a record, the character position within the record is part of the file position.
The standard consistently refers to "position" in contexts such as "position just before the first record","position within a record" (126.96.36.199), and "position within the current record" (188.8.131.52, C6.2), that clearly indicate character position is an aspect of "file position". J3 believes that adding the requested text would be unnecessary and possibly confusing. This is a case where the word "position" has the usual English meaning. J3 believes that no edit is required.
Public Review Comment J32010 from Robert Corbett
commentor's Subject was "constraint C542"
Consider the following program:
PROGRAM MAIN INTRINSIC SQRT INTERFACE SQRT REAL FUNCTION MYSQRT(X) END FUNCTION END INTERFACE END REAL FUNCTION MYSQRT(X) MYSQRT = SQRT(X) END
This program clearly violates constraint C542 in Section 5.3.11 of the Fortran 2008 draft. I have had an e-mail correspondence with a member of the committee who states that interpretation 90/000083 makes it clear that the committee intended to allow programs such as the one above. If that is so, the final clause of constraint C542, which says
and the characteristics of the specific intrinsic procedures and the procedures in the interfaces shall differ as specified in 184.108.40.206.5
should be removed. If the committee holds that the constraint as written is valid, I suggest adding a note giving an example such as the one above to confirm that the constraint is the intent of the committee.
C542 simply restates the requirements of 220.127.116.11.5 (notice that 18.104.22.168.5 paragraph 1 refers to "specific procedures," and that "nonintrinsic" is absent), but makes it clear that a conflict arises only if the INTRINSIC attribute is specified. If the provisions of 22.214.171.124.5 applied where the INTRINSIC attribute is not specified, 126.96.36.199 paragraph 5 would be irrelevant.
188.8.131.52.5 arose from subclause 16.2.3 from the 2003 standard, with some requirements restated as constraints, since Clause 16 has the stature of constraints.
Therefore, the above example is not standard conforming, and J3 believes there is no need to edit the draft.
Public Review Comment J32011 from Robert Corbett
commentor's Subject was "define entity"
The standard uses the term "entity" as a word of art, but does not define it. The standard defines a "construct entity" and a "data entity," but those are clearly not the only language constructs the standard means when it uses the term "entity." I suggest copying the definition of the term "entity" presented in the glossary of the Fortran 2003 standard into the Fortran 2008 standard.
The glossary in Fortran 2003 was not normative, and the definition of "entity" therein was incomplete.
Other than within the terms "data entity" and "construct entity," the term "entity" appears in its common English usage, not as a term of art.
Public Review Comment J32012 from Robert Corbett
commentor's Subject was "attributes"
the fortran 2008 draft states that attributes are properties of entities. that definition does not precisely cover all uses of attributes. attributes are properties of names. the attributes of a name usually reflect properties of the entity named by the name, but not always.
consider the following program:
real function f() f = 1.0 END MODULE MOD EXTERNAL F REAL F END SUBROUTINE SUBR(F) EXTERNAL F END PROGRAM MAIN USE MOD, G => F X = F(X) CALL SUBR(F) ! not standard conforming CALL SUBR(G) END
In the main program, the name F is known to be the name of an external function, but it does not have an explicit interface and it is not declared to have the EXTERNAL attribute. The name G is declared to have the EXTERNAL attribute, and so it can be used as an actual argument. Both F and G name the same function, but only G is declared to have the EXTERNAL attribute. Therefore, the EXTERNAL attribute must be a property of the name, not the function.
The attributes ASYNCHRONOUS and VOLATILE also are attributes of names that do not specify properties of the entities names.
Although F is referenced as a function in the main program, it does not have the EXTERNAL attribute in that scoping unit (it might be an intrinsic procedure on some processors). Subclause 184.108.40.206 paragraph 4, as revised by paper 08-156r2 at meeting 184 simply requires that a procedure used as an actual argument have the EXTERNAL attribute. Therefore the program is not standard conforming.
The definition of "attribute" in 2.1.6 is not defective.
The definition of attributes in 5.1 is not defective, but could be clarified. An edit is supplied.
In the draft at subclause 5.1
"Accessibility attributes apply to identifiers, not the entities they identify, and these attributes may be different in different scoping units. An entity may have the ASYNCHRONOUS or VOLATILE attributes in some scoping units and not have them in others."
Public Review Comment J32013 from Robert Corbett
commentor's Subject was "additional intrinsic functions"
I suggest adding a few more functions to the list of intrinsic functions.
The standard should include an intrinsic function named COMPLEX. The function should be of the form
COMPLEX(X, [Y, KIND])
where X, Y, and KIND are defined as for the intrinsic function CMPLX. Unlike CMPLX, if both X AND Y are present and are REAL and KIND is not present, the kind type parameter values of X and Y shall be the same and the kind type parameter value of the result shall be the same as the kind type parameter values of X and Y.
The degree trigonometric functions COSD, SIND, and TAND are supplied in most Fortran implementations already. I have seen several examples of functions written by users to implement the degree trigonometric functions. Those functions often produce poor results. Producing good results requires a better understanding of floating-point arithmetic than many users have. Producing high-quality results (good to within 0.5+epsilon ulps) is probably beyond the ability of all but a few dozen users.
Fortran should also supply routines the functions EXPM1 and LOGP1, where EXPM1(X) computes EXP(X-1.0) and LOGP1(X) computes LOG(X+1.0). The functions should be computed to greater accuracy than the straightforward implementation. These are functions for people who know very well how floating-point arithmetic works. They offer knowledgeable users a chance to produce highly accurate results in some cases where it would be difficult to produce accurate results without using such functions.
J3 Response to point 1
J3 agrees with the assessment of the limitations of CMPLX and agrees an intrinsic COMPLEX would be useful. To prevent overlapping functionality between the two intrinsics, J3 will propose the following definition of COMPLEX:
where RE and IM are of type REAL and have the same kind type parameters, neither of them is optional. The kind type parameter of the result is the same as that of RE and IM.
See paper 08-266r1 for further details.
J3 Response to point 2
This was not part of the work item list for Fortran 2008. J3 believes the implementation of these intrinsics with the desired floating point semantics too large a change to add them now.
J3 Response to point 3
When the work list was defined, J3 considered this proposal and declined to include it. J3 declines to reconsider this proposal now.
Public Review Comment J32014 from Robert Corbett
commentor's Subject was "definition of vector subscript"
The definition of a vector subscript given in Section 2.1.123 could be clearer. I suggest replacing it with
section-subscript that is an array of rank one (220.127.116.11)
J3 agrees that this is an improved definition.
In the draft at subclause 2.1.123
Public Review Comment J32015 from Robert Corbett
commentor's Subject was "assumed constraints for names"
Some time ago, I had an e-mail correspondence with a member of the committee who asserted that the statement
In order to minimize the number of additional syntax rules and convey constraint information, the following rules are assumed.
in Section 1.6.5 meant that if an xyz-name appeared in a syntax rule, an assumed constraint required the name to be the name of an xyz. I pointed out that constraint C101 explicitly said when an implicit constraint should be assumed, and that because there was no corresponding constraint for names, there were no assumed constraints for names, except, of course, for scalar-names. If my interpretation is wrong, a constraint similar to constraint C101 should be added for xyz-names.
Requiring xyz-name to be the name of an xyz would not work for at least two reasons. First, there is frequently no syntax term xyz, for example, there is no term local to which local-name could refer. Second, there are cases where an implicit constraint would be inappropriate, for example in R438 where an implicit constraint would require the component-name in the definition of component-decl to be the name of a component. Where a constraint is required, one appears explicitly, for example, C437.
Public Review Comment J32016 from Robert Corbett
commentor's Subject was "advice regarding additional intrinsics ignores"
The advice given in paragraph 4 of Section 1.4 of the Fortran 2008 ignores a important issue that affects portability. Consider the program
PROGRAM MAIN INTERFACE SQRT INTEGER FUNCTION NISQRT(I) END FUNCTION END INTERFACE CALL SUBR CONTAINS SUBROUTINE SUBR INTRINSIC SQRT PRINT *, SQRT(4) PRINT *, SQRT(4.0) END SUBROUTINE END INTEGER FUNCTION NISQRT(I) NISQRT = -INT(SQRT(REAL(I))) END
A user might expect that program to write something like
If, however, the implementation provides a specific interface for SQRT that takes an argument of type INTEGER, that interface will be chosen over the user's external function according to the rules presented in Section 18.104.22.168 of the Fortran 2008 draft.
I suggest adding a warning against declaring a name to have the INTRINSIC attribute in a context where that name is accessible as the name of a generic interface.
This is similar to the question asked in J32008 (08-222).
It is not possible for the standard to warn about all possible interactions of programs with processor extensions. This is explicitly addressed by subclause 1.4 paragraph 4. However, in this case, J3 agrees that an informative note would be helpful.
In the draft at subclause 22.214.171.124
Insert a new note after NOTE 12.41:
Host association, the INTRINSIC attribute, and generic resolution interact. Consider the following program:
PROGRAM MAIN INTERFACE SQRT INTEGER FUNCTION NISQRT(I) END FUNCTION END INTERFACE CALL SUBR CONTAINS SUBROUTINE SUBR INTRINSIC SQRT PRINT *, SQRT(4) PRINT *, SQRT(4.0) END SUBROUTINE END INTEGER FUNCTION NISQRT(I) NISQRT = -INT(SQRT(REAL(I))) END
If the processor provides SQRT for integer arguments as an extension, that intrinsic procedure will be invoked instead of the users NISQRT function. This occurs because the INTRINSIC statement takes priority over host association. It is recommended that the INTRINSIC attribute not be specified for a name that is the same as the name of a generic interface accessed by host association."
Public Review Comment J32017 from Robert Corbett
commentor's Subject was "typographical error in CMPLX"
In paragraph 3 of Section 13.7.34, the word "integeror" should be replaced with "integer.".
J3 agrees that this typographical error should be corrected in the manner suggested.
In the draft at subclause 13.7.34 paragraph 3
Public Review Comment J32018 from Robert Corbett
commentor's Subject was "imprecise description of constraints""
The final clause of Section 1.6.3 should state that the syntax rules can be extended by a constraint. I suggest replacing the final clause of Section 1.6.3 with
"where a syntax rule is incomplete, it is restricted or extended (see C1002) by corresponding constraints and text."
The problem should instead be corrected by revising how format-specification is defined.
C1002 as it is presently worded could in addition cause confusion, since it doesn't refer to the comma in R1002; rather, it refers to the comma in xyz-list in Clause 1.
J3 will replace format-item-list in R1002 by format-items, add a rule and apply a new constraint.
In the draft. before paragraph 1 in 10.3.1 add a new syntax rule after R1005:
In the draft at subclause 10.2.1 C1002 Replace "used ... omitted" to "shall not be omitted except", make it a constraint on the new R1005+, and move it (and its bulleted list) to be after C1004.
Public Review Comment J32019 from Robert Corbett
commentor's Subject was "undue claims concerning compatibility"
Section 1.5 claims to describe all incompatibilities between the current standard and the previous standards back to the FORTRAN 77 standard. It never has. It would be better to say that the major incompatibilities are described.
J3 believes it caught them all. If specific instances are omitted, and brought to J3's attention, J3 would be happy to specify them.
There are, however, other minor structural difficulties in subclauses 1.5.4 and 1.5.5.
In the draft at subclause 1.5.4 paragraph 1
In the draft at subclause 1.5.5 paragraph 1
Public Review Comment J32020 from Robert Corbett
commentor's Subject was "constraint C538"
Constraint C538 in Section 5.3.9 introduces an incompatibility with Fortran 2003 that is not described in Section 1.5 of the Fortran 2008 draft.
The Fortran 90 standard required the name of an external procedure used as an actual argument to be declared in an EXTERNAL statement or in an interface block. Because the name of an external procedure could not appear in an interface block in the subprogram in which it is defined, that effectively required the name to appear in an EXTERNAL statement if it was passed as an argument. What once was required now is prohibited.
I suggest adding a mention of constraint C538 to the list of incompatibilities in Section 1.5.2.
C538 repeats a requirement from Fortran 2003 subclause 126.96.36.199. It was made a constraint in 06-007r1.
There is no incompatibility with Fortran 2003.
This requirement did not appear in subclause 188.8.131.52 in Fortran 95.
Instead, subclause 184.108.40.206 of Fortran 95 required that a procedure that is used as an actual argument shall either have explicit interface or be explicitly declared to have the EXTERNAL attribute. In Fortran 95, an external procedure has explicit interface within its own body if it is recursive. Therefore, it was not required to specify a procedure to have the EXTERNAL attribute, within its own body, if it is used as an actual argument. If it is not recursive, it does not have explicit interface, but there is no point in passing it as an actual argument, since it cannot be executed, so there is no need to specify explicitly that it has the EXTERNAL attribute.
In Fortran 2008, all procedures have explicit interface within the subprograms that define them (220.127.116.11 paragraph 1).
It was not clear in Fortran 95 whether a recursive procedure name could be explicitly given the EXTERNAL attribute within its own body.
J3 believes that if there was an incompatibility between Fortran 95 and Fortran 2003, the correct mechanism to correct it or announce it is a corrigendum.
Public Review Comment J32021 from Robert Corbett
commentor's Subject was "Allow compatible specific interfaces"
Constraint C1201 in Section 18.104.22.168 of the Fortran 2008 draft is detested by many users. That constraint should be eliminated. The standard already requires that the characteristics specified by the interface body must match those of the subprogram definition (see paragraph 7 of Section 22.214.171.124). That requirement should be elevated to a constraint for this specific case. Constraint C1201 might be replaced with
c1201 (R1201) If an interface block contains an interface-body for a procedure defined by that subprogram, the characteristics of the specific interface defined by the interface-body shall be consistent with those specified in the procedure definition except that the interface may specify a procedure that is not pure if the procedure is defined to be pure.
Some users write modules containing interface blocks describing the external procedure used in their program. They then use that module in all the external subroutines and functions in their program. Most of them have by now learned to use renaming to avoid problems with constraint C1201, but they don't like it. They would like the information from the interface block created for a procedure to be visible and used for checking in the subprogram that defines that procedure.
J3 agrees this would be a useful feature. The proposed constraint is not, on its own, adequate. J3 has identified some editorial changes that would be necessary to implement this feature (see 08-235r1), but J3 is not confident that all necessary changes have been identified at this time.
Since SUBROUTINE and FUNCTION are optional on END statements for module procedures in the current draft, a better solution for the illustrative problem the commentor presented is to create module procedures from external procedures by using INCLUDE lines.
Public Review Comment J32022 from Robert Corbett
commentor's Subject was "allow multiple generic interfaces that define the same specific interface in a scoping unit"
The restriction given in the last sentence of the seventh paragraph of Section 126.96.36.199 of the Fortran 2008 draft creates unnecessary problems for users. It should be elided.
There is no reason to prohibit two generic interfaces that contain compatible interfaces with the same name from appearing in a the same scoping unit. Some users work around this restriction by writing wrapper routines. More sophisticated users might use alternate entry points to work around the restriction. Neither workaround is desirable.
J3 considered this and believes it is too complicated to pursue at this time.
The problem is that equivalence of characteristics is not sufficient, and there is not adequate time to determine exactly and confidently what the requirements ought to be.
Public Review Comment J32023 from Robert Corbett
commentor's Subject was "zeros and sign control"
Paragraph 3 of Section 4.4.3 should explicitly state that processors that distinguish between positive and negative zeros shall treat zero values that are positive zeros as positive values and negative zeros as negative values during format editing.
J3 agrees that the standard should explicitly state how negative zeroes are represented in formatted output, but feels that 4.4.3 is not the appropriate place for this. J3 also notes that the text needs to reference "the sign mode of the connection" when discussing the sign prefix.
In the draft at subclause 10.7.2.1
"On output with I, F, E, EN, ES, D, and G editing, the representation of a positive internal value in the field may be prefixed with a plus sign, as controlled by the S, SP, and SS edit descriptors or the sign mode (188.8.131.52, 184.108.40.206) for the connection. The representation of a negative internal value in the field shall be prefixed with a minus sign. If the processor distinguishes between positive and negative zero, the representation of a negative zero shall be prefixed with a minus sign; otherwise, a zero value shall be treated as positive for the purpose of determining the sign prefix."
Public Review Comment J32024 from Robert Corbett
commentor's Subject was "pick a model of generic intrinsics"
The draft standard appears to use two distinct models of generic intrinsics in different contexts. One model is that a generic intrinsic is like a user defined generic except that the sets of specific intrinsic procedures associated with some generic intrinsics are infinite sets. The language of constraint C542 in Section 5.3.11 clearly reflects that model. The other model is that there are no specific intrinsic procedures associated with a generic intrinsic. Under that model, the generic intrinsic does not function as a surrogate for a set of specific intrinsics, a reference of a generic intrinsic is resolved against the generic intrinsic itself. That model appears to be the model in effect in the rules for generic resolution in Section 220.127.116.11. Either model could describe the semantics of generic intrinsics. Using both models adds unnecessary confusion.
Some generic intrinsic procedures, such as LBOUND, do not have a definite set of specific procedures. The standard necessarily has two models. J3 believes that no changes are required.
Public Review Comment J32025 from Robert Corbett
commentor's Subject was "types declared to be PRIVATE"
When the standard speaks of a type declared to be PRIVATE, it means a type declared to be PRIVATE in the scoping unit in which the type definition that declared that type appeared. The standard should say that somewhere.
For example, in the program
MODULE MOD1 TYPE T INTEGER :: I END TYPE TYPE(T) :: X END MODULE MOD2 USE MOD1 PRIVATE T TYPE(T) :: Y END PROGRAM MAIN USE MOD2 Y%I = 12 X = Y END
The type T in module MOD2 is not considered a type declared to be PRIVATE, and so there is no conflict between the first and last sentences of the second paragraph in Section 18.104.22.168 of the standard.
The commentor's observation that there is no conflict in this example is correct.
The final sentence of subclause 22.214.171.124 paragraph 2 is not germane since the SEQUENCE attribute does not appear.
If SEQUENCE had been specified, there would be deeper questions that deserve more significant consideration than can be given to them at this time. J3 has internally generated an interpretation request.
Public Review Comment J32026 from Robert Corbett
commentor's Subject was "implicit typing should not be allowed in derived"
Consider the program
PROGRAM MAIN TYPE T INTEGER :: I = BIT_SIZE(J) END TYPE CALL SUBR1 CONTAINS SUBROUTINE SUBR1 J = 1 CALL SUBR2 PRINT *, J END SUBROUTINE SUBROUTINE SUBR2 J = 2 END SUBROUTINE END
This program prints either 1 or 2 depending on the implementation with which it is compiled. Some implementations implicitly declared J in the top-level scope of the main program. Some declare J in the scope of the derived type definition, which is semantic nonsense, but there you have it.
Paragraph 4 of Section 5.5 of the Fortran 2008 draft states
The data entity is treated as if it were explicitly declared in the outermost scoping unit in which it appears.
The derived type definition is the outermost scoping unit in which the occurrence of J in the derived type definition appears, but an explicit definition of J is not allowed in that context.
The simple solution for this problem is to ban implicit typing in derived type definitions.
The same specification appears in the fourth paragraph of subclause 5.3 of the Fortran 2003 and Fortran 95 standards.
This comment raises questions that deserve deeper consideration than J3 can give them at this time. J3 has internally generated an interpretation request.
Public Review Comment J32027 from Robert Corbett
commentor's Subject was "definition is poorly defined"
Consider the program:
PROGRAM MAIN TYPE T1 SEQUENCE INTEGER I, J END TYPE TYPE T2 SEQUENCE INTEGER I, J END TYPE TYPE(T1) X, Y EQUIVALENCE (I, X, Y) X%J = 2 I = 1 PRINT *, I, X, Y END
The assignment to the variable I causes I, X, and Y to become defined (see items (1) and (15) of Section 16.6.5). Therefore, according to item (1) of Section 16.6.6, I, X, and Y become undefined.
Item (1) of Section 16.6.6 should be modified so that it directly applies only to ultimate components. The effect on aggregate types will then occur as is appropriate because of the rules given in Section 16.6.1.
Subclause 16.6.6 item (1) of the Fortran 2003 standard, and subclause 14.7.6 item (1) of the Fortran 95 standard, both specify the same behavior.
This comment raises questions that deserve deeper consideration than J3 can give them at this time. J3 has internally generated an interpretation request.
Public Review Comment J32028 from Robert Corbett
commentor's Subject was "the EXTERNAL attribute"
Paragraph 4 of Section 126.96.36.199 of the Fortran 2008 draft states
If an external procedure name or dummy procedure name is used as an actual argument, its interface shall be explicit or it shall be explicitly declared to have the EXPLICIT attribute.
That statement gets the condition exactly right.
Paragraph 2 of Section 5.3.9 states
If an external procedure or dummy procedure is used as an actual argument or is the target of a procedure pointer assignment, it shall be declared to have the EXTERNAL attribute.
That statement is not as good as the previous statement. It introduces an ambiguity that is not in the previous statement, regarding what constitutes being "declared to have the EXTERNAL attribute." That ambiguity has led to several statements regarding the EXTERNAL attribute to be added to Chapter 12 of the draft standard. That work has made the standard longer for no particular good. Furthermore, there are still important cases that have been missed.
I suggest deleting paragraph 2 of Section 5.3.9. I suggest adding the statement
If an external procedure name or dummy procedure name is the target of a procedure pointer assignment, its interface shall be explicit or it shall be explicitly declared to have the EXPLICIT attribute.
to Section 188.8.131.52.
J3 understands that the commentor intended to refer to the EXTERNAL attribute, not an EXPLICIT attribute.
J3 recognized this problem at meeting 184. When procedure pointers were adopted into Fortran 2003, as with data pointers, the intent was that pointer association and argument association would be as similar as possible. Meeting paper 08-156r2 addressed this problem, making sure the requirements are the same in both cases.
Public Review Comment J32029 from Robert Corbett
commentor's Subject was "Fix error in type equivalence"
Paragraph 2 of Section 184.108.40.206 states
Data entities in different scoping units also have the same type if they are declared with reference to different derived-type definitions that specify the same type name, ...
Why should it matter that that the data entities are in different scoping units? Shouldn't the same rules apply if the data entities are in the same scoping unit? The answer to the first question is that it should not matter, and the answer to the second is that the same rules should apply.
Examination of the first paragraph of Section 220.127.116.11 reveals what likely happened. That paragraph states
Derived-type definitions with the same name may appear in different scoping units, in which case they may be independent and describe different derived types or they may describe the same type.
Obviously, the phrase "in different scoping units" in the quotation from paragraph 2 was misapplied to the data entity. It should have been applied to the derived-types definitions.
J3 agrees that there is a problem, but it is in subclause 18.104.22.168 paragraph 2 (there is no subclause 22.214.171.124, and 126.96.36.199 does not have a paragraph similar to the cited one).
In the draft at subclause 188.8.131.52 paragraph 2
Public Review Comment J32030 from Robert Corbett
commentor's Subject was "derived-type equivalence"
The idea of describing derived type equivalence in terms of data entities, as is done in Section 184.108.40.206 of the Fortran 2008 draft is screwy. Type equivalence should be described in terms of the types and the derived-type definitions that define them.
There is no subclause 220.127.116.11, nor a subclause 18.104.22.168, nor a subclause 4.1.5. Subclause 22.214.171.124 is not germane to this question. The only subclause that appears to be germane is 126.96.36.199.
The interesting question is almost always "do these two objects have the same type." The most obvious examples are argument association, pointer assignment, intrinsic assignment and storage association.
We arrive at the same conclusion by reasoning in terms of objects or in terms of types.
J3 prefers not to change its descriptive model of type equivalence.
Public Review Comment J32031 from Robert Corbett
commentor's Subject was "equivalence of circular types"
the draft fortran standard allow circular type definitions (see section 4.5.3). type equivalence for derived types that do not have the sequence property or the bind attribute is trivial, they are equivalent only if they are defined by the same derived-type definition. for type that have the sequence property or the bind attribute, type equivalence is defined in terms of a hybrid of structural equivalence and name equivalence. this hybrid condition is easier to test than pure structural equivalence, but harder to test than pure name equivalence. like other definitions of type equivalence based on structural equivalence, the definition of the equivalence of two circular types is tricky. the draft fortran standard avoids this problem by not defining what it means for two circular types to be equivalent.
consider the program
module mod type t1 sequence integer i type(t2), pointer :: p end type type t2 sequence integer i type(t1), pointer :: p end type end program main use mod, only: t3 => T1, T4 => T2 TYPE T1 SEQUENCE INTEGER I TYPE(T2), POINTER :: P END TYPE TYPE T2 SEQUENCE INTEGER I TYPE(T1), POINTER :: P END TYPE TYPE(T1) :: X TYPE(T3) :: Y Y%I = 1 NULLIFY(Y%P) X = Y END
The types T1 and T2 defined in the module might or might not be equivalent to the types T1 and T2 defined in the main program depending on the definition of type equivalence for types with circular definitions. Because the standard does not provide such a definition, implementors have had to supply their own definitions. I have found three distinct definitions implemented by different compilers.
In the case of the example given above, Sun Fortran considers the types T1 and T2 defined in the module to be equivalent to the types T1 and T2 defined in the main program. A compiler from another vendor considers them to be different and produces the error message
fortcom: Error: testa.f, line 32: An assignment of different structure types is invalid. [Y] X = Y ............^ compilation aborted for testa.f (code 1)
when it tries to compile the code above.
I know two ways to precisely define structural equivalence of circular types. One is to give an algorithm for testing type equivalence. The other is to define type equivalence in terms of equivalence classes. Either approach will be considerably long and more complicated than the definition of derived-type equivalence given in the draft standard.
The definition in paragraph 2 of subclause 188.8.131.52 is unambiguous, even though it is recursive in the case of recursive types ("... have type parameters and components that agree in order, name and attributes"). The obvious recursive graph-traversal algorithm that determines that the two collections of recursive types in the example are equivalent might have exponential time complexity, but that is a different question.
J3 prefers not to change the description of equivalence of recursive sequence types. Although transforming the definition of equivalence into an efficient algorithm is difficult, J3 prefers clarity over a detailed but extensive and opaque description.
Public Review Comment J32032 from James Giles
commentor's Subject was "New intrinsic procedures"
There are a large number of new intrinsic functions in the proposed new standard. In the last few standards there have been a few as well. But in the past many of the new names were long and unlikely to cause legacy codes any naming conflicts. Sure, some (like NEW_LINE) were problematical, but most were not. That is not the case in this revision.
I think most of the new intrinsic functions should be placed in one or more intrinsic modules rather than joining the "pervasive" category of names (those that are visible every- where unless explicitly hidden by an explicit declaration). Sure, the author of that old legacy code should have used an EXTERNAL declaration for all his functions. But how many actually have?
In fact, I think the committee should set a policy that no new intrinsics will be added to the pervasive namespace in the future. All new intrinsics should be in intrinsic modules - starting with f2008.
J3 considered placing some of the new intrinsics in intrinsic modules. The standard treats intrinsic procedures and module procedures differently; for example, intrinsic procedures may appear in more contexts. J3 believes the additional contexts are useful. Therefore, J3 declines to move these procedures to a separate module.
Public Review Comment J32033 from James Giles
commentor's Subject was "LEADZ and TRAILZ"
The intrinsic functions LEADZ and TRAILZ should be called LEFTZ and RIGHTZ respectively.
It's true that if you look far enough you can find uses of "lead" and "trail" that conform to the meaning you intend in the present proposed document. However, you don't have to look far afield to find uses that aren't consistent with your intent. In fact, the description of TRANSFER talks about the "leading parts" of source values and results. If I look at actual implementations that support more than one INTEGER KIND, I find no compilers available to me where those "leading parts" aren't the least significant parts.
You don't have to look afield at all to find "left" and "right" used in the sense I propose. In fact, many new intrinsics in the F2008 document (shifts and masks) use the terms quite consistently. The BIT model also defines the left bits to be the most significant and the right to be the least significant. I've never seen anyone use "left" and "right", with respect to the bits of a number, differently.
Aside from the issue of clarity, there are no other criteria in which the two naming conventions differ. They even require the same number of characters to write out. The most mnemonic should be the naming convention chosen.
The intrinsic functions LEADZ and TRAILZ were proposed for Fortran 2008 by work item RU-005 which proposed standardizing various functions from HPF. The work item was incorporated into work item J3-047 that introduced other bit manipulation intrinsic functions.
The names of LEADZ and TRAILZ were adopted from the HPF specification. A central purpose of the proposal was to standardize existing practice. Changing the names of these functions would circumvent that purpose. Therefore, J3 prefers to leave the names of these functions as currently specified in the draft.
Public Review Comment J32034 from James Giles
commentor's Subject was "CRITICAL and BLOCK"
I won't be commenting on most of the CO-ARRAY features because I don't quite yet fully understand them. But in most of the different kinds of parallel computing I've done in the past the need for critical sections arises.
Instead of a CRITICAL construct, I think that CRITICAL should be a keyword like PURE or RECURSIVE (and such) that applied to procedure declarations. Similarly, it should be an optional keyword on the new BLOCK construct:
block-stmt is [ block-construct-name : ] [ CRITICAL ] BLOCK
The reason is that when I've needed critical sections the shared data being manipulated is often something that should be imported (USE) for that particular section alone and not visible elsewhere. There are also often additional local variables needed only temporarily for manipulating the shared data. So it's often the case that critical sections coincide with the need for declarations. Rather than add the ability to declare within CRITICAL constructs, it makes sense to combine the feature with existing constructs that already can declare things.
As an aside, except for this possible merging with CRITICAL, the only real value I see for the BLOCK construct is if some form of control of host association is forthcoming.
Many of the expected uses of a CRITICAL construct involve the simple update of a coarray on a fixed image, or forced ordering of input and output operations. These uses are addressed fully by the simple CRITICAL construct.
By separating the CRITICAL and BLOCK constructs in the standard, an implementation could implement one without the other, providing greater flexibility in meeting customer demands.
The argument for combining the critical idea with blocks or procedures has merit and could be considered in a future standard. These ideas could be incorporated as natural extensions of the current specification. J3 prefers not to include the feature in this revision of the standard.
Public Review Comment J32035 from James Giles
commentor's Subject was "IMPURE ELEMENTALs"
I don't see the value in having IMPURE ELEMENTAL procedures. There are no examples in the draft standard and the only example in the document describing new features can be rewritten without the procedure being ELEMENTAL at all. The example in the document is:
impure elemental function accumulate (a,sum) real :: accumulate real, intent(in) :: a real, intent(inout) :: sum sum = sum + a accumulate = sum end function accumulate
Where the call is:
real a(n), sum : sum = 0.0 a = accumulate (a,sum)
This seems simple enough. But suppose SUM was also declared to be an array. The procedure would no longer "accumulate". Nor would it generate any error messages or warnings. An elemental is simply not a good way of accompishing such things in the first place. You're trying to graft inappropriate functionality in a place it doesn't fit well.
Now, if the procedure were declared:
function accumulate (a,s) real, intent(inout) :: s real, intent(in) :: a(:) real :: accumulate(size(a)) s = sum(a) accumulate = s end function accumulate
The caller could be the same. The SUM argument could even be made optional - it is certainly required to remain a scalar.
The case for impure elementals was made in J3 meeting paper 05-238, from meeting 173 in 2005. The feature had earlier been proposed by the UK delegation as item UK-011. The case for them was sufficiently convincing that they were added to the work plan for the current revision. One of the several reasons for their inclusion in the work plan was their applicability to the reverse mode of automatic differentiation. Another reason for impure elemental procedures is that a pure elemental procedure cannot contain a variable with the SAVE attribute, or assign a value to a variable in common or accessed by use or host association. An application where this is important is random number generators.
The example cited in the comment does not appear in the current draft.
One could accumulate into a scalar variable "SUM" by making "SUM" a variable in COMMON rather than a dummy argument (to avoid canonical promotion of scalar dummy arguments of ELEMENTAL procedures to arrays).
This was part of the justification for impure elementals: a pure ELEMENTAL procedure is not permitted to update a variable in COMMON but an impure ELEMENTAL procedure can.
The example handles rank=1 arrays. What is needed is a procedure which handles arrays of all ranks from 1 to 15.
J3 declines to remove impure elemental procedures, or change their description.
Public Review Comment J32036 from James Giles
commentor's Subject was "Submodules"
I understand that when something is issued as a TR it's basically already a part of the standard even though it never went through a public review. However it was the submodule feature that convinced me that public review is just as important for TRs as for whole revised standards.
The submodule feature is supposed to have basically three advantages. First, it provides a way of changing code within modules without causing compilation cascades. Second, it provides the ability for vendors to distribute proprietary code without revealing source while still having the advantage of interface checking at compile-time. Third, it allows conceptually nesting of module scopes to any depth.
At the time submodules were first proposed, several alter- native ways to address the first two points above were also proposed. Any of these would have been easier to integrate into the standard, easier for programmers to learn, and easier to incorporate into existing programs than submodules. Submodules were essentially the most verbose and least convenient of the ways proposed to deal with those issues.
As for the third of the "advantages" of submodules, nesting of scopes to any depth, is something that I believe the language shouldn't support. Once upon a time (in the F8x proposal) internal procedures were permitted to nest to any depth. The F90 standard (I believe correctly) disallowed that. For both practical reasons, and because I've read papers indicating just this point in other languages, I'm convinced that nesting of program units is counterproductive.
As I said, I'm aware that submodules are already officially part of the language and nothing I say can reverse that. If submodules were not themselves also allowed to have submodules, I probably would not have made any comment at all - in spite of the verbose way they manage avoidance of compilation cascades.
One of the uses of submodules specified in TR 19767 was to manage and partition large concepts, which would otherwise require large and monolithic modules. Partitioning these modules in the case that their procedures need to share low-level procedures, types, or data entities, is most easily done with at least three levels, with the middle level containing the shared entities.
The Ada community has found private child units, the Ada structure equivalent to submodules, to be useful.
J3 prefers not to change the submodule feature.
Public Review Comment J32037 from James Giles
commentor's Subject was "The g0 edit descriptor"
According to the draft document:
C1007 (R1006) For the G edit descriptor, d shall be specified if and only if w is not zero.
To me this eliminates any value the g0 feature might have. What's needed is something like list-directed output but with the precision controlled by the programmer.
For example, in order for an input item to have the same internal value as the original value that was output, the output must generally carry at least 9 digits (for IEEE single precision).
If the ability to specify d were present, G would probably become my main output edit descriptor. I was looking forward to g0 before I found that it wasn't allowed a d part.
J3 agrees that this would be a useful feature, and proposes the following edits.
In the draft at subclause 10.3.2
Add new constraint after C1007:
In the draft at subclause 10.7.5.1
In the draft at subclause 10.7.5.2.2 paragraph 2
End of J3's Responses to Public Comments