CVS difference for ai05s/ai05-0074-4.txt

Differences between 1.1 and version 1.2
Log of other versions for file ai05s/ai05-0074-4.txt

--- ai05s/ai05-0074-4.txt	2009/02/17 06:28:13	1.1
+++ ai05s/ai05-0074-4.txt	2009/02/18 05:48:10	1.2
@@ -1,17 +1,17 @@
-!standard 3.9.3 (9)                              09-02-15  AI05-0074-4/01
+!standard 3.9.3 (9)                              09-02-16  AI05-0074-4/02
 !standard 3.10.1 (10/2)
 !standard 7.3 (4)
 !standard 7.3.1 (12/2)
 !standard 7.3.1 (13)
 !standard 10.2.1 (17/2)
-!standard 12.3 (12)          
-!standard 12.3.1(1-28)
+!standard 12.3 (12)
+!standard 12.3.1(0)
 !class amendment 09-02-15
 !status work item 09-02-15
 !status received 09-02-15
 !priority Medium
 !difficulty Hard
-!subject Private Instantiations and Incomplete Instantiations
+!subject Private Instantiations
 
 !summary
 
@@ -32,136 +32,132 @@
 
 Given the signature for a set abstraction:
 
-generic 
-   type Element is private; 
-   type Set is private; 
-   with function Size(Of_Set : Set) return Natural is <>; 
-   with function Union(Left, Right : Set) return Set is <>; 
-   with function Intersection(Left, Right : Set) return Set is <>; 
-   with function Empty return Set is <>; 
-   with function Unit_Set(With_Item : Element) return Set is <>; 
-   with function Nth_Element(Of_Set : Set) return Element is <>; 
+generic
+   type Element is private;
+   type Set is private;
+   with function Size(Of_Set : Set) return Natural is <>;
+   with function Union(Left, Right : Set) return Set is <>;
+   with function Intersection(Left, Right : Set) return Set is <>;
+   with function Empty return Set is <>;
+   with function Unit_Set(With_Item : Element) return Set is <>;
+   with function Nth_Element(Of_Set : Set) return Element is <>;
 package Set_Signature is end;
-... 
+...
 
-we could define a generic that required some set abstraction, but it 
+we could define a generic that required some set abstraction, but it
 didn't care which one so long as it implemented the above signature:
 
-generic 
-   with package Base_Set is new Set_Signature(<>); 
-package Layered_Abstraction is 
-   type Cool_Type(Set : access Base_Set.Set) is limited_private; 
-   procedure Massage(CT : in out Cool_Type; New_Set : Base_Set.Set); 
+generic
+   with package Base_Set is new Set_Signature(<>);
+package Layered_Abstraction is
+   type Cool_Type(Set : access Base_Set.Set) is limited_private;
+   procedure Massage(CT : in out Cool_Type; New_Set : Base_Set.Set);
    ...
 end Layered_Abstraction;
 
 Now if we want to define a set type and provide the pre-instantiated
 signature for it, we run into trouble:
 
-generic 
-   type Elem is private; 
-   with function Hash(El : Elem) return Integer; 
-package Hashed_Sets is 
+generic
+   type Elem is private;
+   with function Hash(El : Elem) return Integer;
+package Hashed_Sets is
 
-   type Set is private; 
-   function Union(Left, Right : Set) return Set; 
+   type Set is private;
+   function Union(Left, Right : Set) return Set;
    ...
 
    package Signature is new Set_Signature(Elem, Set);
-private 
-   type Set is record ... end record; 
+private
+   type Set is record ... end record;
 end Hashed_Sets;
 
 The problem is that we can't do the instantiation of Set_Signature where we
-would want to do so, because the instantiation freezes the type "Set" 
+would want to do so, because the instantiation freezes the type "Set"
 prematurely.
 
-A similar problem occurs when a type wants to include a pointer to a 
-container based on the type being defined. 
+A similar problem occurs when a type wants to include a pointer to a
+container based on the type being defined.
 
 For example:
 
 with Sequences;
-package Expressions is 
+package Expressions is
    type Expr_Ref is private;
    package Expr_Sequences is new Sequences(Expr_Ref); -- Freezing trouble here!
    type Seq_Of_Expr is access Expr_Sequences.Sequence;
    function Operands(Expr : Expr_Ref) return Seq_Of_Expr;
    ...
 private
-   type Expression; -- completion deferred to body 
-   type Expr_Ref is access Expression; 
+   type Expression; -- completion deferred to body
+   type Expr_Ref is access Expression;
 end Expressions;
 
 Here we have a case where we want to instantiate a generic using a private
 type, and use the results of the instantiation as the designated type of an
-access type, which is in turn used as a parameter or result type of an 
+access type, which is in turn used as a parameter or result type of an
 operation on the private type.
 
-Unfortunately, we can't instantiate the "Sequences" generic with Expr_Ref, 
-since it is private. 
+Unfortunately, we can't instantiate the "Sequences" generic with Expr_Ref,
+since it is private.
 
 
 !proposal
 
-Introduce new syntax (a private_instantiation_declaration) that exports a 
-view of a generic instance declared in the private part of a package 
+Introduce new syntax (a private_instantiation_declaration) that exports a
+view of a generic instance declared in the private part of a package
 specification so that a type with a partial view in the visible part of the
 package can be used as an actual in the instantiation.
 
-The real generic_instantiation that completes a 
-private_instantiation_declaration is explicitly placed after the 
-full_type_declaration that completes the type with the partial view, so there 
-are no freezing concerns with the generic instance, nor is there a need to 
+The real generic_instantiation that completes a
+private_instantiation_declaration is explicitly placed after the
+full_type_declaration that completes the type with the partial view, so there
+are no freezing concerns with the generic instance, nor is there a need to
 change rules or add restrictions to the generic contract model.
 
-Two types of views of an instance are defined. (A partial view of an instance, 
-and a full view of an instance.) A partial view of an instance is associated 
-with a private_instantiation_declaration. A full view of an instance is 
-equivalent to the view of the instance provided by the generic_instantiation 
-that completes the partial view at the site of the completion.
-
-A private_instantiation_declaration declares two views of an instance.
-(A partial view of the instance, and the full view of the instance).
-A partial view of the instance applied to the immediately enclosing declarative
-region, while the full view is available to outside program units.
-
-Semantically, it is as though a partial view of an instance sees a copy of the 
-generic template, but the mapping from actuals to formals (and the corresponding 
-substitutions) has not taken place yet, so the view has to make certain limiting 
+Two types of views of an instance are defined. (A partial view of an instance,
+and a full view of an instance.) A partial view of an instance is associated
+with a private_instantiation_declaration. A full view of an instance is
+equivalent to the view of the instance provided by the generic_instantiation
+that completes the partial view at the site of the completion. A partial view of
+the instance applied to the immediately enclosing declarative region, while the
+full view is available to outside program units.
+
+Semantically, it is as though a partial view of an instance sees a copy of the
+generic template, but the mapping from actuals to formals (and the corresponding
+substitutions) has not taken place yet, so the view has to make certain limiting
 assumptions about the types that are exported from the view.
 
-For a partial view of an instance, it is assumed that every visible 
-composite type declaration of the instance (other than array types) have been 
-derived from a formal type that has a partial view (an assume the worst rule), 
-thus each such exported type from the view is considered to have a partial view 
+For a partial view of an instance, it is assumed that every visible
+composite type declaration of the instance (other than array types) have been
+derived from a formal type that has a partial view (an assume the worst rule),
+thus each such exported type from the view is considered to have a partial view
 until the completion of the partial view of the instance.
 
-A private type or private extenstion cannot directly contain a component of a 
+A private type or private extenstion cannot directly contain a component of a
 composite type from the partial view of an instance, since such an exported type
-may have been derived from a formal which may be the private type or private 
-extension. An array type would be allowed, but only if the components of the 
-array are not composite types, as these situations otherwise could potentially 
-create an illegal circular type. The full_type_declaration of a private type or 
-private extension however may define a recursive data structure using access 
-types to designate objects of a type from the partial view of the instance. If 
-the view of the type is a tagged view, then private extension derivations are 
+may have been derived from a formal which may be the private type or private
+extension. An array type would be allowed, but only if the components of the
+array are not composite types, as these situations otherwise could potentially
+create an illegal circular type. The full_type_declaration of a private type or
+private extension however may define a recursive data structure using access
+types to designate objects of a type from the partial view of the instance. If
+the view of the type is a tagged view, then private extension derivations are
 allowed before the completion of the partial view of the instance.
 
-A partial view of an instance does not include any object declarations in the 
-instance, which prevents any references to objects in the instance until the 
-generic_instantiation that completes the partial or incomplete view of the 
-instance. It is also not allowed to declare any objects of types exported from 
-the partial or incomplete view of the instance until the completion of the 
-partial or incomplete view. 
+A partial view of an instance does not include any object declarations in the
+instance, which prevents any references to objects in the instance until the
+generic_instantiation that completes the partial view of the instance. The
+declaration of objects of types exported from the partial view is also not
+allowed until the completion of the partial view.
 
 The syntax for a private_instantiation_declaration allows that actual parameters
-can be left unspecified until the private part of the package specification. 
+can be left unspecified until the private part of the package specification.
 This provides opportunities for improved data hiding and abstractions. Actuals
 for formal types and formal packagese cannot be deferred to the private part,
 but all other formals can. If the actual is visible at the place of a
 private_instantiation_declaration than it must be explictly named in the
-private_instantiation_declaration unless the formal has a default 
+private_instantiation_declaration unless the formal has a default
 value or initialization.
 
 
@@ -170,9 +166,9 @@
 Change 3.9.3 (9)
 
 If a partial view {of a type} is not abstract, the corresponding full view shall
-not be abstract. If a generic formal type is abstract, then for each primitive 
-subprogram of the formal that is not abstract, the corresponding primitive 
-subprogram of the actual shall not be abstract. 
+not be abstract. If a generic formal type is abstract, then for each primitive
+subprogram of the formal that is not abstract, the corresponding primitive
+subprogram of the actual shall not be abstract.
 
 Change 3.10.1 (10/2)
 
@@ -181,80 +177,80 @@
 
 Change 7.3 (4)
 
