* "access constant" discriminant @ 2003-02-10 8:26 tmoran 2003-02-10 14:43 ` Frank J. Lhota ` (3 more replies) 0 siblings, 4 replies; 34+ messages in thread From: tmoran @ 2003-02-10 8:26 UTC (permalink / raw) Can this be done? How? ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-10 8:26 "access constant" discriminant tmoran @ 2003-02-10 14:43 ` Frank J. Lhota 2003-02-10 18:57 ` tmoran 2003-02-10 19:26 ` Robert A Duff ` (2 subsequent siblings) 3 siblings, 1 reply; 34+ messages in thread From: Frank J. Lhota @ 2003-02-10 14:43 UTC (permalink / raw) What is it that you want to do? ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-10 14:43 ` Frank J. Lhota @ 2003-02-10 18:57 ` tmoran 2003-02-15 19:17 ` Richard Riehle 2003-02-20 2:20 ` Matthew Heaney 0 siblings, 2 replies; 34+ messages in thread From: tmoran @ 2003-02-10 18:57 UTC (permalink / raw) >What is it that you want to do? In the case at hand, I'm using the idiom of a limited controlled type whose initialization/finalization grabs/releases a resource lock, and the access discriminant tells which resource. type Lock_Type(Resource : access Resource_Type) is new Ada.Finalization.Limited_Controlled with ... and later Locker : Lock_Type(Resource'unchecked_access); ... But this won't work when Resource is an "in" parameter, eg a function parameter. I suppose Ada is telling me that grabbing a lock is effectively modifying the resource, and thus something that shouldn't be done when the resource is an "in" parameter, but the question remains, why can't one say type Lock_Type(Resource : access constant Resource_Type) ... Did the designers foresee and forestall my use with a function? ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-10 18:57 ` tmoran @ 2003-02-15 19:17 ` Richard Riehle 2003-02-15 19:59 ` Larry Kilgallen 2003-02-20 2:23 ` Matthew Heaney 2003-02-20 2:20 ` Matthew Heaney 1 sibling, 2 replies; 34+ messages in thread From: Richard Riehle @ 2003-02-15 19:17 UTC (permalink / raw) tmoran@acm.org wrote: > > why can't one say > type Lock_Type(Resource : access constant Resource_Type) ... > Did the designers foresee and forestall my use with a function? I raised an issue about this from time to time in this forum, but in a sligthly different way. We have, type Reference is access all some-type; and type Reference is acess constant some-type; A function may have a an access parameter, which almost has in semantics. However, it is possible to modify a component of an access parameter. I would like the option of preventing that with, function F (X : access constant parameter-name) return some-type; This would make it illegal for the function to modify the components of an access parameter. Without the word constant, one could still modify such components, but including it would make absolutely clear, in the contract, that such side-effects would be impossible. Richard Riehle ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-15 19:17 ` Richard Riehle @ 2003-02-15 19:59 ` Larry Kilgallen 2003-02-15 23:53 ` Richard Riehle ` (2 more replies) 2003-02-20 2:23 ` Matthew Heaney 1 sibling, 3 replies; 34+ messages in thread From: Larry Kilgallen @ 2003-02-15 19:59 UTC (permalink / raw) In article <3E4E9248.3E71D984@adaworks.com>, Richard Riehle <richard@adaworks.com> writes: > A function may have a an access parameter, which almost has in > semantics. However, it is possible to modify a component of > an access parameter. I would like the option of preventing that > with, > > function F (X : access constant parameter-name) return > some-type; > > This would make it illegal for the function to modify the components of > an access parameter. Without the word constant, one could still modify > such components, but including it would make absolutely clear, in the > contract, that such side-effects would be impossible. Why is it necessary to have the parameter be an access type ? ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-15 19:59 ` Larry Kilgallen @ 2003-02-15 23:53 ` Richard Riehle 2003-02-16 1:50 ` Eric G. Miller 2003-02-20 2:23 ` Matthew Heaney 2003-02-20 17:34 ` Stephen Leake 2 siblings, 1 reply; 34+ messages in thread From: Richard Riehle @ 2003-02-15 23:53 UTC (permalink / raw) Larry Kilgallen wrote: > Why is it necessary to have the parameter be an access type ? Good question. Consider this package, package Side_Effect_Experiment is type Item_Type is private; type Reference is access all Item_Type; procedure Create (Data : in out Item_Type); function Is_Valid (Data : in Item_Type) return Boolean; function Is_Valid (Data : in Reference) return Boolean; function Is_Valid (Data : access Item_Type) return Boolean; private type Item_Type is record ID : Natural := 0; Description : String(1..20) := (others => ' '); Valid : Boolean := False; end record; end Side_Effect_Experiment; with this corresponding package body, package body Side_Effect_Experiment is procedure Create (Data : in out Item_Type) is begin null; end Create; function Is_Valid (Data : in Item_Type) return Boolean is begin Data.Valid := True; -- not valid for in parameter return Data.Valid; end Is_Valid; function Is_Valid (Data : in Reference) return Boolean is begin Data.Valid := True; return Data.Valid; end Is_Valid; function Is_Valid (Data : access Item_Type) return Boolean is begin Data.Valid := True; return Data.Valid; end Is_Valid; end Side_Effect_Experiment; Note that the side-effect cannot happen when we have a normal in parameter. However, it can occur with any variation of an access type parameter. By adding syntax to the function such as, constant function Is_Valid(Data : access Item_Type) return Boolean; or function Is_Valid (Data : access constant Item_Type) return Boolean; the compiler would be able to note the attempt at a side-effect and prevent it. Richard Riehle ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-15 23:53 ` Richard Riehle @ 2003-02-16 1:50 ` Eric G. Miller 0 siblings, 0 replies; 34+ messages in thread From: Eric G. Miller @ 2003-02-16 1:50 UTC (permalink / raw) In article <3E4ED2FC.3310564A@adaworks.com>, Richard Riehle wrote: > Larry Kilgallen wrote: > >> Why is it necessary to have the parameter be an access type ? Not long ago, I wrote a C library wrapper that takes advantage of being able to modify the contents of a function via an access parameter. Being able to specify "constant" seems like a good thing for safety and for clarifying the "contract" in the API. The "C" library has functions like: typedef struct Foo { /* whatever */} Foo; long Get_Foo (Foo *); long Set_Foo (Foo); So, the Ada wrapper is like: type Foo is record -- whatever... end record; pragma Convention (Convention => C_Pass_By_Copy, Entity => Foo); function Get_Foo (Self : access Foo) return Error_Code; pragma Import (Convention => C, Entity => Get_Foo, External_Name => "Get_Foo"); function Set_Foo (Self : Foo) return Error_Code; pragma Import (Convention => C, Entity => Set_Foo, External_Name => "Set_Foo"); But, maybe there's a function like: #define FOO_NAME_LENGTH 42 typedef char Foo_Name[FOO_NAME_LENGTH]; long Get_Foo_Name (const Foo *, Foo_Name); So, I might want a wrapper function that mirrors this: Foo_Name_Length : constant := 42; subtype Foo_Name is C.Char_Array(1..Foo_Name_Length); function Get_Foo_Name (Self : access constant Foo; Name : access Foo_Name) return Error_Code; pragma Import (Convention => C, Entity => Get_Foo_Name, External_Name => "Get_Foo_Name"); Seems like a reasonable thing. The downside of pointers to constant parameters is functions that are declared using "constant", calling functions or procedures that aren't so marked even if such functions actually treat the parameter as a constant. I've encountered this enough times in the "C" world to see that it diminishes the utility of "const". Still, overall it's probably better to have it available than not. -- echo ">gra.fcw@2ztr< eryyvZ .T pveR" | rot13 | reverse ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-15 19:59 ` Larry Kilgallen 2003-02-15 23:53 ` Richard Riehle @ 2003-02-20 2:23 ` Matthew Heaney 2003-02-20 17:34 ` Stephen Leake 2 siblings, 0 replies; 34+ messages in thread From: Matthew Heaney @ 2003-02-20 2:23 UTC (permalink / raw) Kilgallen@SpamCop.net (Larry Kilgallen) wrote in message news:<zwb0dJM87esk@eisner.encompasserve.org>... > In article <3E4E9248.3E71D984@adaworks.com>, Richard Riehle <richard@adaworks.com> writes: > > > Why is it necessary to have the parameter be an access type ? Because operations that have access parameters are primitive for the type, which means they're inherited during a derivation. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-15 19:59 ` Larry Kilgallen 2003-02-15 23:53 ` Richard Riehle 2003-02-20 2:23 ` Matthew Heaney @ 2003-02-20 17:34 ` Stephen Leake 2003-02-21 0:42 ` Matthew Heaney 2 siblings, 1 reply; 34+ messages in thread From: Stephen Leake @ 2003-02-20 17:34 UTC (permalink / raw) Kilgallen@SpamCop.net (Larry Kilgallen) writes: > Why is it necessary to have the parameter be an access type ? (as opposed to "in", I assume) Because the body needs to call other functions that take access types (that may beg the question, but it's the best I can do :). -- -- Stephe ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-20 17:34 ` Stephen Leake @ 2003-02-21 0:42 ` Matthew Heaney 2003-02-21 10:41 ` Lutz Donnerhacke ` (2 more replies) 0 siblings, 3 replies; 34+ messages in thread From: Matthew Heaney @ 2003-02-21 0:42 UTC (permalink / raw) Stephen Leake <Stephen.A.Leake@nasa.gov> wrote in message news:<uu1eyluui.fsf@nasa.gov>... > > Because the body needs to call other functions that take access types > (that may beg the question, but it's the best I can do :). Access parameters carry accessibility information around, to check that an object in an outer scope doesn't refer to another object in an inner scope. These accessibility checks can be turned off using the 'Unchecked_Access attribute, or by using a pragma to suppress Access_Check. One example of the use of access parameters is the "multiple views" idiom in Ada95, to effect the equivalent of multiple inheritance in other languages. For example, given a mechanism to store objects that are "persistent": procedure Write (Persistence : access Persistence_Type'Class); then we can save any object that supports this view, like this: Some_Object : aliased T; ... Write (Persistence_View (Some_Object'Access)); The selector function would be written as: function Persistence_View (Object : access T) return Persistence_Class_Access; In the canonical model, type T would have an aliased component whose type derives from Root_Persistence_Type, and the selector function is implemented simply as: fuction Persistence_View (Object : access T) return Persistence_Class_Access is begin return Object.Persistence_View'Access; end; Here we see the reason why we passed an access parameter: it's because we're returning an access value that designates one of our own components. The view component would be implemented like this: type Persistence_Type is new Root_Persistence_Type (Object : access T) with null record; type T is limited record Persistence_View : aliased Persistence_Type (T'Access); ... end record; Presumably the Root_Persistence_Type has primitive operations for writing an object into a stream, e.g. procedure Write (Persistence : access Root_Persistence_Type; Stream : in out Root_Stream_Type'Class) is abstract; The Persisence_Type about would override the Write operation, to write a T object into the stream. It has visibility to the T object via its access discriminant. Access discriminants are very powerful. No serious Ada95 program can be written without them. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-21 0:42 ` Matthew Heaney @ 2003-02-21 10:41 ` Lutz Donnerhacke 2003-02-21 20:21 ` Randy Brukardt 2003-02-24 16:03 ` Matthew Heaney 2003-02-21 15:03 ` Hyman Rosen 2003-02-21 20:07 ` Randy Brukardt 2 siblings, 2 replies; 34+ messages in thread From: Lutz Donnerhacke @ 2003-02-21 10:41 UTC (permalink / raw) * Matthew Heaney wrote: > Access discriminants are very powerful. No serious Ada95 program can > be written without them. If there is a serious program without access discriminants, let's call it a Spark program, or trivial, ok? ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-21 10:41 ` Lutz Donnerhacke @ 2003-02-21 20:21 ` Randy Brukardt 2003-02-23 12:22 ` Simon Wright ` (2 more replies) 2003-02-24 16:03 ` Matthew Heaney 1 sibling, 3 replies; 34+ messages in thread From: Randy Brukardt @ 2003-02-21 20:21 UTC (permalink / raw) Lutz Donnerhacke wrote in message ... >* Matthew Heaney wrote: >> Access discriminants are very powerful. No serious Ada95 program can >> be written without them. > >If there is a serious program without access discriminants, let's call it a >Spark program, or trivial, ok? Claw doesn't use access discriminants. That's in large part because they cause limited 'poisoning', as they're restricted to limited types. We prefered to use Adjust to make assignment work properly. Indeed, I'm not aware of any real Ada program, serious or otherwise, that actually uses access discriminants. I know that they were buggy in Janus/Ada until very recently, and we never received any bug reports on them. So, as a practical matter, these are a very marginal feature of Ada with very limited uses. In any case, Matt's statement would probably have been better if it said: Access discriminants are very powerful. They are very much underutilized, probably because hardly anybody understands them. Sweeping statements about programming style are not likely to be helpful. I tend to feel about finalization like Matt apparently does about access discriminants, but the only time I would say something like "No serious Ada program can be written without them." is when I'm looking for fight. Even though I believe that is true, I'm well aware that there are many, many Ada projects which have an irrational fear of finalization, and to characterize them as not being "serious" is not likely to make any friends. Randy. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-21 20:21 ` Randy Brukardt @ 2003-02-23 12:22 ` Simon Wright 2003-02-24 7:06 ` Dale Stanbrough 2003-02-24 18:58 ` Matthew Heaney 2 siblings, 0 replies; 34+ messages in thread From: Simon Wright @ 2003-02-23 12:22 UTC (permalink / raw) "Randy Brukardt" <randy@rrsoftware.com> writes: > Indeed, I'm not aware of any real Ada program, serious or otherwise, > that actually uses access discriminants. I know that they were buggy > in Janus/Ada until very recently, and we never received any bug > reports on them. So, as a practical matter, these are a very > marginal feature of Ada with very limited uses. Very useful for records with task/protected type components, of course! (and I think my current project is fairly serious ..) ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-21 20:21 ` Randy Brukardt 2003-02-23 12:22 ` Simon Wright @ 2003-02-24 7:06 ` Dale Stanbrough 2003-02-24 18:58 ` Matthew Heaney 2 siblings, 0 replies; 34+ messages in thread From: Dale Stanbrough @ 2003-02-24 7:06 UTC (permalink / raw) Randy Brukardt wrote: > Claw doesn't use access discriminants. That's in large part because they > cause limited 'poisoning', as they're restricted to limited types. I call it the "Midas touch". dale ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-21 20:21 ` Randy Brukardt 2003-02-23 12:22 ` Simon Wright 2003-02-24 7:06 ` Dale Stanbrough @ 2003-02-24 18:58 ` Matthew Heaney 2003-02-24 21:05 ` Randy Brukardt 2 siblings, 1 reply; 34+ messages in thread From: Matthew Heaney @ 2003-02-24 18:58 UTC (permalink / raw) "Randy Brukardt" <randy@rrsoftware.com> wrote in message news:<v5d2m6pi5q3tef@corp.supernews.com>... > > Claw doesn't use access discriminants. That's in large part because they > cause limited 'poisoning', as they're restricted to limited types. We > prefered to use Adjust to make assignment work properly. This may simply reflect a philosophical difference about whether types should be limited or non-limited. Certainly I have never agreed with the CLAW decision to make window types non-limited, and to me a non-limited window is completely wacky. > Access discriminants are very powerful. They are very much > underutilized, probably because hardly anybody understands them. I could make this argument about any language feature. For example, when I was using Ada83, my experience was that many Ada programmers never really understood what a private type was. There were many Ada83 programmers who didn't really grok the whole object-oriented programming thing. Another example: I worked on the F22 project for while, at Hughes. No one in the company seemed to know that you could return an unconstrained array from a function: declare S : constant String := Name (File); begin The problem was that Ada83 required the object to be marked as "constant," so when the declaration declare S : String := Name (File); begin didn't compile, everyone assumed that this meant you must return a constrained array. Of course this is incorrect -- but why didn't anyone realize this? I have observed a similar phenomenon among Ada95 programmers. There are many aspects of the Ada95 language with which many programmers are unfamiliar. For example, I gave a talk in London, and declared a private operation that took the tagged type as an access parameter. No one seemed to realize that operations that accept the type as an access parameter are primitive, and therefore dispatch when the parameter has type T'Class. Another of the speakers was talking about the problems he was having with Unchecked_Access. As it turns out, neither he nor anyone else in his company knew that tagged types are passed by reference in Ada95. He was trying to prevent the "slicing" that can occur in C++ (and which he thought would happen in Ada95 too), so he was declaring all the type parameters using a named access type. Of course, this is incorrect, but why didn't anyone realize that tagged types are passed by reference? > Sweeping statements about programming style are not likely to be > helpful. I tend to feel about finalization like Matt apparently does > about access discriminants, but the only time I would say something like > "No serious Ada program can be written without them." is when I'm > looking for fight. Even though I believe that is true, I'm well aware > that there are many, many Ada projects which have an irrational fear of > finalization, and to characterize them as not being "serious" is not > likely to make any friends. Perhaps it was my use of the word "serious" that was confusing. I should have said "essential," with the same sense that Fred Brooks used in his famous paper "Essence and Accidents in Software Engineering." http://atheism.about.com/library/glossary/general/bldef_essence.htm C++ doesn't require you to use classes, but if you don't, it would be a stretch to say that you're programming in "C++." Really, you're using a C++ compiler to compile a C program. This is not necessarily a bad thing -- after all, C++ gives you better compile-time error checking and type-safe linkage. But to not use classes you'd be losing something "essential" to C++ programming. The use of access discriminants in Ada95 is exactly analogous. For example, how would you add controlled-ness to a (tagged) type that is part of type hierarchy that isn't already controlled? The only way I know is to do this: type NT is new T with private; ... private type Control_Type (O : access NT) is new Limited_Controlled with null record; type NT is new T with record Control : Control_Type (NT'Access); ... end record; This is an important Ada95 idiom with which every Ada95 needs to be thoroughly familiar. This idiom and others like it is why I characterize access discriminants as "essential" (again, "per se" vs. "per accidens") to programming in Ada95. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-24 18:58 ` Matthew Heaney @ 2003-02-24 21:05 ` Randy Brukardt 2003-02-25 14:15 ` Frank J. Lhota 0 siblings, 1 reply; 34+ messages in thread From: Randy Brukardt @ 2003-02-24 21:05 UTC (permalink / raw) Matthew Heaney wrote in message <1ec946d1.0302241058.88ca487@posting.google.com>... >"Randy Brukardt" <randy@rrsoftware.com> wrote in message news:<v5d2m6pi5q3tef@corp.supernews.com>... >> >> Claw doesn't use access discriminants. That's in large part because they >> cause limited 'poisoning', as they're restricted to limited types. We >> prefered to use Adjust to make assignment work properly. > >This may simply reflect a philosophical difference about whether types >should be limited or non-limited. Certainly I have never agreed with >the CLAW decision to make window types non-limited, and to me a >non-limited window is completely wacky. That's a consequence of our no access type philosophy. So many people seem to think that O-O means references, and that simply is not true in Ada. The result of our "wackiness" is that you only need to explicitly use access types when you need dynamic (and non-stack-based) allocation of windows. Very few Claw programs have access to windows in them. If I was doing it over, I'd probably have made the windows limited, mainly because of the problems that clones of them cause in a multi-tasking program. But, in general, I tend to be on the side of "provide maximum capability with all reusable object types". Which means non-limited. ... >> Sweeping statements about programming style are not likely to be >> helpful. I tend to feel about finalization like Matt apparently does >> about access discriminants, but the only time I would say something like >> "No serious Ada program can be written without them." is when I'm >> looking for fight. Even though I believe that is true, I'm well aware >> that there are many, many Ada projects which have an irrational fear of >> finalization, and to characterize them as not being "serious" is not >> likely to make any friends. > >Perhaps it was my use of the word "serious" that was confusing. I >should have said "essential," with the same sense that Fred Brooks >used in his famous paper "Essence and Accidents in Software >Engineering." > >http://atheism.about.com/library/glossary/general/bldef_essence.htm > >C++ doesn't require you to use classes, but if you don't, it would be >a stretch to say that you're programming in "C++." Really, you're >using a C++ compiler to compile a C program. This is not necessarily >a bad thing -- after all, C++ gives you better compile-time error >checking and type-safe linkage. But to not use classes you'd be >losing something "essential" to C++ programming. > >The use of access discriminants in Ada95 is exactly analogous. For >example, how would you add controlled-ness to a (tagged) type that is >part of type hierarchy that isn't already controlled? The only way I >know is to do this: > > type NT is new T with private; > ... >private > type Control_Type (O : access NT) is > new Limited_Controlled with null record; > > type NT is new T with record > Control : Control_Type (NT'Access); > ... > end record; > >This is an important Ada95 idiom with which every Ada95 needs to be >thoroughly familiar. This idiom and others like it is why I >characterize access discriminants as "essential" (again, "per se" vs. >"per accidens") to programming in Ada95. Sigh. This is a lousy example, for the simple reason that there should be no such hierarchies. If you can afford the space and time overhead of a tagged type, you can afford the space and time overhead of a controlled type. So there simply should not be any tagged types that aren't controlled. Then this whole example comes up. Secondly, I certainly know of this idiom, but I've never once found a case where I needed to use it. I suspect this comes from the "O-O is everything" mentality, where people are trying to use simulate multiple inheritance in Ada rather than simply solving the problem. Whenever I've needed to "connect" objects, I've always used access-to-classwide types, and added any needed operations. Standing on one's head simply makes tricky, hard-to-maintain code. My point is O-O is the frosting on the cake, not the meat. It's useful for some jobs, but when you start trying to make everything look like it, you get abominations like access parameters and access discriminants. Especially when you try to copy existing O-O dogma instead of realizing that Ada 95 let's you do it better. Randy Brukardt. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-24 21:05 ` Randy Brukardt @ 2003-02-25 14:15 ` Frank J. Lhota 2003-02-26 1:05 ` Randy Brukardt 0 siblings, 1 reply; 34+ messages in thread From: Frank J. Lhota @ 2003-02-25 14:15 UTC (permalink / raw) > My point is O-O is the frosting on the cake, not the meat. Frosting on a meat cake? UG! ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-25 14:15 ` Frank J. Lhota @ 2003-02-26 1:05 ` Randy Brukardt 0 siblings, 0 replies; 34+ messages in thread From: Randy Brukardt @ 2003-02-26 1:05 UTC (permalink / raw) Frank J. Lhota wrote in message ... >> My point is O-O is the frosting on the cake, not the meat. > >Frosting on a meat cake? UG! Sigh. Mixed metaphors. What can I say? Probably that belongs in the Dilbert Newsletter. Randy. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-21 10:41 ` Lutz Donnerhacke 2003-02-21 20:21 ` Randy Brukardt @ 2003-02-24 16:03 ` Matthew Heaney 1 sibling, 0 replies; 34+ messages in thread From: Matthew Heaney @ 2003-02-24 16:03 UTC (permalink / raw) Lutz Donnerhacke <lutz@iks-jena.de> wrote in message news:<slrnb5c0ih.nq.lutz@taranis.iks-jena.de>... > * Matthew Heaney wrote: > > Access discriminants are very powerful. No serious Ada95 program can > > be written without them. > > If there is a serious program without access discriminants, let's call it a > Spark program, or trivial, ok? What I meant was that access discriminants are the sine qua non of Ada95 programming. If you're not using them, you're losing something essential, not accidental (per se vs. per accidens), about an Ada95 program. Of course, this idiom is just a reification of a more general design pattern called the "Adapter Pattern," or more specifically an "Object Adapter." It shows up in myriad languages. You often see C++ written like this: X x; ... Y y(&x); where the object y is bound to object x. Class Y would be implemented as class Y { X* const p public: Y(X* pp) : p(pp) {} //... private: Y& operator=(const Y&); Y(const Y&); }; This shows up even in some Ada95 iterator implementations: Iter : Iterator_Type (Container'Access); Here, you're viewing a container object through an iterator object. Of course, the effect of an object adapter can probably be implemented sans access discriminants (persumably that is the case in SPARK), but I don't consider these alternate locutions as elegant as an access discriminant. In your case you lose access discriminants in order to gain provable correctness -- which is of course the correct tradeoff. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-21 0:42 ` Matthew Heaney 2003-02-21 10:41 ` Lutz Donnerhacke @ 2003-02-21 15:03 ` Hyman Rosen 2003-02-21 20:09 ` Randy Brukardt 2003-02-21 21:33 ` Matthew Heaney 2003-02-21 20:07 ` Randy Brukardt 2 siblings, 2 replies; 34+ messages in thread From: Hyman Rosen @ 2003-02-21 15:03 UTC (permalink / raw) Matthew Heaney wrote: > Access parameters carry accessibility information around, to check > that an object in an outer scope doesn't refer to another object in an > inner scope. Do they actually carry this information around? I thought that the language rules just prevented such "inner" addresses from winding up in an "outer" pointer, not that the pointers themselves were "fat". ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-21 15:03 ` Hyman Rosen @ 2003-02-21 20:09 ` Randy Brukardt 2003-02-21 21:33 ` Matthew Heaney 1 sibling, 0 replies; 34+ messages in thread From: Randy Brukardt @ 2003-02-21 20:09 UTC (permalink / raw) Hyman Rosen wrote in message <1045839826.87966@master.nyc.kbcfp.com>... >Matthew Heaney wrote: >> Access parameters carry accessibility information around, to check >> that an object in an outer scope doesn't refer to another object in an >> inner scope. > >Do they actually carry this information around? >I thought that the language rules just prevented >such "inner" addresses from winding up in an >"outer" pointer, not that the pointers themselves >were "fat". That's true for everything *except* access parameters. They actually are required to carry a runtime accessibility level. (That's usually part of the parameter, not part of the access.) That's another reason to avoid access parameters, because they have more overhead than an in or in out parameter. Randy. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-21 15:03 ` Hyman Rosen 2003-02-21 20:09 ` Randy Brukardt @ 2003-02-21 21:33 ` Matthew Heaney 1 sibling, 0 replies; 34+ messages in thread From: Matthew Heaney @ 2003-02-21 21:33 UTC (permalink / raw) Hyman Rosen <hyrosen@mail.com> wrote in message news:<1045839826.87966@master.nyc.kbcfp.com>... > Matthew Heaney wrote: > > Access parameters carry accessibility information around, to check > > that an object in an outer scope doesn't refer to another object in an > > inner scope. > > Do they actually carry this information around? > I thought that the language rules just prevented > such "inner" addresses from winding up in an > "outer" pointer, not that the pointers themselves > were "fat". Access parameters carry accessibilty information around (not all checks can be done statically). Note that named access types do *not* carry the same information. When an access check fails at run-time, it's often because you're assigning the value of an access parameter to an access object. That's why you sometimes have to do the assignment using 'Unchecked_Access instead. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-21 0:42 ` Matthew Heaney 2003-02-21 10:41 ` Lutz Donnerhacke 2003-02-21 15:03 ` Hyman Rosen @ 2003-02-21 20:07 ` Randy Brukardt 2003-02-24 19:11 ` Matthew Heaney 2 siblings, 1 reply; 34+ messages in thread From: Randy Brukardt @ 2003-02-21 20:07 UTC (permalink / raw) Matthew Heaney wrote in message <1ec946d1.0302201642.66eb93e5@posting.google.com>... >Here we see the reason why we passed an access parameter: it's because >we're returning an access value that designates one of our own >components. That reason being only that Ada doesn't support 'in out' parameters on functions. If it did, fuction Persistence_View (Object : in out T) return Persistence_Class_Access is begin return Object.Persistence_View'Access; end; would work fine, and would be a lot easier to use as well. But that's not going to happen, so we're stuck with terrible workarounds like 'access' parameters. Randy. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-21 20:07 ` Randy Brukardt @ 2003-02-24 19:11 ` Matthew Heaney 2003-02-24 21:17 ` Randy Brukardt 0 siblings, 1 reply; 34+ messages in thread From: Matthew Heaney @ 2003-02-24 19:11 UTC (permalink / raw) "Randy Brukardt" <randy@rrsoftware.com> wrote in message news:<v5d1sfo9ib2df9@corp.supernews.com>... > Matthew Heaney wrote in message > <1ec946d1.0302201642.66eb93e5@posting.google.com>... > > >Here we see the reason why we passed an access parameter: it's because > >we're returning an access value that designates one of our own > >components. > > > That reason being only that Ada doesn't support 'in out' parameters on > functions. If it did, > > fuction Persistence_View > (Object : in out T) return Persistence_Class_Access is > begin > return Object.Persistence_View'Access; > end; > > would work fine, and would be a lot easier to use as well. No -- this would be the wrong way to implement the multiple views idiom. You really do want to make explicit the fact that the object is being aliased. For example, in C++ I could do this: X x; Y y(x); and implement Y this way: class Y { X& x; public: Y(X& xx) : x(xx) {} //... private: Y(const Y&); Y& operator=(const Y&); }; but that would be entirely misleading, even if it's "easier" to declare a Y object. It's better to implement Y's ctor using an explicit pointer: class Y { X& x; public: Y(X* px) : x(*px) {} private: Y(const Y&); Y& operator=(const Y&); }; and then say: X x; Y y(&x); Which makes it identical to how you'd say it in Ada95. So this is not really an Ada issue. > But that's not going to happen, so we're stuck with terrible workarounds > like 'access' parameters. Access parameters have other uses besides getting around the lack of inout mode for function parameters. For example, operations that accept a user-defined type as an access parameter are primitive for the type, and hence are inherited in a derivation. And an access parameter means you don't have to say Op (O.all) everywhere. However, we are in agreement that not having inout mode for functions is a ridiculous restriction, since functions in Ada95 do modify their arguments (the language just doesn't let you *say* that you do). ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-24 19:11 ` Matthew Heaney @ 2003-02-24 21:17 ` Randy Brukardt 2003-02-25 17:49 ` Richard Riehle 0 siblings, 1 reply; 34+ messages in thread From: Randy Brukardt @ 2003-02-24 21:17 UTC (permalink / raw) Matthew Heaney wrote in message <1ec946d1.0302241111.3e816bb@posting.google.com>... >"Randy Brukardt" <randy@rrsoftware.com> wrote in message news:<v5d1sfo9ib2df9@corp.supernews.com>... >> Matthew Heaney wrote in message >> <1ec946d1.0302201642.66eb93e5@posting.google.com>... >> >> >Here we see the reason why we passed an access parameter: it's because >> >we're returning an access value that designates one of our own >> >components. >> >> >> That reason being only that Ada doesn't support 'in out' parameters on >> functions. If it did, >> >> fuction Persistence_View >> (Object : in out T) return Persistence_Class_Access is >> begin >> return Object.Persistence_View'Access; >> end; >> >> would work fine, and would be a lot easier to use as well. > >No -- this would be the wrong way to implement the multiple views >idiom. You really do want to make explicit the fact that the object >is being aliased. All tagged objects are aliased. (It's silly that you have to declare that for object declarations, and it is true otherwise by default, but that's just a glitch in the standard). So the fact that it's tagged makes it explicit. You don't need to introduce junk access types in order to do it. (Yes, both access parameters and access discriminants introduce new access types.) ... >Which makes it identical to how you'd say it in Ada95. So this is not >really an Ada issue. Never, ever use an explicit access in Ada95 if you can avoid it. Save explicit accesses for dynamic allocation. >> But that's not going to happen, so we're stuck with terrible workarounds >> like 'access' parameters. > >Access parameters have other uses besides getting around the lack of >inout mode for function parameters. For example, operations that >accept a user-defined type as an access parameter are primitive for >the type, and hence are inherited in a derivation. And an access >parameter means you don't have to say Op (O.all) everywhere. I realize that's true, but its a pointless distinction. "in out" and "access" have pretty much the same semantics inside the subprogram. Avoid explicit access types unless they are really needed. So 'O' probably won't be a pointer in the first place, and certainly you don't want to require that it is a pointer. I'd much rather say: Op (O.all) (especially as it makes it clear that you're doing a dereference and thus require a non-null pointer) than Op (O'Unchecked_Access) And the latter requires an explicit, junk 'aliased' declaration. (It's junk because all tagged types are effectively aliased anyway -- you just have to pass them to an operation to see that.) >However, we are in agreement that not having inout mode for functions >is a ridiculous restriction, since functions in Ada95 do modify their >arguments (the language just doesn't let you *say* that you do). Wow! We agree on something! :-) Unfortunately, no one is willing to vote to change this restriction (although no one seems to have a legitimate reason for keeping it, just a bunch of FUD). Sigh. Randy. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-24 21:17 ` Randy Brukardt @ 2003-02-25 17:49 ` Richard Riehle 0 siblings, 0 replies; 34+ messages in thread From: Richard Riehle @ 2003-02-25 17:49 UTC (permalink / raw) Randy Brukardt wrote: > Never, ever use an explicit access in Ada95 if you can avoid it. Save > explicit accesses for dynamic allocation. Except, perhaps, as access to subprograms. This turns out to be a powerful capability of Ada 95. Richard Riehle ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-15 19:17 ` Richard Riehle 2003-02-15 19:59 ` Larry Kilgallen @ 2003-02-20 2:23 ` Matthew Heaney 1 sibling, 0 replies; 34+ messages in thread From: Matthew Heaney @ 2003-02-20 2:23 UTC (permalink / raw) Richard Riehle <richard@adaworks.com> wrote in message news:<3E4E9248.3E71D984@adaworks.com>... > tmoran@acm.org wrote: > > > A function may have a an access parameter, which almost has in > semantics. However, it is possible to modify a component of > an access parameter. I would like the option of preventing that > with, > > function F (X : access constant parameter-name) > return some-type; > > This would make it illegal for the function to modify the components of > an access parameter. Without the word constant, one could still modify > such components, but including it would make absolutely clear, in the > contract, that such side-effects would be impossible. The "access constant" locution will probably be incorporated into a future update of the language. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-10 18:57 ` tmoran 2003-02-15 19:17 ` Richard Riehle @ 2003-02-20 2:20 ` Matthew Heaney 1 sibling, 0 replies; 34+ messages in thread From: Matthew Heaney @ 2003-02-20 2:20 UTC (permalink / raw) tmoran@acm.org wrote in message news:<3CS1a.55972$2H6.1357@sccrnsc04>... > >What is it that you want to do? > In the case at hand, I'm using the idiom of a limited controlled type > whose initialization/finalization grabs/releases a resource lock, and the > access discriminant tells which resource. > type Lock_Type(Resource : access Resource_Type) is new > Ada.Finalization.Limited_Controlled with ... > and later > Locker : Lock_Type(Resource'unchecked_access); > ... > But this won't work when Resource is an "in" parameter, eg a function > parameter. I suppose Ada is telling me that grabbing a lock is > effectively modifying the resource, and thus something that shouldn't be > done when the resource is an "in" parameter, but the question remains, why > can't one say > type Lock_Type(Resource : access constant Resource_Type) ... > Did the designers foresee and forestall my use with a function? If your resource is limited, then use the Rosen Trick, and add a handle to the type's representation: procedure Op (Resource : in Resource_Type) is Lock : Lock_Type (Resource.Handle.Resource); begin where Handle is type Handle_Type (Resource : access Resource_Type) is limited null record; type Resource_Type is limited record Handle : Handle_Type (Resource_Type'Access); ... end record; If your resource type isn't limited, then you can safely use Address_To_Access_Conversions the type is pass-by-reference. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-10 8:26 "access constant" discriminant tmoran 2003-02-10 14:43 ` Frank J. Lhota @ 2003-02-10 19:26 ` Robert A Duff 2003-02-10 22:27 ` Rod Chapman 2003-02-20 2:17 ` Matthew Heaney 3 siblings, 0 replies; 34+ messages in thread From: Robert A Duff @ 2003-02-10 19:26 UTC (permalink / raw) tmoran@acm.org writes: > Can this be done? How? Unfortunately, no. AI's 231 and 230 attempt to correct this language design flaw, and some related things. See: http://www.ada-auth.org/cgi-bin/cvsweb.cgi/AIs/AI-00231.TXT and http://www.ada-auth.org/cgi-bin/cvsweb.cgi/AIs/AI-00230.TXT - Bob ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-10 8:26 "access constant" discriminant tmoran 2003-02-10 14:43 ` Frank J. Lhota 2003-02-10 19:26 ` Robert A Duff @ 2003-02-10 22:27 ` Rod Chapman 2003-02-11 2:00 ` Jeffrey Carter 2003-02-20 2:28 ` Matthew Heaney 2003-02-20 2:17 ` Matthew Heaney 3 siblings, 2 replies; 34+ messages in thread From: Rod Chapman @ 2003-02-10 22:27 UTC (permalink / raw) tmoran@acm.org wrote in message news:<lnJ1a.50689$SD6.3473@sccrnsc03>... > Can this be done? How? A great shame that it can't. From the viewpoint of a static analysis tool, this is dreadful, since access parameters don't specify whether the referenced objected is intended to be referenced, updated, or both - this severely limits our ability to do information flow analysis in the presence of access parameters, which needs such information to be available as part of a subprogram's specifiction if it to used usefully and efficiently implemented. In light of this, SPARK currently excludes access parameters. (In SPARK, we have parameter modes as normal, but we extend a subprogram's specification to include a list of all global data and their import/export modes via the global annotation. This makes IFA efficient, since we don't need to look inside the body - all the info we need is on the spec.) If access parameters were allowed to specify such information (e.g. "access in", "access out" and "access in out") this would be a great help. I remember mentioning this to Tucker at SigAda and he took a note of it - not sure if this issue has made it into any of the current AI's, though... - Rod ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-10 22:27 ` Rod Chapman @ 2003-02-11 2:00 ` Jeffrey Carter 2003-02-20 2:28 ` Matthew Heaney 1 sibling, 0 replies; 34+ messages in thread From: Jeffrey Carter @ 2003-02-11 2:00 UTC (permalink / raw) Rod Chapman wrote: > specifiction That's when the specification lies, right? :) -- Jeff Carter "Every sperm is sacred." Monty Python's the Meaning of Life ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-10 22:27 ` Rod Chapman 2003-02-11 2:00 ` Jeffrey Carter @ 2003-02-20 2:28 ` Matthew Heaney 2003-02-20 9:45 ` Lutz Donnerhacke 1 sibling, 1 reply; 34+ messages in thread From: Matthew Heaney @ 2003-02-20 2:28 UTC (permalink / raw) rod.chapman@praxis-cs.co.uk (Rod Chapman) wrote in message news:<cf2c6063.0302101427.51b50e12@posting.google.com>... > tmoran@acm.org wrote in message news:<lnJ1a.50689$SD6.3473@sccrnsc03>... > > Can this be done? How? > > A great shame that it can't. From the viewpoint of a static analysis > tool, this is dreadful, since access parameters don't specify whether > the referenced objected is intended to be referenced, updated, or both - this > severely limits our ability to do information flow analysis in the presence > of access parameters, which needs > such information to be available as part of a subprogram's specifiction > if it to used usefully and efficiently implemented. In light of this, SPARK > currently excludes access parameters. Realize that what the spec says about subprogram parameter modes is largely irrelevent in Ada. If the type is limited, then the Rosen Trick can be used to get a variable view of the object, no matter what the spec says. How does SPARK handle the Rosen Trick? ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-20 2:28 ` Matthew Heaney @ 2003-02-20 9:45 ` Lutz Donnerhacke 0 siblings, 0 replies; 34+ messages in thread From: Lutz Donnerhacke @ 2003-02-20 9:45 UTC (permalink / raw) * Matthew Heaney wrote: > How does SPARK handle the Rosen Trick? Spark disallow it. ^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: "access constant" discriminant 2003-02-10 8:26 "access constant" discriminant tmoran ` (2 preceding siblings ...) 2003-02-10 22:27 ` Rod Chapman @ 2003-02-20 2:17 ` Matthew Heaney 3 siblings, 0 replies; 34+ messages in thread From: Matthew Heaney @ 2003-02-20 2:17 UTC (permalink / raw) tmoran@acm.org wrote in message news:<lnJ1a.50689$SD6.3473@sccrnsc03>... > Can this be done? How? I discuss how in my design patterns tutorial, which I'll be giving in Toulouse in June. You basically have two options: 1) If your type is limited, you can use the Rosen Trick: type T; type Handle_Type (O : access T) is limited null record; type T is limited record H : Handle_Type (T'Access); <other components here> end record; Now you can do this: procedure Op (Read_Only : in T) is Read_Write : T renames Read_Only.H.O.all; begin <modify Read_Write as necessary> end; This is completly portable and safe. 2) If your type isn't limited, you can't use the Rosen Trick. But you can do something similar if you have a pass-by-reference type. Tagged types are pass-by-reference, as are types with volatile components. So you do something like this: type T is tagged record ... end record; package P is new System.Address_To_Access_Conversions (T); procedure Op (Read_Only : in T) is Pointer : constant P.Object_Pointer := P.To_Pointer (Read_Only'Address); Read_Write : T renames Pointer.all; begin <modify Read_Write as necessary> end; You might also be able to use the GNAT 'Unrestricted_Access attribute. It is indeed unfortunate that method #2 requires that we circumvent the type system just to cast away const. The GNAT attribute has the benefit that strong typing is preserved. I acually use the Rosen Trick to implement the bounded vectors in the Charles library. Incredibly, types whose full view is limited aren't implicitly aliased when passed as subprogram parameters (that's only true for tagged types -- don't ask me why...), so you need to use the Rosen Trick to get an aliased view. http://home.earthlink.net/~matthewjheaney/charles/charles-vectors-bounded.html http://home.earthlink.net/~matthewjheaney/charles/index.html ^ permalink raw reply [flat|nested] 34+ messages in thread
end of thread, other threads:[~2003-02-26 1:05 UTC | newest] Thread overview: 34+ messages (download: mbox.gz / follow: Atom feed) -- links below jump to the message on this page -- 2003-02-10 8:26 "access constant" discriminant tmoran 2003-02-10 14:43 ` Frank J. Lhota 2003-02-10 18:57 ` tmoran 2003-02-15 19:17 ` Richard Riehle 2003-02-15 19:59 ` Larry Kilgallen 2003-02-15 23:53 ` Richard Riehle 2003-02-16 1:50 ` Eric G. Miller 2003-02-20 2:23 ` Matthew Heaney 2003-02-20 17:34 ` Stephen Leake 2003-02-21 0:42 ` Matthew Heaney 2003-02-21 10:41 ` Lutz Donnerhacke 2003-02-21 20:21 ` Randy Brukardt 2003-02-23 12:22 ` Simon Wright 2003-02-24 7:06 ` Dale Stanbrough 2003-02-24 18:58 ` Matthew Heaney 2003-02-24 21:05 ` Randy Brukardt 2003-02-25 14:15 ` Frank J. Lhota 2003-02-26 1:05 ` Randy Brukardt 2003-02-24 16:03 ` Matthew Heaney 2003-02-21 15:03 ` Hyman Rosen 2003-02-21 20:09 ` Randy Brukardt 2003-02-21 21:33 ` Matthew Heaney 2003-02-21 20:07 ` Randy Brukardt 2003-02-24 19:11 ` Matthew Heaney 2003-02-24 21:17 ` Randy Brukardt 2003-02-25 17:49 ` Richard Riehle 2003-02-20 2:23 ` Matthew Heaney 2003-02-20 2:20 ` Matthew Heaney 2003-02-10 19:26 ` Robert A Duff 2003-02-10 22:27 ` Rod Chapman 2003-02-11 2:00 ` Jeffrey Carter 2003-02-20 2:28 ` Matthew Heaney 2003-02-20 9:45 ` Lutz Donnerhacke 2003-02-20 2:17 ` Matthew Heaney
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox