Version 1.7 of ai05s/ai05-0102-1.txt

Unformatted version of ai05s/ai05-0102-1.txt version 1.7
Other versions for file ai05s/ai05-0102-1.txt

!standard 3.7(16)          09-10-12 AI05-0102-1/04
!standard 3.7.1(9)
!standard 6.4.1(6)
!standard 8.6(27/2)
!class binding interpretation 08-06-15
!status Amendment 2012 09-06-27
!status WG9 Approved 09-11-05
!status ARG Approved 7-0-0 09-06-13
!status work item 08-06-15
!status received 06-04-24
!priority Low
!difficulty Medium
!qualifier Omission
!subject Some implicit conversions ought to be illegal
A legality rule is added to 8.6 to ensure that all implicit conversions are between types that are convertible.
Consider the following:
declare VObj : access Designated := ...; CObj : access constant Designated := ...; Cnst : aliased constant Designated := ...; begin VObj := Cnst'access; -- (1) VObj := CObj; -- (2) end;
(1) is illegal by 3.10.2(25).
Surely we want (2) to be illegal, too, but there doesn't seem to be any rule that covers it.
Delete 3.7(16), 3.7.1(9), and 6.4.1(6).
Add after 8.6(27/2):
If the expected type of a construct is T1 and the actual type of the construct is T2, then T2 shall be convertible to T1 (see 4.6).
AARM Reason: This is needed to prevent implicit conversions which would be illegal if they were explicit conversions. For instance, we do not want to implicitly convert an access-to-constant value to an anonymous access-to-variable type. We do not want to make the resolution rules specific enough to prevent these sorts of issues, so we need a separate legality rule.
5.2 has no legality rule that applies in this case. The closest we have is 5.2(11), which is a dynamic semantics rule, and it is uncomfortable to have legality depending on a dynamic rule. Thus, a new legality rule is needed somewhere.
4.6 defines the term "convertible" for rules like this. Indeed, some implicit conversion contexts (3.7, 3.7.1, and 6.4.1) already have legality rules. This was an Ada 95 attempt to fix this problem; these are the only places where mismatches were possible in Ada 95. (Ada 95 ultimately did not have this problem, as resolution did not allow an access-to-constant value to match an anonymous access type. But that will not work for Ada 2005, as we now have anonymous access-to-constant types.)
We could try a similar fix for Ada 2005. However, the index lists more than 30 places that use implicit conversion, and it would be silly to add legality rules in that many more places. Besides the sheer volume of change, there would be a lingering maintenance problem where any new implicit conversion contexts could easily forget to add the needed legality rule.
Implicit conversion is implicitly defined in 8.6 (by the definition of which types match an expected type T). So that seems to be the best place for a blanket legality rule.
The three existing rules (3.7(16), 3.7.1(9), and 6.4.1(6)) are then removed, as there is no value to having special rules in 3 out of more than 30 cases.
The new rule should be indexed to "implicit conversion, legality" and to "convertible (required)" (the latter to match the existing rules).
!corrigendum 3.7(16)
Delete the paragraph:
The type of the default_expression, if any, for an access discriminant shall be convertible to the anonymous access type of the discriminant (see 4.6).
!corrigendum 3.7.1(9)
Delete the paragraph:
The expression associated with an access discriminant shall be of a type convertible to the anonymous access type.
!corrigendum 6.4.1(6)
Delete the paragraph:
The type of the actual parameter associated with an access parameter shall be convertible (see 4.6) to its anonymous access type.
!corrigendum 8.6(27/2)
Insert after the paragraph:
When a construct is one that requires that its expected type be a single type in a given class, the type of the construct shall be determinable solely from the context in which the construct appears, excluding the construct itself, but using the requirement that it be in the given class. Furthermore, the context shall not be one that expects any type in some class that contains types of the given class; in particular, the construct shall not be the operand of a type_conversion.
the new paragraph:
If the expected type of a construct is T1 and the actual type of the construct is T2, then T2 shall be convertible to T1 (see 4.6).
An ACATS test should check that implicit conversions like the one in the question are illegal.

From: Randy Brukardt
Sent: Thursday, April 24, 2008  10:01 PM

Can an implicit subtype conversion be illegal (not just raise an exception)?
Channeling Adam, I'm not sure. (I am sure what answer we want, so the only
question is whether the Standard actually justifies that answer.)

Consider the following from an ACATS test now under construction:

        VObj : access Designated := ...;
        CObj : access constant Designated := ...;
        Cnst : aliased constant Designated := ...;
        VObj := Cnst'Access;   -- ERROR: (1)
        VObj := CObj;          -- ERROR: (2)

While I'm certain that we want (2) to be illegal, I'm having trouble justifying
it based on the wording of the Standard.

(1) resolves because the type of the access attribute is that of the expected
type; but it is illegal because it violates 3.10.2(25).

(2) resolves because of 8.6(25/2), which allows these otherwise different types
to match. So no error there. We turn to 5.2's Legality Rules. 5.2(5/2) is
satisfied because the target is a variable. 5.2(6) doesn't apply (VObj isn't
tagged). So why is this illegal?

The only hope resides in the Dynamic Semantics rules, which is not a likely
place to look for rules that make things illegal! The rule is 5.2(11): the value
is converted to the subtype of the target. One can then say that the legality
rule 4.6(24.12/2) applies. But this is weird, because (a) it mentions the
possibility of an exception, but not illegality; (b) it's not clear if the
original type of the value is considered or not; (c) it's not clear that
an actual *type* conversion is possible. (Yes, I know that there are no
named types in Ada [everything is a subtype], but these aren't named anyway... :-).

I think we should at least have a To Be Honest note in the AARM that this
implicit subtype conversion can be illegal in cases involving anonymous types,
and it can convert types, not just subtypes, in such cases. It would be better
for there to be an explicit statement of that fact somewhere (it probably isn't
practical to put it everywhere that it can happen: there is a half a column of
references for "implicit subtype conversion" in the RM's index; but the
assignment case is the most common one).

Do I have the intent right here, or have I missed something??


From: Robert A. Duff
Sent: Friday, April 25, 2008  7:47 AM

> The only hope resides in the Dynamic Semantics rules, which is not a 
> likely place to look for rules that make things illegal!

Indeed, we can't use Dynamic Semantics to say something is illegal!

Implicit things being illegal seems uncomfortable anyway.  Seems like we're 
missing a rule.

The fact that converting to a subtype can convert the type as well is not new.
It is used for example in the semantics of calls to inherited subprograms.

4.6(58) seems relevant:

58    Conversion to a type is the same as conversion to an unconstrained
subtype of the type.

    58.a  Reason: This definition is needed because the semantics of various
          constructs involves converting to a type, whereas an explicit
          type_conversion actually converts to a subtype. For example, the
          evaluation of a range is defined to convert the values of the
          expressions to the type of the range.


Questions? Ask the ACAA Technical Agent