Version 1.3 of ai12s/ai12-0335-1.txt

Unformatted version of ai12s/ai12-0335-1.txt version 1.3
Other versions for file ai12s/ai12-0335-1.txt

!standard 9.5.4(7/4)          19-06-15 AI12-0335-1/02
!class binding interpretation 19-06-04
!status work item 19-06-04
!status received 19-05-19
!priority Low
!difficulty Easy
!qualifier Omission
!subject Dynamic accessibility check needed for some requeue targets
!summary
A dynamic accessibility check is added to requeue to cover cases where there is no static check.
!question
9.5.4(6/3) gives a compile-time accessibility rule for requeue statements.
Should there be a corresponding dynamic accessibility check to handle the cases that the static rule does not cover? (Yes.)
!recommendation
(See Summary.)
!wording
Replace 9.5.4(7/4):
The execution of a requeue_statement proceeds by first evaluating the procedure_or_entry_name[Redundant:, including the prefix identifying the target task or protected object and the expression identifying the entry within entry family, if any]. Precondition checks are then performed as for a call to the requeue target entry or subprogram. The entry_body or accept_statement enclosing the requeue_statement is then completed[Redundant:, finalized, and left (see 7.6.1)].
with:
The execution of a requeue_statement begins with the following sequence of steps:
1. The procedure_or_entry_name is evaluated. [Redundant: This
includes evaluation of the prefix (if any) identifying the target task or protected object and of the expression (if any) identifying the entry within an entry family.]
2. A check is made that the accessibility level of the target object is
not equal to or deeper than the level of the innermost enclosing body or callable construct. If this check fails, Program_Error is raised.
AARM note: This check can only fail if the statically deeper relationship does not apply to the accessibility level of the type of the target object.
3. Precondition checks are performed as for a call to the requeue
target.
4. The entry_body or accept_statement enclosing the
requeue_statement is then completed[, finalized, and left (see 7.6.1)].
!discussion
In many cases where we have a static accessibility rule saying "The accessibility level of This shall not be statically deeper than the accessibility level of That", there is a corresponding runtime check to handle the cases involving dynamic accessibility levels that cannot be handled statically.
There is no such dynamic rule for requeue statements. This probably was OK for Ada 95, but not for Ada 2005 or later.
Consider this example:
requeue Some_Function_Call.Some_Entry;
where Some_Function_Call returns a task type or a protected type.
This one is statically prohibited by the following Legality Rule:
In a requeue_statement of an accept_statement of some task unit, either the target object shall be a part of a formal parameter of the accept_statement, or the accessibility level of the target object shall not be equal to or statically deeper than any enclosing accept_statement of the task unit. In a requeue_statement of an entry_body of some protected unit, either the target object shall be a part of a formal parameter of the entry_body, or the accessibility level of the target object shall not be statically deeper than that of the entry_declaration for the entry_body.
No problem so far.
But now let's get a standalone object of an anonymous access type involved.
declare Local_Var : aliased Some_Type; Ptr : access Foo := Local_Var'access; begin requeue Ptr.all.Some_Entry;
The legality rule cited above doesn't prohibit this case because of the following 3.10.2 rule:
The statically deeper relationship does not apply to the accessibility level of the type of a stand-alone object of an anonymous access-to-object type; that is, such an accessibility level is not considered to be statically deeper, nor statically shallower, than any other.
The dynamic semantics of this example are at best unclear; a change of some kind is needed to deal with such cases.
Other cases where the "statically deeper" relationship doesn't apply include access parameters and generic formal types (this is described in the immediately preceding 3.10.2 paragraph, but we don't care about the details here; the stand-alone object case is enough to demonstrate the problem).
It seems clear that we want to either
a) change the legality rules so that this example is illegal; or b) add a runtime accessibility check which this example will fail.
Ada generally takes the second approach (that is, a runtime accessibility check) in this sort of situation because we don't want to disallow something reasonable like:
Ptr : access Some_Type := Some_Library_Level_Object'access;
begin requeue Ptr.all.Some_Entry;
or even more likely (assuming the type of Some_Parameter is library-level):
Ptr : access Some_Type := Some_Parameter.Some_Anon_Access_Component;
begin requeue Ptr.all.Some_Entry;
!ASIS
No ASIS effect.
!ACATS test
An ACATS C-Test should be constructed for an example like the one in the
!discussion.
!appendix

****************************************************************

Questions? Ask the ACAA Technical Agent