Ada Conformity Assessment Authority      Home Conformity Assessment   Test Suite ARGAda Standard
 
Ada Reference Manual (Ada 2022 with Amendment 1)Legal Information
Contents   Index   References   Search   Previous   Next 

4.1.5 User-Defined References

Static Semantics

1/3
Given a discriminated type T, the following type-related operational aspect may be specified:
2/3
Implicit_Dereference

This aspect is specified by a name that denotes an access discriminant declared for the type T.
3/3
A (view of a) type with a specified Implicit_Dereference aspect is a reference type. A reference object is an object of a reference type. The discriminant named by the Implicit_Dereference aspect is the reference discriminant of the reference type or reference object. A generalized_reference is a name that identifies a reference object, and denotes the object or subprogram designated by the reference discriminant of the reference object.

Syntax

4/3
generalized_reference ::= reference_object_name

Name Resolution Rules

5/3
The expected type for the reference_object_name in a generalized_reference is any reference type. 

Static Semantics

5.1/4
 The Implicit_Dereference aspect is nonoverridable (see 13.1.1).
6/3
A generalized_reference denotes a view equivalent to that of a dereference of the reference discriminant of the reference object.
7/5
Given a reference type T, the Implicit_Dereference aspect is inherited by descendants of type T if not overridden (which is only permitted if confirming). If a descendant type constrains the value of the reference discriminant of T by a new discriminant, that new discriminant is the reference discriminant of the descendant. If the descendant type constrains the value of the reference discriminant of T by an expression other than the name of a new discriminant, a generalized_reference that identifies an object of the descendant type denotes the object or subprogram designated by the value of this constraining expression.

Dynamic Semantics

8/3
The evaluation of a generalized_reference consists of the evaluation of the reference_object_name and a determination of the object or subprogram designated by the reference discriminant of the named reference object. A check is made that the value of the reference discriminant is not the null access value. Constraint_Error is raised if this check fails. The generalized_reference denotes the object or subprogram designated by the value of the reference discriminant of the named reference object.

Examples

9/5
Examples of the specification and use of generalized references:
10/3
type Barrel is tagged ...  -- holds objects of type Element
11/3
type Ref_Element(Data : access Element) is limited private
   with Implicit_Dereference => Data;
      -- This Ref_Element type is a "reference" type.
      -- "Data" is its reference discriminant.
12/3
function Find (B : aliased in out Barrel; Key : String)
   return Ref_Element;
   -- Returns a reference to an element of a barrel.
13/3
B: aliased Barrel;
14/3
...
15/3
Find (B, "grape") := Element'(...);  -- Assign through a reference.
16/3
-- This is equivalent to:
Find (B, "grape").Data.all := Element'(...);

Usage

17/6
For most uses, and in particular for types used with user-defined indexing (see 4.1.6), reference types should be limited types. Doing so helps avoid ambiguities that otherwise can arise. Ambiguities are possible because a name that can be interpreted as a generalized_reference can also be interpreted in the usual way (that is, as a name denoting an object of the reference type). For example, if X and Y are objects of a reference type T1 that has an "access T2" reference discriminant, then the expression X = Y would be ambiguous if equality operators for both T1 and T2 are directly visible. See the example below where T1 is Bad_Ref and T2 is Barrel. Such ambiguities can especially complicate the use of user-defined indexing.
18/6
type Bad_Ref (D : access Barrel) is null record
    with Implicit_Dereference => D;
function Create_Ref (B : aliased in out Barrel) return Bad_Ref;
X, Y : Bad_Ref := Create_Ref (B);
   ...
if X = Y then -- Ambiguous, "=" can be for type Bad_Ref or type Barrel.
   ...

Contents   Index   References   Search   Previous   Next 
Ada-Europe Ada 2005 and 2012 Editions sponsored in part by Ada-Europe