Overview of Ada 2022
Jeff Cousins
Contents   Index   Search   Previous   Next 

7.12 Objects, Values, Conversions and Renaming

There are several AIs that aim to make Ada more consistent in its treatment of type conversions and qualified expressions, objects and values.
Make objects more consistent (AI12-0226).
In Ada 2012 a type conversion between two tagged types (termed a view conversion) gives an object, which can be renamed, whereas a type conversion between two untagged types (termed a value conversion) gives a value, which cannot. In Ada 2022 a value conversion of an object is added to the list of things deemed to be an object, making it consistent with a qualified expression. If we have
Max : constant Natural := 10;
then the following are now all legal:
Ren1 : Natural renames Max;    -- Legal
Ren2 : Natural renames Natural'(Max);    -- Qualified expression, legal
Ren3 : Natural renames Natural(Max);    -- Value conversion, was illegal, now legal
Renaming values (AI12-0383). takes this further by allowing values to be renamed anyway, besides objects.
Make subtype_mark optional in object renames (AI12-0275).
This makes the subtype optional in object renaming declarations (see RM 8.5.1). The expression will be correctly typed as long as the right hand object can be resolved to only one specific type.
It has long been an irritant that writing a renaming declaration required looking up the subtype of the object, and giving the subtype can be misleading anyway. The reader may be surprised to find that the following is valid Ada:
   subtype My_Subtype          is Integer range 3 .. 5;
   subtype Garbage_Subtype is Integer range -19 .. -7;
   X : My_Subtype;
   Y : Garbage_Subtype renames X;
begin
   case Y is
      when 3 .. 5 =>
         pragma Assert (Y in 3 .. 5);
   end case;
The subtype given in the renaming merely has to be a subtype of the same type as the object being renamed. The constraints, null exclusions, and predicates of the subtype given in the renaming are ignored; instead they are taken from the subtype of the object being renamed. Note that the case statement has to have alternatives for each possible value of the subtype of X, not of the supposed subtype of Y.
Requiring the subtypes to match has been considered in the past, but backward compatibility concerns have always prevented this. For backward compatibility reasons the subtype may still be given, but it is (usually) no longer required.
Renaming of a qualified expression of a variable (AI12-0401).
Ada 2012 allows a qualified expression to be renamed (though possibly this had not been implemented by anyone until recently). In the following, three subtypes are involved:
   subtype Subtype_1 is Integer range ...;
   subtype Subtype_2 is Integer range ...;
   subtype Subtype_3 is Integer range ...;
   X : Subtype_1;
   Y : Subtype_2 renames Subtype_3'(X);
As described under Make subtype_mark optional in object renames (AI12-0275), Subtype_2 is largely irrelevant. Typically, a qualified expression is used to confirm which type is meant when there is a possible ambiguity, as in:
type Traffic_Light is (Red, Amber, Green);
type Gemstones is (Amber, Ruby, Topaz);
... Traffic_Lights'(Amber) ...
... Gemstones'(Amber) ...
But in the above it is not a case of X being renamed, and Subtype_3' just being there to confirm the type; instead it is the whole qualified expression Subtype_3'(X) that is the object being renamed. Thus Y takes its constraints, null exclusions, and predicates from Subtype_3. This could be problematic if Subtype_3 has a narrower range than Subtype_1, as in the following:
   X : Natural := ...;
   Y : Positive renames Positive'(X); -- Legal in Ada 2012, illegal in Ada 2022
begin
   X := 0; -- Alert!!
   case Y is
      when 1 .. Positive'Last =>
         pragma Assert (Y > 0);
   end case;
X is set to a value outside of the range of Y, effectively bypassing the range check at the time of renaming, which is meant to be a one-off affair, and not have to be repeated at each subsequent use of Y.
To fix this hole, Renaming of a qualified expression of a variable (AI12-0401) requires Subtype_3 to match either Subtype_1 or its base type (in this case, Integer). Note that the converse problem of writing a value to Y outside of the range of X does not arise as a qualified expression gives a constant (i.e. read-only) view.

Contents   Index   Search   Previous   Next 
© 2021, 2022 Jeff Cousins