-A private_type_declaration or private_extension_declaration declares a partial 
-view of the type; such a declaration is allowed only as a declarative_item of 
-the visible part of a package, and it requires a completion, which shall be a 
-full_type_declaration that occurs as a declarative_item of the private part of 
-the package. The view of the type declared by the full_type_declaration is 
-called the full view. A generic formal private type or a generic formal private 
-extension is also a partial view {of a type. The view of a composite type of a 
-partial view of an instance (see 12.3.1) that does not have an incomplete view 
+A private_type_declaration or private_extension_declaration declares a partial
+view of the type; such a declaration is allowed only as a declarative_item of
+the visible part of a package, and it requires a completion, which shall be a
+full_type_declaration that occurs as a declarative_item of the private part of
+the package. The view of the type declared by the full_type_declaration is
+called the full view. A generic formal private type or a generic formal private
+extension is also a partial view {of a type. The view of a composite type of a
+partial view of an instance (see 12.3.1) that does not have an incomplete view
 and is not an array type, is a partial view of the type}.
 
 AARM
 
 4.a.1  All composite types (Record types, protected types, task types, etc)
-other than array types need to have the same restrictions as a private type or 
-private extension if they are exported from a partial view of an instance, 
-because we do not want to allow components of these types to be declared before 
+other than array types need to have the same restrictions as a private type or
+private extension if they are exported from a partial view of an instance,
+because we do not want to allow components of these types to be declared before
 the declaration of the full view of an instance that completes the partial view
 of the instance. Note that while an array type can be declared as a component
 of a type, it cannot be declared as a component of a private type or private
-extension if it has composite components because it is assumed that the 
+extension if it has composite components because it is assumed that the
 components of the array have been derived from the private type or private
 extension.
 
 Change 7.3.1 (12/2)
 
 10  Partial views {of a type} provide initialization, membership tests, selected
- components for the selection of discriminants and inherited components, 
-qualification, and explicit conversion. Nonlimited partial views also allow use 
+ components for the selection of discriminants and inherited components,
+qualification, and explicit conversion. Nonlimited partial views also allow use
 of assignment_statements.
 
 Change 7.3.1 (13)
-11  For a subtype S of a partial view {of a type}, S'Size is defined (see 13.3). 
-For an object A of a partial view {of a type}, the attributes A'Size and 
-A'Address are defined (see 13.3). The Position, First_Bit, and Last_Bit 
-attributes are also defined for discriminants and inherited components. 
+11  For a subtype S of a partial view {of a type}, S'Size is defined (see 13.3).
+For an object A of a partial view {of a type}, the attributes A'Size and
+A'Address are defined (see 13.3). The Position, First_Bit, and Last_Bit
+attributes are also defined for discriminants and inherited components.
 
 Change 10.2.1 (17/2)
 
- A pragma Pure is used to declare that a library unit is pure. If a pragma Pure 
-applies to a library unit, then its compilation units shall be pure, and they 
-shall depend semantically only on compilation units of other library units that 
-are declared pure. Furthermore, the full view of any partial view {of a type} 
-declared in the visible part of the library unit that has any available stream 
-attributes shall support external streaming (see 13.13.2). 
+ A pragma Pure is used to declare that a library unit is pure. If a pragma Pure
+applies to a library unit, then its compilation units shall be pure, and they
+shall depend semantically only on compilation units of other library units that
+are declared pure. Furthermore, the full view of any partial view {of a type}
+declared in the visible part of the library unit that has any available stream
+attributes shall support external streaming (see 13.13.2).
 
 
 Change 12.3 (12)
 
-A generic_instantiation declares {(a view of)} an instance; it is equivalent to 
-the instance declaration (a package_declaration or subprogram_declaration) 
-immediately followed by the instance body, both at the place of the 
-instantiation. 
+A generic_instantiation declares {(a view of)} an instance; it is equivalent to
+the instance declaration (a package_declaration or subprogram_declaration)
+immediately followed by the instance body, both at the place of the
+instantiation.
 
 Add new section:
-12.3.1 Private Instantiations and Incomplete Instantiations
+12.3.1 Private Instantiations
 
 Add 12.3.1(1 - 31):
 
-1 The declaration (in the visible part of a package) of a private instantiation 
-serves to allow a generic package to be instantiated with an actual that has a 
-partial view of a type.  
+1 The declaration (in the visible part of a package) of a private instantiation
+serves to allow a generic package to be instantiated with an actual that has a
+partial view of a type.
 
 SYNTAX
 
 2 private_instantiation_declaration ::=
-   PACKAGE defining_program_unit_name IS
-         PRIVATE NEW generic_package_name [deferred_generic_actual_part];

-3 deferred_generic_actual_part ::= 
-   (deferred_generic_association {, deferred_generic_association})
-
-4 deferred_generic_association ::= 
-   [generic_formal_parameter_selector_name =>] explicit_generic_actual_parameter
- |  [generic_formal_parameter_selector_name =>] PRIVATE 
+   PACKAGE defining_program_unit_name IS
+        PRIVATE NEW generic_package_name [deferred_generic_actual_part];
+
+3 deferred_generic_actual_part ::=
+   (deferred_generic_association {, deferred_generic_association})
+
+4 deferred_generic_association ::=
+   [generic_formal_parameter_selector_name =>] explicit_generic_actual_parameter
+ |  [generic_formal_parameter_selector_name =>] PRIVATE
  | OTHERS => PRIVATE
 
 5 A deferred_generic_association is named or positional according to whether
@@ -269,47 +265,47 @@
 6 A private_instantiation_declaration declares both a Partial View and a Full
 View of an instance; such a declaration is allowed only as a declarative_item
 of the visible part of a package, and it requires a completion, which shall be
-a generic_instantiation of a package. The completion of a 
-private_instantiation_declaration occurs as a declarative_item of the private 
+a generic_instantiation of a package. The completion of a
+private_instantiation_declaration occurs as a declarative_item of the private
 part of the package.
 
-7 The generic_formal_parameter_selector_name of a deferred_generic_association 
+7 The generic_formal_parameter_selector_name of a deferred_generic_association
 shall denote a generic_formal_parameter_declaration of the generic
-unit being instantiated if the deferred_generic_association has an 
+unit being instantiated if the deferred_generic_association has an
 explicit_generic_actual_parameter. If two or more formal subprograms have the
 same defining name, then named associations are not allowed for the
 corresponding actuals.
 
-8 A private_instantiation_declaration shall contain at most one 
+8 A private_instantiation_declaration shall contain at most one
 deferred_generic_association for each formal. Each formal without an association
 shall have a default_expression or subprogram_default.
 
 9 The actual parameters of a private_instantiation_declaration shall match the
-corresponding actual parameters of the completion, whether the actual 
+corresponding actual parameters of the completion, whether the actual
 parameters are given explicitly or by default.
 
 10 The rules for matching of actual parameters between the completion and the
 private instantiation are as follows:
 
 11   * A named association with the reserved word OTHERS matches all needed
- actual parameters from the completion that are not associated with some 
- previous association. 
+ actual parameters from the completion that are not associated with some
+ previous association.
 
 12   * If an association is a named association in the private instantiation
  then the association shall be a named association in the completion unless
- the actual parameters are given by default and the association has the 
- reserved word OTHERS in the private instantiation. If an association is a 
- positional association in the private instantiation then the association shall 
+ the actual parameters are given by default and the association has the
+ reserved word OTHERS in the private instantiation. If an association is a
+ positional association in the private instantiation then the association shall
  be positional in the completion.
 
 13  * An association with the reserved word PRIVATE but without the reserved
- word OTHERS matches the actual of the completion that has the same 
+ word OTHERS matches the actual of the completion that has the same
  generic_formal_parameter_selector_name if the association is a named
  association, or the actual in the corresponding relative position within the
- generic_actual_part if the association is a positional association. 
+ generic_actual_part if the association is a positional association.
 
 14   * For a formal object of mode IN the actuals match if they are static
- expressions with the same value, of if they statically denote the same 
+ expressions with the same value, of if they statically denote the same
  constant, or if they are both the literal NULL.
 
 15   * For a formal subtype, the actuals match if they denote statically
@@ -325,40 +321,40 @@
     ensure that no evaluations would take place at the point of the
     private instantiation.
 
-17 If the actual of a generic_instantiation that completes a 
-private_instantiation_declaration is visible at the place of the 
-private_instantiation_declaration then there shall be a 
+17 If the actual of a generic_instantiation that completes a
+private_instantiation_declaration is visible at the place of the
+private_instantiation_declaration then there shall be a
 deferred_generic_association with an explicit_generic_actual_parameter that
 names the actual, if the associated formal does not have a default_expression or
 subprogram_default.
 
-18 A private_instantiation_declaration shall not have a 
+18 A private_instantiation_declaration shall not have a
 deferred_generic_association with an explicit_generic_actual_parameter that has
 an incomplete view at the place of the private_instantiation_declaration.
 
 19 A private_instantiation_declaration shall have a deferred_generic_association
-with an explicit_generic_actual_parameter for every formal_type_declaration and 
+with an explicit_generic_actual_parameter for every formal_type_declaration and
 formal_package_declaration of the completion.
 
-20 Neither the declaration of a variable of a type from a partial view of an 
-instance, nor the creation by an allocator of an object of a type from the view 
+20 Neither the declaration of a variable of a type from a partial view of an
+instance, nor the creation by an allocator of an object of a type from the view
 of the instance, are allowed before the completion of a
-private_instantiation_declaration. Similarly, before the completion, such a 
-type cannot be used in a generic_instantiation or in a representation item. 
+private_instantiation_declaration. Similarly, before the completion, such a
+type cannot be used in a generic_instantiation or in a representation item.
 
-21 All visible composite types other than an array type of a partial view of 
+21 All visible composite types other than an array type of a partial view of
 an instance that do not have an incomplete view have a partial view. If the
 view of the type is a tagged view, then the view of the type is a tagged
 partial view.
 
 AARM
 
-21.a Ramification: It is assumed that all such types have been derived from a 
-formal type that has a partial view, or contains a component of a formal type 
-that has a partial view (An assume the worst rule). By saying that these types 
-have partial views, it prevents the declaration of illegal recursive types, 
+21.a Ramification: It is assumed that all such types have been derived from a
+formal type that has a partial view, or contains a component of a formal type
+that has a partial view (An assume the worst rule). By saying that these types
+have partial views, it prevents the declaration of illegal recursive types,
 or declaring other composite types with components that have a partial view
-of a type before the completion of the partial view of the instance in the 
+of a type before the completion of the partial view of the instance in the
 private part. An derivative of an array type is allowed to be declared, but
 if the components of the array are composite types then the array is considered
 to be an array of types that have a partial view. This prevents the declaration
@@ -366,8 +362,8 @@
 extension which could lead to an illegal recursive type declaration.
 
 22 The partial view of a type of an explicit_generic_actual_parameter of a
-deferred_generic_association must be conformant to the formal type declaration
-of the generic package specification. Specifically, if the partial view of a 
+deferred_generic_association must be conformant to the formal type declaration
+of the generic package specification. Specifically, if the partial view of a
 type is a limited view, then the formal_private_type_definition shall have the
 reserved word LIMITED in the formal type declaration. If the partial view of a
 type is an untagged view, then the formal_private_type_definition shall not have
@@ -379,33 +375,33 @@
 view may be of a type with an unlimited view. Similarly, a full view of an
 untagged partial view may be of a type that has a tagged view. We dont want to
 allow a generic_instantiation in the private part of a package that conflicts
-with the declarations of the actuals used in a 
+with the declarations of the actuals used in a
 private_instantiation_declaration.
 
 STATIC SEMANTICS
 
 23 A private_instantiation_declaration declares a private instantiation.
 
-24 A private_instantiation_declaration defines two views of a generic instance. 
-The declaration of a partial view of an instance defines the operations that are 
-available within the immediately enclosing declarative region. The declaration 
-of the full view defines the operations that are available to outside program 
-units. The full view is equivalent to the view of the instance declared by the 
+24 A private_instantiation_declaration defines two views of a generic instance.
+The declaration of a partial view of an instance defines the operations that are
+available within the immediately enclosing declarative region. The declaration
+of the full view defines the operations that are available to outside program
+units. The full view is equivalent to the view of the instance declared by the
 generic_instantiation that completes the private_instantiation_declaration.
 
-25 A partial view of an instance is a view of a copy of the text of the generic 
-template whereby the substitution of formal parameters with actual parameters 
-has not taken place, and the mappings of actual parameters to formal parameters 
-of the generic_instantiation are considered to be unresolved. 
+25 A partial view of an instance is a view of a copy of the text of the generic
+template whereby the substitution of formal parameters with actual parameters
+has not taken place, and the mappings of actual parameters to formal parameters
+of the generic_instantiation are considered to be unresolved.
 
-26 A partial view of an instance does not include a view of any object 
+26 A partial view of an instance does not include a view of any object
 declarations from the instance.
 
 AARM
 
-26.a We do not want to allow any references to objects of a private view of an 
+26.a We do not want to allow any references to objects of a private view of an
 instance until the completion of the deferred_instantiation_declaration. This is
-because the objects really do not come into existence until the 
+because the objects really do not come into existence until the
 generic_instantiation declaration.
 
 
@@ -414,12 +410,12 @@
 27 The full_type_declaration that completes a partial view of a type cannot
 declare a component of a type from a partial view of an instance because it is
 assumed that any type of the instance could have been derived from the type with
-the partial view, and thus could potentially create an illegal circular data 
+the partial view, and thus could potentially create an illegal circular data
 type.
 
-28 A new type cannot be derived from a type from a partial view of an instance 
-unless the type is a tagged type, since such a type may have been derived 
-(directly or indirectly) from an actual that has a partial view. Such a 
+28 A new type cannot be derived from a type from a partial view of an instance
+unless the type is a tagged type, since such a type may have been derived
+(directly or indirectly) from an actual that has a partial view. Such a
 derivation must be either a tagged private type or a tagged private extension.
 
 
@@ -429,88 +425,88 @@
 private types. Certainly the most common is a desire to include an instantiation
 of a generic (possibly a signature generic as mentioned in the "problem" section
 above, or perhaps a container generic), with a private type as one of the actual
-parameters to the instantiation. 
+parameters to the instantiation.
 
 A second problem is a desire to be able to have a recursive data structure where
-a type declaration can contain a component that designates a type from an 
+a type declaration can contain a component that designates a type from an
 instance that was instantiated with an actual of the composite type.
 
 An instantiation requires the type of an actual to be defined first, and since
-the instantiation comes after the type declaration, the type declaration cannot 
-name any type declarations of the instantiation. 
+the instantiation comes after the type declaration, the type declaration cannot
+name any type declarations of the instantiation.
 
 A third problem extends from the second problem as it is desirable that it be
 possible to declare such a recursive data structure that has a primitive that
 has a formal parameter of the type of a component that designates an object of
-an instantiated type or returns a result value of a component that designates an 
-object of an instantiated type. 
+an instantiated type or returns a result value of a component that designates an
+object of an instantiated type.
 
 A fourth problem is another variant of the third, where it is desirable that it
 be possible to declare such a recursive data structure that has a primitive that
 has a formal parameter of the type of a component that is an instantiated type,
 or returns a result value of a component that is an instantiated type.
-In addition, we would like it to be possible  to declare such a recursive type 
-as a remote access to class wide type allowing usage in distributed 
+In addition, we would like it to be possible  to declare such a recursive type
+as a remote access to class wide type allowing usage in distributed
 applications.
 
 A fifth problem is a desire to export a type derived from a tagged type that is
 exported from a generic instance that has a private type as one of the actual
-parameters. 
+parameters.
 
-A sixth problem is a desire to instantiate a generic in the visible part of a 
-package, yet defer the declarations for some or all of the actuals to the 
-private part of the package. 
+A sixth problem is a desire to instantiate a generic in the visible part of a
+package, yet defer the declarations for some or all of the actuals to the
+private part of the package.
 
-The basic idea of this proposal is to add syntax that provides more flexibility 
+The basic idea of this proposal is to add syntax that provides more flexibility
 and capabilities for exporting functionality in the visible part
-of a package specification, creating recursive data structures, and 
+of a package specification, creating recursive data structures, and
 hiding implementation details in the private part of a package specification.
 
 This proposal is limited to packages because you can use renaming-as-body to get
-these effects for subprogram instantiations. Moreover, you cannot export a type 
-from a generic subprogram, so there is no possibility of recursive use. 
+these effects for subprogram instantiations. Moreover, you cannot export a type
+from a generic subprogram, so there is no possibility of recursive use.
 [Note that we could lift this limitation if it if felt to be more regular.]
 
 Ada 2005 provides solutions to some of these problems, but they are not ideal.
-For the first example, making the instantiation a child unit solves the problem. 
+For the first example, making the instantiation a child unit solves the problem.
 However, this is annoying, because accessing the instance requires an extra with
 and instantiation (since children of generics must be generic):
 
-generic 
-   type Elem is private; 
-   with function Hash (El : Elem) return Integer; 
-package Hashed_Sets is 
-   type Set is private; 
-   function Union(Left, Right : Set) return Set; 
-   ... 
-private 
-   type Set is record ... end record; 
+generic
+   type Elem is private;
+   with function Hash (El : Elem) return Integer;
+package Hashed_Sets is
+   type Set is private;
+   function Union(Left, Right : Set) return Set;
+   ...
+private
+   type Set is record ... end record;
 end Hashed_Sets;
 
-generic 
-package.Hashed_Sets.Signature is 
-   package The_Signature is new Set_Signature(Elem, Set); 
+generic
+package.Hashed_Sets.Signature is
+   package The_Signature is new Set_Signature(Elem, Set);
 end Hashed_Sets.Signature;
 
 A user of Hashed_Sets must with and instantiate Hashed_Sets.Signature in order
-to access the instance. 
+to access the instance.
 
 A simpler alternative involves the use of nested packages. This is better, but
 introducing a nested package can still be considered to be awkward.
 
-generic 
-   type Elem is private; 
-   with function Hash (El : Elem) return Integer; 
+generic
+   type Elem is private;
+   with function Hash (El : Elem) return Integer;
 package Hashed_Sets is
-   package Sets is 
-      type Set is private; 
+   package Sets is
+      type Set is private;
       function Union(Left, Right : Set) return Set;
    private
-      type Set is record ... end record; 
+      type Set is record ... end record;
    end Sets;
- 
+
    use Sets;
-   package The_Signature is new Set_Signature(Elem, Set); 
+   package The_Signature is new Set_Signature(Elem, Set);
 
 end Hashed_Sets;
 
@@ -519,78 +515,78 @@
 using the limited with:
 
 with Sequences;
-limited with Expressions.Sequences; 
-package Expressions is 
+limited with Expressions.Sequences;
+package Expressions is
    type Expr_Ref is private;
    type Seq_Of_Expr is access Expressions.Sequences.Sequence;
    function Operands(Expr : Expr_Ref) return Seq_Of_Expr;
    ...
 private
    type Expression; -- completion deferred to body
-   type Expr_Ref is access Expression; 
+   type Expr_Ref is access Expression;
 end Expressions;
 
-package Expressions.Sequences is 
-   package Expr_Sequences is new Sequences(Expr_Ref); 
-   type Sequence is new Expr_Sequences.Sequence; 
+package Expressions.Sequences is
+   package Expr_Sequences is new Sequences(Expr_Ref);
+   type Sequence is new Expr_Sequences.Sequence;
 end Expressions.Sequences;
 
 Here, besides the extra with clause, we need to declare an extra type
-simply so that the type is visible to the limited with clause 
+simply so that the type is visible to the limited with clause
 (which operates purely syntactally). This means that extra type conversions
-are necessary. Another limitation is that this technique requires a type 
-derivation (Sequence), and would not work for types that cannot be extended, 
+are necessary. Another limitation is that this technique requires a type
+derivation (Sequence), and would not work for types that cannot be extended,
 such as synchronized tagged types.
 
 Once again, the use of nested packages provides a simpler work around,
 but this still requires the extra type and having to declare a nested
 package can still be viewed as being awkward. Such a technique is something that
-would likely require the awareness of an expert Ada programmer, as it is 
-questionable whether a less experienced programmer would come up with this 
+would likely require the awareness of an expert Ada programmer, as it is
+questionable whether a less experienced programmer would come up with this
 technique on their own.
 
 with Sequences;
 package Expression_Sequences is
 
-   type Expr_Seq; -- incomplete type 
+   type Expr_Seq; -- incomplete type
    type Seq_Of_Expr is access Expr_Seq;
 
    package Expressions is
       type Expr_Ref is private;
       function Operands(Expr : Expr_Ref) return Seq_Of_Expr;
       ...
-   private 
+   private
       type Expression; -- completion deferred to body
-      type Expr_Ref is access Expression; 
-   end Expressions; 
+      type Expr_Ref is access Expression;
+   end Expressions;
 
    use Expressions;
 
-   package Expr_Sequences is new Sequences(Expr_Ref); 
+   package Expr_Sequences is new Sequences(Expr_Ref);
    type Expr_Seq is new Expr_Sequences.Sequence; --completion of incomplete type
 
-end Expression_Sequences; 
+end Expression_Sequences;
 
 This proposal attempts to provide a more intuitive approach for solving these
-and other problems and eliminates limitations that currently exist in the 
-language as well as introduce new capabilities for data hiding and better 
+and other problems and eliminates limitations that currently exist in the
+language as well as introduce new capabilities for data hiding and better
 abstractions.
 
 First of all, an important capability is to be able to instantiate a generic
 with a private type or private extension as an actual. The concept is to place
 the generic instantiation in the private part after the completion of the
 private type or private view, but provide a view of the instance in the visible
-part of the package that is exported to outside program units. 
+part of the package that is exported to outside program units.
 
-This new syntactic construct is called a partial_instantiation_declaration.
+This new syntactic construct is called a private_instantiation_declaration.
 This is a declaration that is placed in the visible part of a package. It is
 completed by a generic_instantiation in the private part of the package.
 We now say that a generic_instantiation declares a full view of an instance.
-A partial_instantiation_declaration also declares a full view of the instance,
-but that view is only available to outside program units. 
-A partial_instantiation_declaration also declares what is called a partial view
+A private_instantiation_declaration also declares a full view of the instance,
+but that view is only available to outside program units.
+A private_instantiation_declaration also declares what is called a partial view
 of an instance which only applies to the immediately enclosing declarative
-region. A partial_instantiation_declaration can be distinguished from a 
+region. A private_instantiation_declaration can be distinguished from a
 generic_instantiation by the use of the word PRIVATE in the syntax.
 
 e.g.,
@@ -603,8 +599,8 @@
       package I is new Ada.Containers.Doubly_Linked_Lists (T);
    end Pkg;
 
-   The intent is that the exported (full) view of the instance of I is 
-   effectively the same as the view if the generic had been instantiated from 
+   The intent is that the exported (full) view of the instance of I is
+   effectively the same as the view if the generic had been instantiated from
    outside the enclosing package;
 
 i.e.
@@ -623,10 +619,10 @@
    end Pkg;
 
 
-Now suppose we would like type T to be a recursive structure having a 
+Now suppose we would like type T to be a recursive structure having a
 component that designates a type provided by the partial view of the instance.
 In Ada 2005, it is currently possible to achieve this using an approach
-involving a nested package and an Incomplete Type declaration. 
+involving a nested package and an Incomplete Type declaration.
 
 e.g.,
 
@@ -637,9 +633,9 @@
       package Nested is
         type T is private;
       private
-        type T is 
+        type T is
           record
-            List : access List_Type; 
+            List : access List_Type;
           end record;
       end Nested;
 
@@ -649,20 +645,20 @@
       -- ERROR Cannot derive if I.List is a syncronized tagged type
    end Pkg;
 
-Note that the programmer really just wants to instantiate a list of T in the 
-visible part of the package. Here the programmer has had to jump through three 
-mental hurdles to achieve this. The programmer has to think of declaring a 
-nested package, declaring an incomplete type outside the nested package, and 
-completing the an incomplete type with an derived type from an instance. It is 
-quite likely that a reasonably experienced programmer would not come up with 
-this solution on their own, and this would have to be filed away in a book of 
+Note that the programmer really just wants to instantiate a list of T in the
+visible part of the package. Here the programmer has had to jump through three
+mental hurdles to achieve this. The programmer has to think of declaring a
+nested package, declaring an incomplete type outside the nested package, and
+completing the an incomplete type with an derived type from an instance. It is
+quite likely that a reasonably experienced programmer would not come up with
+this solution on their own, and this would have to be filed away in a book of
 "tricks" to get around programming problems that one might run into.
 
 This proposal provide an more intuitive syntax that more closely maps to
-what the programmer wanted to express. Compare the complexity of the visible 
+what the programmer wanted to express. Compare the complexity of the visible
 part of the example above, with the two line visible part using the new proposed
 syntax below. One cannot help but have to mentally process the private part
-in the example above as well, whereas in the example below, the mind is much 
+in the example above as well, whereas in the example below, the mind is much
 more at ease without having to peek at the private part. If Ada is supposed to
 be a language involving code that is written once but read many times, then the
 improved readability of the new syntax should continue to generate savings over
@@ -674,19 +670,19 @@
       type T is private;
       package I is PRIVATE new Ada.Containers.Doubly_Linked_Lists (T);
    private
-      type T is 
+      type T is
         record;
           List : access I.List;
         end record;
       package I is new Ada.Containers.Doubly_Linked_Lists (T);
    end Pkg;
 
-Note also, that if we replace the use of Ada.Containers.Doubly_Linked_List with 
+Note also, that if we replace the use of Ada.Containers.Doubly_Linked_List with
 a different container such as a protected queue that inherits from a synchronous
 interface, then the Ada 2005 example above wont even compile whereas the
 new proposed syntax will compile. This is because it is currently not possible
 to derive a new type from a synchronized tagged type. The Ada 2005 version
-relies on a type derivation of the private type whereas the new proposed 
+relies on a type derivation of the private type whereas the new proposed
 syntax does not involve any type derivations. One might argue that perhaps
 Ada 2005 should be modified to allow derivations of synchronized tagged types.
 That may be true and perhaps that capability will be added to the language
@@ -709,9 +705,9 @@
         -- Cannot return anonymous access type here because function cannot
         -- be dispatching on more than one type
       private
-        type T is 
+        type T is
           record
-            List : List_Ref; 
+            List : List_Ref;
           end record;
       end Nested;
 
@@ -726,7 +722,7 @@
 
 With the new proposed syntax, there is little change other than the additional
 primitive, since the I.List has a partial view, it can be returned with an
-anonymous access type. With the proposed syntax, you have more of a choice 
+anonymous access type. With the proposed syntax, you have more of a choice
 whether to use named access types or not.
 
    with Ada.Containers.Doubly_Linked_Lists;
@@ -735,7 +731,7 @@
       package I is PRIVATE new Ada.Containers.Doubly_Linked_Lists (T);
       function Get_List (Item : T) return access I.List;
    private
-      type T is 
+      type T is
         record;
           List : access I.List;
         end record;
@@ -745,7 +741,7 @@
 
 Now consider that we would like to make T a tagged type and we would like to
 export a primitive of the tagged private type that
-returns the value of an object of an instantiated type that is designated by a 
+returns the value of an object of an instantiated type that is designated by a
 component.
 
 In Ada 2005, we would modify the workaround example as follows;
@@ -781,8 +777,8 @@
 
 With the new proposal, this is not a problem because the type I.List has a
 partial view. (The partial view of an instance assumes that all exported types
-of the view may have been derived from a formal type and thus are considered 
-to have a partial view) This means that Get_List can be declared as a 
+of the view may have been derived from a formal type and thus are considered
+to have a partial view) This means that Get_List can be declared as a
 primitive of T, and thus is inherited by any derived types of T.
 
    with Ada.Containers.Doubly_Linked_Lists;
@@ -800,7 +796,7 @@
 
 Now suppose we would like to use this example in a distributed application,
 as a Remote_Types package. We run into several problems and a fatal roadblock
-that prevents a compilable solution in Ada 2005. 
+that prevents a compilable solution in Ada 2005.
 
 The hopeless workaround code we get ends up looking like;
 
@@ -811,8 +807,8 @@
    pragma Remote_Types;
 
    type List;  -- Incomplete View
-   type RACW_T; -- Incomplete_View of a RACW
-   
+   type RACW_T; -- Incomplete_View of a RACW?
+
    -- type List_Ref is access List;
    -- ERROR Could not use List_Ref declaration because of E.2.2 (9/3) and
    -- E.2.2 (9.2/3). So we try to go back to using an anonymous access type
@@ -820,7 +816,7 @@
    package Nested is
       type L is limited interface;
       type T is synchronized new L with private;
-      procedure Create (Item : in out T; Other : access RACW_T); 
+      procedure Create (Item : in out T; Other : access RACW_T);
       -- Not a RACW here because anonymous access type of an incomplete view
       -- Cant do this because of E.2.2 (14/3)
 
@@ -852,7 +848,7 @@
    type RACW_T is access all Nested.T'Class; -- RACW_T becomes a RACW here
 
    package I is new Ada.Containers.Doubly_Linked_Lists (RACW_T);
-   
+
    type List is new I.List with null record;
    function Get_List (Item : Nested.T) return List;
 
@@ -866,7 +862,7 @@
 package Pkg is
 
    pragma Remote_Types;
-   
+
    type L is limited interface;
    type T is synchronized new L with private;
    type RACW_T is access all T'class;
@@ -891,7 +887,7 @@
 application with this form. It is not hard to come up with an good example.
 Suppose we wanted to write a distributed social networking application similar
 to facebook. Consider a Remote Types package representing a person (type T in
-the example above). A person has a list of friends or contacts which are also 
+the example above). A person has a list of friends or contacts which are also
 persons (The List in the example above). We might want another person to be able
 to remotely retrieve the list of friends from the RACW value representing
 a different person (The Get_List function in the example above) so that the
@@ -900,7 +896,7 @@
 
 It turns out there are other problems with syncronous types, even if we
 give up on the idea of trying to make the workaround work in a distributed
-application. Suppose we just want to have type T be a protected type in a 
+application. Suppose we just want to have type T be a protected type in a
 recursive structure that stores a list of references to type T, where we want
 to have a primitive that returns the list of references.
 
@@ -921,7 +917,7 @@
       procedure Append (Item : in out T; Other : T);
       function Get_List (Item : T) return List_Ref;
       --  BAD BAD BAD access to protected component!!!
- 
+
    private
 
       protected type T is new L with
