!standard 7.5(5/2) 08-04-18 AI05-0087-1/03 !standard 12.5.1(5.1/2) !class binding interpretation 08-01-30 !status ARG Approved 8-0-1 08-02-10 !status work item 08-01-30 !status received 08-01-23 !priority Low !difficulty Medium !qualifier Omission !subject Formal nonlimited derived types should not have limited actual types !summary Formal nonlimited derived types should not have limited actual types. A class-wide type is limited if its specific type is limited. !question It appears that we can use formal derived types derived from a limited interface to copy tasks and other limited objects. Consider: declare type Ifc is limited interface; generic type T is abstract new Ifc with private; -- T is nonlimited: 7.5(6.1/2) procedure Classwide_Store (Target : out T'Class; Source : T'Class); procedure Classwide_Store (Target : out T'Class; Source : T'Class) is begin Target := Source; end Classwide_Store; procedure Store is new Classwide_Store (Ifc); -- legal? (No.) task type Tsk; task body Tsk is begin null; end Tsk; type Has_Task is limited new Ifc with record F : Tsk; end record; X, Y : Has_Task; begin Store (X, Y); end; Is the instantiation legal? (No.) 7.5(3-7) seems to imply that most class-wide types are nonlimited, even if the specific type is limited. That is a change from Ada 95; was this intended? (No.) !recommendation (See Summary.) !wording Replace the deleted paragraph 7.5(5/2) with: * a class-wide type whose specific type is limited; Change 12.5.1(5.1/2) as follows: The actual type for a formal derived type shall be a descendant of the ancestor type and every progenitor of the formal type. {If the formal type is nonlimited, the actual type shall be nonlimited.} If the reserved word synchronized appears in the declaration of the formal derived type, the actual type shall be a synchronized tagged type. AARM Discussion: A type derived from a limited interface could be nonlimited; we do not want a limited type derived from such an interface to match a nonlimited formal derived type. (Otherwise, we could assign limited objects.) !discussion There was no intent that the class-wide type associated with a limited specific type be nonlimited; that would open up ways to assign tasks and the like. So we add explicit wording clarifying that class-wide types are limited if their specific type is. We certainly don't want the example in the question to be legal, so we must add wording to prevent that. !corrigendum 7.5(4/2) @dinsa @xbullet, @b, @b, or @b in its definition; @dinst @xbullet !corrigendum 12.5.1(5.1/2) @drepl The actual type for a formal derived type shall be a descendant of the ancestor type and every progenitor of the formal type. If the reserved word @b appears in the declaration of the formal derived type, the actual type shall be a synchronized tagged type. @dby The actual type for a formal derived type shall be a descendant of the ancestor type and every progenitor of the formal type. If the formal type is nonlimited, the actual type shall be nonlimited. If the reserved word @b appears in the declaration of the formal derived type, the actual type shall be a synchronized tagged type. !ACATS Test A B-Test like the example in the question should be tried. !appendix From: Stephen W. Baird Sent: Wednesday, January 23, 2008 5:43 PM We don't want to allow a limited type to be specified as the actual parameter corresponding to a nonlimited formal type in an instantiation. There may be a hole in this area in the case of a formal type which is derived from a limited interface type. I didn't find RM wording to justify rejecting the following example: declare type Ifc is limited interface; generic type T is abstract new Ifc with private; -- T is nonlimited: 7.5(6.1/2) procedure Classwide_Store (Target : out T'Class; Source : T'Class); procedure Classwide_Store (Target : out T'Class; Source : T'Class) is begin Target := Source; end Classwide_Store; procedure Store is new Classwide_Store (Ifc); -- legal? task type Tsk; task body Tsk is begin null; end Tsk; type Has_Task is new Ifc with record F : Tsk; end record; X, Y : Has_Task; begin Store (X, Y); end; I also didn't find the general rule (whose existence I had always assumed) that a class-wide type is limited iff the corresponding specific type is limited. An unfriendly reading of 7.5 could suggest that if a specific limited type has no limited components, then the corresponding class-wide type is not limited. Is this just an oversight, or am I missing something? **************************************************************** From: Tucker Taft Sent: Wednesday, January 23, 2008 7:32 PM Good point. RM 12.5.1(5.1/2) should probably be revised roughly as follows: The actual type for a formal derived type shall be a descendant of the ancestor type and every progenitor of the formal type. {If the formal type is nonlimited, the actual type shall be nonlimited.} If the reserved word synchronized appears in the declaration of the formal derived type, the actual type shall be a synchronized tagged type. > ... > I also didn't find the general rule (whose existence I had always assumed) > that a class-wide type is limited iff the corresponding specific type is limited. > An unfriendly reading of 7.5 could suggest that if a specific limited type has no > limited components, then the corresponding class-wide type is not limited. > Is this just an oversight, or am I missing something? Another good point. 7.5(3) used to say "a descendant of ..." but that was deleted for Ada 2005. It turns out that classwide types are descendants of their root type, and that is how they were covered. Having deleted that phrase, we need to add back an explicit mention of classwide types. Hence, a bullet at the end is needed, saying something like: * a class-wide type whose associated specific type is limited. (plus the usual replacement of the preceding bullet's "." with a ";") ****************************************************************