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

Differences between 1.6 and version 1.7
Log of other versions for file ai05s/ai05-0123-1.txt

--- ai05s/ai05-0123-1.txt	2009/02/15 07:58:28	1.6
+++ ai05s/ai05-0123-1.txt	2009/03/21 03:43:37	1.7
@@ -1,4 +1,4 @@
-!standard  4.5.2(10-26)                                        08-11-17    AI05-0123-1/03
+!standard  4.5.2(10-26)                                        09-03-20    AI05-0123-1/04
 !class Amendment 08-10-17
 !status work item 08-10-17
 !status received 08-09-03
@@ -8,8 +8,6 @@
 
 !summary
 
-!summary
-
 Primitive "=" ops for tagged and untagged records compose alike .
 
 !problem
@@ -81,8 +79,8 @@
       a generic actual corresponding to a formal private or formal
       derived type (except in the case of a formal derived type which
       also has an abstract "=" operator).
-   2) A user-defined primitive "=" operator for an untagged record
-      type may not be declared after the freezing point of the type,
+   2) A user-defined primitive "=" operator for an untagged record type
+      may not be declared after the freezing point of the type,
       nor may it be declared in the private part of a package
       spec if (a full or partial view of) the record type is declared
       in the visible part.
@@ -107,12 +105,302 @@
 
 !wording
 
-** TBD **
+Append after 4.5.2(9) (i.e., at the end of the Static Semantics section)
+
+  The predefined equality operator for a nonlimited composite type
+  is abstract if any one of the type's noninherited component types
+  is a record or private type (tagged or untagged) whose primitive
+  equality operator is abstract or an array type whose predefined equality
+  operator is abstract. In the case of a nonabstract tagged type,
+  this abstract operator requires overriding.
+
+
+Move the Legality Rules section from just ahead of the Static Semantics
+section to just after and then append at the end of the Legality
+Rules section:
+
+  If the predefined equality operator for an array type
+  is abstract, or if the primitive equality operator for an untagged
+  record or untagged private type is abstract, then:
+    - the type shall not be used as a component type of an enclosing
+      type which is neither tagged nor immutably limited (see 7.5);
+    - the type shall not be passed as actual parameter to an
+      instantiation if the corresponding formal type is nonlimited
+    - the type shall not be passed as actual parameter to an
+      instantiation if the corresponding formal type is a
+      formal derived type which is not immutably limited;
+    - the type shall not be the completion of a nonlimited partial view. 
+
+  The explicit declaration of a primitive equality operator of an
+  untagged record type shall occur before the type is frozen.
+  If the untagged record type has a nonlimited partial view, then the
+  declaration shall occur in the visible part of the enclosing package.
+
+  AARM Note:
+  The phrase "equality operator" as used here refers only to a
+  function whose profile is type conformant with that of the
+  predefined equality operator for the untagged record type.
+  End AARM Note.
+
+  In addition to the places where Legality Rules normally apply (see 12.3),
+  these rules apply also in the private part of an instance of a generic unit.
+
+
+
+In 4.5.2(14), replace
+
+  For a type extension, predefined equality is defined in terms of the
+  primitive [(possibly user-defined)] equals operator of the parent type
+  and of any tagged components of the extension part, and predefined
+  equality for any other components not inherited from the parent type. 
+
+with
+
+  For a type extension, predefined equality is defined in terms of the
+  primitive [(possibly user-defined)] equals operator of the parent type
+  and of any record components (tagged or untagged) of the extension part,
+  and predefined equality for any other components not inherited from the
+  parent type. 
+
+
+In 4.5.2(15), replace 
+
+  For a private type, if its full type is tagged, predefined equality is
+  defined in terms of the primitive equals operator of the full type; if the
+  full type is untagged, predefined equality for the private type is that of
+  its full type.
+
+with
+
+  For a private type, if its full type is a record type (tagged or untagged),
+  predefined equality is defined in terms of the primitive equals operator
+  of the full type; otherwise, predefined equality for the private type is
+  that of its full type.
+
+
+In 4.5.2(24), replace
+
+  Otherwise, the result is defined in terms of the primitive equals operator
+  for any matching tagged components, and the predefined equals for any
+  matching untagged components. 
+
+with
+
+  Otherwise, the result is defined in terms of the primitive equals operator
+  for any matching record components (tagged or untagged), and the predefined
+  equals for any other matching components.
+
+
+In 32.a.1/1, replace
+  "then either the full type must be tagged"
+with
+  "then either the full type must be a record type" .
+
+
+Append after 8.5.4(7.1/1)
+
+  A corresponding rule applies to a call on a renaming of
+  a predefined equality operator for an untagged record type 
+  that is overridden if the overriding occurs after the renaming.
+
    
 !discussion
 
