CVS difference for ais/ai-00173.txt

Differences between 1.4 and version 1.5
Log of other versions for file ais/ai-00173.txt

--- ais/ai-00173.txt	2001/01/29 23:33:41	1.4
+++ ais/ai-00173.txt	2003/08/02 04:51:34	1.5
@@ -1,4 +1,4 @@
-!standard 13.03    (16)                               01-01-29  AI95-00173/01
+!standard 13.03    (16)                               03-08-01  AI95-00173/01
 !class binding interpretation 96-11-16
 !status work item 98-03-17
 !status received 96-11-16
@@ -6,7 +6,7 @@
 !difficulty Hard
 !subject Optimizations and the use of 'Address
 
-!summary 98-03-17
+!summary
 
 Suppose an execution accesses the same storage twice, at least one of the
 accesses modifies the storage, and at least one of the accesses is based on an
@@ -20,7 +20,7 @@
     address specified by an address clause; and both objects are of the same
     type.
 
-!question 98-03-17
+!question
 
 Common optimization techniques, applied to source code that makes
 undisciplined use of 'Address, can result in object code with surprising
@@ -28,7 +28,7 @@
 effects resulting from examining or modifying variables through their
 addresses?
 
-!response 98-03-17
+!response
 
 An access to an object is "based on an address value" if either of the
 following holds:
@@ -51,7 +51,7 @@
     address specified by an address clause; and both objects are of the same
     type.
 
-!discussion 98-03-17
+!discussion
 
 A naive approach would be to allow only optimizations valid in the presence of
 arbitrary aliasing.  This approach is impractical because the possibility of
@@ -151,9 +151,9 @@
 Address work in other cases," and this is nearly true.  However, 13.3(19) adds
 the following condition to the recommended level of support:
 
-         If the address of an object is specified, or it is imported
-or                   exported, then the implementation should not perform
-optimizations          based on assumptions of no aliases.
+         If the address of an object is specified, or it is imported or
+	 exported, then the implementation should not perform optimizations
+	 based on assumptions of no aliases.
 
 Thus this interpretation restricts optimizations only in cases where the
 Standard guarantees the existence of a "useful" address, and in the case of
@@ -198,7 +198,7 @@
 conversions that makes this interpretation a binding interpretation.
 Otherwise, it would be a ramification of the rules in the Standard.)
 
-!appendix 96-11-16
+!appendix
 
 !section 13.3(16)
 !subject Optimizations and the use of 'Address
@@ -811,3 +811,1116 @@
 The priority of this AI was changed based on ARG discussion in November 2000.
 
 ****************************************************************
