10.1.2 Context Clauses - With Clauses
Syntax
limited_with_clause ::= limited [
private]
with library_unit_name {,
library_unit_name};
nonlimited_with_clause ::= [
private]
with library_unit_name {,
library_unit_name};
Name Resolution Rules
Outside its own declarative region, the declaration
or renaming of a library unit can be visible only within the scope of
a
with_clause
that mentions it. The visibility of the declaration or renaming of a
library unit otherwise follows from its placement in the environment.
Legality Rules
the declaration, body, or subunit of a private
descendant of that library unit;
the body or subunit of a public descendant of that
library unit, but not a subprogram body acting as a subprogram declaration
(see
10.1.4); or
the declaration of a public descendant of that
library unit, in which case the
with_clause
shall include the reserved word
private.
A
name
denoting a library item that is visible only due to being mentioned in
one or more
with_clauses
that include the reserved word
private shall appear only within:
a private part;
a private descendant of the unit on which one of
these
with_clauses
appear; or
a pragma within a context clause.
A
library_item
mentioned in a
limited_with_clause
shall be the implicit declaration of the limited view of a library package,
not the declaration of a subprogram, generic unit, generic instance,
or a renaming.
in the
context_clause
for the explicit declaration of the named library package;
in the same
context_clause
as, or within the scope of, a
use_clause
that names an entity declared within the declarative region of the library
package.
3 A
library_item
mentioned in a
nonlimited_with_clause
of a compilation unit is visible within the compilation unit and hence
acts just like an ordinary declaration. Thus, within a compilation unit
that mentions its declaration, the name of a library package can be given
in
use_clauses
and can be used to form expanded names, a library subprogram can be called,
and instances of a generic library unit can be declared. If a child of
a parent generic package is mentioned in a
nonlimited_with_clause,
then the corresponding declaration nested within each visible instance
is visible within the compilation unit. Similarly, a
library_item
mentioned in a
limited_with_clause
of a compilation unit is visible within the compilation unit and thus
can be used to form expanded names.
Examples
package Office is
end Office;
with Ada.Strings.Unbounded;
package Office.Locations is
type Location is new Ada.Strings.Unbounded.Unbounded_String;
end Office.Locations;
limited with Office.Departments; -- types are incomplete
private with Office.Locations; -- only visible in private part
package Office.Employees is
type Employee is private;
function Dept_Of(Emp : Employee) return access Departments.Department;
procedure Assign_Dept(Emp : in out Employee;
Dept : access Departments.Department);
...
private
type Employee is
record
Dept : access Departments.Department;
Loc : Locations.Location;
...
end record;
end Office.Employees;
limited with Office.Employees;
package Office.Departments is
type Department is private;
function Manager_Of(Dept : Department) return access Employees.Employee;
procedure Assign_Manager(Dept : in out Department;
Mgr : access Employees.Employee);
...
end Office.Departments;
The
limited_with_clause
may be used to support mutually dependent abstractions that are split
across multiple packages. In this case, an employee is assigned to a
department, and a department has a manager who is an employee. If a
with_clause
with the reserved word
private appears on one library unit and
mentions a second library unit, it provides visibility to the second
library unit, but restricts that visibility to the private part and body
of the first unit. The compiler checks that no use is made of the second
unit in the visible part of the first unit.