CVS difference for ai05s/ai05-0101-1.txt

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

--- ai05s/ai05-0101-1.txt	2008/05/29 03:31:19	1.1
+++ ai05s/ai05-0101-1.txt	2008/10/18 02:53:57	1.2
@@ -1,4 +1,4 @@
-!standard E.2.2(14/2)                                  08-05-28  AI05-0101-1/01
+!standard E.2.2(14/2)                                  08-09-24  AI05-0101-1/02
 !standard E.2.3(14/2)
 !class binding interpretation 08-05-28
 !status work item 08-05-28
@@ -10,8 +10,15 @@
 
 !summary
 
-The result type of a remote function must support external streaming.
+The result type of a remote function must either support external streaming
+or be a controlling access result type.
 
+A remote function that returns an access result type must have a controlling 
+access result. Such a function returns a value of a remote access-to-class-wide
+type if the function has any controlling operands. Otherwise, a function 
+without a controlling operand must return an access value that designates an 
+object of a non-remote access type (a local object).
+
 !question
 
 E.2.2(14/2) specifies restrictions applying to the types of non-controlling
@@ -29,10 +36,19 @@
 Change E.2.2(14/2) as follows (this wording includes the changes of AI05-0060-1):
 
 The primitive subprograms of the corresponding specific type shall only
-have access parameters if they are controlling formal parameters;
-each non-controlling formal parameter {and result subtype} shall support
+have access parameters if they are controlling formal parameters[;]{. The 
+primitive functions of the corresponding specific type shall only have an
+access result if it is a controlling access result. E}[e]ach non-controlling 
+formal parameter {and non-controlling result subtype} shall support
 external streaming (see 13.13.2); 
 
+Add a new bullet after E.2.2 (15):
+
+* A controlling access result value for a primitive function with any controlling
+  operands of the corresponding specific type shall either be explicitly converted
+  to a remote access-to-class-wide type or be part of a dispatching call where the
+  value designates a controlling operand of the call. 
+
 Change E.2.3(14/2) as follows:
 
 it shall not be, nor shall its visible part contain, a subprogram (or
@@ -40,22 +56,179 @@
 a parameter {or result} of a type that does not support external streaming
 (see 13.13.2).
 
+AARM Ramification: No anonymous access types support external streaming, so
+those are never allowed in RCI subprograms.
+
 [Editor's note: I intend to delete the access parameter portion above as
-it is redundant and including it complicates the wording for little value.
-If this is considered important, it should be mentioned in a user note, not
-in the normative wording.]
+it is redundant and including it complicates the wording for little value.]
 
 !discussion
 