+
+From: Robert Dewar
+Sent: Wednesday, July 16, 2003  10:36 AM
+
+The RM says
+
+   19  If the Address of an object is specified, or it is imported or
+       exported, then the implementation should not perform optimiza-
+       tions based on assumptions of no aliases.
+
+Now for sure this does not mean what it says (which is that the compiler must
+stop ALL optimization based on aliasing EVERYWHERE in the generated code if
+a SINGLE address clause is used).
+
+So it means something about assumptions for this particular variable. What
+exactly is not allowed (we sort of know intuitively if we are compiler
+writers, but it is far from clear semantically, and in this case friendly
+reading is not really sufficient).
+
+What about
+
+    A : Integer;
+    B : Integer;
+    for B'Address use A'Address;
+
+Well it sure seems like we want to stop optimization in both directions,
+but the RM statement probably only affects code generation for references
+to B and not for A.
+
+In GNAT we make A and B implicitly volatile in the above situation (for
+code generation purposes, not for legality purposes, which raises issues
+of lack of protection when passing parameters etc -- the kind of protection
+that officially volatile objects are provided).
+
+Actually the sequence above is not required to be accepted, instead we
+need to write
+
+   A : Integer;
+   A_Address : constant Address := A'Address;
+   B : Integer;
+   for B'Address use A_Address;
+
+Well now it's getting a bit harder to fish out the fact that we should not
+have any optimization on A. GNAT goes this far, but obviously the overlay
+can be "disguised" further than this in a manner we would not detect (e.g.
+by using many different constants defined in terms of one another).
+
+****************************************************************
+
+From: Tucker Taft
+Sent: Wednesday, July 16, 2003  11:28 AM
+
+Aliasing is generally symmetric (though not
+transitive).  That is, if B is potentially aliased
+with A, then A is potentially aliased with B.
+
+So I think a reasonable reading is that when
+the address for B is specified by an expression
+or imported, then the compiler should not assume
+it is an "independent" variable, and in fact might
+be aliased with other things.  Now which other things?
+I suppose anything whose address it might share.  By
+default, that would mean everything whose address was
+taken or which was exported or whose 'Access might
+have been converted to Address.
+
+I agree that some clarification is in order, in any case.
+I can see that just making B volatile by itself would
+not solve the problem.  But if you are using a backend
+that handles C, this seems straightforward, since I presume
+that "under the covers" you are effectively declaring
+an implicit pointer-to-int object B__Addr, and defining
+B as equivalent to *B__Addr.  B__Addr is initialized with
+the expression given in the address clause.
+
+A typical C backend will survive that and will make an
+appropriate determination of what *B__Addr might
+be aliased with.
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Wednesday, July 16, 2003  12:05 PM
+
+The easiest way to say this precisely would be to say that it was implicitly
+volatile, but in fact this is a bit confusing because we would not require
+all the volatile rules to be met.
+
+Also, this seems to miss my point, which is whether you want to have
+constraints on A. In other words, if B is changed, should the compiler "see" a
+change in the value of A.
+
+Note that the use of address clauses to overlay two variables is in my
+experience one of the most common uses of address clauses, and is precisely
+the case in which the symmetrical treatment of aliasing for (suppression of)
+optimization purposes makes sense, so that is why it is perhaps worth
+addressing specially.
+
+****************************************************************
+
+From: Tucker Taft
+Sent: Wednesday, July 16, 2003  1:26 PM
+
+We often use address clauses in the run-time to effect a default
+initialization on some "raw storage" whose address is passed
+into a routine.  In this case, the aliasing is between two
+objects of potentially different types, one being effectively
+a storage array (properly aligned, hopefully), and the other
+some higher level Ada (usually record) type.
+
+I don't particularly like the implicitly volatile semantics; that
+seems more like an implementation approach.  The key thing
+is that at the semantic level, the address used in an address
+clause can be pretty much anything, and the compiler is supposed
+to do the "right thing."  If the compiler can track the address-value used
+in the address clause, and it "knows" where it points, then it need
+not treat the object as implicitly volatile, but rather can treat
+it more like a renaming.  If it does not know where the address
+"came from," then it has to make more pessimistic assumptions in
+terms of what it might be aliased with, but this never seems to
+go to the point of "volatility," though an implementation might
+choose that approach for pragmatic reasons.  But just making
+it volatile doesn't solve the problem, unless all possible objects
+whose address might have been used to produce the value used
+in the address clause are also marked volatile, which seems like
+a lot of distributed overhead for just having one variable with
+an address clause.
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Wednesday, July 16, 2003  2:41 PM
+
+I agree with this.
+
+But I am still concerned about the other way round issue.
+
+****************************************************************
+
+From: Erhard Ploedereder
+Sent: Wednesday, July 16, 2003  1:35 PM
+
+> Also, this seems to miss my point, which is whether you want to have
+> constraints on A. In other words, if B is changed, should the compiler "see"
+> a change in the value of A.
+
+In terms of a language rule, this would be very nasty. Since there are no
+restrictions on the nature of <expression> (there are only implementation
+permissions to restrict), the address clause can refer to
+pretty much anything with the consequence that most variables would have to
+be treated as potentially aliased in the vicinity of accesses to the
+address-spec'ed variable.
+
+I suspect that Tuck's implementation model under separate compilation has
+precisely this effect for all global variables, even if <expression> is
+static and "nice". (Yes, there is an argument of semantic closure making
+the info available -- from private parts, too ?? -- but how do I convince
+my code generator?)
+
+Unfortunately, current wording seems to imply that model.
+
+It is a pretty heavy price to pay for a capability that hopefully is
+almost never used (I mean overlay by means of address specs, so that
+the aliasing matters.)
+
+Parameter aliasing problems in general are considered bounded errors, RM
+6.2.(12). Why aliasing problems due to address or linkname overlay should be
+treated differently, is a bit beyond me.  (Well, I happen to believe that
+Ada83 was right for once -- in making overlays via address clauses
+erroneous, nowadays known as bounded error.)
+
+****************************************************************
+
+From: Erhard Ploedereder
+Sent: Wednesday, July 16, 2003  1:49 PM
+
+A small PS, so I am not being misunderstood...
+
+> almost never used (I mean overlay by means of address specs, so that
+> the aliasing matters.)
+
+The "never used" referred to the "aliasing matters".
+
+As in the parameter aliasing problem, "matters" means that you use
+alternate access paths for reading and writing, where both paths still
+exist and are being in use (so that the assumption of "no aliasing"
+would actually affect the results of the program).
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Wednesday, July 16, 2003  2:43 PM
+
+We have cases all the time where aliasing matters. Users have reported our
+failure to avoid optimization here in some marginal cases as bugs :-)
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Wednesday, July 16, 2003  2:48 PM
+
+> Parameter aliasing problems in general are considered bounded errors, RM
+> 6.2.(12). Why aliasing problems due to address or linkname overlay should be
+> treated differently, is a bit beyond me.  (Well, I happen to believe that
+> Ada83 was right for once -- in making overlays via address clauses
+> erroneous, nowadays known as bounded error.)
+
+I disagree, legacy code is full of the use of address clauses to achieve
+overlayh. Many programmers find it more convenient and natural than the
+use of unchecked conversion (Fortran COMMON and COBOL REDEFINES are of
+course precedents for this kind of usage).
+
+It is a bit silly for the official definition to ignore actual usage, so making
+it impl defined is definitely a step forward.
+
+The question is in the direct kind of case that I gave:
+
+   A : Integer;
+   B : Float;
+   for B'Address use A'Address;
+
+should the compiler understand that A and B are aliased? In other words, if
+one of them is assigned to, then the other one has changed.
+
+If a pedantic viewpoint leads to answering No, then you are simply creating
+a tension between the language definition and actual implementations (certainly
+we know from experience that once we started doing better aliasing analysis
+in teh transition from GCC 2 to GCC 3, several users complained about wrong
+results, and we have to go to quite a bit of effort to make things "work"
+again (yes you can explain to users that their code is wrong, but you only
+do this if you are really stuck :-)
+
+****************************************************************
+
+From: Randy Brukardt
+Sent: Wednesday, July 16, 2003  1:59 PM
+
+> What about
+>
+>     A : Integer;
+>     B : Integer;
+>     for B'Address use A'Address;
+>
+> Well it sure seems like we want to stop optimization in both directions,
+> but the RM statement probably only affects code generation for references
+> to B and not for A.
+
+My reading of the intent of 13.3(16) is that the use of 'Address on objects
+that aren't declared aliased (explicitly or implicitly) is not expected to
+work properly in the face of optimizations. So I would say that the intent
+of 13.3(19) is that it only applies to the object with the address clause
+(it implicitly gives it "aliased").
+
+So in the above case, there are no guarantees on A. If you had written
+instead:
+
+    A : aliased Integer;
+    B : Integer;
+    for B'Address use A'Address;
+
+Then clearly both A and B are aliased as far the optimizer is concerned.
+
+Now, I realize that this doesn't fit well with Ada 83 practice, but
+compilers are always allowed to go beyond the standard. And if they do,
+THEY, not the ARG, has to figure out what it means.
+
+This is an area I think Ada 95 got right, in that it allows limited
+overlaying of objects by address clauses, but only if both objects are
+appropriately declared (so the compiler has no surprises). And other
+overlays are not guaranteed to work. It's unfortunate that the Ada 83
+practice of not marking objects referenced by the 'Address attribute hasn't
+been discouraged more forcefully. (We're as guilty as any implementor here.)
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Wednesday, July 16, 2003  1:59 PM
+
+> Now, I realize that this doesn't fit well with Ada 83 practice, but
+> compilers are always allowed to go beyond the standard. And if they do,
+> THEY, not the ARG, has to figure out what it means.
+
+Not so fast. Implementation Advice is in the business of going "beyond the
+[normative] standard". Remember that this whole thread is about what 13.3(9)
+is trying to suggest!
+
+> It's unfortunate that the Ada 83
+> practice of not marking objects referenced by the 'Address attribute hasn't
+> been discouraged more forcefully. (We're as guilty as any implementor here.)
+
+Er, we are not in the business of forcefully discouraging our users, we are
+in the business of meeting their needs. Of course we will not go so far as
+to deliberately not conform to the standard, but short of that, user needs
+come ahead of language lawyer aesthetic opinions :-)
+
+****************************************************************
+
+From: Randy Brukardt
+Sent: Wednesday, July 16, 2003  8:14 PM
+
+But in the case the "user need" is to avoid typing "aliased". I can hardly
+find that to be a major problem; it's not like the fixed point operators
+(for instance), where the workaround is obnoxious. In this case, the
+workaround is trivial.
+
+I'm well aware the problem will still occur in legacy code, and that most of
+us will probably continue to support it in some way. But I think NEW code
+should be "encouraged" to be correct; probably with warnings on 'Address
+used on non-aliased objects and more documentation of the issues. And I
+certainly don't think the standard should get into 'inferring' aliasing as
+you suggest; it is much too hard to describe and implement. And given that
+13.3(19) is a REQUIREMENT for most implementations, I am strongly opposed to
+expanding it as you suggest. (Remember, this is "Recommended Level of
+Support, which is required by Annex C).
+
+I don't disagree that the wording is pretty vague, and clearly it should
+state that it only means for the object and it subcomponents that has the
+address clause. But that's as far as the language should go.
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Wednesday, July 16, 2003  9:21 PM
+
+I don't see this. Using the keyword aliased is not enough to say that something
+is aliased with something of some other type entirely. What's your point here?
+Aliased just deals with whether typed pointers to the object caqn be created.
+
+****************************************************************
+
+From: Randy Brukardt
+Sent: Wednesday, July 16, 2003  9:47 PM
+
+The point of 13.3(16) is that you cannot portably take 'Address of an object
+that is not declared to be aliased. And that 'Address must work sensibly on
+an object that is aliased. To me, at least, that means that optimization
+must take into account the possibility of overlaying with anything.
+
+Thus, a compiler cannot use type information to eliminate possible aliasing
+for an aliased object unless it can prove that no 'Address can be taken of
+the object (which of course also includes foreign language calls).
+
+We pretty much "turn off" optimization of aliased objects, and we certainly
+don't use type information for them. (Of course, that's partly because we
+only have very limited type information available in the optimizer in the
+first place.) If we had more type information, we'd use it only for locals,
+because only those could be proven to be safe.
+
+That's actually a lot more aggressive than our Ada 83 compiler; for that we
+assumed that all objects were aliased unless they were copy parameters or we
+could prove that they weren't aliased. (We tried more aggressive rules, but
+they always had problems with address clauses, and we ended up going back.)
+
+The converse point, of course, is that a compiler is allowed to do any
+assumption of non-aliasing that it pleases on an object that is none of:
+    by-reference type;
+    aliased;
+    or has an address clause or pragma Import.
+
+I think this is right, as it gives the proper balance of control and
+optimization. (It would be nice to have "degrees" of aliasedness, but it
+hardly seems worth the complication.)
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Wednesday, July 16, 2003 10:46 PM
+
+> The point of 13.3(16) is that you cannot portably take 'Address of an object
+> that is not declared to be aliased. And that 'Address must work sensibly on
+> an object that is aliased. To me, at least, that means that optimization
+> must take into account the possibility of overlaying with anything.
+
+If this is more than an unfounded opinion, please quote justification
+
+> Thus, a compiler cannot use type information to eliminate possible aliasing
+> for an aliased object unless it can prove that no 'Address can be taken of
+> the object (which of course also includes foreign language calls).
+
+Again, how do you figure this?
+
+> We pretty much "turn off" optimization of aliased object
+
+Well that's pretty pessimistic, perhaps this pessimistic view of alias analysis
+leads you to what I consider the above non-obvious viewpoints.
+
+These kind of undocumented, unsupportable "assumptions" make me think that it
+is definitely important for the IA in the RM to state what it means.
+
+****************************************************************
+
+From: Randy Brukardt
+Sent: Wednesday, July 16, 2003  11:18 PM
+
+It's a 'founded' opinion. :-) Optimization cannot change the meaning of a
+legal Ada program unless the standard gives a specific permission to do so.
+I see no such permission in terms of 'Address and optimizations in the
+standard, with the exception of unaliased objects. In particular, the
+erroneousness of overlaying was removed from Ada 95; thus it must work and
+optimization cannot 'break' it.
+
+Now it certainly is true that the AARM never says this, and perhaps the
+intent was different. But this is certainly the model I took away from the
+DR meetings where all of the implications of the model were discussed.
+
+If you think that some other rule is implied by the standard, then I think
+the onus is on you to point it out, not on me to prove that it doesn't
+exist! And if you want to propose some other rule, please feel free to do
+so -- now is the time.
+
+> > We pretty much "turn off" optimization of aliased object
+>
+> Well that's pretty pessimistic, perhaps this pessimistic view of alias
+> analysis leads you to what I consider the above non-obvious viewpoints.
+>
+> These kind of undocumented, unsupportable "assumptions" make me think that
+> it is definitely important for the IA in the RM to state what it means.
+
+My only assumption is that unless there is a language rule to the contrary,
+in the standard mode, a program should operate the same whether or not
+optimization is applied. I consider that the fundamental rule of
+optimization, and breaking it is almost never worth it (as you are finding
+out). While a few customers might find some (unlikely to be critical) extra
+performance, the vendor ends up with a lot of additional support headaches.
+
+The "assumption" that you ought to be able to do aggressive optimizations in
+the face of explicitly declared aliasing is the one that seems to be
+undocumented and unsupportable. Where is the language rule that allows that?
+
+Of course, I'm not aware of any Ada vendors that considers their optimizer
+to be part of the standard mode, so the whole question is irrelevant in
+practice. Vendors should do something that makes sense to their customers,
+because they will anyway.
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Thursday, July 17, 2003  5:39 AM
+
+What does work mean?>
+
+For example, in C if you use pointer conversion to point to two different
+types, that definitely does NOT "work" in the sense you mean according
+to the C standard.
+
+In the Ada standard, there simply is not enough detail to determine that
+unlike the case in C, you are guaranteed for things to "work". For one
+thing what "works" means is definitely implementation defined, it has
+to be in semantic terms.
+
+> Now it certainly is true that the AARM never says this, and perhaps the
+> intent was different. But this is certainly the model I took away from the
+> DR meetings where all of the implications of the model were discussed.
+
+Well what the AARM says has no force in any case, we are talking about teh
+ARM here, and really the above sentence is my whole point. If the ARM intends
+to say something useful here, it should say what it means. We cannot depend
+on what Randy has "taken away from DR meetings" to understand Ada :-)
+
+****************************************************************
+
+From: Randy Brukardt
+Sent: Thursday, July 17, 2003  11:07 AM
+
+> What does work mean?>
+>
+> For example, in C if you use pointer conversion to point to two different
+> types, that definitely does NOT "work" in the sense you mean according
+> to the C standard.
+>
+> In the Ada standard, there simply is not enough detail to determine that
+> unlike the case in C, you are guaranteed for things to "work". For one
+> thing what "works" means is definitely implementation defined, it has
+> to be in semantic terms.
+
+You're right of course. I thought about that this morning, and concluded
+that in the case of different types, the behavior has to be unspecified in
+language terms. (That is, the implementation does whatever it does. It
+certainly isn't implementation-defined, because that would require
+documentation, and I'm pretty sure we don't want to have to document what
+every possible combination of types results in!)
+
+My personal opinion is that the optimizer shouldn't change the behavior of
+the implementation, because that reduces surprises (and "optimizer fear")
+and thus support costs. But that obviously is just an opinion, as it
+certainly is the case that the implementation can do something different and
+still be unspecified.
+
+In the case you gave though:
+
+  X : aliased Integer;
+  Y : aliased Integer;
+  for Y'address use X'address;
+
+There is clear semantics in the language, and I see no justification for
+  X := 4;
+  if Y = 4 then -- Better take this branch.
+not working, optimizer or no.
+
+So, in your example replying to Jean-Pierre:
+
+>  X : Integer;
+>  Y : aliased Integer;
+
+>the compiler can (and GNAT does) make use of the fact that X and Y cannot
+>be aliased.
+
+That's only true if Y doesn't have any occurrences of Y'Address. If Y is a
+global, you can't prove that in general.
+
+> > Now it certainly is true that the AARM never says this, and perhaps the
+> > intent was different. But this is certainly the model I took away from the
+> > DR meetings where all of the implications of the model were discussed.
+>
+> Well what the AARM says has no force in any case, we are talking about teh
+> ARM here, and really the above sentence is my whole point. If the ARM intends
+> to say something useful here, it should say what it means. We cannot depend
+> on what Randy has "taken away from DR meetings" to understand Ada :-)
+
+I originally said "RM and AARM" here, and edited it out because it seemed
+redunant.
+
+And I don't argue that 13.3(19) is unnecessarily vague (it needs to say "the
+object" - it certainly can't mean the world); and there ought to be more
+AARM notes for 13.3(16) to explain the model (mine or whichever).
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Thursday, July 17, 2003  12:45 PM
+
+> My personal opinion is that the optimizer shouldn't change the behavior of
+> the implementation, because that reduces surprises (and "optimizer fear")
+> and thus support costs. But that obviously is just an opinion, as it
+> certainly is the case that the implementation can do something different and
+> still be unspecified.
+
+That's a HUGE restriction on an optimizer. It would tend to fix the order
+of evaluation of expressions, and as a result limit schedulability. And in
+the case of uninitialized variables, it is a very heavy cost to restrict
+them from being in registers.
+
+****************************************************************
+
+
+From: Jean-Pierre Rosen
+Sent: Wednesday, July 16, 2003  2:25 AM
+
+> The question is in the direct kind of case that I gave:
+>
+>    A : Integer;
+>    B : Float;
+>    for B'Address use A'Address;
+>
+> should the compiler understand that A and B are aliased? In other words, if
+> one of them is assigned to, then the other one has changed.
+
+I liked the idea that the compiler is not forced to consider A as aliased,
+*unless* it is declared with the aliased keyword.
+After all, requiring A to be declared aliased is just telling the truth to
+both the compiler and the human reader!
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Thursday, July 17, 2003  6:08 AM
+
+possibly, but please note that this does not help that much. Saying something
+is aliased in Ada merely allows you to take access values of the object, it
+does NOT say that the object is potentially aliased with everything else of
+its type, let alone with everything of other types. For instance, in
+
+  X : Integer;
+  Y : alised Integer;
+
+the compiler can (and GNAT does) make use of the fact that X and Y cannot
+be aliased. This is true even for:
+
+  X : aliased Integer;
+  Y : aliased Integer;
+
+It is still the case that X and Y cannot be aliased.
+
+... in the absence of an address clause, and that's the whole point here.
+
+If we now say
+
+  for Y'Address use X'Address;
+
+the question is how this changes the aliasing assumptions.
+
+It seems clear from the current IA language, that the compiler should now
+assume that Y can be aliased with X. It is not so clear that it can be
+aliased with anything else.
+
+It is FAR from clear that X must be assumed to be aliased with Y.
+
+I really don't see what it buys you to say that the aliasing assumption is
+changed by the aliased keyword during processing of the address clause.
+It makes the implementation slightly more complicated, and means that the
+typical Ada 83 usage will still not "work", so any reasonable compiler is
+going to try to make this "work" without the aliased keyword anyway. Randy
+apparently does this easily, because his compiler basically doesn't do much
+with aliasing optimziations anyway.
+
+The reason that we are focusing attention is that GCC 3, unlike GCC 2 does
+very careful aliasing analysis, and after all this is one area in which Ada
+is superior to C, so it is worth studying exactly what we intend compilers
+to be able to do.
+
+****************************************************************
+
+From: Erhard Ploedereder
+Sent: Thursday, July 17, 2003  8:08 AM
+
+> I disagree, legacy code is full of the use of address clauses to achieve
+> overlayh. Many programmers find it more convenient and natural than the
+> use of unchecked conversion (Fortran COMMON and COBOL REDEFINES are of
+> course precedents for this kind of usage).
+
+I am not disagreeing with that. However, in terms of usage, there is quite a
+difference between code of the form:
+
+somewhere:
+     A : Integer;
+     B : Integer;
+     for B'Address use A'Address;
+
+-----
+somewhere else:
+     -- A unread, unassigned
+     B := 7;
+     A = 7 ?
+
+and
+
+     ... := some word-sized usage of A, so it may be cached in a register;
+         or some assignment to A of compile-time propagatable values
+     B := 7;
+     A = 7  ?
+
+Only in the second case will compilers be tempted to ignore the aliasing in
+ontoward ways; unless you go for serious inter-procedural analysis,
+straightline code of the first kind will work as expected, i.e. always yield
+true.
+
+Now, while I certainly understand the motivation for the first case, i.e.,
+avoid casting as part of memory management or some such, the number of cases
+where the second idiom is used ought to be much smaller. It is a very hefty
+penalty (see below) to have the optimization restriction to make the second
+example work as the user expects.
+
+And if an implementer feels that this should work, well, nothing in the
+standard hinders him to disable the optimization. To place the restriction
+on all implementers, on the other hand, is bitter.
+
+In terms of actually defining language semantics for it (or defining an
+individual implementation strategy without resorting to the most general
+model of (over)estimating potential aliasing), have fun with stuff like
+
+    A: some_array_of_my_type;
+
+    type Acc is access My_Type;
+-----
+    B: My_2ndType;
+    for B'address use A(J)'Address;
+
+    C: aliased My_Type;
+    for C'Address use A(I)'Address;
+
+    C1: aliased My_Type;  -- !! (or even without the aliased, using
+                                 casting later on)
+
+    X: Acc;
+    X := C'Access; X:= C1'Access;
+
+    D: My_3rdType:
+    for D'Address use X.all'Address;
+
+with these variables declared in various places, with their address specs
+in private parts, and the X assignment in some body, and then somewhere
+
+    B := 5;
+    D := 7;
+    B=D? , B=C?   -- presuming I=J
+    C1 = 7?
+(Not without enforcing that no caching in registers takes place for all
+ the variables involved.)
+
+A language semantics would need to give an answer to this example and I know
+of no implementation model that would not make all global variables and some
+locals potentially aliased with X'all.
+
+An implementation is allowed to simply eliminate the example by posing a
+restriction that address specs need to be static or suitably simple to allow
+for decidability of aliasing at compile-time.
+
+Or the language puts the decidability restrictions in place; that's fine,
+too.
+
+But to require an "all potential aliasing considered" from every
+implementation, without restrictions, seems unreasonable to me.
+
+****************************************************************
+
+From: Tucker Taft
+Sent: Thursday, July 17, 2003  11:54 AM
+
+I think one way we could bound the problem is require
+that the possibility of "unorthodox" aliasing need only
+be of concern to the implementation when the original
+stand-alone object declaration is denoted (directly
+or via a rename).  If the object is passed as a by-reference
+parameter, we can't really expect that
+all by-reference parameters be treated as though they
+had their address specified.  That seems excessive.
+
+So as a worst case, any assignment to a part of an object
+using a name that denotes an object declaration with an
+associated address clause, must be considered to kill
+everything.  Of course if the compiler is smarter, it
+can know that certain objects have never had their
+address taken, etc.  Similarly, such an object must be
+killed by an assignment to anything else.
+
+That seems simple enough for a compiler to implement, and
+many compilers can do better than that.
+
+Secondly, once a part of such an object is passed by
+reference, the programmer must ensure that the program obeys
+the normal rules having to do with aliasing.
+
+The only remaining issue might be whether compilers are required
+to pass parts of such objects by copy if pass-by-copy is permitted.
+That seems too fierce a requirement (though that is what we
+require for volatile objects that are not of a volatile type).
+Hence, I would recommend that if it *could* be passed by reference,
+then the normal parameter aliasing rules apply, putting the burden
+back on the programmer.
+
+The basic philosophy is then that the burden is on the compiler
+when a name is used that denotes (directly or indirectly) an
+object declaration with an address clause, and the burden is
+on the programmer if a part of such an object is passed as
+a might-be-by-reference parameter (following the rules in 6.2(12)).
+
+****************************************************************
+
+From: Robert I. Eachus
+Sent: Thursday, July 17, 2003  12:20 PM
+
+Robert Dewar wrote:
+
+>Er, we are not in the business of forcefully discouraging our users, we are
+>in the business of meeting their needs. Of course we will not go so far as
+>to deliberately not conform to the standard, but short of that, user needs
+>come ahead of language lawyer aesthetic opinions :-)
+>
+That is--or should be--true of the ARG as well. Our coustomers are the
+potential users of Ada. And if the ARG fails to meet the needs of some
+subset of them, Ada is less widely used.
+
+So what IS the need in this case, and how can the ARG act to meet it? I
+strongly agree with Robert Dewar that taking the address of something
+should have a langauge-defined semantic effect. I also agree that the
+scope of that effect can and should be limited.
+
+How to balance these? Well, I know what I need and often depend on,
+sometimes with a slight feeling of sin. Let me give examples and
+proposed scopes:
+
+type T is record
+TC: Integer;
+...
+end record;
+-- any type passed by reference. (Note: I did not say, required to be
+passed by reference. The compiler knows what it is doing, so there is no
+"additional" burden to the wider scope. In fact probably the opposite.)
+
+function F (TP: T) return Foo is
+Local: T;
+for Local'Address use TP'Address;
+begin... end F;
+
+I don't need (or particularly want) every component of Local to be
+treated as volitile. I do want and need for every assignment to Local.TC
+to be treated as used when end F; is reached. We can have the argument
+about what is required to have happened when this exception or that is
+raised when discussing some other section. For this issue though, we can
+restrict the discussion to non-predefined exceptions and raise
+statements, which tend to be the exceptions I care about anyway The
+"write-back" of Local.TC should also happen when an exception is raised.
+
+What about references to TP.TC inside F? If there is an assignment to
+Local.TC, the programmer is on his own, and should expect it. Of course,
+if the programmer says:
+
+Local_Int: Integer;
+for Local_Int'Address use TP.TC;
+
+...the programmer's expectations could be different. So it seems that
+any rule should be stated in terms of local scopes, and of objects whose
+Address has been taken, but not components of that object. I guess that
+I would sort of as a reasonable compromise treat the 'local scope' of a
+package spec for this purpose as the package itself, its body, and any
+children and or subunits. If a programmer is binding a varible to a
+particular (hardware) location, he should be using Volitile as well. And
+if someone wants to take an address in a relatively global scope such as
+the main program, he can pay the optimization penalty.
+
+Pragma Inline should not affect the rules. We should try in this case to
+hold to the precept that most pragmas do not affect the meaning of a
+program.
+
+****************************************************************
+
+From: Robert I. Eachus
+Sent: Thursday, July 17, 2003  12:29 PM
+
+Tucker and I litterally crossed in the e-mail on this. Tucker's approach
+and mine to limiting the excess are different, but as far as I am
+concerned that just shows that this really is an issue that the ARG
+should resolve. Some standardized reasonable limit on the potential
+effect of taking an address is needed, but assuming away everything is
+not a programmer-friendly option.
+
+****************************************************************
+
+From: Robert A. Duff
+Sent: Thursday, July 17, 2003  1:40 PM
+
+Whatever the rules are, there should be zero distributed overhead.
+That is, the compiler has to know what to do based on the Address
+clauses it can see, and not on some Address clauses that might exist
+in some other compilation unit.
+
+I suppose this might be obvious to everybody on this list, but I thought
+I'd just put in my $0.02.  I don't have anything useful to say, beyond
+what various folks have already said.  I probably wrote the RM paragraph
+in question, and the reason it's so vague is probably that I didn't know
+what I was talking about at the time.
+
+Randy said:
+
+> > My personal opinion is that the optimizer shouldn't change the behavior of
+> > the implementation, because that reduces surprises (and "optimizer fear")
+> > and thus support costs. But that obviously is just an opinion, as it
+> > certainly is the case that the implementation can do something different and
+> > still be unspecified.
+
+And Robert Dewar replied:
+
+> That's a HUGE restriction on an optimizer. It would tend to fix the order
+> of evaluation of expressions, and as a result limit schedulability. And in
+> the case of uninitialized variables, it is a very heavy cost to restrict
+> them from being in registers.
+
+Randy's requirement can easily be achieved, with no cost in run-time
+speed, simply by always compiling in optimized mode.  ;-)
+
+P.S. Is it time for my usual admonishment to include who said what,
+when quoting (as I goodly did above, but often forget to do)?  ;-)
+I even goodly distinguished "Dewar" from various other Roberts around
+the place, such as me.
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Thursday, July 17, 2003  4:34 PM
+
+> I strongly agree with Robert Dewar that taking the address of something
+> should have a langauge-defined semantic effect. I also agree that the
+> scope of that effect can and should be limited.
+
+Note that this is stronger than what I asked for. I am quite happy for this
+to be implementation advice, I would just like it to be IA that made sense
+and that everyone interpreted the same way.
+
+One point that seems to be getting lost in what I am saying (especially in
+Tuck's last msg) is that I think the following two should be equivalent
+
+   A : Integer;
+   B : Integer;
+
+   for B'Address use A'Address;
+
+and
+
+   B : Integer;
+   A : Integer;
+   for A'Address use B'Address;
+
+I don't see a basis for asymmetrical treatment here. Either A and B are
+aliased and the compiler knows about it, or they are not.
+
+Note that in a case like this it is absolutely unnecessary to throw up your
+hands and decide that either or both variables can be arbitrarily aliased
+to anything. On the contrary, they are only aliased to one another and
+nothing else.
+
+This is an argument *against* requiring aliased keywords, since the use of
+such keywords greatly increases the aliased sets involved.
+
+****************************************************************
+
+From: Tucker Taft
+Sent: Thursday, July 17, 2003  4:34 PM
+
+I agree that a particular compiler could treat them symmetrically,
+but I fear the effort involved in trying to define this in the
+reference manual.  Compilers are always allowed to be smarter,
+if the effect is equivalent (the old "as if" rule).  In this case,
+the compiler pretty much sees everything, and what you have is
+the moral equivalent of a rename.  But I can't imagine using
+an Address clause for something as simple as this.  There is
+always something else going on, such as viewing a piece of
+"raw storage" as a particular higher level type, or perhaps
+using it to default reinitialize an existing object, or whatever.
+
+It is rarely equivalent to a simple rename, and so it seems silly
+to put much effort into specifying the semantics in that
+case.
+
+What I was suggesting was a "worst case" semantics, where
+any assignment to the address-specified object kills everything,
+and it is in turn killed by any assignment to anything else.
+But this would *not* apply when referring to the object
+via a by-reference parameter.
+
+And of course compilers could do better if they have tracked
+the possible values of the expression used in the address clause,
+and can thereby narrow down the number of possible aliases.
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Thursday, July 17, 2003  5:10 PM
+
+> But I can't imagine using
+> an Address clause for something as simple as this.  There is
+> always something else going on, such as viewing a piece of
+> "raw storage" as a particular higher level type, or perhaps
+> using it to default reinitialize an existing object, or whatever.
+
+Yes, of course in practice the two types will usually be different, although
+we have seen instances of address clauses that were renames, so a more
+realistic example is:
+
+     A : Integer;
+     B : String (1 .. 4);
+
+> I agree that a particular compiler could treat them symmetrically,
+> but I fear the effort involved in trying to define this in the
+> reference manual.
+
+Then I think it is better that the reference manual say nothing. The idea
+of asymmetrical alias sets is just too confusing. Why not just remove the
+dubious implementation advice since we don't really know what it means.
+I see no reason in trying to pin down precisely one side of this, if the
+other side is left to cause surprising results.
+
+Here would be Robert's first half baked attempt at more useful IA here.
+
+
+  If an address clause causes an object to be aliased with other objects
+  in the program, than changes to these other objects should be reflected
+  in the value of the object with the address clause. In the simple case
+  where an address clause is used to overlay two variables, as in
+
+       A : Integer;
+       B : Float;
+       for B'Address use A'Address;
+
+  then the implementation should recognize that A and B are aliased, and
+  changes to either one should be reflected in the other.
+
+Note this is IA, so we are not trying to be semantically precise here, just
+to get something that we can read in a friendly manner and all end up with
+at least roughly the same understanding :-)
+
+****************************************************************
+
+From: Tucker Taft
+Sent: Thursday, July 17, 2003  5:55 PM
+
+Robert Dewar wrote:
+> ...
+> > I agree that a particular compiler could treat them symmetrically,
+> > but I fear the effort involved in trying to define this in the
+> > reference manual.
+>
+> Then I think it is better that the reference manual say nothing. The idea
+> of asymmetrical alias sets is just too confusing.
+
+The aliasing relationship is still "symmetric" in the sense that
+B is aliased with A (and everything else) and
+A (and everything else) is aliased with B.
+
+...
+> Here would be Robert's first half baked attempt at more useful IA here.
+...
+
+I would still like to limit this to cases where the object with the
+Address clause is being referred to "directly" as opposed to via
+a by-reference parameter.
+
+****************************************************************
+
+From: Robert Dewar
+Sent: Thursday, July 17, 2003 10:32 PM
+
+> The aliasing relationship is still "symmetric" in the sense that
+> B is aliased with A (and everything else) and
+> A (and everything else) is aliased with B.
+
+But that is absurdly pessimistic and unnecessary in this case. I certainly
+don't want IA that implies this very poor implementation.
+
+****************************************************************
+
+From: Robert I. Eachus
+Sent: Thursday, July 17, 2003  6:11 PM
+
+>Note that this is stronger than what I asked for. I am quite happy for this
+>to be implementation advice, I would just like it to be IA that made sense
+>and that everyone interpreted the same way.
+
+I didn't intented to overstate your position. It is just hard to say
+"the reference manual should say something sensible about this case so
+we can all implement it the same way" and fit it in one clause. (And of
+course, that is still a simplification.)
+
+A different way of stating my opinion is, "The Rosen trick must work." I
+don't know how much Ada code out there depends on the Rosen trick. Since
+most of it probably gets that way by using an implementation defined
+random-number generator I am not all that worried about compiler
+suddenly deciding not to compile those packages correctly.
+
+>One point that seems to be getting lost in what I am saying (especially in
+>Tuck's last msg) is that I think the following two should be equivalent
+>
+>   A : Integer;
+>   B : Integer;
+>
+>   for B'Address use A'Address;
+>
+>and
+>
+>   B : Integer;
+>   A : Integer;
+>   for A'Address use B'Address;
+>
+>I don't see a basis for asymmetrical treatment here. Either A and B are
+>aliased and the compiler knows about it, or they are not.
+>
+>Note that in a case like this it is absolutely unnecessary to throw up your
+>hands and decide that either or both variables can be arbitrarily aliased
+>to anything. On the contrary, they are only aliased to one another and
+>nothing else.
+>
+>This is an argument *against* requiring aliased keywords, since the use of
+>such keywords greatly increases the aliased sets involved.
+
+Agreed. It would be like requiring the aliasing keyword for parameters.
+We all know, and compilers all know that parameters create aliasing. But
+that is a far cry from assuming that every value that might be passed as
+a parameter is aliased to every object of the same type.
+
+****************************************************************
+
+From: Robert I. Eachus
+Sent: Thursday, July 17, 2003  9:51 PM
+
+Now we are getting down to the nitty-gritty. Why do you object to this
+case, which may be the one I see as vital. But I wouldn't say that it is
+the aliasing that occurs with a by-reference parameter we are protecting
+here, it is the subsequent aliasing by an address clause. From my
+previous example:
+
+type T is record
+TC: Integer;
+...
+end record;
+
+function F (TP: T) return Foo is
+Local: T;
+for Local'Address use TP'Address;
+begin... end F;
+
+-- Let me add a call:
+
+TO: T:
+Foo_Obj: Foo;
+...
+Foo_Obj := F(TO);
+
+I want to say that Local is an alias for TP, and TP is an alias for
+Local, and that the (only IMHO) important synchronization points are at
+the creation of local and the exit from the scope of F. The fact that
+inside the call, Local is also an alias of TO is interesting, but I
+would rush to the barracades if an ACATS test tried to check if the
+transitive aliasing worked, especially if type T was potentially call by
+reference but not required to be.
+
+The aliasing between Local and TP on the other hand should always hold
+even if F were a procedure and TP passed by value return. (We could then
+spend a few minutes discussing an implementation specific pragma that
+guaranteed by reference semantics for parameters where the RM doesn't
+specify, or the copy back with call by value on a function call. But
+that should almost be outside the ARG's scope.)
+
+****************************************************************
+

Questions? Ask the ACAA Technical Agent