CVS difference for ais/ai-00218.txt

Differences between 1.2 and version 1.3
Log of other versions for file ais/ai-00218.txt

--- ais/ai-00218.txt	1999/03/30 02:38:56	1.2
+++ ais/ai-00218.txt	1999/11/25 01:03:32	1.3
@@ -1,4 +1,4 @@
-!standard 8.3(9-13)                                   99-03-29  AI95-00218/02
+!standard 8.3(9-13)                                   99-11-24  AI95-00218/03
 !standard 6.1(1)
 !class amendment 99-03-23
 !status work item 99-03-23
@@ -9,7 +9,7 @@
 
 !summary
 
-In order to reduce problems with overriding of primitive operations, two
+In order to reduce problems with overriding of primitive operations, three
 pragmas are introduced.
 
 !problem
@@ -75,18 +75,19 @@
 
 The problem of accidental overloading rather than overriding can be eliminated
 if the Ada compiler knows when the programmer wishes to override a routine.
-Similarly, accidental overriding can be minimized if the Ada compiler knows that
-the programmer has declared all intentional overriding.
+Similarly, accidental overriding can be minimized if the Ada compiler knows
+that the programmer has declared all intentional overriding.
 
 Unfortunately, a complete solution to this problem will be incompatible with
-existing Ada 95 code. Therefore, we have to introduce an optional solution which
-applies only when the programmer asks for it.
+existing Ada 95 code. Therefore, we have to introduce an optional solution
+which applies only when the programmer asks for it.
 
-Thus, we introduce two new pragmas, Explicit_Overriding and Overrides.
-Explicit_Overriding is a configuration pragma which requires explicit marking
-of overriding subprograms. Pragma Overrides is used to mark subprograms that
-are overriding. Unmarked subprograms are new declarations, and may not override
-another routine.
+Thus, we introduce three new pragmas, Explicit_Overriding, Overrides, and
+Might_Override. Explicit_Overriding is a configuration pragma which requires
+explicit marking of overriding subprograms. Pragma Overrides is used to mark
+subprograms that are overriding. Pragma Might_Override marks subprograms which
+may or may not be overriding. Unmarked subprograms are new declarations,
+and may not override another routine.
 
 !wording
 
@@ -98,24 +99,39 @@
 
 The form of a pragma Overrides is as follows:
 
-pragma Overrides [(subprogram_name)];
+pragma Overrides [(designator)];
 
+The form of a pragma Might_Override is as follows:
+
+pragma Might_Override [(designator)];
+
 Add to 8.3 after paragraph 26:
 
 Pragma Explicit_Overriding is a configuration pragma.
 
-Pragma Overrides applies to the preceding subprogram_declaration. Pragma
-Overrides shall immediately follow the subprogram_declaration to which it
-applies, separated only by space_characters, format_effectors, and comments.
-The optional subprogram_name of a pragma Overrides shall be the same as the
-name of the subprogram_declaration to which it applies.
+Pragmas Overrides and Might_Override shall immediately follow (except
+for other pragmas) the declaration for a primitive operation. The optional
+designator of a pragma Overrides or Might_Override shall be the same as the
+designator of the operation which it follows. Only one of pragmas Overrides
+and Might_Override shall be given for a single primitive operation.
+
+A primitive operation to which pragma Overrides applies shall override another
+operation. This rule is not enforced at the compile time of a
+generic_declaration. In addition to the places where Legality Rules normally
+apply, this rule also applies in the private part of an instance of a generic
+unit.
 
-A subprogram_declaration to which pragma Overrides applies shall override the
-implicit declaration of a primitive subprogram.
-
 For a primitive subprogram inherited in a unit to which a pragma
 Explicit_Overriding applies, an overriding explicit declaration shall be
-a subprogram_declaration to which pragma Overrides applies.
+a subprogram to which pragma Overrides or Might_Override applies. This rule
+is not enforced at the compile time of a generic_declaration. In addition to
+the places where Legality Rules normally apply, this rule also applies in the
+private part of an instance of a generic unit.
+
+Note:
+The overriding required by these rules does not necessarily need to happen
+immediately at the declaration of a primitive operation. It could occur later
+because of a later implicit declaration in the declarative region (see 7.3.1).
 
 !example
 
@@ -141,6 +157,13 @@
 when no overriding subprograms are declared. This checking will prevent
 accidental overriding.
 
+We add the third pragma (Might_Override) so that we can handle generic units
+where we cannot tell for sure whether overriding occurs. For instance, a mix-in
+generic does not care whether its operations override existing ones (the user
+of the generic may care, but that cannot be specified as part of the generic).
+Therefore, we provide Might_Override as a "don't care" marker, so that projects
+can still use Explicit_Overriding even if such generics are included.
+
 Requiring the explicit declaration of overriding is used in some other
 programming languages, most notably Eiffel. They also have noticed this
 problem.
@@ -154,7 +177,7 @@
 We considered adding syntax rather than defining pragma Overrides. Syntax was
 determined to be too heavyweight a solution for an amendment. One idea
 considered using existing keywords was: subprogram_specification is not new;
