!standard 7.6(17.1/3) 11-01-20 AI05-0232-1/01 !class confirmation 11-01-20 !status work item 10-10-25 !status received 10-09-24 !priority Low !difficulty Easy !subject Hole in AI05-0067-1 !summary Whether a call is required to be built-in-place is a dynamic property of the object. !question Is the following call built-in-place? type Interface_Type is limited interface; Obj : Interface_Type'Class := Some_Function(...); where Some_Function is declared as returning Interface_Type'Class. Interface_Type'Class is not immutably limited, since a type derived from Interface_Type could be limited or nonlimited (AARM 7.5(8.c)). This would seem to mean that it's unspecified whether this function call is built in place, since the rule in 7.6(17.2) refers to the (full) type of the object, not to the type determined by the tag of the function result. But this doesn't seem desirable, since the function result *could* be of a limited type, and in that case we still want to have the result built in place, with no copying. Is a fix needed? (No.) !response The existing wording is correct. RM 7.6 states: When a function call or aggregate is used to initialize an object, the result of the function call or aggregate is an anonymous object, which is assigned into the newly-created object. For such an assignment, the anonymous object might be built in place. Under certain circumstances, the anonymous object is required to be built in place, in which case the assignment does not involve any copying. In particular: If the full type of any part of the object is immutably limited, the anonymous object is built in place. ... One part of any object is the object itself, so this rule implies that build-in-place is required if the full type of the object is immutably limited. But because this wording is under "Dynamic Semantics", 3.1(7/3) does not apply and thus views are not involved here. For a given part, this wording refers to the specific nonabstract type of the part. Also note that parts other than the object itself cannot be class-wide (as indefinite components are not allowed); thus there always is a specific type. In the case that the object itself has a class-wide type (as opposed to a specific tagged type), this wording refers to the type identified by the tag of the part. [One could imagine that we ought to have a "To Be Honest" note to cover this unlikely case - although if we do that, we need to classify this as a ramification - Randy.] This is what distinguishes this situation from the related question addressed in AI05-0099-1, where explicit wording changes such as "If the full type of the object is a tagged type, and the tag of the object identifies a controlled type.", were needed. [Not quite sure I buy this; that wording originally seemed to imply a compile-time determination of the type -- it said "is of", not just "is" -- while this wording is clearly runtime. Even so, this seems to be a horribly weak argument. We decided in AI05-0099-1 that there is no implicit "dynamic type" for an object, so to assume one here is uncomfortable. It would be better to bite the bullet and add explicit words like the above to the 7.6(17.1/3) rule. - Randy.] In the case of a function returning Some_Limited_Interface_Type'Class, build-in-place is required if and only if the specific nonabstract type of the function result is immutably limited. This means that for two different elaborations of the object declaration given in the question, one call to Some_Function might require build-in-place while the other might not. !ACATS Test !appendix !topic Possible hole in AI05-0067? !reference 7.6(17.1/3-17.4/3) !from Adam Beneschan 10-09-24 !discussion I've just now found a reason to look over the new build-in-place rules, and I've run into something that may be an important omission. The new rules say that, for a function call used to initialize an object, the function call must be built in place if the object's type is immutably limited, but it's unspecified whether it's built in place in other cases. What happens in this case? type Interface_Type is limited interface; Obj : Interface_Type'Class := Some_Function(...); where Some_Function is declared as returning Interface_Type'Class. Interface_Type'Class is not immutably limited, since a type derived from Interface_Type could be limited or nonlimited (AARM 7.5(8.c)). This would seem to mean that it's unspecified whether this function call is built in place, since the rule in 7.6(17.2) refers to the (full) type of the object, not to the type determined by the tag of the function result. But this doesn't seem desirable, since the function result *could* be of a limited type, and I'd think that in this case we still want to have the result built in place, with no copying. Should 7.6(17.1-17.4) be modified to require build in place when an object type is the 'Class of a limited interface type? I don't think this would be harmful in cases where the function result is actually a nonlimited type (see the last sentence of AARM 7.6(17.o)), but maybe there are cases where it would be a problem. (An alternative would be to require implementations to build the result in place if the function result's tag identifies a limited type, and let them choose if it identifies a nonlimited type. But from my point of view, in our implementation, generating code to decide this at runtime isn't feasible.) ****************************************************************