13.14 Freezing Rules
This Reference Manual output has not been verified, and may contain omissions or errors. Report any problems on the tracking issue
[This subclause defines a place in the program text where each declared entity becomes “frozen”. A use of an entity, such as a reference to it by name, or (for a type) an expression of the type, causes freezing of the entity in some contexts, as described below. The Legality Rules forbid certain kinds of uses of an entity in the region of text where it is frozen.]
attribute_designator
shall be static. In a record aggregate, variant-controlling discriminants shall be static. In an array aggregate with more than one named association, the choices shall be static. The compiler needs to know the value of these expressions in order to perform overload resolution and legality checking.) We wish to allow a compiler to evaluate static expressions when it sees them in a single pass over the compilation_unit
. The freezing rules ensure that.- For a tagged type, the implementations of all the primitive subprograms of the type — that is (in the canonical implementation model), the contents of the type descriptor, which contains pointers to the code for each primitive subprogram.
- For a type, the full type declaration of any parts (including the type itself) that are private.
- For a deferred constant, the full constant declaration, which gives the constant's value. (Since this information necessarily comes after the constant's type and subtype are fully known, there's no need to worry about its type or subtype.)
- For any entity, representation information specified by the user via representation items. Most representation items are for types or subtypes; however, various other kinds of entities, such as objects and subprograms, are possible.
Language Design Principles
default_expression
s and default_name
s. (Formal parameters, generic formal parameters, and components can have default_expression
s or default_name
s.)type T is
record
...
end record;
function F return T;
function G(X : T) return Boolean;
Y : Boolean := G(F); -- doesn't force T in Ada 83
for T use
record
...
end record;
package P is
type T is private;
function F return T;
function G(X : T) return Boolean;
Y : Boolean := G(F); -- doesn't force T in Ada 83
private
type T is
record
...
end record;
end P;
full_type_declaration
). The freezing of an entity occurs at one or more places (freezing points) in the program text where the representation for the entity has to be fully determined. Each entity is frozen from its first freezing point to the end of the program text (given the ordering of compilation units defined in 10.1.4).
This subclause also defines a place in the program text where the profile of each declared callable entity becomes frozen. A use of a callable entity causes freezing of its profile in some contexts, as described below. At the place where the profile of a callable entity becomes frozen, the entity itself becomes frozen.
{8652/0014} The end of a declarative_part
, protected_body
, or a declaration of a library package or generic library package, causes freezing of each entity and profile declared within it, as well as the entity itself in the case of the declaration of a library unit . A noninstance proper_body
, body_stub
, or entry_body
causes freezing of each entity and profile declared before it within the same declarative_part
.
package_specification
will be frozen by some containing construct.package_specification
can be completed in the body. For other incomplete types (and in the bodies of library packages), the completion of the type will be frozen at the end of the package or declarative_part
.proper_bodies
and body_stub
s to be interchangeable — one should be able to move a proper_body
to a subunit
, and vice versa, without changing the semantics. Clearly, anything that should cause freezing should do so even if it's inside a proper_body
. However, if we make it a body_stub
, then the compiler can't see that thing that should cause freezing. So we make body_stub
s cause freezing, just in case they contain something that should cause freezing. But that means we need to do the same for proper_bodies
.declarative_part
is frozen within a nested body, since some compilers look at bodies after looking at the containing declarative_part
.null_procedure_declaration
s and expression_function_declaration
s (even when those are used as completions), as well as generic_instantiation
s and renames-as-bodies do not necessarily cause freezing; each have their own specific rules. declarative_part
s. All of the kinds of bodies (see 3.11.1 – keep in mind the difference from body
s) that are allowed in a package specification have their own freezing rules, so they don't need to be covered by the above rule. {8652/0046} A construct that (explicitly or implicitly) references an entity can cause the freezing of the entity, as defined by subsequent paragraphs. At the place where a construct causes freezing, each name
, expression
, implicit_dereference
[, or range
] within the construct causes freezing:
subtype_mark
“references” the denoted subtype, but not the type. - The occurrence of a
generic_instantiation
causes freezing, except that aname
which is a generic actual parameter whose corresponding generic formal parameter is a formal incomplete type (see 12.5.1) does not cause freezing. In addition, if a parameter of the instantiation is defaulted, thedefault_expression
ordefault_name
for that parameter causes freezing.
generic_instantiation
. - At the occurrence of an
expression_function_declaration
that is a completion, the return expression of the expression function causes freezing.
body
it does not by itself freeze anything that precedes it. - At the occurrence of a renames-as-body whose callable_entity_
name
denotes an expression function, the return expression of the expression function causes freezing. 6 - The occurrence of an
object_declaration
that has no corresponding completion causes freezing.
formal_object_declaration
. - The declaration of a record extension causes freezing of the parent subtype.
- The declaration of a record extension, interface type, task unit, or protected unit causes freezing of any progenitor types specified in the declaration.
- At the freezing point of the entity associated with an
aspect_specification
, any static expressions within theaspect_specification
cause freezing, as doexpression
s orname
s inaspect_definition
s for representation aspects, or operational aspects that have a corresponding operational attribute. Similarly, if anaspect_definition
for an operational aspect, other than an assertion aspect, can affect the Name Resolution, Static Semantics, or Legality Rules of a subsequent construct, then anyexpression
s orname
s within theaspect_definition
cause freezing at the freezing point of the associated entity. Any static expressions within anaspect_specification
also cause freezing at the end of the immediately enclosing declaration list. For the purposes of this rule, if there is no declared entity associated with anaspect_specification
, the freezing point is considered to occur immediately following theaspect_specification
.
{8652/0046} A static expression (other than within an aspect_specification
) causes freezing where it occurs. An object name or nonstatic expression causes freezing where it occurs, unless the name or expression is part of a default_expression
, a default_name
, the return expression of an expression function, an aspect_specification
, or a per-object expression of a component's constraint
, in which case, the freezing occurs later as part of another construct or at the freezing point of an associated entity.
{8652/0046} An implicit call freezes the same entities and profiles that would be frozen by an explicit call. This is true even if the implicit call is removed via implementation permissions.
{8652/0046} If an expression is implicitly converted to a type or subtype T, then at the place where the expression causes freezing, T is frozen.
The following rules define which entities are frozen at the place where a construct causes freezing:
- At the place where an expression causes freezing, the type of the expression is frozen, unless the expression is an enumeration literal used as a
discrete_choice
of thearray_aggregate
of anenumeration_representation_clause
or as theaspect_definition
of a specification for aspect Default_Value.
package P1 is
type T is private;
package P2 is
type Composite(D : Boolean) is
record
case D is
when False => Cf : Integer;
when True => Ct : T;
end case;
end record;
end P2;
X : Boolean := P2."="( (False,1), (False,1) );
private
type T is array(1..Func_Call) of Integer;
end;
- At the place where a function call causes freezing, the profile of the function is frozen. Furthermore, if a parameter of the call is defaulted, the
default_expression
for that parameter causes freezing. If the function call is to an expression function, the return expression of the expression function causes freezing.
body
s; the end of a declarative_part
or library package freezes everything in it, and a body
freezes everything declared before it. - At the place where a
generic_instantiation
causes freezing of a callable entity, the profile of that entity is frozen unless the formal subprogram corresponding to the callable entity has a parameter or result of a formal untagged incomplete type; if the callable entity is an expression function, the return expression of the expression function causes freezing.
expression
. - At the place where a use of the Access or Unchecked_Access attribute whose
prefix
denotes an expression function causes freezing, the return expression of the expression function causes freezing.
package Pack is
10.k/3type Flub is range 0 .. 100;
10.l/3function Foo (A : in Natural) return Natural is
(A + Flub'Size); -- The expression is not frozen here.
10.m/4type Bar is access function (A : in Natural) return Natural;
10.n/3P : Bar := Foo'Access; -- (A)
10.o/3Val : Natural := P.all(5); -- (B)
10.p/3end Pack;
- At the place where a
name
causes freezing, the entity denoted by thename
is frozen, unless thename
is aprefix
of an expanded name; at the place where an objectname
causes freezing, the nominal subtype associated with thename
is frozen.
object_declaration
other than a deferred constant declaration causes freezing of the nominal subtype, plus all component junk.- {8652/0046} At the place where an
implicit_dereference
causes freezing, the nominal subtype associated with theimplicit_dereference
is frozen.
implicit_dereference
is neither a name
nor expression
by itself, so it isn't covered by other rules. - At the place where an
allocator
causes freezing, the designated subtype of its type is frozen. If the type of theallocator
is a derived type, then all ancestor types are also frozen.
type Pool_Ptr is access System.Storage_Pools.Root_Storage_Pool'Class;
function F return Pool_Ptr;
13.dpackage P is
type A1 is access Boolean;
type A2 is new A1;
type A3 is new A2;
X : A3 := new Boolean; -- Don't know what pool yet!
for A1'Storage_Pool use F.all;
end P;
- At the place where a profile is frozen, each subtype of the profile is frozen. If the corresponding callable entity is a member of an entry family, the index subtype of the family is frozen.
- At the place where a subtype is frozen, its type is frozen. At the place where a type is frozen, any expressions or
name
s within the full type definition cause freezing, other than those that occur within anaccess_type_definition
or anaccess_definition
; the first subtype, and any component subtypes, index subtypes, and parent subtype of the type are frozen as well. For a specific tagged type, the corresponding class-wide type is frozen as well. For a class-wide type, the corresponding specific type is frozen as well.
- At the place where a specific tagged type is frozen, the primitive subprograms of the type are frozen. At the place where a type is frozen, any subprogram named in an
attribute_definition_clause
for the type is frozen.
attribute_definition_clause
s without jumping through hoops. - At the place where a construct causes freezing, if the construct includes a check associated with some assertion aspect [(independent of whether the check is enabled)], or depends on the definition of some operational aspect as part of its Dynamic Semantics, any
name
s orexpression
s in theaspect_definition
for the aspect cause freezing.
name
in a Constant_Indexing would cause freezing when a generalized_indexing
that makes use of it causes freezing. Notwithstanding the rest of this subclause, freezing an incomplete view has no effect.
Legality Rules
16[The explicit declaration of a primitive subprogram of a tagged type shall occur before the type is frozen (see 3.9.2).]
[A type shall be completely defined before it is frozen (see 3.11.1 and 7.3).]
[The completion of a deferred constant declaration shall occur before the constant is frozen (see 7.4).]
{8652/0009} [An operational or representation item that directly specifies an aspect of an entity shall appear before the entity is frozen (see 13.1).]
aspect_clause
itself, which was not true of the Ada 83 wording. The wording of this rule is carefully written to work properly for type-related representation items. For example, an enumeration_representation_clause
is illegal after the type is frozen, even though the _clause
refers to the first subtype.type T is ...;
function F return T;
type R is
record
C : T := F;
D : Boolean := F = F;
end record;
X : R;
default_expression
“F = F”, there is no need to freeze the types involved at that point. However, the declaration of X does need to freeze these things. Note that even if component C did not exist, the elaboration of the declaration of X would still need information about T — even though D is not of type T, its default_expression
requires that information. statement
s — they only apply within a single declarative_part
, package_specification
, task_definition
, protected_definition
, or protected_body
. default_expression
s and default_name
s in line at the place of use. Alternatively, an implementation may choose to generate thunks (subprograms implicitly generated by the compiler) for evaluation of defaults. Thunk generation cannot, in general, be done at the place of the declaration that includes the default. Instead, they can be generated at the first freezing point of the type(s) involved. (It is impossible to write a purely one-pass Ada compiler, for various reasons. This is one of them — the compiler needs to store a representation of defaults in its symbol table, and then walk that representation later, no earlier than the first freezing point.)aspect_clause
for an entity should most certainly not be a freezing point for the entity. Dynamic Semantics
20/2The tag (see 3.9) of a tagged type T is created at the point where T is frozen.
Incompatibilities With Ada 83
pragma
, or a representation_clause
for the type itself. In any case, an occurrence within an expression is always forcing.”type A is array(Integer range 1..10) of Boolean;
subtype S is Integer range A'Range;
-- not forcing for A
Extensions to Ada 83
generic_formal_parameter_declaration
s do not normally freeze the entities from which they are defined. For example: package Outer is
type T is tagged limited private;
generic
type T2 is
new T with private; -- Does not freeze T
-- in Ada 95.
package Inner is
...
end Inner;
private
type T is ...;
end Outer;
explicit_generic_actual_parameter
s cause freezing, even though a package equivalent to the instance would not cause freezing. This is primarily because such an equivalent package would have its body in the body of the containing program unit, whereas an instance has its body right there. Wording Changes from Ada 83
representation_clause
s. We have expanded the concept to cover private types, because the rules stated in RM83-7.4.1(4) are almost identical to the forcing occurrence rules.- The Ada 83 rules do not work right for subtype-specific aspects. In an earlier version of Ada 9X, we considered allowing representation items to apply to subtypes other than the first subtype. This was part of the reason for changing the Ada 83 rules. However, now that we have dropped that functionality, we still need the rules to be different from the Ada 83 rules.
- The Ada 83 rules do not achieve the intended effect. In Ada 83, either with or without the AIs, it is possible to force the compiler to generate code that references uninitialized dope, or force it to detect erroneousness and exception raising at compile time.
- It was a goal of Ada 83 to avoid uninitialized access values. However, in the case of deferred constants, this goal was not achieved.
- The Ada 83 rules are not only too weak — they are also too strong. They allow loopholes (as described above), but they also prevent certain kinds of
default_expression
s that are harmless, and certain kinds ofgeneric_declaration
s that are both harmless and very useful. 20.o/2 - Ada 83 had a case where an
aspect_clause
had a strong effect on the semantics of the program — 'Small. This caused certain semantic anomalies. There are more cases in Ada 95, because theattribute_definition_clause
has been generalized.
Incompatibilities With Ada 95
Wording Changes from Ada 95
Incompatibilities With Ada 2005
Wording Changes from Ada 2005
aspect_specification
s; these are frozen at the freezing point of the associated entity, not the point of declaration.Wording Changes from Ada 2012
expression_function_declaration
that is a completion or that is the target of a renames-as-body freezes. This is formally an incompatibility, but as all known implementations freeze expression functions more aggressively than allowed by either the old or new wording, practically this will be an extension.aspect_specification
s; these now depend on the kind of aspect.