-These ideas were not considered satisfactory; it was felt that proper systax
+These ideas were not considered satisfactory; it was felt that proper syntax
 would need a new reserved word "overriding" or "redefined". That is much too
 heavy to introduce at this time. A pragma solution also has
 the advantage that compilers can implement it, and users can use it, even
@@ -162,15 +185,131 @@
 pragmas, it will ignore them, and will accept any legal program (along with
 some that would be illegal if the pragmas were accepted).
 
-Pragma Overrides was defined in such a way that it can be treated almost as
-a part of the subprogram declaration. This eases the implementation, as a
-compiler can determine what kind of declaration it is processing before it
-starts doing so. (Without this rule, an implementation must postpone error
-messages until it reaches the next declaration. Since the next declaration
-could be almost anything, this would provide a distributed overhead.)
-In addition, it is important that this pragma is not accidentially
-separated from the subprogram declaration.
+The pragmas Overrides and Might_Override were defined so that they apply only
+to the immediately preceding subprogram. This is even true if a designator is
+given, which is different than most other Ada pragmas. This behavior is
+required for these pragmas, as it is very important that they do not
+automatically apply to all members of a set of overloaded operations with
+a single designator. For instance, consider a tagged type with a constructor
+routine called "Create". An extension of the type might define a new
+constructor (also named "Create") with additional parameters, as well
+as overriding the existing constructor (giving appropriate defaults for the
+new parameters). It is critical that these pragmas handle this case.
+The solution adopted is that the pragmas only apply to the operation which
+immediately precede them. This makes it important that these pragmas are not
+accidentally separated from the subprogram declaration. The optional
+designator in the pragma provides a means to ensure that this does not happen.
+
+This semantics means that the pragmas can be treated almost as a part of the
+subprogram declaration. This eases the implementation, as a compiler can
+determine what kind of declaration it is processing before it starts doing so.
+(Without this rule, an implementation must postpone error messages until it
+reaches the next declaration. Since the next declaration could be almost
+anything, this would provide a distributed overhead.)
+
+Implementing the checking of these pragmas takes some care, because an
+operation may become overriding at a later point (because of the rules of
+7.3.1(6)). A compiler always knows that such overriding will happen later,
+so this should not provide an implementation burden.
+
+An example of how this could happen:
+
+package P is
+    type T is tagged private;
+private
+    procedure Op (Y : T);
+end P;
+
+package P.C is
+    type NT is new T;
+    procedure Op (Y : NT);
+    pragma Overrides (Op); -- OK.
+    package Nested is
+        type NNT is new T;
+	procedure Op (Y : NNT); -- Illegal (Overrides or
+				-- Might_Override needs to be given)
+    end Nested;
+private
+    -- P.C.Op overrides P.Op here (P.Op is inherited here).
+end P.C;
+
+package body P.C is
+    package body Nested is
+	-- P.C.Nested.Op overrides P.Op here (P.Op is inherited here).
+    end Nested;
+end P.C;
+
+Another use for Might_Override exists in this example; it can be used
+here is avoid breaking the abstraction (privateness) of the original type P.
+
+The pragmas Overrides and Might_Override are not checked in a
+generic_declaration. We do this because the an operation may not override
+in the generic_definition, but be intended to override in an instance. We
+do not want to force the use of Might_Override in all generics; the checking
+can be useful.
+
+For instance:
+
+generic
+    type GT is tagged private;
+package Gen is
+    type DGT is new GT with private;
+    procedure Op (Z : DGT);
+    pragma Overrides (Op); -- OK.
+private
+    -- ...
+end Gen;
+
+If we enforced these pragmas in generic_declarations, we could not give
+Overrides in this generic, as Op does not override anything in the
+generic_declaration or formal part. However, this pragma can be useful, as
+it forces all actual types for GT to have an operation Op. For example,
+using the types from the preceding example:
+
+    package Inst1 is new Gen (P.C.NT); -- OK, P.C.Op is overridden by Gen.Op.
+    package Inst2 is new Gen (P.T); -- Illegal, P.Op is not visible in Inst2,
+                                    -- and does not override.
 
+
 !appendix
+
+!from Randy Brukardt 11-24-99
+
+Following are my notes on this AI from the Marlboro ARG meeting (Sept. 1999).
+All of these changes have been made to the AI.
+
+----
+
+Should Explicit_Overriding be a Restriction or Feature? (No, after much
+discussion)
+
+Why no syntax?  Syntax was ugly. New keyword is bad. New reserved word is bad.
+Existing keywords are ugly.
+
+The wording was revised to use "designator" and "primitive operation".
+
+A discussion about whether the optional designator should be included ended
+inconclusively.
+
+Add wording so rule is enforced only upon instantiation, and add
+"Might_Override" pragma allowing unknown overriding. (Generic mix-ins may or
+may not override, depending on the actual).
+
+Make sure the wording covers the following:
+
+package P is
+    type T is tagged private;
+private
+    procedure P (Y : T);
+end P;
+
+package P.C is
+    type NT is new T;
+    procedure P (Y : NT);
+    pragma Overrides (P);   -- Could use Might_Overrides here,
+			    -- so privateness is not broken.
+private
+    -- Overrides here P.
+end P.C;
 
 *************************************************************

Questions? Ask the ACAA Technical Agent