@@ -938,16 +934,16 @@
       end T;
    end Nested;
 
-   package I is new Ada.Containers.Vectors 
+   package I is new Ada.Containers.Vectors
      (Index_Type => Natural,
-      Element_Type => Nested.T_Ref, 
+      Element_Type => Nested.T_Ref,
       "=" => Nested."=");
 
    type List is new I.Vector with null record;
    function Unsafe_Get_List (Item : Nested.T) return List;
    -- Looks safe but it really isnt because it has to get
    -- a pointer to a protected list, while it is copying the
-   -- list in the return value, someone else could be 
+   -- list in the return value, someone else could be
    -- modifying it.
 
 end Pkg;
@@ -962,7 +958,7 @@
 one would have to replace the container being used in this example with a
 protected container. This also rules out containers that are synchronous tagged
 types because a type derivation is needed (type List), which is currently
-not possible with synchronous tagged types. Even if the programmer finds or 
+not possible with synchronous tagged types. Even if the programmer finds or
 creates a suitable container, this adds an extra protected structure which is
 less efficient.
 
@@ -975,7 +971,7 @@
   b) Improved efficiency  (List does not need to be synchronous)
   c) Improved data hiding ("=" for T can be hidden in private part)
      (See next examples for explanation)
-  d) Improved readability (Compare visible parts, 
+  d) Improved readability (Compare visible parts,
                              7 contiguous lines vs 13 lines with a nested
                              private part inbetween to distract the reader)
 
@@ -988,7 +984,7 @@
    procedure Initialize (Item : in out T; Id : Natural);
    procedure Append (Item : in out T; Other : T);
 
-   package I is private new Ada.Containers.Vectors 
+   package I is private new Ada.Containers.Vectors
      (Element_Type => T_Ref, Index_Type => Natural, Others => private);
    -- Note "=" is deferred to private part
 
@@ -1008,7 +1004,7 @@
 
    function "=" (L, R : T) return Boolean;
 
-   package I is new Ada.Containers.Vectors 
+   package I is new Ada.Containers.Vectors
      (Index_Type => Natural, Element_Type => T_Ref, "=");
 
 end Pkg;
@@ -1018,25 +1014,25 @@
 with a private_instantiation_declaration in the private part of a package
 specification. In particular, we want to be able to declare certain actuals
 in the private part, instead of having to declare them in the visible part
-of a package specification. 
+of a package specification.
 
 For example:
 
-Supposing we have a generic package that can be used to create a specific 
-abstraction, and we want the generic instantiation of this package to 
-directly provide all the operations that are available to clients in the 
+Supposing we have a generic package that can be used to create a specific
+abstraction, and we want the generic instantiation of this package to
+directly provide all the operations that are available to clients in the
 package containing the specific abstraction.
 
-In other words, the generic instantiation needs to be declared in the 
+In other words, the generic instantiation needs to be declared in the
 visible part of the package associated with specific abstraction.
 
 Currently this requires that all the generic actuals be fully visible
-at the point of the generic instantiation. This can lead to the 
+at the point of the generic instantiation. This can lead to the
 exposure of constants, variable, subprograms, and entries in the visible part of
 the package that might have been better off hidden from view.
 
 To illustrate these points, consider the following generic that provides
-a template for a device driver which can be plugged into some fictional 
+a template for a device driver which can be plugged into some fictional
 target OS.
 
 generic
@@ -1073,7 +1069,7 @@
 end Device_Driver;
 
 Now Suppose we want to create an Audio Driver that utilizes this generic.
-We really want to to expose just the calls provided by the generic to 
+We really want to to expose just the calls provided by the generic to
 Activate the audio driver, and to check to see if the audio driver
 Is_Operational. Unfortunately, we end up having to expose other
 details that clients might have no business looking at, and the package
@@ -1083,16 +1079,16 @@
 with Device_Driver;
 
 package Audio_Driver is
-   
+
    type Audio_Device is private;
 
    procedure Power_On (Device : Audio_Device);  -- Actual procedure
    function Playing_Music (Device : Audio_Device) return Boolean; -- Actual Function
-   
+
    Muted : Boolean := False;  -- Actual Variable
 
    Manfacturer : constant String := "Acme Corp";
-   Model : constant String := "SoundWhomper Mark IV";   
+   Model : constant String := "SoundWhomper Mark IV";
 
    package Audio_Device_Driver is PRIVATE new Device_Driver
      (Device_Type => Audio_Device,
@@ -1104,7 +1100,7 @@
 
 private
 
-   type Audio_Device is 
+   type Audio_Device is
      record
        ...
      end record;
@@ -1121,10 +1117,10 @@
 
 
 The idea is to be able to indicate that declarations for
-actuals of the partial generic instantiation in the visible part of a 
-package specification are being deferred into the private part of a package 
+actuals of the partial generic instantiation in the visible part of a
+package specification are being deferred into the private part of a package
 specification. The private keyword is used in the declaration of the
-private_instantiation_declaration to indicate that a particular actual 
+private_instantiation_declaration to indicate that a particular actual
 (or group of actuals if the named association is others) is being deferred
 to the private part of the package specification.
 
@@ -1136,29 +1132,29 @@
 package Audio_Driver is
    type Audio_Device is private;
 
-   package Audio_Device_Driver is private new 
+   package Audio_Device_Driver is private new
      Device_Driver (Device_Type => Audio_Device, others => private);
-   
+
    -- These renamed subprograms are the only visible operations
    procedure Activate renames Audio_Device_Driver.Driver.Activate;
-   function Is_Operational return Boolean 
+   function Is_Operational return Boolean
         renames Audio_Device_Driver.Driver.Is_Operational;
-      
+
 private
-   
+
    type Audio_Device is
       record
          ...
       end record;
 
    procedure Power_On (Device : Audio_Device);  -- Actual procedure
-   function Playing_Music (Device : Audio_Device) return Boolean; 
-   --  Clients cannot call these functions 
-   
+   function Playing_Music (Device : Audio_Device) return Boolean;
+   --  Clients cannot call these functions
+
    Muted : Boolean := False;  -- Actual Variable
    Manfacturer : constant String := "Acme Corp";
    Model : constant String := "SoundWhomper Mark IV";
-   
+
    package Audio_Device_Driver is new Device_Driver
      (Device_Type => Audio_Device,
       Manufacturer => Manufacturer,
@@ -1172,7 +1168,7 @@
 
 A second example of using deferred actuals would be helpful.
 Suppose we have a set of container packages that implement a queue abstraction.
-The root package defines the interface to a queue, and child packages create 
+The root package defines the interface to a queue, and child packages create
 various implementations of the interface
 
 generic
@@ -1184,15 +1180,15 @@
    type Queue_Interface is limited interface;
 
    --  Get and Put a single element from/to the queue
-   procedure Get 
-     (Container : in out Queue_Interface; 
+   procedure Get
+     (Container : in out Queue_Interface;
       Item : out Element_Type) is abstract;
 
-   procedure Put 
-     (Container  : in out Queue_Interface; 
+   procedure Put
+     (Container  : in out Queue_Interface;
       Item : Element_Type) is abstract;
 
-   type Queue_Type (Capacity : Natural) 
+   type Queue_Type (Capacity : Natural)
       is abstract new Queue_Interface with null record;
 
    type Queue_Class_Access is access all Queue_Interface'Class;
@@ -1200,11 +1196,11 @@
 end Queues;
 
 Suppose that there exist two implementations of this interface.
-  1) A Bounded queue  
-  2) A Queue of bounded queues that presents an abstraction of a 
+  1) A Bounded queue
+  2) A Queue of bounded queues that presents an abstraction of a
      an array of Bounded queues as a single queue
 
-1) Bounded Queue 
+1) Bounded Queue
 
 generic
 package Queues.Bounded is
@@ -1311,19 +1307,19 @@
 
 Here is the generic signature example:
 
-generic 
-   type Elem is private; 
-   with function Hash (El : Elem) return Integer; 
-package Hashed_Sets is type Set is private; 
-   function Union(Left, Right : Set) return Set; 
-   function Size(Of_Set : Set) return Natural is <>; 
-   function Intersection(Left, Right : Set) return Set is <>; 
-   function Empty return Set is <>; 
-   function Unit_Set(With_Item : Element) return Set is <>; 
-   function Nth_Element(Of_Set : Set) return Element is <>; 
+generic
+   type Elem is private;
+   with function Hash (El : Elem) return Integer;
+package Hashed_Sets is type Set is private;
+   function Union(Left, Right : Set) return Set;
+   function Size(Of_Set : Set) return Natural is <>;
+   function Intersection(Left, Right : Set) return Set is <>;
+   function Empty return Set is <>;
+   function Unit_Set(With_Item : Element) return Set is <>;
+   function Nth_Element(Of_Set : Set) return Element is <>;
    package Signature is new private Set_Signature (Elem, Set);
-private 
-   type Set is record ... end record; 
+private
+   type Set is record ... end record;
    package Signature is new Set_Signature(Elem, Set);
 end Hashed_Sets;
 
@@ -1334,29 +1330,29 @@
 Suppose however, that this package were intended to be only
 used to create higher level abstractions by using the Signature
 Instantiation as a package formal to instantiate a higher level
-generic package. In a sense this could be considered as a type of 
-abstract package that is not to be used on its own. 
-In this case, we would like to be able to hide more details in the 
+generic package. In a sense this could be considered as a type of
+abstract package that is not to be used on its own.
+In this case, we would like to be able to hide more details in the
 private part, and ensure that only the Signature instantiation is
 exported from this generic package. Using the proposed syntax,
 this allows us to write:
 
-generic 
-   type Elem is private; 
-   with function Hash (El : Elem) return Integer; 
+generic
+   type Elem is private;
+   with function Hash (El : Elem) return Integer;
 package Hashed_Sets is
 
-   type Set is private; 
+   type Set is private;
    package Signature is private new Set_Signature (Elem, Set, others => private);
 
-private 
-   type Set is record ... end record; 
-   function Union (Left, Right : Set) return Set; 
-   function Size (Of_Set : Set) return Natural; 
-   function Intersection (Left, Right : Set) return Set; 
-   function Empty return Set; 
-   function Unit_Set (With_Item : Element) return Set; 
-   function Nth_Element (Of_Set : Set) return Element; 
+private
+   type Set is record ... end record;
+   function Union (Left, Right : Set) return Set;
+   function Size (Of_Set : Set) return Natural;
+   function Intersection (Left, Right : Set) return Set;
+   function Empty return Set;
+   function Unit_Set (With_Item : Element) return Set;
+   function Nth_Element (Of_Set : Set) return Element;
    package Signature is new Set_Signature (Elem, Set);
 end Hashed_Sets;
 
@@ -1365,20 +1361,20 @@
 
 package Expressions is
    type Expr_Ref is private;
-   package Expr_Sequences is private new Sequences(Expr_Ref); 
+   package Expr_Sequences is private new Sequences(Expr_Ref);
    function Operands (Expr : Expr_Ref) return access Expr_Sequences.Sequence;
    ...
-private 
-   type Expression; -- completion deferred to body 
-   type Expr_Ref is access Expression; 
-   package Expr_Sequences is new Sequences(Expr_Ref); 
+private
+   type Expression; -- completion deferred to body
+   type Expr_Ref is access Expression;
+   package Expr_Sequences is new Sequences(Expr_Ref);
 end Expressions;
 
 Note that being able to access the instantation in the visible part
-with a partial view provides a simple easy to understand solution 
+with a partial view provides a simple easy to understand solution
 without having to introduce incomplete types, derived types, or even named
 access types. Note with this proposal we also have the option of having
-the Operands function return an Expr_Sequences.Sequence instead of 
+the Operands function return an Expr_Sequences.Sequence instead of
 access Expr_Sequences.Sequence.
 
 !ACATS test
@@ -1388,59 +1384,2995 @@
 !appendix
 
 From: Brad Moore
-Sent: Sunday, February 15, 2009  4:05 PM
+Sent: Thursday, December 11, 2008  8:56 PM
 
-I have made significant changes to the proposal I have been working on for
-AI05-0074. Thanks to Randy for providing good feedback, I have had a pretty
-good email exchange with him on these ideas over that past month or so.
+I recently encountered several issues involving generic instantiations that are
+discouraging me from implementing an abstraction I have in mind.
 
-Randy will probably be somewhat surprised however, as what I have ended up
-with has changed quite a bit since our last email exchange. My thoughts have
-evolved considerably since I started on this, but I think I am finally at a
-stable place and hopefully something worthy of consideration.
+I'm not quite sure the best way to proceed with presenting these thoughts, but I
+think it might be interesting and possibly beneficial to describe my experiences
+leading up to what might possibly be an alternate proposal to the "end private"
+and "deferred generic freezing" solutions proposed thus far.
 
-To summarize the changes and where I am at now;
+Please bear with me.
 
-1) I have done away with the need for a May_Be_Partial pragma with this
-   proposal
-2) There are no changes to the freezing rules, or the generic contract
-   model.
-3) There are no restrictions placed on the content of a generic package,
-   Though there are restrictions on the use of the instance until the
-   completion of the private instantiation.
-4) I still have the ability to defer actuals to the private part
-5) I have done away with a lot of other features that I had been toying
-   with.  (No derivations of partial untagged types, no private objects)
-6) I have also realized that there isn't sufficient need to be able to
-   instantiate generics with a type that has an incomplete view.
-   One workaround is to make the type a private type and use a
-   private_instantiation_declaration.
+The problem I encountered is related to the issues being addressed by Tucker's
+"end private" proposal, and Steve Baird's deferred freezing proposal, but
+neither of those solutions seem to address the problems I was having.
 
-    -- Private_Instantiation_Declaration eg. package Foo is private new 
-       Ada.Containers.Doubly_Linked_Lists 
-         (Element_Type => T, Others => Private);
-    --  "=" has been deferred to the private part
+My problem is related to the problems associated with those proposals in that I
+have a visible type declared in a package specification, and I need a partial
+instantiation of a generic container to support the abstraction I have in mind.
 
-However, actuals for formal types or formal packages must be explicitly
-specified and cannot be deferred. This eliminates cases that I found to be
-problematic.
+The primary issue I have is that the generic container requires some setup to
+prepare the generic formal parameters, and that I want to hide the setup of the
+formal generic parameters in the private part of the package.
 
-A private_instantiation_declaration declares two views of an instance.
-A partial view of an instance, and a full view of an instance.
-The partial view applies to the immediately enclosing declarative region,
-while the full view applies to outside program units, and is equivalent to
-the view provided by the generic_instantiation declaration in the private
-part, which is placed after the actuals have been defined.
+I want to restrict visibility of this package to just the declared type and the
+instantiated container as much as possible. If I have to move all the setup of
+the instantiation into the public part of the package, the abstraction
+deteriorates from having a simpler, cleaner interface to a rather unattractive
+one.
 
-Semantically, a partial view of an instance is like a view of the text of
-the generic template, without having made substitutions of actuals for
-formals, and where the mappings from actuals to formals has not yet been
-resolved.
+For me, it jumped over the fence from "look what I can do in Ada!"
+to "look what I had to do in Ada!".
 
-In my travels, I have also ran into some problems with existing workarounds,
-which are addressed by this proposal, and I have captured these in the
-attachment.
+Note: Initially, the type used to instantiate the container was not a private
+type, it was just a simple record type, so I did not recognize this as being the
+same issue being addressed the deferred freezing issue. In that sense, this
+issue is different than the one Tucker and Steve are trying to solve. This one
+can apply to both private and non-private types.
 
