AI22-0097-1
!standard 1.1.4(19) 24-09-05 AI22-0097-1/06
!standard 1.1.4(21)
!standard 3.2.2(13/5)
!standard 3.5.1(12)
!standard 3.5.10(14)
!standard 3.5.10(16)
!standard 3.5.7(28)
!standard 3.9.1(5)
!standard 3.9.1(7/2)
!standard 3.10.2(32.6/5)
!standard 3.10.2(37/5)
!standard 3.10.2(38/5)
!standard 4.1.6(18/4)
!standard 4.3.3(33/5)
!standard 4.7(5/5)
!standard 5.4(15/5)
!standard 5.5(12/5)
!standard 5.5(14/5)
!standard 8.5(3)
!standard 8.5(6)
!standard 8.5(7)
!standard 9.5.1(18/5)
!standard 9.5.1(23/5)
!standard 11.5(29/5)
!standard 11.5(29.1/2)
!standard 13.11.3(9/5)
!standard 13.11.4(33/5)
!standard 13.11.4(34/5)
!standard 13.11.4(35/5)
!standard 13.13.1(39/2)
!standard 13.13.2(57/5)
!standard A.4.3(107/5)
!standard A.4.3(108)
!standard A.4.11(108/3)
!standard A.18.2(263/2)
!standard B.1(41/5)
!standard B.1(43/3)
!standard B.1(44/5)
!standard B.3(72)
!standard B.3(73)
!standard B.3(75/4)
!standard C.7.2(30.1/2)
!standard C.7.2(32/5)
!standard D.3(17)
!standard D.3(21/5)
!standard D.3(22)
!standard D.5.1(14)
!standard D.5.1(19/5)
!standard F.2(17)
!standard H(6/5)
!class binding interpretation 24-02-24
!status Revision-202Y 24-07-18
!status WG9 Approved 24-10-10
!status ARG Approved 8-0-1 24-07-18
!status work item 24-02-24
!status received 24-02-22
!submitter Christoph Grein
!priority Low
!difficulty Easy
!qualifier Clarification
!subject Usage Advice (Part 2)
Move certain NOTEs and some examples into the “Usage” category (see AI22-0055-1), replacing some of the separate “Examples" sections.
AI22-0055-1 added a “Usage” category to RM text, so that we can provide advice to the Ada user. Traditionally, that was done with Notes, but words like "should", "recommended", or "preferred" are not allowed in notes by the current JTC1 drafting standards.
AI22-0055-1 moved a number of notes to the new category, those which caused problems during the ISO review or clearly should have (the ISO editors missed a few).
However, additional notes and some examples also provide advice to the Ada user. These also should be handled consistently, lest readers of the RM be confused.
(See Summary.)
[Courtesy of Christoph Grein <christ-usch.grein@t-online.de>.]
Modify 1.1.4(19):
{Usage}
[NOTE 1 ] The syntax rules describing structured constructs are presented in a form that corresponds to the recommended paragraphing. For example, an if_statement is defined as:
Modify 1.1.4(21):
[NOTE 2 ] The line breaks and indentation in the syntax rules indicate the recommended line breaks and indentation in the corresponding constructs. The preferred places for other line breaks are after semicolons.
Modify 3.2.2(13/5):
{Usage}
[NOTE ] A scalar_constraint can be applied to a subtype of an appropriate scalar type (see 3.5, 3.5.9, and J.3), even if the subtype is already constrained. On the other hand, a composite_constraint can be applied to a composite subtype (or an access-to-composite subtype) only if the composite subtype is unconstrained (see 3.6.1 and 3.7.1).
Modify 3.5.1(12):
{Usage}
[NOTE ] If an enumeration literal occurs in a context that does not otherwise suffice to determine the type of the literal, then qualification by the name of the enumeration type is one way to resolve the ambiguity (see 4.7).
Add after 3.5.10(14):
Usage
S'Scale is not always the same as S'Aft for a decimal subtype; for example, if S'Delta = 1.0 then S'Aft is 1 while S'Scale is 0.
Delete 3.5.10(16):
NOTE 2 S'Scale is not always the same as S'Aft for a decimal subtype; for example, if S'Delta = 1.0 then S'Aft is 1 while S'Scale is 0.
Modify 3.7(28):
{Usage}
[NOTE 1 ] If a discriminated type has default_expressions for its discriminants, then unconstrained variables of the type are permitted, and the values of the discriminants can be changed by an assignment to such a variable. If defaults are not provided for the discriminants, then all variables of the type are constrained, either by explicit constraint or by their initial value; the values of the discriminants of such a variable cannot be changed after initialization.
Add after 3.9.1(5):
Usage
When an extension is declared immediately within a body, primitive subprograms are inherited and are overridable, but new primitive subprograms cannot be added.
Delete 3.9.1(7/2):
NOTE 2 When an extension is declared immediately within a body, primitive subprograms are inherited and are overridable, but new primitive subprograms cannot be added.
Add after 3.10.2(32.6/5):
Usage
The Access attribute for subprograms and parameters of an anonymous access-to-subprogram type can be used together to implement “downward closures” — that is, to pass a more-nested subprogram as a parameter to a less-nested subprogram, as can be appropriate for an iterator abstraction or numerical integration. Downward closures can also be implemented using generic formal subprograms (see 12.6). Unlike for objects, there is no Unchecked_Access attribute for subprograms.
Using an access-to-class-wide tagged type with a dispatching operation is a potentially more structured alternative to using an access-to-subprogram type.
Delete 3.10.2(37/5):
NOTE 5 The Access attribute for subprograms and parameters of an anonymous access-to-subprogram type can be used together to implement “downward closures” — that is, to pass a more-nested subprogram as a parameter to a less-nested subprogram, as can be appropriate for an iterator abstraction or numerical integration. Downward closures can also be implemented using generic formal subprograms (see 12.6). Unlike for objects, there is no Unchecked_Access attribute for subprograms.
Delete 3.10.2(38/5):
NOTE 6 Using an access-to-class-wide tagged type with a dispatching operation is a potentially more structured alternative to using an access-to-subprogram type.
Modify 4.1.6(18/4):
{Usage}
[NOTE ] The Constant_Indexing and Variable_Indexing aspects cannot be redefined when inherited for a derived type, but the functions that they denote can be modified by overriding or overloading.
[Author’s Note: This sounds like a weak advice.]
Modify 4.3.3(33/5):
{Usage}
[NOTE 1 ] An array_aggregate delimited by square brackets can be used to specify an array with a single component, while in an array_aggregate delimited by parentheses, positional notation can only be used with two or more expressions; a single expression in parentheses is interpreted as a parenthesized expression.
Modify 4.7(5/5):
{Usage}
[NOTE ] When a given context does not uniquely identify an expected type, a qualified_expression can be used to do so. In particular, if an overloaded name or aggregate is passed to an overloaded subprogram, it can be necessary to qualify the operand to resolve its type.
Modify 5.4(14/5):
{Usage}
[NOTE ] The execution of a case_statement chooses one and only one alternative. Qualification of the expression of a case_statement by a static subtype can often be used to limit the number of choices that [can]{have to} be given explicitly.
Add after 5.5(12/5):
Usage
An object_declaration should not be given for a loop parameter, since the loop parameter is automatically declared by the loop_parameter_specification. The scope of a loop parameter extends from the loop_parameter_specification to the end of the loop_statement, and the visibility rules are such that a loop parameter is only visible within the sequence_of_statements of the loop.
Delete 5.5(14/5):
NOTE 2 No separate object_declaration is expected for a loop parameter, since the loop parameter is automatically declared by the loop_parameter_specification. The scope of a loop parameter extends from the loop_parameter_specification to the end of the loop_statement, and the visibility rules are such that a loop parameter is only visible within the sequence_of_statements of the loop.
[We’ve reverted the wording to use “should”, which makes it clear this is advice.]
Add after 8.5(3):
Usage
A subtype defined without any additional constraint can be used to achieve the effect of renaming another subtype (including a task or protected subtype) as in
subtype Mode is Ada.Text_IO.File_Mode;
Delete 8.5(6):
NOTE 3 A subtype defined without any additional constraint can be used to achieve the effect of renaming another subtype (including a task or protected subtype) as in
Delete 8.5(7):
subtype Mode is Ada.Text_IO.File_Mode;
[Author’s Note: Very weak advice.]
Add after 9.5.1(18/5):
Usage
The aspect Nonblocking can be specified True on the definition of a protected unit in order to reject most attempts to use potentially blocking operations within the protected unit (see 9.5). The pragma Detect_Blocking can be used to ensure that any remaining executions of potentially blocking operations during a protected action raise Program_Error. See H.5.
Delete 9.5.1(23/5):
NOTE 5 The aspect Nonblocking can be specified True on the definition of a protected unit in order to reject most attempts to use potentially blocking operations within the protected unit (see 9.5). The pragma Detect_Blocking can be used to ensure that any remaining executions of potentially blocking operations during a protected action raise Program_Error. See H.5.
Modify 11.5(29/5):
{Usage}
[NOTE 1 ] There is no guarantee that a suppressed check is actually removed; hence a pragma Suppress should be used only for efficiency reasons.
[Reverted to original wording using “should”.]
Modify 11.5(29.1/2):
[NOTE 2 ] It is possible to give both a pragma Suppress and Unsuppress for the same check immediately within the same declarative_part. In that case, the last pragma given determines whether or not the check is suppressed. Similarly, it is possible to resuppress a check which has been unsuppressed by giving a pragma Suppress in an inner declarative region.
[Author’s Note: Also without "should" this looks like advice.]
Modify 13.11.3(9/5):
{Usage}
[NOTE 1 ] Default_Storage_Pool can be used with restrictions No_Coextensions and No_Access_Parameter_Allocators (see H.4) to ensure that all allocators use the default pool.
Modify 13.11.4(33/5):
{Usage}
[NOTE 1 ] A user-defined storage pool type that supports subpools can be implemented by extending the Root_Storage_Pool_With_Subpools type, and overriding the primitive subprograms Create_Subpool, Allocate_From_Subpool, and Deallocate_Subpool. Create_Subpool {should}[is expected to] call Set_Pool_Of_Subpool before returning the subpool handle. To make use of such a pool, a user can declare an object of the type extension, can use it to define the Storage_Pool attribute of one or more access types, and then can invoke Create_Subpool to obtain subpool handles associated with the pool.
[Author’s Note: The first change was reverted to “should”, the other changes here are retained.]
Modify 13.11.4(34/5):
[NOTE 2 ] A user-defined storage pool type that supports subpools can define additional subpool constructors similar to Create_Subpool (these typically will have additional parameters).
Modify 13.11.4(35/5):
[NOTE 3 ] The pool implementor can override Default_Subpool_For_Pool if they want the pool to support a default subpool for the pool. The implementor can override Deallocate if individual object reclamation is to be supported, and can override Storage_Size if there is some limit on the total size of the storage pool. The implementor can override Initialize and Finalize if there is any desire for nontrivial initialization and finalization for the pool as a whole. For example, Finalize can reclaim blocks of storage that are allocated over and above the space occupied by the pool object itself. The pool implementor can extend the Root_Subpool type as necessary to carry additional information with each subpool provided by Create_Subpool.
[Author’s Note: We’ve used the revised wording here rather than reverting to “should” as it works either way, and many of the words aren’t allowed. It still is advice.]
Modify 13.13.1(39/2):
{Usage}
[NOTE 2 ] If the end of stream has been reached, and Item'First is Stream_Element_Offset'First, Read will raise Constraint_Error.{ Therefore, Stream_Element_Arrays should start at 0 or 1, not Stream_Element_Offset'First.}
[Author’s Note: This does not sound like advice. However, AARM 13.13.1(39.a/2) does sound like advice and should be promoted to the RM proper.]
Delete AARM 13.13.1(39.a/2):
Ramification: Thus, Stream_Element_Arrays should start at 0 or 1, not Stream_Element_Offset'First.]
Modify 13.13.2(57/5):
{Usage}
[NOTE 1 ] For a definite subtype S of a type T, only T'Write and T'Read are necessary to pass an arbitrary value of the subtype through a stream. For an indefinite subtype S of a type T, T'Output and T'Input will normally be necessary, since T'Write and T'Read do not pass bounds, discriminants, or tags.
[Author’s Note: This looks like weak advice. The original wording used “needed” rather than “necessary”; unfortunately that can only be used in requirements so we cannot revert this wording. (“needed” makes more sense for the first sentence.)]
Modify A.4.3(107/5):
{Usage}
[NOTE 1 ] In the Index and Count functions taking Pattern and Mapping parameters, for there to be a match, the actual String parameter passed to Pattern can contain only characters occurring as target characters of the mapping.
[Author’s Note: Another weak advice.]
Modify A.4.3(108):
[NOTE 2 ] In the Insert subprograms, inserting at the end of a string is obtained by passing Source'Last+1 as the Before parameter.
[Author’s Note: Also weak advice.]
Modify A.4.11(108/3):
{Usage}
[NOTE ] A BOM (Byte-Order Mark, code position 16#FEFF#) can be included in a file or other entity to indicate the encoding; it is skipped when decoding. Typically, only the first line of a file or other entity contains a BOM. When decoding, the Encoding function can be called on the first line to determine the encoding; this encoding will then be used in subsequent calls to Decode to convert all of the lines to an internal format.
Modify A.18.2(263/5):
{Usage}
[NOTE 1 ] All elements of a vector occupy locations in the internal array. If a sparse container is required, a Hashed_Map [can]{should} be used rather than a vector.
Add after B.1(41/5):
Usage
The Convention aspect in combination with the Import aspect indicates the conventions for accessing external entities. It is possible that the actual entity is written in assembly language, but reflects the conventions of a particular language. For example, with Convention => Ada can be used to interface to an assembly language routine that obeys the Ada compiler's calling conventions.
To obtain “call-back” to an Ada subprogram from a foreign language environment, the Convention aspect should be specified both for the access-to-subprogram type and the specific subprogram(s) to which 'Access is applied.
[Author’s Note: The original “should” was replaced in the second paragraph, and makes it clearly advice.]
Delete B.1(43/3):
NOTE 2 The Convention aspect in combination with the Import aspect indicates the conventions for accessing external entities. It is possible that the actual entity is written in assembly language, but reflects the conventions of a particular language. For example, with Convention => Ada can be used to interface to an assembly language routine that obeys the Ada compiler's calling conventions.
Delete B.1(44/5):
NOTE 3 To obtain “call-back” to an Ada subprogram from a foreign language environment, the Convention aspect can be specified both for the access-to-subprogram type and the specific subprogram(s) to which 'Access is applied.
Modify B.3(72):
{Usage}
[NOTE 1 ] Values of type char_array are not implicitly terminated with nul. If a char_array is to be passed as a parameter to an imported C function requiring nul termination, it is the programmer's responsibility to obtain this effect.
Modify B.3(73):
[NOTE 2 ] To obtain the effect of C's sizeof(item_type), where Item_Type is the corresponding Ada type, evaluate the expression: size_t(Item_Type'Size/CHAR_BIT).
Modify B.3(75/4):
[NOTE 3 ] A variadic C function can correspond to several Ada subprograms, taking various specific numbers and types of parameters.
Add after C.7.2(30.1/2):
Usage
The result of the Reference function should be used with care; it is always safe to use in the task body whose attribute is being accessed. However, when the result is being used by another task, the programmer has to ensure that the task whose attribute is being accessed is not yet terminated. Failing to do so can make the program execution erroneous.
[Author’s Note: This wording was reverted to its original form (which used “should”) above; then it was rewritten again as “must make” and “could” aren’t allowed in Standard text.]
Delete C.7.2(32/5):
NOTE 2 The result of the Reference function is always safe to use in the task body whose attribute is being accessed. However, when the result is being used by another task, the programmer will want to make sure that the task whose attribute is being accessed is not yet terminated. Failing to do so can make the program execution erroneous.
Add after D.3(17):
Usage
When specifying the ceiling of a protected object, one should choose a value that is at least as high as the highest active priority at which tasks can be executing when they call protected operations of that object. In determining this value the following factors, which can affect active priority, should be considered: the effect of Set_Priority, nested protected operations, entry calls, task activation, and other implementation-defined factors.
Attaching a protected procedure whose ceiling is below the interrupt hardware priority to an interrupt causes the execution of the program to be erroneous (see C.3.1).
Delete D.3(21/5):
NOTE 4 When specifying the ceiling of a protected object, a correct value is one that is at least as high as the highest active priority at which tasks can be executing when they call protected operations of that object. In determining this value the following factors, which can affect active priority, are relevant: the effect of Set_Priority, nested protected operations, entry calls, task activation, and other implementation-defined factors.
[Author’s Note: This wording was reverted to its original form (which used “should”) above; that makes it clear that it is usage advice.]
Delete D.3(22):
NOTE 5 Attaching a protected procedure whose ceiling is below the interrupt hardware priority to an interrupt causes the execution of the program to be erroneous (see C.3.1).
[Author’s Note: An advice not to do something.]
Add after D.5.1(14):
Usage
Changing the priorities of a set of tasks can be performed by a series of calls to Set_Priority for each task separately. For this to work reliably, it should be done within a protected operation that has high enough ceiling priority to guarantee that the operation completes without being preempted by any of the affected tasks.
Delete D.5.1(19/5):
NOTE 5 Changing the priorities of a set of tasks can be performed by a series of calls to Set_Priority for each task separately. This can be done reliably within a protected operation that has high enough ceiling priority to guarantee that the operation completes without being preempted by any of the affected tasks.
[Author’s Note: This wording was reverted to its original form (which used “should”) above; that makes it clear that it is usage advice.]
Modify F.2(17):
{Usage}
[NOTE ] The effect of division yielding a quotient with control over rounding versus truncation is obtained by applying either the function attribute Quotient_Type’Round or the conversion Quotient_Type to the expression Dividend/Divisor.
[Author’s Note: A cookbook advice.]
Modify H(6/5):
{Usage}
[NOTE ] The Valid attribute (see 13.9.2) is also useful in addressing these needs, to avoid problems that can otherwise arise from scalars that have values outside their declared range constraints.
For background on why the Usage category was created, see AI22-0055-1.
Christoph Grein kindly read all of the existing notes (in the entire RM) and determined which should be moved to this new category.
We also believe that some of the examples are essentially usage notes. However, we need to be careful that the examples still can be formatted in appropriate ISO format when we need to produce a new Ada Standard.
@drepl
@xindent{@s9{NOTE 1 @ The syntax rules describing structured constructs are presented in a form that corresponds to the recommended paragraphing. For example, an @fa{if_statement} is defined as:}}
@dby
@s8{@i{Usage}}
The syntax rules describing structured constructs are presented in a form that corresponds to the recommended paragraphing. For example, an @fa{if_statement} is defined as:
@drepl
@xindent{@s9{NOTE 2 @ The line breaks and indentation in the syntax rules indicate the recommended line breaks and indentation in the corresponding constructs. The preferred places for other line breaks are after semicolons.}}
@dby
The line breaks and indentation in the syntax rules indicate the recommended line breaks and indentation in the corresponding constructs. The preferred places for other line breaks are after semicolons.
@drepl
@xindent{@s9{NOTE @ A @fa{scalar_constraint} can be applied to a subtype of an appropriate scalar type (see @ref{3.5}, @ref{3.5.9}, and @ref{J.3}), even if the subtype is already constrained. On the other hand, a @fa{composite_constraint} can be applied to a composite subtype (or an access-to-composite subtype) only if the composite subtype is unconstrained (see @ref{3.6.1} and @ref{3.7.1}).}}
@dby
@s8{@i{Usage}}
A @fa{scalar_constraint} can be applied to a subtype of an appropriate scalar type (see @ref{3.5}, @ref{3.5.9}, and @ref{J.3}), even if the subtype is already constrained. On the other hand, a @fa{composite_constraint} can be applied to a composite subtype (or an access-to-composite subtype) only if the composite subtype is unconstrained (see @ref{3.6.1} and @ref{3.7.1}).
@drepl
@xindent{@s9{NOTE @ If an enumeration literal occurs in a context that does not otherwise suffice to determine the type of the literal, then qualification by the name of the enumeration type is one way to resolve the ambiguity (see @ref{4.7}).}}
@dby
@s8{@i{Usage}}
If an enumeration literal occurs in a context that does not otherwise suffice to determine the type of the literal, then qualification by the name of the enumeration type is one way to resolve the ambiguity (see @ref{4.7}).
@dinsa
@xindent{The function returns the value obtained by rounding X (away from 0, if X is midway between two values of the type of S).}
@dinst
@s8{@i{Usage}}
S'Scale is not always the same as S'Aft for a decimal subtype; for example, if S'Delta = 1.0 then S'Aft is 1 while S'Scale is 0.
@ddel
@xindent{@s9{NOTE 2 @ S'Scale is not always the same as S'Aft for a decimal subtype; for example, if S'Delta = 1.0 then S'Aft is 1 while S'Scale is 0.}}
@drepl
@xindent{@s9{NOTE @ If a discriminated type has @fa{default_expression}s for its discriminants, then unconstrained variables of the type are permitted, and the values of the discriminants can be changed by an assignment to such a variable. If defaults are not provided for the discriminants, then all variables of the type are constrained, either by explicit constraint or by their initial value; the values of the discriminants of such a variable cannot be changed after initialization.}}
@dby
@s8{@i{Usage}}
If a discriminated type has @fa{default_expression}s for its discriminants, then unconstrained variables of the type are permitted, and the values of the discriminants can be changed by an assignment to such a variable. If defaults are not provided for the discriminants, then all variables of the type are constrained, either by explicit constraint or by their initial value; the values of the discriminants of such a variable cannot be changed after initialization.
@dinsa
The elaboration of a @fa{record_extension_part} consists of the elaboration of the @fa{record_definition}.
@dinst
@s8{@i{Usage}}
When an extension is declared immediately within a body, primitive subprograms are inherited and are overridable, but new primitive subprograms cannot be added.
@ddel
@xindent{@s9{NOTE 2 @ When an extension is declared immediately within a body, primitive subprograms are inherited and are overridable, but new primitive subprograms cannot be added.}}
@dinsa
Any static accessibility requirement that is imposed on an @fa{expression} that has distributed accessibility (or on its type) is instead imposed on the @i{dependent_}@fa{expression}s of the underlying @fa{conditional_expression}. This rule is applied recursively if a @i{dependent_}@fa{expression} also has distributed accessibility.
@dinst
@s8{@i{Usage}}
The Access attribute for subprograms and parameters of an anonymous access-to-subprogram type can be used together to implement “downward closures” @emdash that is, to pass a more-nested subprogram as a parameter to a less-nested subprogram, as can be appropriate for an iterator abstraction or numerical integration. Downward closures can also be implemented using generic formal subprograms (see @ref{12.6}). Unlike for objects, there is no Unchecked_Access attribute for subprograms.
Using an access-to-class-wide tagged type with a dispatching operation is a potentially more structured alternative to using an access-to-subprogram type.
@ddel
@xindent{@s9{NOTE 5 @ The Access attribute for subprograms and parameters of an anonymous access-to-subprogram type can be used together to implement “downward closures” @emdash that is, to pass a more-nested subprogram as a parameter to a less-nested subprogram, as can be appropriate for an iterator abstraction or numerical integration. Downward closures can also be implemented using generic formal subprograms (see @ref{12.6}). Unlike for objects, there is no Unchecked_Access attribute for subprograms.}}
@ddel
@xindent{@s9{NOTE 6 @ Using an access-to-class-wide tagged type with a dispatching operation is a potentially more structured alternative to using an access-to-subprogram type.}}
@drepl
@xindent{@s9{NOTE @ The Constant_Indexing and Variable_Indexing aspects cannot be redefined when inherited for a derived type, but the functions that they denote can be modified by overriding or overloading.}}
@dby
@s8{@i{Usage}}
The Constant_Indexing and Variable_Indexing aspects cannot be redefined when inherited for a derived type, but the functions that they denote can be modified by overriding or overloading.
@drepl
@xindent{@s9{NOTE 1 @ In an @fa{array_aggregate} delimited by parentheses, positional notation can only be used with two or more @fa{expression}s; a single @fa{expression} in parentheses is interpreted as a parenthesized expression. An @fa{array_aggregate} delimited by square brackets can be used to specify an array with a single component.}}
@dby
@s8{@i{Usage}}
An @fa{array_aggregate} delimited by square brackets can be used to specify an array with a single component, while in an @fa{array_aggregate} delimited by parentheses, positional notation can only be used with two or more @fa{expression}s; a single @fa{expression} in parentheses is interpreted as a parenthesized expression.
@drepl
@xindent{@s9{NOTE @ When a given context does not uniquely identify an expected type, a @fa{qualified_expression} can be used to do so. In particular, if an overloaded @fa{name} or @fa{aggregate} is passed to an overloaded subprogram, it can be necessary to qualify the operand to resolve its type.}}
@dby
@s8{@i{Usage}}
When a given context does not uniquely identify an expected type, a @fa{qualified_expression} can be used to do so. In particular, if an overloaded @fa{name} or @fa{aggregate} is passed to an overloaded subprogram, it can be necessary to qualify the operand to resolve its type.
@drepl
@xindent{@s9{NOTE @ The execution of a @fa{case_statement} chooses one and only one alternative. Qualification of the expression of a @fa{case_statement} by a static subtype can often be used to limit the number of choices that can be given explicitly.}}
@dby
@s8{@i{Usage}}
The execution of a @fa{case_statement} chooses one and only one alternative. Qualification of the expression of a @fa{case_statement} by a static subtype can often be used to limit the number of choices that have to be given explicitly.
@dinsa
For details about the execution of a @fa{loop_statement} with the @fa{iteration_scheme} including an @fa{iterator_specification}, see 5.5.2. For details relating to a @fa{procedural_iterator}, see 5.5.3.
@dinst
@s8{@i{Usage}}
An @fa{object_declaration} should not be given for a loop parameter, since the loop parameter is automatically declared by the @fa{loop_parameter_specification}. The scope of a loop parameter extends from the @fa{loop_parameter_specification} to the end of the @fa{loop_statement}, and the visibility rules are such that a loop parameter is only visible within the @fa{sequence_of_statements} of the loop.
@ddel
@xindent{@s9{NOTE 2 @ No separate @fa{object_declaration} is expected for a loop parameter, since the loop parameter is automatically declared by the @fa{loop_parameter_specification}. The scope of a loop parameter extends from the @fa{loop_parameter_specification} to the end of the @fa{loop_statement}, and the visibility rules are such that a loop parameter is only visible within the @fa{sequence_of_statements} of the loop.}}
@dinsa
The elaboration of a @fa{renaming_declaration} evaluates the @fa{name} that follows the reserved word @b{renames} and thereby determines the view and entity denoted by this name (the @i{renamed view} and @i{renamed entity}). A @fa{name} that denotes the @fa{renaming_declaration} denotes (a new view of) the renamed entity.
@dinst
@s8{@i{Usage}}
A subtype defined without any additional constraint can be used to achieve the effect of renaming another subtype (including a task or protected subtype) as in
@xcode{@b{subtype} Mode @b{is} Ada.Text_IO.File_Mode;}
@ddel
@xindent{@s9{NOTE 3 @ A subtype defined without any additional constraint can be used to achieve the effect of renaming another subtype (including a task or protected subtype) as in}}
@ddel
@xcode{@b{subtype} Mode @b{is} Ada.Text_IO.File_Mode;}
@dinsa
During a protected action, a call on a subprogram whose body contains a potentially blocking operation is a bounded error. If the bounded error is detected, Program_Error is raised; otherwise, the call proceeds normally.
@dinst
@s8{@i{Usage}}
The aspect Nonblocking can be specified True on the definition of a protected unit in order to reject most attempts to use potentially blocking operations within the protected unit (see @ref{9.5}). The @fa{pragma} Detect_Blocking can be used to ensure that any remaining executions of potentially blocking operations during a protected action raise Program_Error. See @Ref{H.5}.
@ddel
@xindent{@s9{NOTE 5 @ The aspect Nonblocking can be specified True on the definition of a protected unit in order to reject most attempts to use potentially blocking operations within the protected unit (see @ref{9.5}). The @fa{pragma} Detect_Blocking can be used to ensure that any remaining executions of potentially blocking operations during a protected action raise Program_Error. See @Ref{H.5}.}}
@drepl
@xindent{@s9{NOTE 1 @ There is no guarantee that a suppressed check is actually removed; hence a @fa{pragma} Suppress is useful only for efficiency.}}
@dby
@s8{@i{Usage}}
There is no guarantee that a suppressed check is actually removed; hence a @fa{pragma} Suppress should be used only for efficiency reasons.
@drepl
@xindent{@s9{NOTE 2 @ It is possible to give both a @fa{pragma} Suppress and Unsuppress for the same check immediately within the same @fa{declarative_part}. In that case, the last @fa{pragma} given determines whether or not the check is suppressed. Similarly, it is possible to resuppress a check which has been unsuppressed by giving a @fa{pragma} Suppress in an inner declarative region.}}
@dby
It is possible to give both a @fa{pragma} Suppress and Unsuppress for the same check immediately within the same @fa{declarative_part}. In that case, the last @fa{pragma} given determines whether or not the check is suppressed. Similarly, it is possible to resuppress a check which has been unsuppressed by giving a @fa{pragma} Suppress in an inner declarative region.
@drepl
@xindent{@s9{NOTE @ Default_Storage_Pool can be used with restrictions No_Coextensions and No_Access_Parameter_Allocators (see @ref{H.4}) to ensure that all @fa{allocator}s use the default pool.}}
@dby
@s8{@i{Usage}}
Default_Storage_Pool can be used with restrictions No_Coextensions and No_Access_Parameter_Allocators (see @ref{H.4}) to ensure that all @fa{allocator}s use the default pool.
@drepl
@xindent{@s9{NOTE 1 @ A user-defined storage pool type that supports subpools can be implemented by extending the Root_Storage_Pool_With_Subpools type, and overriding the primitive subprograms Create_Subpool, Allocate_From_Subpool, and Deallocate_Subpool. Create_Subpool is expected to call Set_Pool_Of_Subpool before returning the subpool handle. To make use of such a pool, a user can declare an object of the type extension, can use it to define the Storage_Pool attribute of one or more access types, and then can invoke Create_Subpool to obtain subpool handles associated with the pool.}}
@dby
@s8{@i{Usage}}
A user-defined storage pool type that supports subpools can be implemented by extending the Root_Storage_Pool_With_Subpools type, and overriding the primitive subprograms Create_Subpool, Allocate_From_Subpool, and Deallocate_Subpool. Create_Subpool should call Set_Pool_Of_Subpool before returning the subpool handle. To make use of such a pool, a user can declare an object of the type extension, can use it to define the Storage_Pool attribute of one or more access types, and then can invoke Create_Subpool to obtain subpool handles associated with the pool.
A user-defined storage pool type that supports subpools can define additional subpool constructors similar to Create_Subpool (these typically will have additional parameters).
The pool implementor can override Default_Subpool_For_Pool if they want the pool to support a default subpool for the pool. The implementor can override Deallocate if individual object reclamation is to be supported, and can override Storage_Size if there is some limit on the total size of the storage pool. The implementor can override Initialize and Finalize if there is any desire for nontrivial initialization and finalization for the pool as a whole. For example, Finalize can reclaim blocks of storage that are allocated over and above the space occupied by the pool object itself. The pool implementor can extend the Root_Subpool type as necessary to carry additional information with each subpool provided by Create_Subpool.
@ddel
@xindent{@s9{NOTE 2 @ A user-defined storage pool type that supports subpools can define additional subpool constructors similar to Create_Subpool (these typically will have additional parameters).}}
@ddel
@xindent{@s9{NOTE 3 @ The pool implementor can override Default_Subpool_For_Pool if they want the pool to support a default subpool for the pool. The implementor can override Deallocate if individual object reclamation is to be supported, and can override Storage_Size if there is some limit on the total size of the storage pool. The implementor can override Initialize and Finalize if there is any desire for nontrivial initialization and finalization for the pool as a whole. For example, Finalize can reclaim blocks of storage that are allocated over and above the space occupied by the pool object itself. The pool implementor can extend the Root_Subpool type as necessary to carry additional information with each subpool provided by Create_Subpool.}}
@dinsa
Ada.Streams.Storage above provides an example of extending type Root_Stream_Type.
@dinst
@s8{@i{Usage}}
If the end of stream has been reached, and Item'First is Stream_Element_Offset'First, Read will raise Constraint_Error. Therefore, Stream_Element_Arrays should start at 0 or 1, not Stream_Element_Offset'First.
@ddel
@xindent{@s9{NOTE 2 @ If the end of stream has been reached, and Item'First is Stream_Element_Offset'First, Read will raise Constraint_Error.}}
@drepl
@xindent{@s9{NOTE 1 @ For a definite subtype S of a type @i{T}, only @i{T}'Write and @i{T}'Read are necessary to pass an arbitrary value of the subtype through a stream. For an indefinite subtype S of a type @i{T}, @i{T}'Output and @i{T}'Input will normally be necessary, since @i{T}'Write and @i{T}'Read do not pass bounds, discriminants, or tags.}}
@dby
@s8{@i{Usage}}
For a definite subtype S of a type @i{T}, only @i{T}'Write and @i{T}'Read are necessary to pass an arbitrary value of the subtype through a stream. For an indefinite subtype S of a type @i{T}, @i{T}'Output and @i{T}'Input will normally be necessary, since @i{T}'Write and @i{T}'Read do not pass bounds, discriminants, or tags.
@drepl
@xindent{@s9{NOTE 1 @ In the Index and Count functions taking Pattern and Mapping parameters, for there to be a match, the actual String parameter passed to Pattern can contain only characters occurring as target characters of the mapping.}}
@dby
@s8{@i{Usage}}
In the Index and Count functions taking Pattern and Mapping parameters, for there to be a match, the actual String parameter passed to Pattern can contain only characters occurring as target characters of the mapping.
In the Insert subprograms, inserting at the end of a string is obtained by passing Source'Last+1 as the Before parameter.
@ddel
@xindent{@s9{NOTE 2 @ In the Insert subprograms, inserting at the end of a string is obtained by passing Source'Last+1 as the Before parameter.}}
@drepl
@xindent{@s9{NOTE @ A BOM (Byte-Order Mark, code position 16#FEFF#) can be included in a file or other entity to indicate the encoding; it is skipped when decoding. Typically, only the first line of a file or other entity contains a BOM. When decoding, the Encoding function can be called on the first line to determine the encoding; this encoding will then be used in subsequent calls to Decode to convert all of the lines to an internal format.}}
@dby
@s8{@i{Usage}}
A BOM (Byte-Order Mark, code position 16#FEFF#) can be included in a file or other entity to indicate the encoding; it is skipped when decoding. Typically, only the first line of a file or other entity contains a BOM. When decoding, the Encoding function can be called on the first line to determine the encoding; this encoding will then be used in subsequent calls to Decode to convert all of the lines to an internal format.
@dinsa
For each supported convention @i{L} other than Intrinsic, an implementation should support specifying the Import and Export aspects for objects of @i{L}-compatible types and for subprograms, and the Convention aspect for @i{L}-eligible types and for subprograms, presuming the other language has corresponding features. Specifying the Convention aspect should be supported for enumeration types whose internal codes fall within the range 0 .. 2**15–1, but no recommendation is made for other scalar types.
@dinst
@s8{@i{Usage}}
The Convention aspect in combination with the Import aspect indicates the conventions for accessing external entities. It is possible that the actual entity is written in assembly language, but reflects the conventions of a particular language. For example, @fc{@b{with} Convention => Ada} can be used to interface to an assembly language routine that obeys the Ada compiler's calling conventions.
To obtain “call-back” to an Ada subprogram from a foreign language environment, the Convention aspect should be specified both for the access-to-subprogram type and the specific subprogram(s) to which 'Access is applied.
@ddel
@xindent{@s9{NOTE 2 @ The Convention aspect in combination with the Import aspect indicates the conventions for accessing external entities. It is possible that the actual entity is written in assembly language, but reflects the conventions of a particular language. For example, @fc{@b{with} Convention => Ada} can be used to interface to an assembly language routine that obeys the Ada compiler's calling conventions.}}
@ddel
@xindent{@s9{NOTE 3 @ To obtain “call-back” to an Ada subprogram from a foreign language environment, the Convention aspect can be specified both for the access-to-subprogram type and the specific subprogram(s) to which 'Access is applied.}}
@drepl
@xindent{@s9{NOTE 1 @ Values of type char_array are not implicitly terminated with nul. If a char_array is to be passed as a parameter to an imported C function requiring nul termination, it is the programmer's responsibility to obtain this effect.}}
@dby
@s8{@i{Usage}}
Values of type char_array are not implicitly terminated with nul. If a char_array is to be passed as a parameter to an imported C function requiring nul termination, it is the programmer's responsibility to obtain this effect.
To obtain the effect of C's sizeof(item_type), where Item_Type is the corresponding Ada type, evaluate the expression: @fc{size_t(Item_Type'Size/CHAR_BIT)}.
A variadic C function can correspond to several Ada subprograms, taking various specific numbers and types of parameters.
@ddel
@xindent{@s9{NOTE 2 @ To obtain the effect of C's sizeof(item_type), where Item_Type is the corresponding Ada type, evaluate the expression: @fc{size_t(Item_Type'Size/CHAR_BIT)}.}}
@ddel
@xindent{@s9{NOTE 3 @ A variadic C function can correspond to several Ada subprograms, taking various specific numbers and types of parameters.}}
@dinsa
Finalization of task attributes and reclamation of associated storage should be performed as soon as possible after task termination.
@dinst
@s8{@i{Usage}}
The result of the Reference function should be used with care; it is always safe to use in the task body whose attribute is being accessed. However, when the result is being used by another task, the programmer has to ensure that the task whose attribute is being accessed is not yet terminated. Failing to do so can make the program execution erroneous.
@ddel
@xindent{@s9{NOTE 2 @ The result of the Reference function is always safe to use in the task body whose attribute is being accessed. However, when the result is being used by another task, the programmer will want to make sure that the task whose attribute is being accessed is not yet terminated. Failing to do so can make the program execution erroneous.}}
@dinsa
The implementation should use names that end with “_Locking” for implementation-defined locking policies.
@dinst
@s8{@i{Usage}}
When specifying the ceiling of a protected object, one should choose a value that is at least as high as the highest active priority at which tasks can be executing when they call protected operations of that object. In determining this value the following factors, which can affect active priority, should be considered: the effect of Set_Priority, nested protected operations, entry calls, task activation, and other implementation-defined factors.
Attaching a protected procedure whose ceiling is below the interrupt hardware priority to an interrupt causes the execution of the program to be erroneous (see @ref{C.3.1}).
@ddel
@xindent{@s9{NOTE 4 @ When specifying the ceiling of a protected object, a correct value is one that is at least as high as the highest active priority at which tasks can be executing when they call protected operations of that object. In determining this value the following factors, which can affect active priority, are relevant: the effect of Set_Priority, nested protected operations, entry calls, task activation, and other implementation-defined factors.}}
@ddel
@xindent{@s9{NOTE 5 @ Attaching a protected procedure whose ceiling is below the interrupt hardware priority to an interrupt causes the execution of the program to be erroneous (see @ref{C.3.1}).}}
@dinsa
@xbullet{The execution time of a call to Set_Priority, for the nonpreempting case, in processor clock cycles. This is measured for a call that modifies the priority of a ready task that is not running (which cannot be the calling one), where the new base priority of the affected task is lower than the active priority of the calling task, and the affected task is not on any entry queue and is not executing a protected operation.}
@dinst
@s8{@i{Usage}}
Changing the priorities of a set of tasks can be performed by a series of calls to Set_Priority for each task separately. For this to work reliably, it should be done within a protected operation that has high enough ceiling priority to guarantee that the operation completes without being preempted by any of the affected tasks.
@ddel
@xindent{@s9{NOTE 5 @ Changing the priorities of a set of tasks can be performed by a series of calls to Set_Priority for each task separately. This can be done reliably within a protected operation that has high enough ceiling priority to guarantee that the operation completes without being preempted by any of the affected tasks.}}
@drepl
@xindent{@s9{NOTE @ The effect of division yielding a quotient with control over rounding versus truncation is obtained by applying either the function attribute Quotient_Type’Round or the conversion Quotient_Type to the expression Dividend/Divisor.}}
@dby
@s8{@i{Usage}}
The effect of division yielding a quotient with control over rounding versus truncation is obtained by applying either the function attribute Quotient_Type’Round or the conversion Quotient_Type to the expression Dividend/Divisor.
@drepl
@xindent{@s9{NOTE @ The Valid attribute (see @ref{13.9.2}) is also useful in addressing these needs, to avoid problems that can otherwise arise from scalars that have values outside their declared range constraints.}}
@dby
@s8{@i{Usage}}
The Valid attribute (see @ref{13.9.2}) is also useful in addressing these needs, to avoid problems that can otherwise arise from scalars that have values outside their declared range constraints.
None needed, this is not intended to be testable text (even if included in the text of the RM).