-There is more discussion in the e-mail that I don't understand: in particular,
-I don't see how converting the result of a type that does not support streaming
-is supposed to work. If the function has a controlling access result, doing
-whatever is needed to make it work is the compiler's responsibility, and the
-result can be used in any way that an access parameter could have been used (I
-don't see any special restrictions on what can be passed as a controlling access
-parameter).
+Annex E provides adequate rules describing the restrictions for parameters
+of a remote call, but lacks clarity on describing the restrictions that 
+should be applied to the results of remote function calls. Generally, the
+same rules should apply, but there are cases that need special consideration.
+
+In the case of a non-controlling function result, the function result has to
+be streamed from a remote partition, so this should be clearly stated in the
+rules. However, E.2.2(14/2) and E.2.3 (14/2) only describe rules for parameters
+of remote subprogram calls; there is no mention of restrictions that apply to a
+remote function result type. 
+
+There is no reason why a non-controlling function result should be treated 
+differently than non-controlling parameters. That is, it only makes sense to 
+allow remote function calls that have a result type that supports external 
+streaming. This rules out non-controlling access result types since anonymous
+access types do not support external streaming.
+
+Special consideration needs to be given to functions that have a controlling
+access result however.
+
+E.4 (5) states that a remote subprogram call can be executed as “a dispatching
+call with a controlling operand designated by a value of a remote 
+access-to-class-wide type.”
+
+3.9.2 (2/2) states that “a controlling operand in a call on a dispatching 
+operation of a tagged type T is one whose corresponding formal parameter is of
+type T or is of an anonymous access type with designated type T”.
+
+If controlling anonymous access parameters of dispatching subprograms can be
+designated by a value of a remote access-to-class-wide type, it seems logical
+that a controlling access result of a dispatching function should be treated
+the same way; as a result type that can be designated by a value of a remote
+access-to-class-wide type. Indeed, there does not seem to be any other semantic
+meaning that could be applied to such an access result returned from a remote 
+function call. It surely must be a value of a remote access-to-class-wide type.
+
+However, 13.13.2 (52/2) states that “an anonymous access type does not support
+external streaming”, so if we are to allow streaming of a remote 
+access-to-class-wide type as a controlling access result, then special wording
+will need to be added to the RM to allow this, similar to the wording used to
+allow streaming of remote access-to-class-wide types for subprogram parameters.
+The wording should should add restrictions that ensure such a result is either
+explicitly converted to a remote access-to-class-wide type by the caller, or
+used as a controlling operand of another dispatching call to a remote subprogram.
+
+There is a further distinction that needs to be observed. E.4 (5) stated above
+that a dispatching function call with a controlling operand is a remote 
+subprogram call. A dispatching function call that does not have a controlling
+operand is not a remote subprogram call. The controlling access result returned
+by such a function should be treated as a value of a local anonymous access
+type. This is enforced by E.2.2 (15) which states “A value of a remote 
+access-to-class-wide type shall be explicitly converted only to another remote
+access-to-class-wide type” and by E.2.2(16/1) which states that “A value of a
+remote access-to-class-wide type shall be dereferenced (or implicitly converted
+to an anonymous access type) only as part of a dispatching call where the value
+designates a controlling operand of the call”. 
+
+These rules makes it impossible for a local function to obtain a value of a 
+remote access-to-class-wide type and return it to the caller, because it would
+have to be implictly converted from an access-to-class-wide type to an anonymous
+access-to-specific type of the controlling result, which is not allowed. For the
+same reason, these rules makes it impossible for a remote function to obtain a
+value of a remote access-to-class-wide type from another partition and return 
+that value to the caller.
+
+
+package P is
+   pragma Remote_Types;
+
+   type T is tagged limited private;
+
+   function Remote_Call (Controlling_Operand : access T) return access T;
+   function Local_Call return access T;
+
+private
+   type T is tagged limited null record;
+end P;
+
+with Distributed_P;
+
+package body P is
+
+   Foo : aliased T;
+
+   function Local_Call return access T is
+   begin
+--    return Distributed_P.Get_Foo;  -- illegal E.2.2 (16/1)
+      return Foo'Access;  -- OK
+   end Local_Call;
+
+   function Remote_Call (Controlling_Operand : access T) return access T is
+      pragma Unreferenced (Controlling_Operand);
+   begin
+      --  return Distributed_P.Get_Foo; -- illegal E.2.2 (16/1)
+      return Foo'Access; -- OK
+
+   end Remote_Call;
+
+end Foo_Pkg;
+
+with P;
+
+package Distributed_P is
+
+   pragma Remote_Call_Interface;
+
+   type T_Access is access all P.T'Class;
+
+   procedure Set_Foo (Item : T_Access);
+
+   function Get_Foo return T_Access;
+end Distributed_P;
+
+package body Distributed_P is
+
+   Remote_Foo : T_Access;
+
+   function Get_Foo return T_Access is
+   begin
+      return Remote_Foo;
+   end Get_Foo;
+
+   procedure Set_Foo (Item : T_Access) is
+   begin
+      Remote_Foo := Item;
+   end Set_Foo;
+
+end Distributed_P;
+
+with P;
+with Distributed_P;
+
+procedure Test_Function_Access_Return is
+   My_Foo : aliased P.T;
+
+   --  1) Function returns local RACW value that must be explicity converted
+   --     to a RACW
+   Remote : constant Distributed_P.T_Access  -- Legal Conversion? (Yes)
+     := Distributed_P.T_Access (P.Remote_Call (My_Foo'Access));
+
+begin
+
+   --  Send the local RACW off to some remote location
+   Distributed_P.Set_Foo (Remote);
+
+   declare
+      --  2) Function returns local access value that is optionally converted
+      --     to a RACW
+      Local : constant Distributed_P.T_Access
+        := Distributed_P.T_Access (P.Local_Call);
+
+      --  3) Same call as 2) but not converted to a RACW
+      Local2 : constant access P.T := P.Local_Call;
+
+      --  4) First call returns RACW that dispatches to same remote partition
+      --     returning a controlling access result from that partition that
+      --     must be explicitly converted to a RACW
+      Remote2 : constant Distributed_P.T_Access
+        := Distributed_P.T_Access
+          (P.Remote_Call (P.Remote_Call (Distributed_P.Get_Foo)));
+   begin
+      null;
+   end;
 
-So this AI may need work if I have missed something - Editor.
+end Test_Function_Access_Return;
 
 --!corrigendum E.2.2(14/2)
 

Questions? Ask the ACAA Technical Agent