-** TBD **
+Is the cure worse than the disease?
+Should this whole AI should be abandoned?
+This is the most important question about the AI. Note that the cost of this
+AI is incurred in several areas - the RM becomes more complex,
+implementations becomes more complex, an inconsistency between
+the treatment of records and arrays is introduced,
+and some (hopefully unimportant) incompatibilities are introduced.
+
+----
+
+An array type may end up with an abstract predefined "=" operator
+(and "/=" operator, for that matter) if the element type has
+this property. Such an array type must not be passed as an actual
+to a generic with a formal array type which expects non-abstract
+equality operators. This was not previously discussed in the AI.
+
+----
+
+The restriction on the use of abstract-"=" types as components
+stems from a desire to avoid scenarios such as the following:
+  package Pkg is
+    type Rec is null record;
+    function "=" (L, R) return Boolean is abstract;
+
+    type Drec is new Rec; -- inherits abstract "="
+
+    type Vec is array (Boolean) of Drec;
+
+    function "=" (L, R : Drec) return Boolean;
+  end Pkg;
+
+Would Vec's "=" operator begin life as an abstract subprogram and then
+be transformed when the "=" operator for Drec is encountered?
+Let's just avoid the problem.
+
+--------
+
+The same keep-it-simple logic applies to the idea of relaxing
+the instantiation restrictions in the case where the formal
+type has an abstract "=" operator.
 
+It does seem a bit odd to disallow
+
+    type T is ... ; -- untagged, nonlimited, has abstract "=" operator
+
+    generic
+        type D is new T;
+    package G is ... ; end G;
+
+    package I is new G (T);
+
+So, we could include the exemption that is already discussed
+in the AI for a formal derived type which has an abstract "="
+operator. It's only the camel's nose, right?
+What about a formal array type which has an abstract "="
+operator (because its element type does)? Ok, just the nose
+and the muzzle.
+
+We should do enough to make this corner case (i.e., the use
+of untagged abstract-equality-op types) well-defined; there is no
+justification for adding complexity beyond that.
+
+-------
+
+What about this one?
+
+    package P is
+      type T is limited private;
+      package Inner is
+        type Rec is record X : T; end record;
+      end Inner;
+    private
+      function "=" (L, R : T) return Boolean is abstract;
+      type T is null record;
+    end P;
+
+    package body P is
+      package body Inner is
+        X, Y : Rec;
+        Flag : Boolean := X = Y;
+      end Inner;
+    end P;
+
+We want to reject this example, but it's not clear what
+rule needs to be invented to handle this case.
+
+Perhaps a dynamic semantics rule to the effect that "if this
+rule would result in calling an abstract function, then
+do it the old way instead". If we are going to add such a
+rule, then perhaps we could get rid of the conservative
+static checks on instantiations.
+
+It seems that this approach is worth considering, particularly
+because we do have to do something with this example.
+
+Note that if the word "nonlimited" were deleted from
+
+  If the untagged record type has a nonlimited partial view, then the
+  declaration shall occur in the visible part of the enclosing package.
+
+, then the example could be modified by moving the function
+declaration from the beginning of the private part to the end
+of the visible part (swapping the order of two lines). Thus, that
+wouldn't solve the problem.
+
+----
+
+The need for the "immutably limited" business with formal
+derived types is illustrated by the following example:
+
+  package Pkg is
+    type T1 is limited private;
+
+    generic
+      type D is new T1; -- not immutably limited
+    package G is
+    end G;
+  private
+    type T1 is null record;
+  end Pkg;
+
+  package body Pkg is
+    package body G is
+      X, Y : D;
+      Eq : Boolean := X = Y;
+    end G;
+  end Pkg;
+
+  with Pkg;
+  pragma Elaborate (Pkg);
+  package Client is
+    type T2 is new Pkg.T1;
+    function "=" (L, R : T2) return Boolean is abstract;
+    packge I is new Pkg.G (T2);
+  end Client;
+
+----
+
+The proposed wording in 8.5.4 uses "A corresponding rule", even though
+existing wording in 7.3.1(4/1) uses "The corresponding rule".
+Should the two agree? If so, then should 7.3.1 be changed?
+
+-----
+
+Is the treatment of "/=" correct in this AI?
+It would be good to review the wording with
+this in mind. The RM seems a little murky with
+respect to the status of "/=" in the case of
+an abstract "=" operator; perhaps I'm just confused.
+
+--------
+
+This would add the 25th occurrence in the
+RM of the famous "In addition to the places where
+Legality Rules normally apply ..." boilerplate.
+
+The need for an AI which would make that the default
+rule and explicitly enumerate the exceptions in the
+opposite direction (e.g., no homograph collisions in
+a declarative region) slowly builds.
+
+---------
+
+The decision to treat arrays and records inconsistently
+may have been a mistake.
+
+It seems odd that replacing
+
+  type Foo is array (Positive range <>) of Element;
+  function "=" (L, R : Foo) return Boolean;
+
+with
+
+  type Foo_Implementation is array (Positive range <>) of Element;
+  type Foo (Last : Natural) is
+    record
+      Elements : Foo_Implementation (1 .. Last);
+    end record;
+  function "=" (L, R : Foo) return Boolean;
+
+could cause a program to start behaving differently in mysterious ways.
+
+The argument was made that we don't want to introduce an
+inconsistency in the behavior of "=" and, for example, "<=" for
+a discrete array type. This makes no sense. Nobody is
+talking about changing the behavior of a composite type's
+equality op if someone adds/deletes a user-defined equality op for
+an *elementary* component type. A function whose behavior might
+be affected by this decision would be the predefined equality operator for
+some type which includes this array type as a component type.
+
+As the !wording section illustrates, the inconsistent treatment of
+records and arrays also cannot be justified on the grounds that it
+somehow simplifies the definition.
+
 !example
 
 ** TBD **