-Looking forward to seeing everyone in Tallahassee
+I then proceeded to think about the possible syntax changes that would be needed
+to allow me to do what I wanted to do.
+
+After some thought I came up with a potential solution and then realized that it
+could also be applied to the problems that Steve Baird, and Tucker were trying
+to solve.
+
+I was getting excited by this point, thinking I had an alternate proposal that
+might work.
+
+I then went into research mode looking at past AI's and past ARG meeting minutes
+to understand all the past discussions relating to partial generic
+instantiation, and then discovered that what I had arrived at had mostly been
+proposed before in the past.
+
+In fact, my solution had a remarkably similar resemblance to something that was
+discussed in AI95-00359-04, but never ended being part of the final proposal of
+that AI.
+
+While I am encouraged that the earlier proposal seemed to resonate well with
+several people at least in some point in time and that the idea must have some
+merit for it to have made it that far, I am discouraged that the idea was not
+selected way back then (about 5 years ago).
+
+Nevertheless, I think there are some differences in what I arrived at that might
+avoid the wrath of Randy for dredging up past proposals. While much of what I am
+proposing has been seen before in various bits and pieces from different
+proposals, I did not see anywhere where all these "bits" had been packaged
+together and looked at as the single solution I have in mind.
+
+Basically, the syntax in my mind for partial generic instantiation involves
+partially instantiating the generic in the visible part of the package using the
+"private" keyword to indicate that the full instantiating has been moved into
+the private section, analogous to how private type declarations work. In
+addition, the private keyword can be also substituted for generic formal
+parameters to indicate that the formal parameters are defined in the private
+section.
+
+An example of the syntax can be seen in the following;
+
+   package I is new private Queues
+       (Element_Type => T, others  => private);
+
+The first occurrence of "private" indicates that the instantiation is a partial
+instantiation.
+
+The second occurrence indicates the formal parameter is defined in the private
+section.
+
+
+A stripped down version showing my example proposed usage is the following;
+
+Basically the abstraction I am trying to present is a protected queue that is
+implemented as a several several smaller queues joined together
+
+
+private with Queues.Bounded;   -- A "low-level" generic bounded queue
+                               --   container
+private with Queues.Multi;     -- A "medium-level" generic
+                               --   queue-of-queues container
+with Queues.Concurrent;        -- A "high-level" container that wraps a
+                               -- lower level container into a protected
+                               -- type.
+                               -- Note this is the only visible generic
+
+package Pkg is
+
+   Maximum_Capacity : constant := 300;  -- Max. no. of elements in the Q
+
+   --  Problem A: Steve and Tuckers problem, use private type to
+   --     instantiate generics
+   type T is tagged private;
+
+   function Create return T;
+   pragma Preelaborable_Initialization (T);
+
+   --  Problem B: Package subsetting: Only want to make visible the
+   --  operations that operate on T, not arrays of T
+   --
+   --  Instantiate the generic interface (Ada 2005 interface)
+   package I is new private Queues
+     (Element_Type => T, others  => private);
+
+   -- Problem C: Implementation Hiding: protected generic container
+   -- storing elements of type T
+   --
+   --  Instantiate the protected queue of bounded queues abstraction
+   package I4 is new private I.Concurrent
+     (Queue_Implementation => private);
+
+
+private
+
+   --  Problem A: Instantiate a visible container with a private type.
+   type T is tagged
+      record
+         Value : Integer := 0;
+      end record;
+
+   --  Problem B:
+   --  These types are not used, but are needed to instantiate the
+   --  generic interface.
+   --  Hiding them in the private section makes for a simpler interface
+   --  in the visible part.
+   --  This ensures that the client only makes use of calls that operate
+   --  on single elements and not calls that involve arrays of elements.
+   --  If I decide some day to replace with a generic that does not
+   --  operate on arrays, then I can replace in the private section
+   --  without having to worry if clients have written code that makes
+   --  calls that operate on arrays.
+   type T_Index_Type is new Natural;
+   type T_Array_Type is array (T_Index_Type range <>) of T;
+
+   --  Instantiate the interface in the private section (problem B)
+   package I is new Queues
+     (Element_Type => T,
+      Element_Index_Type => T_Index_Type,
+      Element_Array_Type => T_Array_Type);
+
+   --  Instantiate the "low-level" bounded queue implementation capable
+   --  of storing elements of type T
+   package I2 is new I.Bounded;
+
+   --  Declare some queues to be used in instantiating a queue of queues
+   Q1 : aliased I2.Queue (Capacity => 100);
+   Q2 : aliased I2.Queue (Capacity => Maximum_Capacity - Q1.Capacity);
+
+   --  Declare types needed to instantiate queue of queues generic
+   type Queue_Array is array (Natural range <>)
+     of access I.Queue_Interface'Class;
+   Queues : constant Queue_Array
+     := Queue_Array'(1 => Q1'Access, 2 => Q2'Access);
+
+   --  Instantiate a queue of queues generic
+   package I3 is new I.Multi
+     (Queue_Array_Type => Queue_Array, Queues => Queues);
+
+   -- Problem C: Instantiating generic needing private setup
+   --  Now instantiate a protected queue of queues.
+   package I4 is new I.Concurrent (Queue_Implementation => I3.Queue);
+
+end Pkg;
+
+
+I realize the use of the word "private" to represent deferred formal parameters is only cosmetically different from what Tucker had proposed years ago, where he had substituted with the box "<>" notation.
+
+In the ARG meeting notes, he mentioned that he dropped the boxy notation from
+the proposal because he felt this was too confusing. I actually had considered
+using the box notation also before I discovered Tuckers past solution, but also
+dropped it for the same reasons. Using "private" here I found to be quite a bit
+less confusing, and more intuitive. (It does not conflict with the syntax for
+default formal parameters that involves the box syntax to represent defaults.
+Also it points the user to look at the private section for more details)
+
+It is important to note that what I am proposing is not so much an alternative
+to Steve Baird's proposal, as an extension to his proposal.
+
+In other words, if the May_Be_Partial pragma is needed for Steve's proposal, it
+would also be needed here. Also, the freezing and elaboration of the generic
+would occur in the same place as in Steve's proposal, at the end of the
+enclosing package spec, not where the instantiations occur in the private part
+of the specification.
+
+The main difference from Steve's proposal is the added syntax for the partial
+instantiation, and the full instantiation of the generic in the private section.
+
+If we are OK with Steve's proposal, maybe it's not that big a stretch to get to
+this proposal from his.
+
+>From reading the past meeting minutes, the impression I got for why the earlier
+proposal was voted no action is because the ARG was running out of time and
+wanted to get Ada 2005 out the door. The sense I gathered was that generally
+people liked the idea, but felt it wasn't mature enough to get into Ada 2005.
+
+Now that we are in the earlier phases of the amendment process, we now have the
+benefit of Steve Baird's proposal and discussion points, and the earlier ideas
+have been developed a bit further, is this approach worth considering as an
+alternate/extended proposal?
+
+The difference between this proposal and the others is that this proposal
+provides a solution to all three problems shown in the code fragment above,
+while the other two solutions only solve problem A.
+
+Otherwise the differences between this proposal and the "end private" proposal
+should be the same as the differences between Steve Baird's proposal and the
+"end private" proposal.
+
+Are there reasons (other than the ones I found in meeting minutes and in the
+various versions of the AI) why this solution is not workable?
+
+****************************************************************
+
+From: Randy Brukardt
+Sent: Thursday, December 11, 2008  9:26 PM
+
+...
+> Please bear with me.
+
+No problem. You can't do any worse than we have to this point. :-)
+
+...
+> Basically, the syntax in my mind for partial generic instantiation
+> involves partially instantiating the generic in the visible part of
+> the package using the "private" keyword to indicate that the full
+> instantiating has been moved into the private section, analogous to
+> how private type declarations work. In addition, the private keyword
+> can be also substituted for generic formal parameters to indicate that
+> the formal parameters are defined in the private section.
+>
+> An example of the syntax can be seen in the following;
+>
+>    package I is new private Queues
+>        (Element_Type => T, others  => private);
+>
+> The first occurrence of "private" indicates that the instantiation is
+> a partial instantiation.
+>
+> The second occurrence indicates the formal parameter is defined in the
+> private section.
+
+I don't think the syntax was a major problem here. The major problem was with
+the semantics, and you haven't said much about that.
+
+...
+...
+> In other words, if the May_Be_Partial pragma is needed for Steve's
+> proposal, it would also be needed here.
+> Also, the freezing and elaboration of the generic would occur in the
+> same place as in Steve's proposal, at the end of the enclosing package
+> spec, not where the instantiations occur in the private part of the
+> specification.
+
+If you have the full instantiation in the private part, it makes the most sense
+for it to work exactly as an instantiation that does not have a partial
+instance. (That's surely how types work.) Thus, the elaboration and freezing
+surely ought to happen at the point of the full instance. The only reason Steve
+proposed doing that at the end of the package is that there is no obvious other
+place that doesn't cause maintaince issues -- but that doesn't apply if there is
+an explicit full instance.
+
+> The main difference from Steve's proposal is the added syntax for the
+> partial instantiation, and the full instantiation of the generic in
+> the private section.
+>
+> If we are OK with Steve's proposal, maybe it's not that big a stretch
+> to get to this proposal from his.
+
+I think you are leaping to conclusions. See below.
+
+> >From reading the past meeting minutes, the impression I got for why
+> >the
+> earlier proposal was voted no action is because the ARG was running
+> out of time and wanted to get Ada 2005 out the door.
+> The sense I gathered was that generally people liked the idea, but
+> felt it wasn't mature enough to get into Ada 2005.
+
+Well, there were semantic issues discussed at that Atlanta meeting. We didn't
+have a clear approach to fixing them; other than reverting to my "limited
+instance" proposal (see AI05-0074-1 for the most recent version of that). There
+is a reason I didn't carry the partial instance version over to the Ada 2005
+AIs.
+
+> Now that we are in the earlier phases of the amendment process, we now
+> have the benefit of Steve Baird's proposal and discussion points, and
+> the earlier ideas have been developed a bit further, is this approach
+> worth considering as an alternate/extended proposal?
+
+Sure, but you need to propose some semantics for the partial instance. I see
+none in your message, and the ones in AI95-0359-4 are known to not work.
+
+> The difference between this proposal and the others is that this
+> proposal provides a solution to all three problems shown in the code
+> fragment above, while the other two solutions only solve problem A.
+
+Right.
+
+> Otherwise the differences between this proposal and the "end private"
+> proposal should be the same as the differences between Steve Baird's
+> proposal and the "end private" proposal.
+>
+> Are there reasons (other than the ones I found in meeting minutes and
+> in the various versions of the AI) why this solution is not workable?
+
+You haven't explained the semantics. The previous proposals for partial
+instances ran into nasty semantic problems with what was exported; having only
+partial visibility on things that you can then derive from (for instance) caused
+all kinds of new cases in Ada. It looked like lots of odd restrictions on the
+use of the instance would be needed.
+
+The solution that I had proposed to that was to revert to my original idea of a
+limited instance (not a partial instance). The idea is that the limited instance
+would export the full operations (of the full instance) to clients, but would
+only export a limited view (not quite exactly, but think of that as the model)
+within the package. That works, but is somewhat confusing (the clients get more
+than a limited view from the limited instance, but that isn't clear from the
+syntax). See AI05-0074-1 for the most recent write-up of this idea.
+
+Anyway, it's obvious that you want something else. So you need to propose
+precisely what would be exported from such a partial instance. (The proposal in
+AI95-0359-4 doesn't work, at least without quite a bit of additional tweaking.)
+That is clearly complicated by the "private" formal parameter keyword. Formal
+parameters can be used in many ways, and you would need rules for all of those
+ways (I don't think you can -- or want to -- say that anything using such a
+parameter is invisible; for instance, if a formal object is used in a default
+expression, that's pretty much irrelevant to the use by clients of the type or
+subprogram parameter with the default).
+
+Note that the solution Steve and Ed were proposing would export *everything*
+from the instance; only the freezing and elaboration rules within the package
+would be changed. (The freezing changes prevent "early" use.) Complicating that
+to hide some operations probably is possible, but without some details, its
+impossible to say whether that even can work. (That also would allow Steve to
+work his magic, and provide obscure counter-examples to break the good ideas.
+:-)
+
+I'll expect to see the complete proposal when I come in in the morning. ;-)
+
+****************************************************************
+
+From: Tucker Taft
+Sent: Friday, December 12, 2008  12:19 AM
+
+Very interesting ideas.  The "others => private" reads quite well.  One thing I
+think is important is being able to take a type declared within an instantiation
+and bring it out to the same level as the instantiation:
+
+     package T_Vecs is new private Vectors(Element => T, others => private);
+     type T_Vec is new T_Vecs.Container with null record;
+
+Doing this requires that the parent type be completely defined, which it isn't
+in this case.  If the type exported by the instantiation is tagged, you could
+use a private extension:
+
+     type T_Vec is new T_Vecs.Container with private;
+
+which doesn't freeze the parent type.  For a non-tagged type, you would need a
+post-private part or equivalent, or some relaxation in the rules for type
+derivation, to be able to do this before you see the "full" instantiation.
+
+I should probably go back and read the old proposal, but I forget how the
+partial instantiation could work if you didn't specify actuals for all the
+generic formals. I can't quite imagine what is the profile of any subprograms
+exported by the instantiation if they use formal types that didn't have an
+actual type specified. E.g.:
+
+     package Some_Vecs is new private Vectors(others => private);
+
+If there is an operation "Some_Vecs.Append(Vec, Element)", how could you make
+any use of it since you have no idea what is the actual type associated with
+"Element".  Or is it required that all type parameters be specified (possibly
+with private types), but none of the other parameters?
+
+Sounds like I have a reading assignment...
+
+****************************************************************
+
+From: Brad Moore
+Sent: Tuesday, December 16, 2008  10:41 AM
+
+Sorry it's been a few days for me to put a response together.
+I've needed to review the various incarnations of AI05-0074, and my thoughts
+have been evolving, and getting more refined. I've been thinking about freezing
+quite a bit over the past few days, I think the 40 below temperatures are
+providing some inspiration somehow.
+
+I'll try to capture more details of my thoughts in this email...
+
+> > Brad Moore Writes:
+> > An example of the syntax can be seen in the following;
+> >
+> >   package I is new private Queues
+> >       (Element_Type => T, others  => private);
+> >
+>
+> I don't think the syntax was a major problem here. The major problem
+> was with the semantics, and you haven't said much about that.
+
+My current thoughts incorporate more of Steve Baird's proposal, and I think more
+of your limited view proposal.
+
+My idea now is that the syntax is as I have described above, except that the
+word "private" is optional.
+
+If the word "private" does not appear at all, then you essentially get the Baird
+proposal. There is no explicit instantiation of the generic in the private part,
+and the freezing/elaboration occur at the end of the enclosing package
+specification.
+
+If the word "private" occurs, it must at least occur after the word "new". This
+means that the full instantiation occurs explicitly in the private section. The
+freezing and elaboration occur after the full instantiation, the same as it does
+today with normal generic instantiations.
+
+If the word "private" occurs after the word "new", then it may also optionally
+occur as a substitute for generic formal parameters.
+
+This means that the formal(s) is/are provided in the private section, as part of
+the explicit full generic instantiation.
+
+The restrictions are that until freezing occurs, (whether implicitly at the end
+of the package spec, or explicitly after the full instantiation), you cannot
+create an object or an expression of anything declared in the generic spec. You
+also cannot directly use any of the types declared in the generic spec as
+components in an object declaration. You can however have components that are
+access types that designate types in the generic spec. I think this is similar
+to your limited view concept. I think from a user perspective though, it is an
+easier concept to understand that the generic is partially declared and things
+are being deferred to the private section, rather than thinking in terms of
+being limited. I think it might make sense to use the term "limited view" in
+describing the semantics for the wording in the RM, but it is better to avoid
+the use of "limited" in the syntax for this purpose.
+
+Supporting both Steve Baird's syntax and my extensions gives you the option of
+having the best of both worlds.
+
+Steve's syntax is less verbose (can be thought of as a shorthand form), but also
+allows you to have multiple indirect references to generic instantiated types,
+as in the following example taken from past discussions.
+
+package P is
+    type T is private;
+    package T_Sets is new Sets(T);
+    package T_Maps is new Maps(T);
+private
+    type T is record
+        S : access T_Sets.Set;
+        M : access T_Maps.Maps;
+    end record;
+
+    -- Problems if we are not using the Baird proposal..
+    -- package T_Sets is new Sets(T);
+        -- T freezes here, but T_Maps isn‘t full yet.
+    -- package T_Maps is new Maps(T);
+end P;
+
+Am I correct in presuming the Baird proposal is intending to allow such an
+example?
+
+If you use the "private" syntax, then you would not be able to do this, but you
+should be able to designate one of the generic instantiations as a component of
+the private type. However, with the private syntax, this would allow you to
+create objects and expressions from the generic specification after the freezing
+point in the package, which you could not do if you are using the implicit form.
+
+(This is a feature I need in my protected queue of queues example, that I
+provided in my initial email. I declare some queue objects)
+
+The other thing I see is a need for a change to Steve's "May_Be_Partial"
+pragma.
+
+I believe if we are to allow generic formals to be deferred to the private
+section, there are potential problems if we allow the generic to derive types
+from these formals. For example, a "not overriding" clause used in the generic
+might conflict with a primitive subprogram declared in the private section for
+the type. This would be an example of breaking privacy.
+
+As far as I can tell, deriving types in the generic are the only places where
+such problems might arise. We need someone like Steve to point out where I am
+being naive, and poke other holes, but hopefully my hypothesis will hold true.
+
+Assuming this is the case, then I think the May_Be_Partial pragma should instead
+look something like;
+
+pragma Allow (T, {Partially_Visible | Partially_Private});
+
+The Partially_Visible has the same meaning as Steve's May_Be_Partial, and means
+that the generic will not declare an object or use an expression that would
+cause freezing to occur.
+
+The Partially_Private has the same restrictions as Partially_Visible, except
+that in addition, the generic cannot derive a new type from the specified formal
+type.
+
+
+Partially_Private means that the formal actual can be deferred to the full
+instantiation in the private section. (as in; (others => private))
+
+Partially_Visible means you cannot defer the formal actual, and that it must be
+specified in the partial instantiation.
+
+In general, to use this pragmas, you would probably want to use the
+Partially_Private in most cases, unless your generic needs to derive new types
+from the formals.
+
+
+> > In other words, if the May_Be_Partial pragma is needed for Steve's
+> > proposal, it would also be needed here.
+> > Also, the freezing and elaboration of the generic would occur in the
+> > same place as in Steve's proposal, at the end of the enclosing package
+> > spec, not where the instantiations occur in the private part of the
+> > specification.
+>
+>
+> If you have the full instantiation in the private part, it makes the
+> most sense for it to work exactly as an instantiation that does not
+> have a partial instance. (That's surely how types work.) Thus, the
+> elaboration and freezing surely ought to happen at the point of the
+> full instance. The only reason Steve proposed doing that at the end of
+> the package is that there is no obvious other place that doesn't cause
+> maintaince issues -- but that doesn't apply if there is an explicit
+> full instance.
+
+Yes, I have revised my design as outlined above.
+
+
+> Anyway, it's obvious that you want something else. So you need to
+> propose precisely what would be exported from such a partial instance.
+...
+> Formal parameters can be used in many ways, and you would need rules
+> for all of those ways
+
+I think more of these details need to be provided, but before I go to that level
+of detail, does what I have outlined above seem to hold some potential, or have
+I already stepped off a cliff?
+
+I plan to respond to Tucker's email separately, but I have run out of time at
+the moment.
+
+****************************************************************
+
+From: Tucker Taft
+Sent: Tuesday, December 11, 2008  10:12 PM
+
+It would be helpful to remind us of the motivating example that got you
+re-interested in this problem, and show how it could use these proposed
+features. Good examples can make a big difference when it comes to deciding on
+the appropriate solution.
+
+I will say I am reluctant to have two distinct solutions to this problem.
+Perhaps the two you suggest can be unified a bit so they are simply different
+ways of using essentially same feature.
+
+It would also be nice to know whether something like the "post-private" visible
+part would work for your motivating example, or whether other proposals would or
+would not work and why.
+
+****************************************************************
+
+From: Brad Moore
+Sent: Wednesday, December 17, 2008  10:43 AM
+
+> One thing I think is important is being able to take a type declared
+> within an instantiation and bring it out to the same level as the
+> instantiation:
+>
+>  package T_Vecs is new private Vectors
+>    (Element => T, others => private);
+>  type T_Vec is new T_Vecs.Container with null record;
+>
+> Doing this requires that the parent type be completely defined, which
+> it isn't in this case.  If the type exported by the instantiation is
+> tagged, you could use a private extension:
+>
+>     type T_Vec is new T_Vecs.Container with private;
+>
+> which doesn't freeze the parent type.  For a non-tagged type, you
+> would need a post-private part or equivalent, or some relaxation in
+> the rules for type derivation, to be able to do this before you see
+> the "full" instantiation.
+
+I am thinking that it should be possible to use a private extension in the
+visible part of the specification as you've suggested, if you use an explicit
+partial instantiation (i.e. using the "private" keyword), provided that the full
+declaration comes after the full generic instantiations and the full parent type
+declaration in the private part.
+
+If you use an implicit partial instantiation (without the "private" keyword)
+then you wouldn't be able to do this, because the freezing of the generics
+occurs too late to declare the full declaration of the derived type.
+
+I am currently thinking that you would not be able to do a record extension in
+the visible part of the package spec involving the partial generic extension.
+
+Does this provide enough flexibility? I think the semantics as I have described
+seem to fall fairly easily from the syntax. In theory, it might be possible to
+provide more flexibility (to be able to have visible record extensions involving
+partial generics), but this would require more effort to define.
+
+> I can't quite imagine what is the profile of any subprograms exported
+> by the instantiation if they use formal types that didn't have an
+> actual type specified.
+> E.g.:
+>
+>     package Some_Vecs is new private Vectors(others => private);
+>
+> If there is an operation "Some_Vecs.Append(Vec, Element)", how could
+> you make any use of it since you have no idea what is the actual type
+> associated with "Element".  Or is it required that all type parameters
+> be specified (possibly with private types), but none of the other
+> parameters?
+
+The idea is that you wouldn't be able to make use of this operation (in the
+visible part of the package, or from outside the package), if it involved types
+that were declared in the private section of a package spec.
+
+For the most part, I would think the existing visibility rules would cover this.
+You already do not have visibility to the formal parameters of a generic from
+outside the generic. Also, I think the existing rules would not let you
+formulate a call on such an operation, because you do not have visibility to
+create an object of a type that is declared in a private section.
+
+In the example you've given, if you want to be able to make the call
+Some_Vecs.Append(Vec, Element), then you would need to ensure that the Element
+type is provided visibly in the partial instantiation.
+
+i.e.
+
+  package T_Vecs is new private Vectors
+    (Element => T, others => private);
+
+However, you might want to hide other operations. For example, suppose you also
+have an operation "Some_Vecs.Append(Vec, Array_Of_Elements)"
+
+If the array type is one of the formal parameters to the generic, you could
+declare the array type in the private section of the generic and then this
+operation can not be made from outside the private section.
+
+****************************************************************
+
+From: Brad Moore
+Sent: Wednesday, December 17, 2008  11:09 AM
+
+> It would be helpful to remind us of the motivating example that got
+> you re-interested in this problem, and show how it could use these
+> proposed features.
+> Good examples can make a big difference when it comes to deciding on
+> the appropriate solution.
+
+I have not shown the original motivating example yet, though I have shown a very
+stripped down version of it in my first email involving a protected queue of
+queues generic.
+
+The original example I think makes a better case for these features than my
+stripped down version, but is a bit more of a read. I will provide this example
+shortly.
+
+> I will say I am reluctant to have two distinct solutions to this
+> problem.  Perhaps the two you suggest can be unified a bit so they are
+> simply different ways of using essentially same feature.
+
+I was thinking the two solutions can be considered as a single solution, since
+they both seem to fit together well from a syntax perspective. But so far the
+only real reason for having the implicit instantiation is to allow multiple
+components from multiple partial instantiations as in;
+
+package P is
+    type T is private;
+    package T_Sets is new Sets(T);
+    package T_Maps is new Maps(T);
+private
+    type T is record
+        S : access T_Sets.Set;
+        M : access T_Maps.Maps;
+    end record;
+
+    -- Problems if we are not using the Baird proposal..
+    -- package T_Sets is new Sets(T);
+        -- T freezes here, but T_Maps isn‘t full yet.
+    -- package T_Maps is new Maps(T);
+end P;
+
+
+If the implicit partial instantiation (also the Baird proposal) does not allow
+this, then this part of the solution can be dropped.
+
+Also, because the two solutions are fairly independent, we could go with one
+solution for now, and decide further on down the road (Ada 2025?) to add the
+other part of the solution.
+
+I am somewhat inclined to think that we could drop the implicit partial
+instantiation capability from this proposal, if everyone agreed that having
+multiple components of partial instantiations is not likely to be something that
+users would want to do often enough to be worthwhile.
+
+
+> It would also be nice to know whether something like the
+> "post-private" visible part would work for your motivating example, or
+> whether other proposals would or would not work and why.
+
+I don't believe the post-private visible part would work for example as it is
+defined today, because the post private visible part does not have visibility
+into the private part. The protected queue of queues example needs to see
+objects declared in the private section.
+
+I will provide more details in my next email showing the original motivating
+example, and elaborate more on why the other proposals do not seem to  work well
+with the problem.
+
+****************************************************************
+
+From: Tucker Taft
+Sent: Wednesday, December 17, 2008  12:44 PM
+
+>> I can't quite imagine what is the profile of any subprograms exported
+>> by the instantiation if they use formal types that didn't have an
+>> actual type specified.
+>> E.g.:
+>>
+>>     package Some_Vecs is new private Vectors(others => private);
+>>
+>> If there is an operation "Some_Vecs.Append(Vec, Element)", how could
+>> you make any use of it since you have no idea what is the actual type
+>> associated with "Element".  Or is it required that all type
+>> parameters be specified (possibly with private types), but none of
+>> the other parameters?
+>
+> The idea is that you wouldn't be able to make use of this operation
+> (in the visible part of the package, or from outside the package), if
+> it involved types that were declared in the private section of a
+> package spec.
+
+What is the "private section of a package spec" in this context? Is this the
+private part of the original generic, or is this somehow defined by which actual
+parameters are specified as "private"?
+
+> For the most part, I would think the existing visibility rules would
+> cover this. You already do not have visibility to the formal
+> parameters of a generic from outside the generic. Also, I think the
+> existing rules would not let you formulate a call on such an
+> operation, because you do not have visibility to create an object of a
+> type that is declared in a private section.
+
+Again, I'm not sure how you are defining "a type that is declared in a private
+section" in this context.
+
+> In the example you've given, if you want to be able to make the call
+> Some_Vecs.Append(Vec, Element), then you would need to ensure that the
+> Element type is provided visibly in the partial instantiation.
+>
+> i.e.
+>
+>   package T_Vecs is new private Vectors
+>     (Element => T, others => private);
+>
+> However, you might want to hide other operations. For example, suppose
+> you also have an operation "Some_Vecs.Append(Vec, Array_Of_Elements)"
+>
+> If the array type is one of the formal parameters to the generic, you
+> could declare the array type in the private section of the generic and
+> then this operation can not be made from outside the private section.
+
+Again, I need clarification of what you mean by "private section." I presume
+this is not simply the "private part" of the original generic, but is rather
+related to which operations make use of formal types whose actuals are specified
+as "private."
+
+****************************************************************
+
+From: Brad Moore
+Sent: Sunday, December 21, 2008  12:04 PM
+
+> I will say I am reluctant to have two distinct solutions to this
+> problem.  Perhaps the two you suggest can be unified a bit so they are
+> simply different ways of using essentially same feature.
+
+I gave some more thought to this comment. I realized that the two solutions
+could become one if the wording was changed so that 13.14(5) would not apply for
+the private generic instantiation.
+
+To better capture the semantics of the ideas I was trying to present, I started
+looking at wording changes needed to implement what I had in mind. I then
+realized that the part of the solution involving being able to partially
+instantiate a generic and having the completed instantiation in the private part
+is exactly the same thing that Randy proposed in AI05-0074-1 with the minor
+difference that I was using the private keyword in the syntax where Randy was
+using the word limited.
+
+Therefore, I am factoring that part of the solution out of this proposal, and
+will note that this proposal requires AI05-0074-1 as a prerequisite.
+
+This is good because it reduces the problem set back to the original problem I
+was trying to solve. (Being able to defer the declaration of generic actual
+parameters to the private part of a package specification)
+
+To capture the ideas in one place, I have written up a candidate for a new AI
+(See the attached). I see this as a different AI, because it solves a different
+problem than AI05-0074, but it is relevant to AI05-0074 because it can affect
+the selection of proposals for that AI, and it does include some suggested minor
+syntax changes for AI05-0074-1.
+
+Writing up the proposed wording changes was a worthwhile exercise, I think,
+because it strikes me that the proposed wording changes are syntactic sugar in
+nature, and probably would not be difficult to implement I am guessing, assuming
+that AI05-0074-1 is selected and is already implemented.
+
+Also, please ignore my comments regarding the need for a pragma Allow in my
+previous email. I came to realize that there was no need for that pragma. The
+May_Be_Partial pragma of AI05-0074-3 may be useful to include in AI05-0074-1
+though that is discussion that should be captured under that AI. All the
+thoughts related to this proposal are hopefully captured in the attachment.
+
+----
+
+!subject Private Generic Actual Parameters
+
+!summary
+
+(See proposal.)
+
+!problem
+
+There are times when it would be desirable to be able to instantiate a generic
+in the visible part of a package spec, yet hide implementation details or limit
+the visible operations from outside the package by having the generic actual
+parameters declared in the private part of the package specification.
+
+For example:
+
+Supposing we have a generic package that can be used to create a specific
+abstraction, and we want the generic instantiation of this package to directly
+provide all the operations that are available to clients in the package
+containing the specific abstraction. In other words, the generic instantiation
+needs to be declared in the visible part of the package associated with specific
+abstraction.
+
+Currently this requires that all the generic actuals be fully visible at the
+point of the generic instantiation. It is not even possible to use a private
+type as an actual of the generic. This can lead to the exposure of constants,
+variable, types, subprograms, entries, and packages in the visible part of the
+package that might have been better off hidden from view.
+
+To illustrate these points, consider the following generic that provides a
+template for a device driver which can be plugged into some fictional target OS.
+
+generic
+   type Device_Type is private;
+   Manufacturer : String;
+   Model : String;
+   Disabled : in out Boolean;
+   with procedure Activate_Device (Device : Device_Type);
+
+   with function Device_Is_Operational
+     (Device : Device_Type) return Boolean;
+   type Configuration_Settings is private;
+   with procedure Configure_Device
+     (Device : Device_Type; Settings : Configuration_Settings);
+package Device_Driver is
+
+   protected Driver  is
+      procedure Activate;
+      function Is_Operational return Boolean;
+      procedure Configure (Settings : Configuration_Settings);
+   private
+      Device : Device_Type;
+   end Driver;
+end Device_Driver;
+
+package body Device_Driver is
+   protected body Driver is
+
+      procedure Activate is
+      begin
+         Activate_Device (Device);
+      end Activate;
+
+      procedure Configure (Settings : Configuration_Settings) is
+      begin
+         Configure_Device (Device, Settings);
+      end Configure;
+
+      function Is_Operational return Boolean is
+      begin
+         return Device_Is_Operational (Device);
+      end Is_Operational;
+   end Driver;
+end Device_Driver;
+
+Now Suppose we want to create an Audio Driver that utilizes this generic.
+We really want to to expose just the calls provided by the generic to
+Activate the audio driver, and to check to see if the audio driver
+Is_Operational. Unfortunately, we end up having to expose a lot of
+details that clients have no business looking at, and the package
+specification suffers from poor readability due to the excess clutter.
+
+
+with Device_Driver;
+with Interfaces.C;
+
+package Audio_Driver is
+
+   use Interfaces;
+   type Audio_Device is
+      record
+         Handle : C.int;
+         Big_Ugly_Structure : ...
+      end record;
+   pragma Convention (C, Audio_Device);
+
+   procedure Power_On (Device : Audio_Device);  -- Actual procedure
+   function Playing_Music (Device : Audio_Device) return Boolean; -- Actual Function
+
+   Muted : Boolean := False;  -- Actual Variable
+
+   type Audio_Quality is (High, Medium, Low);
+   Default_Codec : constant := 16#DEADBEEF#;
+   type Audio_Settings is
+      record
+         Codec : C.unsigned_long := Default_Codec;
+         Quality : Audio_Quality := High;
+      end record;
+   procedure Setup (Device : Audio_Device; Settings : Audio_Settings);
+   pragma Convention (C, Audio_Settings);
+
+   package Audio_Device_Driver is new Device_Driver
+     (Device_Type => Audio_Device,  -- Actual Type
+      Manufacturer => "Acme Corp",  -- Actual Constant
+      Model => "SoundWhomper Mark IV", -- Actual Constant
+      Disabled => Muted, -- Actual Variable
+      Activate_Device => Power_On, -- Actual procedure
+      Device_Is_Operational => Playing_Music, -- Actual function
+      Configuration_Settings => Audio_Settings, -- Actual procedure
+      Configure_Device => Setup);  -- Actual type
+
+end Audio_Driver;
+
+!proposal
+
+The proposal is to select AI05-0074-1 as the solution to allow private types
+to be specified as actuals for generic instantiations, and to provide new syntax
+that allows actual parameters of a private generic instantiation to be left
+unspecified until the completing full generic instantiation in the private
+part of the package specification.
+
+!wording
+
+Change 12.3(4):
+
+generic_association ::=
+   [generic_formal_parameter_selector_name =>] explicit_generic_actual_parameter
+{| [generic_formal_parameter_selector_name =>] private
+ | others => private}
+
+Change 12.3(6):
+A generic_association is named or positional according to whether or not the generic_formal_parameter_selector_name is specified. Any positional
+associations shall precede any named associations. {If there is a named
+association with a generic_formal_parameter_selector_name of others, it shall
+come last.}
+
+Replace 12.3(7/2):
+
+The generic actual parameter is one of the following:
+
+* the explicit_generic_actual_parameter given in a generic_association
+ for each formal;
+* the corresponding default_expression or default_name if no generic_association
+ is given for the formal;
+* For a named association of a private_generic_instantiation with the reserved
+ word others, all needed actual parameters from the completing
+ full_generic_instantiation that at are not associated with some previous association.
+* For an association of a private_generic_instantiation with the reserved word
+ private but without the reserved word others, the corresponding matching
+ explicit_generic_actual_parameter of the completing full_generic_instantiation.
+
+When the meaning is clear from context, the term "generic actual," or simply
+"actual," is used as a synonym for "generic actual parameter" and also for the
+view denoted by one, or the value of one. A generic actual parameter of a
+private generic instantiation denoted by the private keyword is called a private
+generic actual parameter.
+
+Add a note 12.3(22.1):
+
+Where a subtype_mark of a private generic actual parameter is not visible,
+subprogram calls and entry calls involving formal parameters of that
+subtype_mark cannot be made. This may restrict the operations that are available
+from outside the enclosing package containing the private generic instantiation.
+
+
+!discussion
+
+Unless other proposals come forward that are compatible with this AI,
+this proposal requires implementing AI05-0074-1 as a prerequisite.
+AI05-0074-1 solves the problem of being able to use private types
+as actuals for a generic instantiation in the visible part of a
+package specification, but that solution applied to the above would
+still leave a lot of details exposed in the visible part of the package
+that we would rather not have to expose. The Device_Type record and the
+Audio_Setting record could be made into private types, hiding some of
+details, but still we would have to expose the Manufacturer, the Model,
+the Mute setting variable, and the various subprograms supplied as
+actuals. Furthermore, this particular generic wraps a single device
+object in a protected object, but otherwise does not provide any
+interface to access the device object directly. Ideally, we would
+not even have to expose the device object as a private type.
+Suppose also that this particular audio device driver only supports one
+configuration, and that the Configure call of the generic does not
+do anything. Ideally, we would like to be able to hide the Configure
+call from clients.
+
+The idea is to be able to indicate that declarations for
+actuals of the partial generic instantiation in the visible part of a
+package specification are being deferred into the private part of a package
+specification. The private keyword is used in the declaration of the
+partial instantiation to indicate that a particular actual (or group
+of actuals if the named association is others) is being deferred.
+
+This AI also recommends a second use of the private keyword in the syntax.
+
+AI05-0074-1 uses the syntax;
+    limited_generic_instantiation ::=
+      PACKAGE defining_identifier IS LIMITED NEW generic_package_name generic_actual_part;
+
+While this works with this proposal, substituting the word "LIMITED" with
+"PRIVATE" should also be considered as in;
+
+    private_generic_instantiation ::=
+      PACKAGE defining_identifier IS NEW PRIVATE generic_package_name generic_actual_part;
+
+"Private" seems to better capture the idea that the instantiation is being
+deferred into the private part of the package specification. It also is more
+consistent with the syntax associated with private type and private extensions.
+For the purpose of illustrating the examples in this AI, this alternate
+variation of the syntax is assumed. This difference is only a syntactic
+difference. There is no semantic difference associated with this alternative
+syntax. This AI assumes that AI05-0074-1 has selected the private keyword over
+the limited keyword, and this alternate syntax is not included in the wording
+section of this AI. If AI05-0074-1 is selected without selecting this alternate
+syntax, then this AI should be reworded to reflect the original syntax.
+
+It was considered whether the other proposals associated with AI05-0074
+would support the capabilities of this AI. The conclusion is that neither
+AI05-0074-2 or AI05-0075-3 would support these features.
+
+AI05-0074-2 is the proposal involving a second visible part of a package
+that proceeds after the end of the private part of the package denoted by an
+"end private" marker. This is not helpful here because any instantiation
+would have to occur in the second visible part. It is not possible to
+hide anything more in the private part of the package specification, and
+this is further restricted because of the statement;
+"The post-private visible part has no visibility on the private part."
+Actuals would need to be defined in a visible part, and exposed needlessly,
+although private types would allow hiding some of the details. This is the
+same situation as if AI05-0074-1 was implemented, except that it precludes
+the possibility of implementing this proposal.
+
+AI05-0074-3 is the proposal involving having the instantiation in the visible
+part of a package but deferring the freezing until the end of the package
+specification. This solution does not help us here because there is no way
+to move anything into the private part.
+
+Note also that the problems associated with AI05-0074 involve instantiating
+generics with private types. The solution of this AI can be applied to both
+private and non-private types.
+
+!example
+
+Applying the new syntax to the example given in the problem section of this AI
+allows us to write;
+
+with Device_Driver;
+private with Interfaces.C;
+
+package Audio_Driver is
+   package Audio_Device_Driver is new private Device_Driver (others => private);
+
+   -- These renamed subprograms are the only visible operations
+   procedure Activate renames Audio_Device_Driver.Driver.Activate;
+   function Is_Operational return Boolean renames Audio_Device_Driver.Driver.Is_Operational;
+
+   --  Note Audio_Device is more private than if we had declared it as a private type.
+   --  You cannot even declare an Audio Device, or call Power_On, or Playing_Music directly
+   --  But you can call Audio_Device_Driver.Activate, or Audio_Device_Driver.Is_Operational
+   --  to do the same thing.
+   -- Note you cannot call Configure because the type associated with one of the formal parameters
+   -- of that call (Audio_Settings) is not visible.
+
+private
+
+   use Interfaces;
+   type Audio_Device is
+      record
+         Handle : C.int;
+         Big_Ugly_Structure : ...
+      end record;
+   pragma Convention (C, Audio_Device);
+
+   procedure Power_On (Device : Audio_Device);  -- Actual procedure
+   function Playing_Music (Device : Audio_Device) return Boolean; -- Actual Function
+
+   Muted : Boolean := False;  -- Actual Variable
+
+   type Audio_Quality is (High, Medium, Low);
+   Default_Codec : constant := 16#DEADBEEF#;
+   type Audio_Settings is
+      record
+         Codec : C.unsigned_long := Default_Codec;
+         Quality : Audio_Quality := High;
+      end record;
+   procedure Setup (Device : Audio_Device; Settings : Audio_Settings);
+   pragma Convention (C, Audio_Settings);
+
+   package Audio_Device_Driver is new Device_Driver
+     (Device_Type => Audio_Device,  -- Actual Type
+      Manufacturer => "Acme Corp",  -- Actual Constant
+      Model => "SoundWhomper Mark IV", -- Actual Constant
+      Disabled => Muted, -- Actual Variable
+      Activate_Device => Power_On, -- Actual procedure
+      Device_Is_Operational => Playing_Music, -- Actual function
+      Configuration_Settings => Audio_Settings, -- Actual procedure
+      Configure_Device => Setup);  -- Actual type
+
+end Audio_Driver;
+
+This dramatically simplifies the visible part of the package specification.
+
+Now suppose, we want to allow clients to access the mute variable which is
+supplied as an actual.
+
+The visible part of the package specification would then look like;
+
+package Audio_Driver is
+
+   Muted : Boolean := False;  -- Actual Variable
+
+   package Audio_Device_Driver is new private Device_Driver
+            (Disabled => Muted, others => private);
+...
+
+Clients can mute the sound simply by modifying the Muted variable. This seems to
+better separate the actual variable from the instantiated abstraction.
+
+Now suppose we want to support multiple configurations, and allow clients
+to be able to use of the Configure call.
+This can be accomplished by modifying the visible part of the package
+to look like;
+
+package Audio_Driver is
+
+   Muted : Boolean := False;
+
+   type Audio_Settings is private;
+
+   package Audio_Device_Driver is new private Device_Driver
+            (Disabled => Muted,
+             Configuration_Settings => Audio_Settings,
+             others => private);
+...
+
+
+!ACATS test
+
+ACATS B and C-Test(s) are necessary.
+
+****************************************************************
+
+From: Brad Moore
+Sent: Sunday, December 21, 2008  12:09 PM
+
+One of the advantages of the AI05-0074-2 proposal (end private) that is missing
+from the other proposals of that AI is that it is possible to declare a derived
+non-tagged type from a type exported in the private generic instantiation that
+is visible outside the package. We run into freezing problems if we try to do
+this with the current proposals involving AI05-0074-1.
+
+eg.
+generic
+  Y : private;
+  X : Integer;
+  Z : String;
+ ...
+package A_Container is
+  type Q is null record;
+end A_Container;
+
+with A_Container;
+package Foo
+  type T is private;
+  package I is new private A_Container(T, others => private);
+  type D is new I.Q; -- ERROR: Freezing problem here private
+  type T is null record;
+  package I is new A_Container(T, 1, "I Container", ...); end Foo;
+
+To solve this problem with this version of the AI, would it be worth considering
+allowing the syntax for type extensions to also be applied to non-tagged types?
+
+This would allow non-tagged types to be completed at the correct place in the
+private part similar to how it works for tagged type extensions.
+
+e.g.
+with A_Container;
+package Foo
+  type T is private;
+  package I is new private A_Container(T, others => private);
+  type D is new I.Q with private; --  Type extension for non-tagged type private
+  type T is null record;
+  package I is new A_Container(T, 1, "I Container", ...);
+  type D is new I.Q;
+end Foo;
+
+****************************************************************
+
+From: Brad Moore
+Sent: Friday, January 2, 2009  1:03 PM
+
+Randy pointed out to me that a limited view of a type precludes the ability to
+derive new types, whereas I was going for a solution that allows such
+derivations. In order to do that, a partial view rather than a limited view is
+needed.
+
+e.g.,
+
+with Ada.Containers.Doubly_Linked_Lists;
+package Pkg is
+  type T is private;
+  package T_List is new private Ada.Containers.Doubly_Linked_List(T);
+  type List_Type is new T_List.List; -- Partial View needed here private
+  type T is null record;
+  package T_List is new Ada.Containers.Doubly_Linked_List(T);
+end Pkg;
+
+While the proposed syntax for private generic actuals seems to be compatible
+with the solution of AI05-0074-1, and could possibly be considered as an option
+to that solution, I wanted to aim for a solution that also covers the other
+problems mentioned in the other proposals. Randy suggested I create a new
+proposal for AI05-0074, that incorporates a partial view which I have done. (See
+attached)
+
+I have also incorporated a few more ideas. Now in addition to being able to
+declare private types, private extensions, and private instantiations, you can
+also declare private objects. Also, this proposes a way to declare private
+extensions for untagged types.
+
+The proposed wording changes are mostly confined to section 7.3 in the RM. I
+think the wording probably needs some more polish but hopefully it is clear
+enough that the semantics can be understood.
+
+----
+
+!subject Private Generic Actual Parameters
+
+!summary
+
+(See proposal.)
+
+!problem
+
+Ada 95 provides formal package parameters. One way of using these parameters
+is to define a "signature" for a class of abstractions, such as all set
+abstractions, or all physical unit abstractions, and then build a new
+generic abstraction on top of the original class of abstractions using this
+signature as the template for a formal package parameter.
+
+Unfortunately, it is difficult to use signatures because of the fact that an
+instantiation freezes all of its actual parameters.
+
+For example:
+
+Given the signature for a set abstraction:
+
+generic
+   type Element is private;
+   type Set is private;
+   with function Size(Of_Set : Set) return Natural is <>;
+   with function Union(Left, Right : Set) return Set is <>;
+   with function Intersection(Left, Right : Set) return Set is <>;
+   with function Empty return Set is <>;
+   with function Unit_Set(With_Item : Element) return Set is <>;
+   with function Nth_Element(Of_Set : Set) return Element is <>;
+package Set_Signature is end;
+...
+
+we could define a generic that required some set abstraction, but it
+didn't care which one so long as it implemented the above signature:
+
+generic
+   with package Base_Set is new Set_Signature(<>);
+package Layered_Abstraction is
+   type Cool_Type(Set : access Base_Set.Set) is limited_private;
+   procedure Massage(CT : in out Cool_Type; New_Set : Base_Set.Set);
+   ...
+end Layered_Abstraction;
+
+Now if we want to define a set type and provide the pre-instantiated
+signature for it, we run into trouble:
+
+generic
+   type Elem is private;
+   with function Hash(El : Elem) return Integer;
+package Hashed_Sets is
+
+   type Set is private;
+   function Union(Left, Right : Set) return Set;
+   ...
+
+   package Signature is new Set_Signature(Elem, Set);
+private
+   type Set is record ... end record;
+end Hashed_Sets;
+
+The problem is that we can't do the instantiation of Set_Signature where we
+would want to do so, because the instantiation freezes the type "Set"
+prematurely.
+
+A similar problem occurs when a type wants to include a pointer to a
+container based on the type being defined.
+
+For example:
+
+package Expressions is
+   type Expr_Ref is private;
+   package Expr_Sequences is new Sequences(Expr_Ref); -- Freezing trouble here!
+   type Seq_Of_Expr is access Expr_Sequences.Sequence;
+   function Operands(Expr : Expr_Ref) return Seq_Of_Expr;
+   ...
+private
+   type Expression; -- completion deferred to body
+   type Expr_Ref is access Expression;
+end Expressions;
+
+Here we have a case where we want to instantiate a generic using a private
+type, and use the results of the instantiation as the designated type of an
+access type, which is in turn used as a parameter or result type of an
+operation on the private type.
+
+Unfortunately, we can't instantiate the "Sequences" generic with Expr_Ref,
+since it is private.
+
+
+!proposal
+
+- Introduce new syntax (a private_instantiation_declaration) that allows
+an incomplete declaration of a generic package instantiation to be made in
+the visible part of a package specification and completed with a
+generic_instantiation in the private part of the package.
+
+- In the region between the private_instantiation_declaration and the
+generic_instantiation in the package specification, implicitly declare
+limited and private views of all type declarations from the
+generic_instantiation that are accessible from outside the
+generic_instantiation. The limited views apply only to any
+record_definition associated with a type declaration in this region.
+Otherwise the partial view of these type declarations are available in
+this region.
+
+- In the region between the completing generic_instantiation and the
+end of the package specification, and from views outside the package
+specification, the full view of the generic instantiation applies.
+
+- A new pragma (May_Be_Partial) is defined that must be applied to
+any generic formal declarations for which the actual may be a partial
+view named in a private_instantiation_declaration. This pragma restricts
+the usage of the formal within the generic package to not allow any
+constructs that would require freezing of the formal type. In particular,
+this means that an object or an expression of the type cannot be used
+in the package specification, nor can new types be derived from these
+generic formals within the package specification.
+
+- To allow type derivations of untagged partial views named in a
+private_instantiation_declaration within the same visible part of
+a package specification, a private_extension is allowed to apply
+to both tagged and untagged types.
+
+- Allow a private_instantiation_declaration to be able to specify that any
+actual parameters can be left unspecified until the private part of the package
+specification.
+
+- Add new syntax to allow a variable of a private type or private extension
+to be exported from a package.
+
+!wording
+
+Change the title of Section 7.3:
+Private Types{,}[and] Private Extensions{, Private Objects, and Private
+Instantiations}
+
+Change 7.3(1):
+
+The declaration (in the visible part of a package) of a type as a private
+type or private extension {or of a generic instantiation as a private
+instantiation} serves to separate the characteristics that can be used
+directly by outside program units (that is, the logical properties) from
+other characteristics whose direct use is confined to the package
+[(the details of the definition of the type itself)]. See 3.9.1 for an
+overview of type extensions.
+
+Add 7.3(3.1-3.4):
+
+3.1 private_object_declaration ::=
+    defining_identifier_list : [ALIASED] [CONSTANT] PRIVATE subtype_indication;
+  | defining_identifier_list : [ALIASED] [CONSTANT] PRIVATE array_type_definition;
+
+3.2 private_instantiation_declaration ::=
+   PACKAGE defining_program_unit_name IS
+         NEW PRIVATE generic_package_name [deferred_generic_actual_part];
+
+3.3 deferred_generic_actual_part ::=
+   (deferred_generic_association {, deferred_generic_association})
+
+3.4 deferred_generic_association ::=
+   [generic_formal_parameter_selector_name =>]  explicit_generic_actual_parameter
+ |  [generic_formal_parameter_selector_name =>] PRIVATE
+ | others => PRIVATE
+
+3.5 A deferred_generic_association is named or positional according to whether
+or not the generic_formal_parameter_selector_name is specified. Any positional
+associations shall precede any named associations. If there is an association
+with the reserved word OTHERS, it shall come last.
+
+Add 7.3(4.1-4.10):
+
+4.1 A private_object_declaration declares a view of an object. The view is an
+aliased view if the ALIASED keyword is associated with the declaration. The view
+is a constant view if the CONSTANT keyword is associated with the declaration.
+Such a declaration is allowed only as a declarative_item of the visible part of
+a package, and it requires a completion, which shall be an object_declaration
+that occurs as a declarative_item of the private part of the package. The view
+of the private_object_declaration is a view of the completed object_declaration.
+The view can only be referenced from outside the package specification.
+
+4.2 The named object of a private_object_declaration shall either be an object
+associated with a private type or private extension declared within the visible
+part of the package specification containing the private_object_declaration, or
+an array whose component's are of a type that is associated with a private type
+or private extension declared within the visible part of the package
+specification containing the private_object_declaration.
+
+4.3 The subtype_indication of a private_object_declaration shall statically
+match the subtype_indication in the completing declaration.
+
+4.4 If the private_object_declaration includes the reserved word ALIASED, then
+the completing declaration shall also.
+
+4.5 If the subtype of the private_object_declaration excludes null, the subtype
+of the completing declaration shall also exclude null.
+
+4.6 A private_instantiation_declaration implicitly declares a partial view
+and a limited view of all type declarations of the generic package associated
+with the instantiation that are visible from outside the completed generic
+instantiation. A private_instantiation_declaration also declares a full view
+of the completed generic instantiation. The applicable set of views is
+determined by context, but no more than one set of views (either the partial
+views, the limited views, or the full view) may apply to any given context.
+
+4.7 A private_instantiation_declaration is allowed only as a declarative_item
+of the visible part of a package, and it requires a completion, which shall be
+a generic_instantiation (see 12.3) that occurs as a declarative_item of the
+private part of the package.
+
+4.8 The actual parameters of the completion shall match the corresponding actual
+parameters of the private_instantiation_declaration, whether the actual parameters
+are given explicitly or by default.
+
+4.9 The rules for matching of actual parameters between the completion and the
+private instantiation are as follows:
+
+4.10   * If an association is a named association in the private instantiation
+ then the association shall be a named association in the completion. If an
+ association is a positional association in the private instantiation then the
+ association shall be positional in the completion.
+
+4.11   * A named association with the reserved word OTHERS matches all needed
+ actual parameters from the completing generic_instantiation that are not
+ associated with some previous association. This includes the corresponding
+ default_expression or default_name of a formal if no generic_association is
+ given for the formal in the completing generic instantiation;
+
+4.12  * An association with the reserved word PRIVATE but without the reserved
+ word OTHERS matches the actual of the completing generic instantiation that has
+ the same  generic_formal_parameter_selector_name if the association is a named
+ association, or the actual in the corresponding relative position within the
+ generic_actual_part if the association is a positional association.
+
+4.13   * For a formal object of mode IN the actuals match if they are static
+ expressions with the same value, of if they statically denote the same constant,
+ or if they are both the literal NULL.
+
+4.14   * For a formal subtype, the actuals match if they denote statically
+ matching subtypes.
+
+4.15  * For other kinds of formals, the actuals match if they statically
+ denote the same entity.
+
+AARM NOTE: We considered using full conformance rules here instead of
+    formal-package-ish matching. However, we wanted to use rules consistent
+    with formal packages, and it seemed simpler to just define the particular
+    matching rules needed between instantiations. Also we wanted to
+    ensure that no evaluations would take place at the point of the
+    private instantiation.}
+
+Change 7.3(5):
+A type shall be completely defined before it is frozen (see 3.11.1 and 13.14).
+Thus, neither the declaration of a variable of a partial view of a type, nor
+the creation by an allocator of an object of the partial view are allowed before
+the [full] declaration {providing the full view} of the type. Similarly, before
+the full declaration, the name of the partial view cannot be used in a
+generic_instantiation or in a representation item. {If the name of a partial
+view is used in a private_instantiation_declaration then the generic formal
+parameter of the completing generic_instantiation shall have the May_Be_Partial
+pragma applied to it. See 12.3.1}
+
+Change 7.3(6/2):
+A private type is limited if its declaration includes the reserved word limited;
+a private extension is limited if its ancestor type is a limited type that is not
+an interface type, or if the reserved word limited or synchronized appears in its
+definition. If the partial view is nonlimited, then the full view shall be
+nonlimited. If a tagged partial view is limited, then the full view shall be limited.
+On the other hand, if an untagged partial view {of a private type} is limited, the
+full view may be limited or nonlimited.
+
+Change 7.3(7):
+If the partial view is tagged, then the full view shall be tagged. On the other
+hand, if the partial view is untagged, then the full view may be tagged or untagged.
+In the case where the partial view is untagged and the full view is tagged, no
+derivatives of the partial view are allowed within the immediate scope of the
+partial view {unless the derivative is a private_extension_declaration};
+derivatives of the full view {do not have this restriction}[are allowed].
+
+Change 7.3(8):
+The ancestor subtype of a private_extension_declaration is the subtype defined
+by the ancestor_subtype_indication; the ancestor type shall be a specific [tagged]
+type. The full view of a private extension shall be derived (directly or
+indirectly) from the ancestor type. In addition to the places where Legality Rules
+normally apply (see 12.3), the requirement that the ancestor be specific applies
+also in the private part of an instance of a generic unit.
+
+Add 7.3(15.1):
+
+15.1 The implicit declaration of partial views and limited views, and the full
+view of the generic_instantiation define three sets of views associated with a
+private_instantiation_declaration. The limited views define the allowed usage
+within a component_list of any record_definition declared between the
+private_instantiation_declaration in the visible part and the completed
+generic_instantiation in the private part of a package specification; otherwise,
+the partial views define the allowed usage for the same region of a package
+specification. The full view together with the visible part define the
+operations that are available to outside program units. The full view together
+with the private part define other operations whose direct use is possible only
+within the declarative region of the package itself between the completing generic
+instantiation and the end of the declarative region.
+
+Change 7.3(17):
+The elaboration of a private_type_declaration creates a partial view of a type.
+The elaboration of a private_extension_declaration elaborates the
+ancestor_subtype_indication, and creates a partial view of a type.
+{The elaboration of a private_object_declaration elaborates the subtype_indication
+or the array_type_definition. The elaboration of a private_generic_instantiation
+creates limited and partial views for all type declarations of the generic package
+associated with the instantiation that are visible from outside the completed
+generic instantiation. The elaboration also creates a full view of the
+generic instantiation.}
+
+Add 7.3(20.2):
+
+The completing object_declaration for a private_object_declaration is not allowed
+before the corresponding full_type_declaration of the private_type or
+private_extension. This is a consequence of the freezing rules for types (see 13.14).
+
+Add 7.3(20.3):
+If a private_instantiation_declaration is referenced from outside the package
+specification and the completed generic_instantiation is not visible, then any
+generic actual parameters that were declared in the private part of the package
+are not visible and therefore cannot be referenced. Any subprograms or entries
+declared visibly in the generic that have formal parameters of a non-visible
+formal type declared in the private part of the package containing the
+private_instantiation_declaration cannot be called from a context where the
+private part of the package is not visible.
+
+Add new section 12.3.1:
+
+12.3.1 Actual Types With Partial Views
+
+1 This subclause defines a pragma that allow a private_instantiation_declaration
+to use a name of a partial view.
+
+Syntax
+
+2 The form of a pragma May_Be_Partial is as follows:
+
+3 pragma May_Be_Partial(direct_name);
+
+Legality Rules
+
+4   The pragma May_Be_Partial specifies that a formal type may correspond to a
+generic_instantiation that is associated with a
+private_instantiation_declaration for which the matching actual is a partial
+view. The formal type associated with the pragma shall not be used in a context
+within the generic package specification that would require freezing of the type
+(See 13.14, “Freezing Rules”). This pragma shall appear in a generic_formal_part
+and the direct_name shall denote a generic formal private type or a generic
+formal derived type declared in the same generic_formal_part as the pragma.
+
+Change 13.14(5):
+The occurrence of a generic_instantiation causes freezing {unless the instantiation
+has a corresponding private_generic_instantiation}; also, if a parameter of the
+instantiation is defaulted, the default_expression or default_name for that
+parameter causes freezing.
+
+Change 13.14(8/1):
+A static expression 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, {a private_generic_instantiation,
+a generic_instantiation that has a corresponding private_generic_instantiation,}
+or a per-object expression of a component's constraint, in which case, the
+freezing occurs later as part of another construct.
+
+
+!discussion
+
+This proposal solves several problems that come up frequently in practice with
+private types. Certainly the most common is a desire to include an instantiation
+of a generic (possibly a signature generic as mentioned in the "problem" section
+above, or perhaps a container generic), with a private type as one of the actual
+parameters to the instantiation. Another problem is a desire to export a
+variable of a private type. This is not permitted prior to the private type
+being completed. A third problem is a desire to derive a new type from an
+untagged private type in the visible part of the package that declared the
+untagged private type. Tagged types can declare a private extension, but there
+is no corresponding syntax to declare a private extension of an untagged type. A
+fourth problem is a desire to derive a new type in the visible part of a package
+from a type (tagged or untagged) that is declared in a generic package that is
+instantiated in the same visible part of the package, where the generic is
+instantiated with a private type or private extension. A fifth problem is a
+desire to be able to have a type declaration that contains an access to an
+instantiated type of a generic whereby the type declaration was supplied as an
+actual for the instantiation. An instantiation requires the type to be defined
+first, but if the instantiation comes after the type declaration, then the type
+declaration cannot name any type declarations of the instantiation.  A sixth
+problem is a desire to instantiate a generic in the visible part of a package,
+yet defer the declarations for some or all of the actuals to the private part of
+the package. A seventh problem is a desire to have a way to make certain
+operations of a generic unavailable for use if they do not support the
+particular abstraction associated with the instantiation.
+
+The basic idea of this proposal is to add syntax that provides more ways to
+create incomplete declarations in the visible part of a package specification
+that are completed in the private part of the package thus providing more
+flexibility and capabilities for exporting functionality in the visible part
+of a package specification.
+
+This is limited to packages because you can use renaming-as-body to get this
+effect for subprogram instantiations. Moreover, you cannot export a type from
+a generic subprogram, so there is no possibility of recursive use.
+[Note that we could lift this limitation if it if felt to be more regular.]
+
+Ada 2005 provides solutions to these problems, but they are not ideal.
+For the first example, making the instantiation a child unit solves the problem.
+However, this is annoying, because accessing the instance requires an extra with
+and instantiation (since children of generics must be generic):
+
+generic
+   type Elem is private;
+   with function Hash (El : Elem) return Integer;
+package Hashed_Sets is
+   type Set is private;
+   function Union(Left, Right : Set) return Set;
+   ...
+private
+   type Set is record ... end record;
+end Hashed_Sets;
+
+generic
+package.Hashed_Sets.Signature is
+   package The_Signature is new Set_Signature(Elem, Set);
+end Hashed_Sets.Signature;
+
+A user of Hashed_Sets must with and instantiate Hashed_Sets.Signature in order
+to access the instance. The second problem can also be solved with child units,
+using the limited with:
+
+limited with Expressions.Sequences;
+package Expressions is
+   type Expr_Ref is private;
+   type Seq_Of_Expr is access Expressions.Sequences.Sequence;
+   function Operands(Expr : Expr_Ref) return Seq_Of_Expr;
+   ...
+private
+   type Expression; -- completion deferred to body
+   type Expr_Ref is access Expression;
+end Expressions;
+
+package Expressions.Sequences is
+   package Expr_Sequences is new Sequences(Expr_Ref);
+   type Sequences is Expr_Sequences.Sequence;
+end Expressions.Sequences;
+
+Here, besides the extra with clause, we need to declare an extra type
+simply so that the type is visible to the limited with clause
+(which operates purely syntactally). This means that extra type conversions
+are necessary.
+
+The most important capability is to be able to instantiate a generic with a
+private type or private extension as an actual. The concept is to be able
+to declare a generic instantiation in two parts. The first part is called
+a private_generic_instantiation and is declared in the visible part of a package
+specification. The second part is the completing generic_instantiation that
+occurs in the private part of the package specification. The instantiation in
+the private part is the real instantiation. The syntax in the visible part
+really just provides a view of the instantiation that is exported.
+
+e.g.,
+   with Ada.Containers.Doubly_Linked_Lists;
+   package Pkg is
+      type T is private;
+      package I is new PRIVATE Ada.Containers.Doubly_Linked_Lists (T);
+   private
+      type T is null record;
+      package I is new Ada.Containers.Doubly_Linked_Lists (T);
+   end Pkg;
+
+   The intent is that the exported view of the instantiation of I is effectively
+   the same as the view if the generic had been instantiated from outside the
+   Pkg;
+
+i.e.
+
+   package Pkg is
+      type T is private;
+   private
+      type T is null record;
+   end Pkg;
+
+   with Pkg; use Pkg;
+   with Ada.Containers.Doubly_Linked_Lists;
+   procedure Use_Pkg is
+      package I is new Ada.Containers.Doubly_Linked_Lists (T);
+   begin
+      ...
+   end Use_Pkg;
+
+Now suppose we would like to have type T include an access to a type
+provided by the instantiation. There is no way to do this currently
+in Ada. It is possible to use an incomplete type, and then complete
+this type with a derivation from a type provided by the instantiation.
+e.g.,
+
+   with Ada.Containers.Doubly_Linked_Lists;
+   package Pkg is
+      type T is private;
+   private
+      type List_Type;
+      type T is
+        record
+          List : access List_Type;
+        end record;
+      package I is new Ada.Containers.Doubly_Linked_Lists (T);
+      type List_Type is new I.List with null record;
+   end Pkg;
+
+However it is not always possible to derive a new type. Supposing
+we decided to use a different container based on a protected type.
+
+   with Ada.Containers.Protected_Queue; -- A new container currently being proposed.
+   package Pkg is
+      type T is private;
+   private
+      type Queue_Type;
+      type T is
+        record
+          Queue : access Queue_Type;
+        end record;
+      package I is new Ada.Containers.Protected_Queue (T);
+      type Queue_Type is new I.Queue with null record;
+      -- ERROR Cannot derive a new type from a protected type or interface.
+   end Pkg;
+
+Using the new syntax however, this becomes possible, and simpler,
+because the generic has been already been named in a
+private_instantiation_declaration. Note there is no longer a need to declare
+an incomplete type. There is also no longer a need to derive a new type
+from the instantiation.
+
+e.g.,
+
+   with Ada.Containers.Protected_Queue; -- A new container currently being proposed.
+   package Pkg is
+      type T is private;
+      package I is new private Ada.Containers.Protected_Queue (T);
+   private
+      type T is
+        record
+          Queue : access I.Queue;
+        end record;
+      package I is new Ada.Containers.Protected_Queue (T);
+   end Pkg;
+
+
+For this to work, only a limited view of the instantiated package
+is needed. By saying that the view of the instantiated types within
+the record_declaration is a limited view, it avoids problems with
+recursive declarations by ensuring that only access types may be used
+to name the instantiated types.
+
+Now suppose we want this example to export two containers instantiated
+from the same type.
+
+e.g.,
+   with Ada.Containers.Doubly_Linked_Lists;
+   with Ada.Containers.Protected_Queue;
+   package Pkg is
+      type T is private;
+      package I1 is new private Ada.Containers.Protected_Queue (T);
+      package I2 is new private Ada.Containers.Doubly_Linked_Lists (T);
+   private
+      type T is
+        record
+          Queue : access I1.Queue;
+          List : access I2.List;
+        end record;
+      package I1 is new Ada.Containers.Protected_Queue (T);
+      package I2 is new Ada.Containers.Doubly_Linked_Lists (T);
+      -- ERROR FREEZING Problem here. I1 instantiation freezes T. (See 13.14(5))
+   end Pkg;
+
+We would like to be able to instantiate the above without running into
+freezing problems. To achieve this goal, we need to relax the freezing
+rules so that instantiations associated with private_instantiation_declarations
+do not cause freezing to occur. It should be possible to not have 13.14(5) apply
+so that freezing occurs at the next freezing point instead.
+
+To avoid freezing problems in the generic, we also need to ensure that the
+generic does not have any declarations that would cause freezing of the formal
+whereby the corresponding actual is a private type or private extension. In
+particular, we need to ensure that the generic does not declare any objects of
+the formal type, or have any expressions involving the formal type in the
+package specification. In addition, the generic cannot derive a new type from
+the formal, because of 13.14(7). We also want to have a way to make it explicit
+that a formal could be a partial type, so that maintenance of a generic package
+wont introduce changes that could cause compilations to fail. To address this
+need, a new pragma is introduced, pragma May_Be_Partial, which may be applied to
+a generic formal type, and makes it explicit that the associated formal type
+will not be used in a way that would cause freezing of that type within the
+generic specification and body.
+
+For example, if we were to apply this pragma to the
+Ada.Containers.Doubly_Linked_List package, it would appear as;
+
+generic
+   type Element_Type is private;
+   pragma May_Be_Partial (Element_Type);
+
+   with function "=" (Left, Right : Element_Type)
+      return Boolean is <>;
+
+package Ada.Containers.Doubly_Linked_Lists is
+   ...
+
+
+Now consider that we would like to be able to export a derived type of an
+instantiated type associated with a private_instantiation_declaration. For
+this to work, a private_extension must be used because otherwise a type
+derivation would cause freezing to occur. This is fine, but we run into
+problems with a limited view.
+
+e.g.,
+   with Ada.Containers.Doubly_Linked_Lists;
+   with Ada.Containers.Protected_Queue;
+   package Pkg is
+      type T is private;
+      package I1 is new private Ada.Containers.Protected_Queue (T);
+      package I2 is new private Ada.Containers.Doubly_Linked_Lists (T);
+      type New_List is new I2.List with private;
+      --  ERROR if view of I2 is a limited view!
+   private
+      type T is
+        record
+          Queue : access I1.Queue;
+          List : access I2.List;
+        end record;
+      package I1 is new Ada.Containers.Protected_Queue (T);
+      package I2 is new Ada.Containers.Doubly_Linked_Lists (T);
+      type New_List is new I2.List with null record;
+   end Pkg;
+
+A limited view of a type is a very restricted view and does not allow
+type derivations. To be able to do this, we need a partial view of the type.
+However, we want a limited view within record definitions. To get around this
+we say that a private_instantiation_declaration declares 3 sets of views.
+There is a set of limited views of all type declarations exported from the
+instantiation, there is a set of partial views of all type declarations
+exported form the declaration, and there is the full view of the instantiation.
+
+The limited and private views only apply to the package specification and
+together cover the region in the package specification between the
+private_instantiation_declaration and the completing generic_instantiation. The
+limited views only apply to record_definitions within this region, whereas the
+partial views apply everywhere else within this region. The full view applies to
+the region between the generic_instantiation and the end of the package
+specification, and also outside of the package;
+
+It was considered whether we could say only partial views are created, instead
+of both limited and partial views, and then special rules could be added to
+ensure that only access types are used within record definitions, but it seemed
+that it was easier and safer to say that a limited view applied in such a
+context instead.
+
+Currently the wording of this proposal only creates views of type
+declarations that are externally visible from the instantiation. The wording
+does not create views for subtype declarations. The reasons for this are that
+it seems like there would be less likely to be problems if we leave subtype
+declarations out of the picture. A limited view of a package does not see
+subtype declarations, and it seems simpler if the limited and partial views
+are for the same set of declarations. Note that limited and partial views
+are also provided for any visible instantiations declared within the generic
+being instantiated.
+
+Now consider that we would like to also derive from an untagged type. We need
+to declare a type extension, but there is no such thing for an untagged type.
+
+e.g.,
+
+   with Ada.Containers.Doubly_Linked_Lists;
+   with Ada.Containers.Protected_Queue;
+   package Pkg is
+      type T is private;
+      package I1 is new private Ada.Containers.Protected_Queue (T);
+      package I2 is new private Ada.Containers.Doubly_Linked_Lists (T);
+      type New_Cursor is new I2.Cursor;
+      --  ERROR a type derivation causes freezing!
+   private
+      type T is
+        record
+          Queue : access I1.Queue;
+          List : access I2.List;
+        end record;
+      package I1 is new Ada.Containers.Protected_Queue (T);
+      package I2 is new Ada.Containers.Doubly_Linked_Lists (T);
+   end Pkg;
+
+To get around this, we need a way to declare a private derivation for an
+untagged type. Rather than create new syntax, it is proposed that we use
+the same syntax as for tagged types, but allow a private_extension to
+be used for both tagged and untagged types.
+
+e.g.,
+
+   with Ada.Containers.Doubly_Linked_Lists;
+   with Ada.Containers.Protected_Queue;
+   package Pkg is
+      type T is private;
+      package I1 is new private Ada.Containers.Protected_Queue (T);
+      package I2 is new private Ada.Containers.Doubly_Linked_Lists (T);
+      type New_List is new I2.List with private;      -- private extension for a tagged type
+      type New_Cursor is new I2.Cursor with private;  -- private extension for an untagged type
+   private
+      type T is
+        record
+          Queue : access I1.Queue;
+          List : access I2.List;
+        end record;
+      package I1 is new Ada.Containers.Protected_Queue (T);
+      package I2 is new Ada.Containers.Doubly_Linked_Lists (T);
+      type New_List is new I2.List with null record;  -- Completion of tagged private extension
+      type Cursor is new I2.Cursor;                   -- Completion of untagged private extension
+   end Pkg;
+
+The use of "with private" might seem to conflict a bit for the case of an
+untagged type as it suggests an extension to the record structure, but this
+could be possibly rationalized as it is possible to add more primitives in the
+private part, and could be thought of as being extended by an implicit null
+record. It seemed better to use the same syntax for both, rather than invent new
+syntax that applies specifically to untagged types.
+
+Now suppose we want to export a variable of a private type or a private
+extension. This is currently not possible in Ada.
+
+e.g.,
+
+   package Pkg is
+      type T is private;
+      Global_List : T;
+      --  ERROR the variable declaration freezes T!
+   private
+      type T is null record;
+   end Pkg;
+
+To get around this, we take a similar approach as we did for generic
+instantiations. We add syntax to allow an incomplete object declaration
+in the visible part of a package specification that is completed by an
+object_declaration in the private part;
+
+e.g.,
+
+   package Pkg is
+      type T is private;
+      Global_List : private T;  -- private_object_declaration
+      Global_Array : private array (1 .. 5) of T;
+   private
+      type T is null record;
+      Global_List : T;          -- completing object_declaration
+      Array_Of_T : array (1 .. 5) of T;
+   end Pkg;
+
+In this case, we say that the private_object_declaration is a *view* of an
+object, not an object declaration. The view is that of the completing object
+declaration.
+
+A private_object_declaration may use the ALIASED or CONSTANT keyword.
+If ALIASED appears in the private_object_declaration, it must also
+appear in the completing object declaration. The CONSTANT keyword
+does not need to appear in the completing object_declaration if it
+appears in the private_object_declaration however. In this case,
+the exported view is a constant view, but may be variable within
+the private part. To simplify things, it is proposed
+that the private_object_declaration can only be referenced from
+outside the package specification. In theory, it should be possible
+to create wording that allows an aliased variable to be referenced
+within the package specification, but it seems that this would be
+tricky to get right. For now, it seems best to only allow references
+to private_object_declarations from outside the package specification.
+Also, it only seemed to be worthwhile to allow objects, or arrays of
+objects to be defined in a private_object_declaration. For example,
+an access to object declaration can be setup in Ada today, in the
+elaboration of a package body.
+
+The proposed rules state that a private_object_declaration can only
+be applied to a private type or private extension, or to an array
+of objects of a private type or private extension.
+
+Note also that a constant private_object_declaration is very
+similar to a deferred constant declaration. There are a few differences
+however. A deferred constant can be combined with pragma import, to
+link to an external value. Also, a deferred constant does not need to
+be of a private type, or of a private extension. It seemed worthwhile
+to provide the constant view of a private_object_declaration even if
+it does overlap with a deferred constant somewhat.
+
+Now suppose we would like to be able to hide more details associated
+with a private_instantiation_declaration in the private part of a package
+specification. In particular, we want to be able to declare certain actuals
+in the private part, instead of having to declare them in the visible part
+of a package specification. It may also be desirable to limit the visible
+operations from outside the package by having the generic actual parameters
+declared in the private part of the package specification.
+
+For example:
+
+Supposing we have a generic package that can be used to create a specific
+abstraction, and we want the generic instantiation of this package to
+directly provide all the operations that are available to clients in the
+package containing the specific abstraction.
+
+In other words, the generic instantiation needs to be declared in the
+visible part of the package associated with specific abstraction.
+
+Currently this requires that all the generic actuals be fully visible
+at the point of the generic instantiation. This can lead to the
+exposure of constants, variable, types, subprograms, entries, and
+packages in the visible part of the package that might have been better
+off hidden from view.
+
+To illustrate these points, consider the following generic that provides
+a template for a device driver which can be plugged into some fictional
+target OS.
+
+generic
+   type Device_Type is private;
+   Manufacturer : String;
+   Model : String;
+   Disabled : in out Boolean;
+   with procedure Activate_Device (Device : Device_Type);
+
+   with function Device_Is_Operational
+     (Device : Device_Type) return Boolean;
+   type Configuration_Settings is private;
+   with procedure Configure_Device
+     (Device : Device_Type; Settings : Configuration_Settings);
+package Device_Driver is
+
+   protected Driver  is
+      procedure Activate;
+      function Is_Operational return Boolean;
+      procedure Configure (Settings : Configuration_Settings);
+   private
+      Device : Device_Type;
+   end Driver;
+end Device_Driver;
+
+package body Device_Driver is
+   protected body Driver is
+
+      procedure Activate is
+      begin
+         Activate_Device (Device);
+      end Activate;
+
+      procedure Configure (Settings : Configuration_Settings) is
+      begin
+         Configure_Device (Device, Settings);
+      end Configure;
+
+      function Is_Operational return Boolean is
+      begin
+         return Device_Is_Operational (Device);
+      end Is_Operational;
+   end Driver;
+end Device_Driver;
+
+Now Suppose we want to create an Audio Driver that utilizes this generic.
+We really want to to expose just the calls provided by the generic to
+Activate the audio driver, and to check to see if the audio driver
+Is_Operational. Unfortunately, we end up having to expose a lot of
+details that clients might have no business looking at, and the package
+specification suffers from poor readability due to the excess clutter.
+
+
+with Device_Driver;
+with Interfaces.C;
+
+package Audio_Driver is
+
+   use Interfaces;
+   type Audio_Device is
+      record
+         Handle : C.int;
+         Big_Ugly_Structure : ...
+      end record;
+   pragma Convention (C, Audio_Device);
+
+   procedure Power_On (Device : Audio_Device);  -- Actual procedure
+   function Playing_Music (Device : Audio_Device) return Boolean; -- Actual Function
+
+   Muted : Boolean := False;  -- Actual Variable
+
+   type Audio_Quality is (High, Medium, Low);
+   Default_Codec : constant := 16#DEADBEEF#;
+   type Audio_Settings is
+      record
+         Codec : C.unsigned_long := Default_Codec;
+         Quality : Audio_Quality := High;
+      end record;
+   procedure Setup (Device : Audio_Device; Settings : Audio_Settings);
+   pragma Convention (C, Audio_Settings);
+
+   package Audio_Device_Driver is new Device_Driver
+     (Device_Type => Audio_Device,  -- Actual Type
+      Manufacturer => "Acme Corp",  -- Actual Constant
+      Model => "SoundWhomper Mark IV", -- Actual Constant
+      Disabled => Muted, -- Actual Variable
+      Activate_Device => Power_On, -- Actual procedure
+      Device_Is_Operational => Playing_Music, -- Actual function
+      Configuration_Settings => Audio_Settings, -- Actual procedure
+      Configure_Device => Setup);  -- Actual type
+
+end Audio_Driver;
+
+
+The Device_Type record and the Audio_Setting record could be made
+into private types, hiding some of details, but still we would have
+to expose the Manufacturer, the Model, the Mute setting variable,
+and the various subprograms supplied as actuals. Furthermore, this
+particular generic wraps a single device object in a protected
+object, but otherwise does not provide any interface to access
+the device object directly. Ideally, we would not even have to
+expose the device object as a private type.
+
+Suppose also that this particular audio device driver only supports one
+configuration, and that the Configure call of the generic does not
+do anything. Ideally, we would like to be able to hide the Configure
+call from clients.
+
+The idea is to be able to indicate that declarations for
+actuals of the partial generic instantiation in the visible part of a
+package specification are being deferred into the private part of a package
+specification. The private keyword is used in the declaration of the
+private_instantiation_declaration to indicate that a particular actual
+(or group of actuals if the named association is others) is being deferred
+to the private part of the package specification.
+
+Applying the syntax for a private_instantiation_declaration to the above
+allows us to write;
+
+with Device_Driver;
+private with Interfaces.C;
+
+package Audio_Driver is
+   package Audio_Device_Driver is new private Device_Driver (others => private);
+
+   -- These renamed subprograms are the only visible operations
+   procedure Activate renames Audio_Device_Driver.Driver.Activate;
+   function Is_Operational return Boolean renames Audio_Device_Driver.Driver.Is_Operational;
+
+   --  Note Audio_Device is more private than if we had declared it as a private type.
+   --  You cannot even declare an Audio Device, or call Power_On, or Playing_Music directly
+   --  But you can call Audio_Device_Driver.Activate, or Audio_Device_Driver.Is_Operational
+   --  to do the same thing.
+   -- Note you cannot call Configure because the type associated with one of the formal parameters
+   -- of that call (Audio_Settings) is not visible.
+
+private
+
+   use Interfaces;
+   type Audio_Device is
+      record
+         Handle : C.int;
+         Big_Ugly_Structure : ...
+      end record;
+   pragma Convention (C, Audio_Device);
+
+   procedure Power_On (Device : Audio_Device);  -- Actual procedure
+   function Playing_Music (Device : Audio_Device) return Boolean; -- Actual Function
+
+   Muted : Boolean := False;  -- Actual Variable
+
+   type Audio_Quality is (High, Medium, Low);
+   Default_Codec : constant := 16#DEADBEEF#;
+   type Audio_Settings is
+      record
+         Codec : C.unsigned_long := Default_Codec;
+         Quality : Audio_Quality := High;
+      end record;
+   procedure Setup (Device : Audio_Device; Settings : Audio_Settings);
+   pragma Convention (C, Audio_Settings);
+
+   package Audio_Device_Driver is new Device_Driver
+     (Device_Type => Audio_Device,  -- Actual Type
+      Manufacturer => "Acme Corp",  -- Actual Constant
+      Model => "SoundWhomper Mark IV", -- Actual Constant
+      Disabled => Muted, -- Actual Variable
+      Activate_Device => Power_On, -- Actual procedure
+      Device_Is_Operational => Playing_Music, -- Actual function
+      Configuration_Settings => Audio_Settings, -- Actual procedure
+      Configure_Device => Setup);  -- Actual type
+
+end Audio_Driver;
+
+This dramatically simplifies the visible part of the package specification.
+
+Now suppose, we want to allow clients to access the mute variable which is
+supplied as an actual.
+
+The visible part of the package specification would then look like;
+
+package Audio_Driver is
+
+   Muted : Boolean := False;  -- Actual Variable
+
+   package Audio_Device_Driver is new private Device_Driver
+            (Disabled => Muted, others => private);
+...
+
+Clients can mute the sound simply by modifying the Muted variable.
+This seems to better separate the actual variable from the instantiated abstraction.
+
+Now suppose we want to support multiple configurations, and allow clients
+to be able to use of the Configure call.
+This can be accomplished by modifying the visible part of the package
+to look like;
+
+package Audio_Driver is
+
+   Muted : Boolean := False;
+
+   type Audio_Settings is private;
+
+   package Audio_Device_Driver is new private Device_Driver
+            (Disabled => Muted,
+             Configuration_Settings => Audio_Settings,
+             others => private);
+...
+
+
+A second example of using deferred actuals would be helpful.
+Suppose we have a set of container packages that implement a queue abstraction.
+The root package defines the interface to a queue, and child packages create various
+implementations of the interface
+
+generic
+   type Element_Type is private;
+   pragma Preelaborable_Initialization (Element_Type);
+   type Element_Index_Type is range <>;
+   type Element_Array_Type is array (Element_Index_Type range <>) of Element_Type;
+
+package Queues is
+   pragma Pure;
+
+   type Queue_Interface is limited interface;
+
+   --  Get and Put a single element from/to the queue
+   procedure Get (Container : in out Queue_Interface; Item : out Element_Type) is abstract;
+   procedure Put (Container  : in out Queue_Interface; Item : Element_Type) is abstract;
+
+   --  Get and Put multiple elements from/to the queue
+   procedure Get (Container : in out Queue_Interface;
+                  Item : out Element_Array_Type;
+                  Last : out Element_Index_Type) is abstract;
+
+   procedure Put (Container  : in out Queue_Interface; Item : Element_Array_Type) is abstract;
+
+   type Queue_Type (Capacity : Natural) is abstract new Queue_Interface with null record;
+
+   type Queue_Class_Access is access all Queue_Interface'Class;
+
+end Queues;
+
+Suppose that there exist three implementations of this interface.
+  1) A Bounded queue
+  2) A Queue of bounded queues that presents an abstraction of a
+     queue that presents an array of Bounded queues as a single queue
+
+
+generic
+   type Queue_Array_Type is
+     array (Natural range <>) of Queue_Class_Access;
+   Queues : Queue_Array_Type;
+package Queues.Multi is
+...
+
+   3) A protected queue that wraps a lower level queue into a protected object
+      to allow save concurrent access
+
+generic
+
+   type Queue_Implementation is new Queue_Type with private;
+   pragma Preelaborable_Initialization (Queue_Implementation);
+
+package Queues.Concurrent is
+   pragma Pure;
+
+   protected type Queue (Capacity : Natural) is new Queue_Interface with
+      overriding procedure Get (Item : out Element_Type);
+      overriding procedure Get (Item : out Element_Array_Type; Last : out Element_Index_Type);
+      overriding procedure Put (Item : Element_Type);
+      overriding procedure Put (Item : Element_Array_Type);
+   private
+      Data          : Queue_Implementation (Capacity);
+   end Queue;
+   pragma Preelaborable_Initialization (Queue);
+end Queues.Concurrent;
+
+Now suppose we want to create a protected queue of bounded queues, but for this
+abstraction we are only interested in Get and Put calls that operate on a single
+element. The Get and Put calls that operate on an array of elements are not
+going to be used. Further, we want to ensure that clients of this abstraction do
+not use these Get and Put calls, because someday we might want to replace the
+use of these containers with a simpler set of abstractions that do not have
+these calls. The proposed syntax allows us to write:
+
+
+private with Queues.Bounded; -- Simple bounded queue
+private with Queues.Multi;   -- A "medium-level" generic queue-of-bounded-queues container
+with Queues.Concurrent;      -- A "high-level" protected queue of bounded queues container
+
+package Pkg is
+
+   Maximum_Capacity : constant := 300;  -- Max. no. of elements in the Q
+
+   type T is tagged private;
+
+   function Create return T;
+   pragma Preelaborable_Initialization (T);
+
+   -- Declare a private instantiation of the interface. Since the array
+   -- type actuals are being deferred to the private part, clients can not
+   -- use primitives that involve these types, because they are not visible types.
+   package I is new private Queues
+     (Element_Type => T, others  => private);
+
+   -- The protected queue of bounded queues abstraction
+   package I4 is new private I.Concurrent
+     (Queue_Implementation => private);
+
+
+private
+
+   type T is tagged
+      record
+         ...
+      end record;
+
+   --  Deferred actuals not accessible from outside this package
+   type T_Index_Type is new Natural;
+   type T_Array_Type is array (T_Index_Type range <>) of T;
+
+   --  Instantiate interface for a queue
+   package I is new Queues
+     (Element_Type => T,
+      Element_Index_Type => T_Index_Type,
+      Element_Array_Type => T_Array_Type);
+
+   --  Instantiate the "low-level" bounded queue implementation capable
+   --  of storing elements of type T
+   package I2 is new I.Bounded;
+
+   --  Declare some queues to be used in instantiating a queue of queues
+   Q1 : aliased I2.Queue (Capacity => 100);
+   Q2 : aliased I2.Queue (Capacity => Maximum_Capacity - Q1.Capacity);
+
+   --  Declare types needed to instantiate queue of queues generic
+   type Queue_Array is array (Natural range <>)
+     of access I.Queue_Interface'Class;
+   Queues : constant Queue_Array
+     := Queue_Array'(1 => Q1'Access, 2 => Q2'Access);
+
+   --  Instantiate a queue of queues generic
+   package I3 is new I.Multi
+     (Queue_Array_Type => Queue_Array, Queues => Queues);
+
+   --  Now instantiate a protected queue of queues.
+   package I4 is new I.Concurrent (Queue_Implementation => I3.Queue);
+
+end Pkg;
+
+
+
+!Example
+
+Now lets look at how the proposed syntax could be applied to the
+examples in the problem section of this AI.
+
+Here is the generic signature example:
+
+generic
+   type Elem is private;
+   with function Hash (El : Elem) return Integer;
+package Hashed_Sets is type Set is private;
+   function Union(Left, Right : Set) return Set;
+   function Size(Of_Set : Set) return Natural is <>;
+   function Intersection(Left, Right : Set) return Set is <>;
+   function Empty return Set is <>;
+   function Unit_Set(With_Item : Element) return Set is <>;
+   function Nth_Element(Of_Set : Set) return Element is <>;
+   package Signature is new private Set_Signature (Elem, Set);
+private
+   type Set is record ... end record;
+   package Signature is new Set_Signature(Elem, Set);
+end Hashed_Sets;
+
+In this case, it appears that Hashed_Sets is itself a general purpose
+container abstraction meant to be used on its own, and the above
+would be an appropriate package specification.
+
+Suppose however, that this package were intended to be only
+used to create higher level abstractions by using the Signature
+Instantiation as a package formal to instantiate a higher level
+generic package. In a sense this could be considered as a type of
+abstract package that is not to be used on its own.
+In this case, we would like to be able to hide more details in the
+private part, and ensure that only the Signature instantiation is
+exported from this generic package. Using the proposed syntax,
+this allows us to write:
+
+generic
+   type Elem is private;
+   with function Hash (El : Elem) return Integer;
+package Hashed_Sets is
+
+   type Set is private;
+   package Signature is new private Set_Signature (Elem, Set, others => private);
+
+private
+   type Set is record ... end record;
+   function Union (Left, Right : Set) return Set;
+   function Size (Of_Set : Set) return Natural is <>;
+   function Intersection (Left, Right : Set) return Set is <>;
+   function Empty return Set is <>;
+   function Unit_Set (With_Item : Element) return Set is <>;
+   function Nth_Element (Of_Set : Set) return Element is <>;
+   package Signature is new Set_Signature (Elem, Set);
+end Hashed_Sets;
+
+
+Here is an example where we want to instantiation a container:
+
+package Expressions is
+   type Expr_Ref is private;
+   package Expr_Sequences is new private Sequences(Expr_Ref);
+   function Operands(Expr : Expr_Ref) return access Expr_Sequences.Sequence;
+   ...
+private
+   type Expression; -- completion deferred to body
+   type Expr_Ref is access Expression;
+   package Expr_Sequences is new Sequences(Expr_Ref);
+end Expressions;
+
+Note that being able to access the instantation in the visible part
+with a partial view provides a simple easy to understand solution
+without having to introduce incomplete types, derived types, or even named
+access types.
+
+This proposal appears to have the capabilities of the other proposals of this
+AI, (AI05-0074-1, AI05-0074-2, and AI05-0074-3), plus additional capabilities
+although at first glance it would appear that AI05-0074-2 solves a problem that
+this proposal does not.
+
+The example sited is;
+
+package Constructs is
+   type Root_Construct_Handle is abstract tagged private;
+   ...
+   generic
+      type Data_Part is private;
+   package Handles is
+      type Construct_Handle is new Root_Construct_Handle with private;
+      type RO_Access is access constant Data_Part;
+      type RW_Access is access all Data_Part;
+      function Get_RO_Access(Handle : Construct_Handle) return RO_Access;
+      function Get_RW_Access(Handle : Construct_Handle) return RW_Access;
+   private
+      type Construct_Handle is new Root_Construct_Handle with ...
+      -- ERROR: Parent type of record extension
+      -- must be completely defined. end Handles;
+private
+   type Root_Construct_Record; -- completed in pkg body
+   type Root_Construct_Access is access all Root_Construct_Record;
+   type Root_Construct_Handle is abstract tagged
+      record
+         Construct : Root_Construct_Access;
+         ...
+      end record;
+end Constructs;
+
+However, a reasonable solution to this example seems to already exist
+with the current version of the Ada standard. By moving the first
+set of declarations into a nested package, the nested generic is able
+to exist without the need for declaring an "end private".
+
+package Constructs is
+
+   package Sub is
+      type Root_Construct_Handle is abstract tagged private;
+      ---  ...
+   private
+      type Root_Construct_Record;
+      --  completed in pkg body
+      type Root_Construct_Access is access all Root_Construct_Record;
+      type Root_Construct_Handle is abstract tagged
+         record
+            Construct : Root_Construct_Access;
+           --  ...
+         end record;
+   end Sub;
+
+   use Sub;
+   generic
+      type Data_Part is private;
+   package Handles is
+      type Construct_Handle is new Root_Construct_Handle with private;
+      type RO_Access is access constant Data_Part;
+      type RW_Access is access all Data_Part;
+      function Get_RO_Access (Handle : Construct_Handle) return RO_Access;
+      function Get_RW_Access (Handle : Construct_Handle) return RW_Access;
+   private
+      type Construct_Handle is new Root_Construct_Handle with
+         record
+            X : Integer;
+         end record;
+   end Handles;
+end Constructs;
+
+It might be worth considering how the various proposals compare
+with regard to solving the seven problems mentioned in the discussion
+of this proposal.
+
+Problem 1: Using Private types as actuals to a generic
+
+AI05-0074-1 - Solves
+AI05-0074-2 - Solves
+AI05-0074-3 - Solves
+AI05-0074-4 - Solves
+
+Problem 2: Exporting a variable of a private type
+
+AI05-0074-1 - Does not solve
+AI05-0074-2 - Solves
+AI05-0074-3 - Does not solve
+AI05-0074-4 - Solves
+
+Problem 3: Exporting a derived untagged private type
+
+AI05-0074-1 - Does not solve
+AI05-0074-2 - Solves
+AI05-0074-3 - Does not solve
+AI05-0074-4 - Solves
+
+Problem 4: Exporting derived type of instantiated package
+
+AI05-0074-1 - Does not solve
+AI05-0074-2 - Solves
+AI05-0074-3 - Does not solve
+AI05-0074-4 - Solves
+
+Problem 5: Types can have components that access instantiations using the type
+
+AI05-0074-1 - Partly solves but does not see into visible instantiations of instantiated generic
+              because only a limited view is seen of the instantiated package.
+AI05-0074-2 - Partly solves in a more awkward manner using incomplete types and type derivations.
+              Does not work for protected types, because you cannot derive from a protected type.
+AI05-0074-3 - Does not solve
+AU05-0074-4 - Solves
+
+Problem 6: Deferring declaration of actuals to the private part for an exported instantiation
+
+AI05-0074-1 - Does not solve
+AI05-0074-2 - Does not solve
+AI05-0074-3 - Does not solve
+AI05-0074-4 - Solves
+
+Problem 7: Limiting access to exported instantiation
+
+AI05-0074-1 - Does not solve
+AI05-0074-2 - Does not solve
+AI05-0074-3 - Does not solve
+AI05-0074-4 - Solves
+
+!ACATS test
+
+ACATS B and C-Test(s) are necessary.
+
+****************************************************************
+
+From: Steve Baird
+Sent: Wednesday, January 7, 2009  1:25 PM
+
+Steve Wrote:
+ > P.S. Do you think there is any benefit in allowing the May_Be_Partial  > pragma (or whatever name we might settle on) to apply to a  > formal array type?
+ >
+ >    type T is private;
+ >    type T_Vector is array (Positive range <>) of T;
+ >
+ >    package I is new G (T, T_Vector);
+ >   private
+ >    type T is ... ;
+ >
+ > Or is this just a solution looking for a problem?
+
+Brad Moore replied:
+
+That's a good point. I think that is needed. That raises another question. If
+May_Be_Partial is applied to a private type, is it implicitly also applied to
+formal array of that type, or does it need to be explicit?
+
+I would think, this the wording should say that this can be implicit, but
+explicitly is allowed also, as that may help document that fact that it may be a
+partial type.
+
+eg. From my example below....
+
+generic
+    type Element_Type is private;
+    pragma Preelaborable_Initialization (Element_Type);
+    pragma May_Be_Partial (Element_Type);
+
+    type Element_Index_Type is range <>;
+
+    type Element_Array_Type is array (Element_Index_Type range <>) of Element_Type;
+    pragma May_Be_Partial (Element_Array_Type); -- Can this pragma be Implicitly declared here?
+
+package Queues is ...
+
+
+
+I think I have a pretty good example of how this might be beneficial.
+See below.
+
+
+I have a generic that can be applied to any object that one might want to sell.
+
+with Ada.Calendar; use Ada.Calendar;
+generic
+    type Sellable_Type is tagged private;
+    pragma May_Be_Partial (Sellable_Type);
+    pragma Preelaborable_Initialization (Sellable_Type); package Sellable_Item is
+    type Dollars is delta 0.01 digits 10;
+    type Condition is (Poor, Fair, Good, Excellent);
+
+    type Valued_Item is new Sellable_Type with private;
+    pragma Preelaborable_Initialization (Valued_Item);
+
+    function Buying_Price (Item : Valued_Item) return Dollars;
+    function Estimated_Value (Item : Valued_Item) return Dollars;
+    function Selling_Price (Item : Valued_Item) return Dollars;
+
+    function Create
+      (Item : Sellable_Type;
+       Purchase_Cost : Dollars;
+       Asking_Price : Dollars;
+       Purchase_Date : Time;
+       Original_Condition : Condition;
+       Current_Condition : Condition) return Valued_Item;
+
+private
+
+    type Valued_Item is new Sellable_Type with
+       record
+          Purchase_Price : Dollars;
+          Purchase_Year : Integer;
+          Purchase_Condition : Condition;
+          Asking_Price : Dollars;
+          Current_Condition : Condition;
+       end record;
+
+end Sellable_Item;
+
+package body Sellable_Item is
+
+    function Buying_Price (Item : Valued_Item) return Dollars is
+    begin
+       return Item.Purchase_Price;
+    end Buying_Price;
+
+    function Create
+      (Item : Sellable_Type;
+       Purchase_Cost : Dollars;
+       Asking_Price : Dollars;
+       Purchase_Date : Time;
+       Original_Condition : Condition;
+       Current_Condition : Condition) return Valued_Item
+    is
+    begin
+       return Valued_Item'
+           (Item  with
+            Purchase_Price => Purchase_Cost,
+            Asking_Price => Asking_Price,
+            Purchase_Year => Year (Purchase_Date),
+            Purchase_Condition => Original_Condition,
+            Current_Condition => Current_Condition);
+    end Create;
+
+    function Estimated_Value (Item : Valued_Item) return Dollars is
+       pragma Unreferenced (Item);
+    begin
+       return 0.00;  -- Calculated value from purchase date, price, depreciation, currency value changes, market conditions, etc.
+    end Estimated_Value;
+
+    function Selling_Price (Item : Valued_Item) return Dollars is
+    begin
+       return Item.Asking_Price;
+    end Selling_Price;
+
+end Sellable_Item;
+
+Now I want to use this package to sell paintings, and the goal is to be able to
+add collections of paintings to an Art Gallery (which is implemented as a
+bounded buffer in this case)
+
+with Sellable_Item;
+with Queues.Bounded;
+
+package Art_Sale is
+
+    type Painting is tagged private;
+    pragma Preelaborable_Initialization (Painting);
+
+    procedure Create
+      (Artist : String;
+       Title : String;
+       Item : out Painting);
+
+    function Artist (Item : Painting) return String;
+    function Title (Item : Painting) return String;
+
+    package Sellable_Art is new private Sellable_Item (Painting);
+
+    type Masterpiece is new Sellable_Art.Valued_Item with private;
+    function May_Have_Been_Stolen (Item : Masterpiece) return Boolean;
+
+    type Collection is array (Integer range <>) of Masterpiece;
+
+    package Exhibit is new private Queues -- Instantiate Interface
+      (Element_Type => Masterpiece,
+       Element_Index_Type => Natural,
+       Element_Array_Type => Collection);
+
+    package Art_Gallery is new private Exhibit.Bounded;  -- Can store collections of paintings into a buffer
+
+private
+
+    type Painting is tagged record
+       Artist_Name : String (1 .. 10);
+       Work_Title : String (1 .. 10);
+    end record;
+
+    package Sellable_Art is new Sellable_Item (Painting);
+
+    type Masterpiece is new Sellable_Art.Valued_Item with
+       record
+          Appraised_Value : Sellable_Art.Dollars;
+       end record;
+
+    package Exhibit is new Queues
+       (Element_Type => Masterpiece,
+        Element_Index_Type => Natural,
+        Element_Array_Type => Collection);
+
+    package Art_Gallery is new Exhibit.Bounded;
+
+end Art_Sale;
+
+package body Art_Sale is
+    function Artist (Item : Painting) return String is
+    begin
+       return Item.Artist_Name;
+    end Artist;
+
+    procedure Create
+      (Artist : String;
+       Title : String;
+       Item : out Painting) is
+    begin
+       Item := Painting'(Artist, Title);
+    end Create;
+
+    function May_Have_Been_Stolen (Item : Masterpiece) return Boolean is
+       function Reported_Stolen (Artist, Title : String) return Boolean is
+       begin
+          return False; -- Check public data bases
+       end Reported_Stolen;
+       use type Sellable_Art.Dollars;
+    begin
+       if Reported_Stolen (Item.Artist, Item.Title) or Item.Selling_Price < Item.Appraised_Value * 0.5 then
+          return True;
+       else
+          return False;
+       end if;
+    end May_Have_Been_Stolen;
+
+    function Title (Item : Painting) return String is
+    begin
+       return Item.Work_Title;
+    end Title;
+
+end Art_Sale;
+
+generic
+    type Element_Type is private;
+    pragma Preelaborable_Initialization (Element_Type);
+    pragma May_Be_Partial (Element_Type);
+
+    type Element_Index_Type is range <>;
+
+    type Element_Array_Type is array (Element_Index_Type range <>) of Element_Type;
+    pragma May_Be_Partial (Element_Array_Type); -- Can be Implicitly declared?
+
+package Queues is
+    pragma Pure;
+
+    type Queue_Interface is limited interface;
+
+    --  Get and Put a single element from/to the queue
+    procedure Get (Container : in out Queue_Interface; Item : out Element_Type) is abstract;
+    procedure Put (Container  : in out Queue_Interface; Item : Element_Type) is abstract;
+
+    --  Get and Put multiple elements from/to the queue
+    procedure Get (Container : in out Queue_Interface;
+                         Item : out Element_Array_Type;
+                         Last : out Element_Index_Type) is abstract;
+
+    procedure Put (Container  : in out Queue_Interface; Item : Element_Array_Type) is abstract;
+
+    type Queue_Type (Capacity : Natural) is abstract new Queue_Interface with null record;
+
+    type Queue_Class_Access is access all Queue_Interface'Class;
+
+end Queues;
+
+generic
+package Queues.Bounded is
+
+    pragma Pure;
+
+    type Queue_Data (Capacity : Natural) is private;
+    pragma Preelaborable_Initialization (Queue_Data);
+
+    type Queue (Capacity : Natural) is new Queue_Type (Capacity) with
+       record
+          Data : Queue_Data (Capacity);
+       end record;
+
+    overriding procedure Get (Container : in out Queue; Item : out Element_Type);
+    overriding procedure Get (Container : in out Queue;
+                                        Item : out Element_Array_Type;
+                                        Last : out Element_Index_Type);
+
+    overriding procedure Put (Container : in out Queue; Item : Element_Type);
+    overriding procedure Put (Container : in out Queue; Item : Element_Array_Type);
+
+private
+
+    type Data_Array_Type is array (Natural range <>) of Element_Type;
+
+    type Queue_Data (Capacity : Natural)
+      is
+       record
+          Items      : Data_Array_Type (1 .. Capacity);
+          Read_Pos  : Natural := 1;
+          Write_Pos : Natural := 1;
+          Full : Boolean := False;
+       end record;
+
+end Queues.Bounded;
+
+****************************************************************
+
+From: Brad Moore
+Sent: Sunday, February 15, 2009  4:05 PM
+
+I have made significant changes to the proposal I have been working on for
+AI05-0074. Thanks to Randy for providing good feedback, I have had a pretty
+good email exchange with him on these ideas over that past month or so.
+
+Randy will probably be somewhat surprised however, as what I have ended up
+with has changed quite a bit since our last email exchange. My thoughts have
+evolved considerably since I started on this, but I think I am finally at a
+stable place and hopefully something worthy of consideration.
+
+To summarize the changes and where I am at now;
+
+1) I have done away with the need for a May_Be_Partial pragma with this
+   proposal
+2) There are no changes to the freezing rules, or the generic contract
+   model.
+3) There are no restrictions placed on the content of a generic package,
+   Though there are restrictions on the use of the instance until the
+   completion of the private instantiation.
+4) I still have the ability to defer actuals to the private part
+5) I have done away with a lot of other features that I had been toying
+   with.  (No derivations of partial untagged types, no private objects)
+6) I have also realized that there isn't sufficient need to be able to
+   instantiate generics with a type that has an incomplete view.
+   One workaround is to make the type a private type and use a
+   private_instantiation_declaration.
+
+    -- Private_Instantiation_Declaration eg. package Foo is private new
+       Ada.Containers.Doubly_Linked_Lists
+         (Element_Type => T, Others => Private);
+    --  "=" has been deferred to the private part
+
+However, actuals for formal types or formal packages must be explicitly
+specified and cannot be deferred. This eliminates cases that I found to be
+problematic.
+
+A private_instantiation_declaration declares two views of an instance.
+A partial view of an instance, and a full view of an instance.
+The partial view applies to the immediately enclosing declarative region,
+while the full view applies to outside program units, and is equivalent to
+the view provided by the generic_instantiation declaration in the private
+part, which is placed after the actuals have been defined.
+
+Semantically, a partial view of an instance is like a view of the text of
+the generic template, without having made substitutions of actuals for
+formals, and where the mappings from actuals to formals has not yet been
+resolved.
+
+In my travels, I have also ran into some problems with existing workarounds,
+which are addressed by this proposal, and I have captured these in the
+attachment.
+
+Looking forward to seeing everyone in Tallahassee
+
+[This was version /01 of the AI - ED.]
+
+****************************************************************
+
+From: Brad Moore
+Sent: Monday, February 16, 2009  10:33 PM
+
+Sorry, this is a minor update to the update. It corrects some typos and
+deletes some residual wording left over from an earlier version of the
+write up. I thought I had caught them all, but noticed today that I missed
+a few.
+
+[This was version /02 of the AI - ED.]
 
 ****************************************************************

Questions? Ask the ACAA Technical Agent