@@ -1883,22 +2171,81 @@
 
 ****************************************************************
 
-From: Randy Brukardt
-Sent: Tuesday, December 9, 2008  8:24 PM
+From: Steve Baird
+Sent: Friday, March 20, 2009  7:40 PM
 
-****************************************************************
+In Thursday's conference call, it was decided that I should attempt wording for AI05-0123.
 
-From: Randy Brukardt
-Sent: Tuesday, December 9, 2008  8:24 PM
+The result of that decision is attached. [This is version /04 of the
+AI - ED]
 
 ****************************************************************
 
 From: Randy Brukardt
-Sent: Tuesday, December 9, 2008  8:24 PM
+Sent: Friday, March 20, 2009  xx:xx PM
 
-****************************************************************
+>formatting error (wrong font, bad indentation) for
+>#2 in the "These cases are dealt with as follows" list, starting with 
+>"type may not be declared".
 
-From: Randy Brukardt
-Sent: Tuesday, December 9, 2008  8:24 PM
+Well, the formatting of the on-line viewer isn't technically part of an AI,
+but I suppose it doesn't hurt to fix it.
+
+The formatter has to guess on the fly if a line represents code, generally
+by looking at the first couple of words/symbols. If it guesses wrong, well,
+you get some ugly output. The guessing assumes that code is indented, and then
+checks whether lines start with something that looks like code. That means that
+indented lines in AIs ought not start with words that are Ada reserved words
+that start a declaration or statement: "procedure", "function", "type", etc.
+In this case, the second line starts with "type", and thus the formatter screws
+up. All that needs to be done is to move "type" to the previous line, and all
+is well.
+
+>!discussion (not intended to replace the existing !discussion section)
+
+Well, since the existing one consists solely of "**TBD**", I think we can safely
+replace it. ;-)
+
+[Now to actually read your AI...]
+
+>What about this one?
+>
+>    package P is
+>      type T is limited private;
+>      package Inner is
+>        type Rec is record X : T; end record;
+>      end Inner;
+>    private
+>      function "=" (L, R : T) return Boolean is abstract;
+>      type T is null record;
+>    end P;
+>
+>    package body P is
+>      package body Inner is
+>        X, Y : Rec;
+>        Flag : Boolean := X = Y;
+>      end Inner;
+>    end P;
+>
+>We want to reject this example, but it's not clear what rule needs to 
+>be invented to handle this case.
+
+Shouldn't we simply make the declaration of "=" illegal by analog with
+3.9.3(10)? That's what's done for tagged types, and I can't quite imagine
+why this ought to be a hidden property. That might make something or other
+impossible, but what is the point of trying to figure this one out??
+
+If the declaration is in the visible part, the abstract "=" is a visible
+property, so Rec "clearly" has an abstract "=".
+
+---
+
+As to the question of arrays, I'm not sure. It doesn't look like it would
+simplify the wording any to extend this to all composite types. (I doubt it
+would make it longer, but I don't see any simplifications, either.)
+
+I think your argument boils down to "anyone that redefines "=" without redefining
+"<=" compatibly is nuts, so we don't care what happens to them".
+Maybe that's OK.
 
 ****************************************************************

Questions? Ask the ACAA Technical Agent