* Re: put of access type
2009-08-19 19:00 ` Rob Solomon
@ 2009-08-19 19:44 ` sjw
2009-08-20 1:54 ` Rob Solomon
2009-08-19 21:01 ` Adam Beneschan
` (2 subsequent siblings)
3 siblings, 1 reply; 43+ messages in thread
From: sjw @ 2009-08-19 19:44 UTC (permalink / raw)
On Aug 19, 8:00 pm, Rob Solomon <use...@drrob1-noreply.com> wrote:
> >> I would like to output a pointer to the screen. (I am just learning
> >> Ada).
>
> >> How do I put(Any_Access_Type)
>
> >You probably meant the address of the pointed object. Here you go. Let Ptr
> >be a pointer to some object
>
> >(with System.Storage_Elements; use System.Storage_Elements;)
>
> > Integer_Address'Image (To_Integer (Ptr.all'Address)));
>
> >Ptr.all'Address is the address of the object. To_Integer converts the
> >address to a plain integer type (Integer_Address defined in
> >System.Storage_Elements). This type can be output as any other.
>
> I am trying to understand this.
>
> Back when I learned Modula-2, I learned that pointer types are
> assignment compatible with System.Address and I understand them as
> being the same thing. They differ in context, not value.
>
> I see that access types are being used the same as pointer types, but
> if I understand correctly, are actually quite different. But I don't
> understand how. ie, how are access types and pointers different?
For simple types (integer; simple records) there's probably no
difference. For types with constraints/discriminants, bets are off:
consider
S : access String := "foo";
S will most likely (this is compiler-dependent) *not* point to the 'f'
in "foo"; it might point to a structure containing
4-byte integer, lower bound of string (= 1)
4-byte integer, upper bound of string (= 3)
1-byte character = f
1-byte character = o
1-byte character = o
> What is the difference between integer_address and address?
integer_address is some sort of integer, with 'image, "=", "-" etc;
address is private, with no such operations (it does have comparators;
see package System).
> I need help with this code:
>
> procedure adr is
>
> c: integer;
> x: aliased integer;
> p1, p2 : access integer;
> str : string (1..255);
>
> Begin
> p1 := x'access;
> p2 := p1;
> str := integer_address'image(to_integer(p1.all'address));
> c := integer(to_integer(p2.all'address));
>
> some put statements
> end adr;
>
> This compiles w/ GNAT under Ubuntu 9.04, but I am getting
> constraint_error, range check failed.
>
> I don't understand why
integer_address'image is going to be up to about 10 (32-bit addresses)
or 20 (64-bit addresses) characters long, and you are assigning it to
a string of length 255; that won't work.
Either pass the value directly to the put routine -- put
(integer_address'image(... -- or (probably less useful to you?) use a
declare block:
declare
str : constant string := integer_address'image(....
begin
put(str);
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-19 19:44 ` sjw
@ 2009-08-20 1:54 ` Rob Solomon
2009-08-20 2:06 ` Rob Solomon
2009-08-20 15:18 ` (see below)
0 siblings, 2 replies; 43+ messages in thread
From: Rob Solomon @ 2009-08-20 1:54 UTC (permalink / raw)
>> >You probably meant the address of the pointed object. Here you go. Let Ptr
>> >be a pointer to some object
>>
>> >(with System.Storage_Elements; �use System.Storage_Elements;)
>>
>> > � Integer_Address'Image (To_Integer (Ptr.all'Address)));
>>
>> >Ptr.all'Address is the address of the object. To_Integer converts the
>> >address to a plain integer type (Integer_Address defined in
>> >System.Storage_Elements). This type can be output as any other.
>>
>> I am trying to understand this. �
>>
>> Back when I learned Modula-2, I learned that pointer types are
>> assignment compatible with System.Address and I understand them as
>> being the same thing. �They �differ in context, not value.
>>
>> I see that access types are being used the same as pointer types, but
>> if I understand correctly, are actually quite different. �But I don't
>> understand how. �ie, how are access types and pointers different?
>
>For simple types (integer; simple records) there's probably no
>difference. For types with constraints/discriminants, bets are off:
>consider
>
> S : access String := "foo";
>
>S will most likely (this is compiler-dependent) *not* point to the 'f'
>in "foo"; it might point to a structure containing
>
> 4-byte integer, lower bound of string (= 1)
> 4-byte integer, upper bound of string (= 3)
> 1-byte character = f
> 1-byte character = o
> 1-byte character = o
>
>> What is the difference between integer_address and address?
>
>integer_address is some sort of integer, with 'image, "=", "-" etc;
>address is private, with no such operations (it does have comparators;
>see package System).
>
>integer_address'image is going to be up to about 10 (32-bit addresses)
>or 20 (64-bit addresses) characters long, and you are assigning it to
>a string of length 255; that won't work.
This is what I came up with, that works. But I have another question,
to follow the code:
procedure adr is
type card32 is mod 4_294_967_296;
package card32_IO is new Ada.Text_IO.Modular_IO(card32);
X : aliased Integer := 1;
c,k : card32 := 0;
P1,P2,P3 : Access Integer;
Str,S : String(1..255);
begin
P1 := X'Access;
P2 := P1;
P3 := new integer;
Ada.Strings.Fixed.Move(Integer_Address'Image(To_Integer(P1.all'Address)),Str);
Move(System.Address_Image(P1.all'address),s);
C :=
card32'value(Integer_Address'Image(To_Integer(P2.all'Address)));
K :=
card32'value(Integer_Address'Image(To_Integer(P3.all'Address)));
put("Str = ");
put(Str);
new_line;
put("s = ");
put(s);
put("C = ");
Card32_io.put(c);
new_line;
put("K = ");
Card32_io.put(k);
new_line;
end adr;
My question is that the value of Str and S should be equal, after
converting hex <-> decimal. They are not. I am getting this as the
relevent output
Str = 3215841220
S = BFADD7C4
These numbers are not equal, according to my conversion.
What am I missing?
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-20 1:54 ` Rob Solomon
@ 2009-08-20 2:06 ` Rob Solomon
2009-08-20 15:18 ` (see below)
1 sibling, 0 replies; 43+ messages in thread
From: Rob Solomon @ 2009-08-20 2:06 UTC (permalink / raw)
On Wed, 19 Aug 2009 21:54:05 -0400, Rob Solomon
<usenet@drrob1-noreply.com> wrote:
>>> >You probably meant the address of the pointed object. Here you go. Let Ptr
>>> >be a pointer to some object
>>>
>>> >(with System.Storage_Elements; �use System.Storage_Elements;)
>>>
>>> > � Integer_Address'Image (To_Integer (Ptr.all'Address)));
>>>
>>> >Ptr.all'Address is the address of the object. To_Integer converts the
>>> >address to a plain integer type (Integer_Address defined in
>>> >System.Storage_Elements). This type can be output as any other.
>>>
>>> I am trying to understand this. �
>>>
>>> Back when I learned Modula-2, I learned that pointer types are
>>> assignment compatible with System.Address and I understand them as
>>> being the same thing. �They �differ in context, not value.
>>>
>>> I see that access types are being used the same as pointer types, but
>>> if I understand correctly, are actually quite different. �But I don't
>>> understand how. �ie, how are access types and pointers different?
>>
>>For simple types (integer; simple records) there's probably no
>>difference. For types with constraints/discriminants, bets are off:
>>consider
>>
>> S : access String := "foo";
>>
>>S will most likely (this is compiler-dependent) *not* point to the 'f'
>>in "foo"; it might point to a structure containing
>>
>> 4-byte integer, lower bound of string (= 1)
>> 4-byte integer, upper bound of string (= 3)
>> 1-byte character = f
>> 1-byte character = o
>> 1-byte character = o
>>
>>> What is the difference between integer_address and address?
>>
>>integer_address is some sort of integer, with 'image, "=", "-" etc;
>>address is private, with no such operations (it does have comparators;
>>see package System).
>>
>>integer_address'image is going to be up to about 10 (32-bit addresses)
>>or 20 (64-bit addresses) characters long, and you are assigning it to
>>a string of length 255; that won't work.
>
>This is what I came up with, that works. But I have another question,
>to follow the code:
>
>procedure adr is
>
> type card32 is mod 4_294_967_296;
> package card32_IO is new Ada.Text_IO.Modular_IO(card32);
>
>
> X : aliased Integer := 1;
> c,k : card32 := 0;
>
> P1,P2,P3 : Access Integer;
> Str,S : String(1..255);
> begin
> P1 := X'Access;
> P2 := P1;
> P3 := new integer;
>
>Ada.Strings.Fixed.Move(Integer_Address'Image(To_Integer(P1.all'Address)),Str);
> Move(System.Address_Image(P1.all'address),s);
> C :=
>card32'value(Integer_Address'Image(To_Integer(P2.all'Address)));
> K :=
>card32'value(Integer_Address'Image(To_Integer(P3.all'Address)));
> put("Str = ");
> put(Str);
> new_line;
> put("s = ");
> put(s);
> put("C = ");
> Card32_io.put(c);
> new_line;
> put("K = ");
> Card32_io.put(k);
> new_line;
> end adr;
>
>My question is that the value of Str and S should be equal, after
>converting hex <-> decimal. They are not. I am getting this as the
>relevent output
>Str = 3215841220
>S = BFADD7C4
>
>These numbers are not equal, according to my conversion.
>
>What am I missing?
NEVERMIND
I figured it out. The output is not putting all digits on the same
line. When I corrected for this, the actual output does match when
converting from hex <-> dec
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-20 1:54 ` Rob Solomon
2009-08-20 2:06 ` Rob Solomon
@ 2009-08-20 15:18 ` (see below)
1 sibling, 0 replies; 43+ messages in thread
From: (see below) @ 2009-08-20 15:18 UTC (permalink / raw)
On 20/08/2009 02:54, in article 0gap85troslh5llfuiou61m67piv187fdr@4ax.com,
"Rob Solomon" <usenet@drrob1-noreply.com> wrote:
> procedure adr is
>
> type card32 is mod 4_294_967_296;
Better, type card32 is mod 2**32;
Ada is not Modula-2++.
> ....
> Ada.Strings.Fixed.Move(Integer_Address'Image(To_Integer(P1.all'Address)),Str);
> Move(System.Address_Image(P1.all'address),s);
> C :=
> card32'value(Integer_Address'Image(To_Integer(P2.all'Address)));
> K :=
> card32'value(Integer_Address'Image(To_Integer(P3.all'Address)));
> What am I missing?
That this is a complete waste of time if you want to learn *Ada* ?
--
Bill Findlay
<surname><forename> chez blueyonder.co.uk
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-19 19:00 ` Rob Solomon
2009-08-19 19:44 ` sjw
@ 2009-08-19 21:01 ` Adam Beneschan
2009-08-19 22:45 ` Randy Brukardt
2009-08-20 6:08 ` Martin Krischik
2009-08-20 20:57 ` Robert A Duff
3 siblings, 1 reply; 43+ messages in thread
From: Adam Beneschan @ 2009-08-19 21:01 UTC (permalink / raw)
On Aug 19, 12:00 pm, Rob Solomon <use...@drrob1-noreply.com> wrote:
> I am trying to understand this.
>
> Back when I learned Modula-2, I learned that pointer types are
> assignment compatible with System.Address and I understand them as
> being the same thing. They differ in context, not value.
>
> I see that access types are being used the same as pointer types, but
> if I understand correctly, are actually quite different. But I don't
> understand how. ie, how are access types and pointers different?
Access types can potentially carry more information than just an
"address" of something. Simon mentioned one; if a type is "access
String;", then a value that designates a string has to carry not just
the address of the sequence of characters, it also has to carry the
lower and upper bounds of the string, somehow (either the access value
is a pointer to a structure that contains the bounds somewhere, or the
bounds could be part of the access value).
Besides that, there are other cases where access objects need
additional information. In some cases, like access parameters, an
access object may carry both an "address" and some information about
the accessibility level, in order to prevent these access objects from
being stored in a way that produce pointers to objects that no longer
exist (on the stack). For access-to-subprogram objects, the access
object may need to carry information about the stack frame, so that
when a subprogram is called indirectly, it will refer to the right
local variables. Here, it's possible to implement access-to-
subprogram objects without that extra information. But since Ada
refuses to equate an "access" with an "address", it allows
implementors the freedom to implement access types as something more
than mere addresses.
Also, there's no rule saying that an access value has to be an address
at all. It's certainly conceivable that an access value may be
implemented as a reference to some storage pool and an offset into
that pool, allowing for the possibility that the memory management
system may just decide to pick up the whole pool and move it to some
other address, without making any of the access values invalid. I
don't know of any implementation that actually does this, but since
Ada doesn't equate accesses with addresses, it certainly makes
something like that possible if it's needed. Also, I can envision
that an access-to-task might, in some cases, not be an address at all,
but rather a thread ID or some other sort of ID known to the operating
system. Others have argued with me on whether this is feasible; but
since Ada doesn't equate accesses with addresses, it's at least
conceivable, and might be a fine idea in some implementations, perhaps
in limited cases.
> What is the difference between integer_address and address?
Please keep in mind that although most people are familiar with
architectures where all of memory is considered to be one big block
and addresses are just offsets into that block (a "linear address
space"), it isn't always the case. One processor I work with heavily
allows objects to be created outside that linear address space. A
System.Address in that case cannot be a mere integer; for that
processor, a System.Address is two words, where one is a descriptor
that identifies an "object" (essentially an index into the processor's
object table), and the other word is an offset into that object.
Also, I think there are some processors in which code and data are in
two separate address spaces, so that the same integer may refer to one
chunk of memory if used in a "data" context, but a different chunk if
used in a "code" context. In such a case, an implementor may not want
System.Address to be a simple integer. Also, on systems such as
these, there is no requirement that To_Integer to convert a
System.Address to an Integer_Address will always succeed (it could
raise an exception), and conversely there is no requirement that
To_Address to convert an Integer_Address to a System.Address be
capable of producing every possible address that an object could
occupy.
-- Adam
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-19 21:01 ` Adam Beneschan
@ 2009-08-19 22:45 ` Randy Brukardt
2009-08-20 6:18 ` Martin Krischik
0 siblings, 1 reply; 43+ messages in thread
From: Randy Brukardt @ 2009-08-19 22:45 UTC (permalink / raw)
"Adam Beneschan" <adam@irvine.com> wrote in message
news:c9aec6d6-4e9b-4bf6-9586-68a237175c9d@i18g2000pro.googlegroups.com...
...
>Also, there's no rule saying that an access value has to be an address
>at all. It's certainly conceivable that an access value may be
>implemented as a reference to some storage pool and an offset into
>that pool, allowing for the possibility that the memory management
>system may just decide to pick up the whole pool and move it to some
>other address, without making any of the access values invalid.
I think the Ada 95 definition of storage pools would make this
implementation hard to make work. (Which is unfortunate, it would have
worked fine in Ada 83).
I've been looking at ways to change this (a storage pool that returns
persistent handles for access values ought to be possible), but I'm not
completely certain that it is worth the effort.
Randy.
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-19 22:45 ` Randy Brukardt
@ 2009-08-20 6:18 ` Martin Krischik
2009-08-21 0:18 ` Randy Brukardt
0 siblings, 1 reply; 43+ messages in thread
From: Martin Krischik @ 2009-08-20 6:18 UTC (permalink / raw)
Randy Brukardt schrieb:
> "Adam Beneschan" <adam@irvine.com> wrote in message
> news:c9aec6d6-4e9b-4bf6-9586-68a237175c9d@i18g2000pro.googlegroups.com...
> ...
>> Also, there's no rule saying that an access value has to be an address
>> at all. It's certainly conceivable that an access value may be
>> implemented as a reference to some storage pool and an offset into
>> that pool, allowing for the possibility that the memory management
>> system may just decide to pick up the whole pool and move it to some
>> other address, without making any of the access values invalid.
>
> I think the Ada 95 definition of storage pools would make this
> implementation hard to make work. (Which is unfortunate, it would have
> worked fine in Ada 83).
It still works:
type Simple_Access is record
Offset : Integer;
end record;
type Access_All (Pool_Access : Boolean) is record
case Pool_Access is
true =>
Pool : access Pool_Type;
Offset : Integer;
false =>
Address : System.Address;
end case;
end record;
Since a simple access type always points into the pool only the Offset
is needed. since an access all can point anywhere more info is needed.
This is why I always advice against use of access all when not needed.
Martin
--
mailto://krischik@users.sourceforge.net
Ada programming at: http://ada.krischik.com
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-20 6:18 ` Martin Krischik
@ 2009-08-21 0:18 ` Randy Brukardt
2009-08-21 1:20 ` Adam Beneschan
2009-08-21 14:47 ` Robert A Duff
0 siblings, 2 replies; 43+ messages in thread
From: Randy Brukardt @ 2009-08-21 0:18 UTC (permalink / raw)
"Martin Krischik" <krischik@users.sourceforge.net> wrote in message
news:4a8cea9c$1@news.post.ch...
> Randy Brukardt schrieb:
>> "Adam Beneschan" <adam@irvine.com> wrote in message
>> news:c9aec6d6-4e9b-4bf6-9586-68a237175c9d@i18g2000pro.googlegroups.com...
>> ...
>>> Also, there's no rule saying that an access value has to be an address
>>> at all. It's certainly conceivable that an access value may be
>>> implemented as a reference to some storage pool and an offset into
>>> that pool, allowing for the possibility that the memory management
>>> system may just decide to pick up the whole pool and move it to some
>>> other address, without making any of the access values invalid.
>>
>> I think the Ada 95 definition of storage pools would make this
>> implementation hard to make work. (Which is unfortunate, it would have
>> worked fine in Ada 83).
>
> It still works:
I think you missed my point. The definition of the Allocate function for a
storage pool returns an System.Address. Moreover, there is no notification
when the access value returned from Allocate is dereferenced or converted to
another access type. So if Allocate returns an offset rather than an
address, the compiler generated code to implement .all and to implement
conversions to anonymous access type is not going to take that into
account -- it will think it received a System.Address. So this cannot work
for any user-defined storage pool.
A compiler *could* implement something like this for the default storage
pool. But that is exactly the case when you need a general implementation,
so it seems rather pointless. But you can't do this with a user-defined
storage pool. (I suppose a compiler could provide its own magic storage pool
with these semantics, but it is unlikely to be worth the effort.)
Randy.
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-21 0:18 ` Randy Brukardt
@ 2009-08-21 1:20 ` Adam Beneschan
2009-08-21 14:47 ` Robert A Duff
1 sibling, 0 replies; 43+ messages in thread
From: Adam Beneschan @ 2009-08-21 1:20 UTC (permalink / raw)
On Aug 20, 5:18 pm, "Randy Brukardt" <ra...@rrsoftware.com> wrote:
> "Martin Krischik" <krisc...@users.sourceforge.net> wrote in message
>
> news:4a8cea9c$1@news.post.ch...
>
>
>
>
>
> > Randy Brukardt schrieb:
> >> "Adam Beneschan" <a...@irvine.com> wrote in message
> >>news:c9aec6d6-4e9b-4bf6-9586-68a237175c9d@i18g2000pro.googlegroups.com...
> >> ...
> >>> Also, there's no rule saying that an access value has to be an address
> >>> at all. It's certainly conceivable that an access value may be
> >>> implemented as a reference to some storage pool and an offset into
> >>> that pool, allowing for the possibility that the memory management
> >>> system may just decide to pick up the whole pool and move it to some
> >>> other address, without making any of the access values invalid.
>
> >> I think the Ada 95 definition of storage pools would make this
> >> implementation hard to make work. (Which is unfortunate, it would have
> >> worked fine in Ada 83).
>
> > It still works:
>
> I think you missed my point. The definition of the Allocate function for a
> storage pool returns an System.Address. Moreover, there is no notification
> when the access value returned from Allocate is dereferenced or converted to
> another access type. So if Allocate returns an offset rather than an
> address, the compiler generated code to implement .all and to implement
> conversions to anonymous access type is not going to take that into
> account -- it will think it received a System.Address. So this cannot work
> for any user-defined storage pool.
It could still work using a type like Martin suggested---as long as
the compiler sets up an access type with Pool_Access=False whenever it
is using a user-defined storage pool. It would use Pool_Access=True
only for the default storage pool. Yes, that makes it less useful.
More generally, though: My comment assumed that there would be a lot
of compiler support required for an access type that is implemented as
a pool reference plus an offset. There's no reason that a compiler
that has this support couldn't also add its own rule that it supports
this kind of access type only for storage pools that are descendants
of System.Storage_Pools.Movable_Storage_Pools.-
Root_Movable_Storage_Pool (with this last child package and type
being vendor-defined). This type would contain additional operations
that the compiler would depend on to get things right; Allocate would
still return a System.Address, but some new operation defined for
Root_Movable_Storage_Pool would convert that address to an offset, and
the compiler would depend on that operation when setting up an access
type with Pool_Access=True.
A lot of work, certainly, and probably not worth the effort unless
some customer has special requirements. But my original point wasn't
intended to suggest anything practical, but just to get people
thinking a bit about the *possibility* that an access type doesn't
need to be implemented as an address, and thus to start thinking about
things like that in more abstract ways instead of being tied to low-
level concepts that other languages sometimes make you think in.
-- Adam
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-21 0:18 ` Randy Brukardt
2009-08-21 1:20 ` Adam Beneschan
@ 2009-08-21 14:47 ` Robert A Duff
2009-08-21 21:43 ` Randy Brukardt
1 sibling, 1 reply; 43+ messages in thread
From: Robert A Duff @ 2009-08-21 14:47 UTC (permalink / raw)
"Randy Brukardt" <randy@rrsoftware.com> writes:
> "Martin Krischik" <krischik@users.sourceforge.net> wrote in message
> news:4a8cea9c$1@news.post.ch...
>> Randy Brukardt schrieb:
>>> "Adam Beneschan" <adam@irvine.com> wrote in message
>>> news:c9aec6d6-4e9b-4bf6-9586-68a237175c9d@i18g2000pro.googlegroups.com...
>>> ...
>>>> Also, there's no rule saying that an access value has to be an address
>>>> at all. It's certainly conceivable that an access value may be
>>>> implemented as a reference to some storage pool and an offset into
>>>> that pool, allowing for the possibility that the memory management
>>>> system may just decide to pick up the whole pool and move it to some
>>>> other address, without making any of the access values invalid.
>>>
>>> I think the Ada 95 definition of storage pools would make this
>>> implementation hard to make work. (Which is unfortunate, it would have
>>> worked fine in Ada 83).
>>
>> It still works:
>
> I think you missed my point.
I still don't understand your point. I agree with your comments
about Ada 95 user-defined Storage_Pools. But that feature did
not exist in Ada 83, so you can't be referring to them when
you say "worked fine in Ada 83". What worked fine in Ada 83
is to represent access values as offsets from some known
place (e.g. segment-relative offsets on a 8086).
I think that still works fine in Ada 95/2005 for pool-specific access
types (which is the only kind that existed in Ada 83). The only
relevant language change is that you can convert from pool-specific to
general. So you have to be able to take your offset, and produce a
"full" address, or whatever a general access type is represented as. As
far as I can see, the addition of user-defined storage pools to the
language is irrelevant here.
(By the way, "pool-specific" is a misnomer. I was confused
when I invented that term during Ada 9X!)
I agree with you that it would be nice if user-defined storage
pools _could_ be used with offsets, or other oddball representations
of access types.
>...The definition of the Allocate function for a
> storage pool returns an System.Address. Moreover, there is no notification
> when the access value returned from Allocate is dereferenced or converted to
> another access type. So if Allocate returns an offset rather than an
> address, the compiler generated code to implement .all and to implement
> conversions to anonymous access type is not going to take that into
> account -- it will think it received a System.Address. So this cannot work
> for any user-defined storage pool.
>
> A compiler *could* implement something like this for the default storage
> pool. But that is exactly the case when you need a general implementation,
> so it seems rather pointless. But you can't do this with a user-defined
> storage pool. (I suppose a compiler could provide its own magic storage pool
> with these semantics, but it is unlikely to be worth the effort.)
- Bob
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-21 14:47 ` Robert A Duff
@ 2009-08-21 21:43 ` Randy Brukardt
2009-08-22 0:07 ` Robert A Duff
0 siblings, 1 reply; 43+ messages in thread
From: Randy Brukardt @ 2009-08-21 21:43 UTC (permalink / raw)
"Robert A Duff" <bobduff@shell01.TheWorld.com> wrote in message
news:wccr5v5xlza.fsf@shell01.TheWorld.com...
...
> I think that still works fine in Ada 95/2005 for pool-specific access
> types (which is the only kind that existed in Ada 83). The only
> relevant language change is that you can convert from pool-specific to
> general. So you have to be able to take your offset, and produce a
> "full" address, or whatever a general access type is represented as. As
> far as I can see, the addition of user-defined storage pools to the
> language is irrelevant here.
I don't see how this could work. There is no call-back to the storage pool
when converting from pool-specific to general access, so how could the pool
make the conversion? The compiler can't make the conversion, it doesn't know
anything about the implementation of the pool for an access type.
Even if the compiler could know about the need for this magic for some
specific type, it would have to be prepared to generate code to convert to
address in many places other than a straight conversion (renaming .all or
passing .all as a parameter, for instance). The code to make that conversion
probably would be more expensive than any savings gained elsewhere. And such
a model would completely prevent any implementation strategies based on all
access types having a well-defined storage pool. (Humm, I suppose it could
be done with an extension of Root_Storage_Pool, but that would make the code
for dereferencing prohibititively expensive, since you'd have to do a tag
test before you could dispatch.)
So I guess I was a bit strong at the start here: it could be made to work,
but only by abandoning all reasonable implementation strategies and
accepting substantial overhead. Which doesn't make sense to me.
Randy.
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-21 21:43 ` Randy Brukardt
@ 2009-08-22 0:07 ` Robert A Duff
2009-09-01 1:57 ` Randy Brukardt
0 siblings, 1 reply; 43+ messages in thread
From: Robert A Duff @ 2009-08-22 0:07 UTC (permalink / raw)
"Randy Brukardt" <randy@rrsoftware.com> writes:
> "Robert A Duff" <bobduff@shell01.TheWorld.com> wrote in message
> news:wccr5v5xlza.fsf@shell01.TheWorld.com...
> ...
>> I think that still works fine in Ada 95/2005 for pool-specific access
>> types (which is the only kind that existed in Ada 83). The only
>> relevant language change is that you can convert from pool-specific to
>> general. So you have to be able to take your offset, and produce a
>> "full" address, or whatever a general access type is represented as. As
>> far as I can see, the addition of user-defined storage pools to the
>> language is irrelevant here.
>
> I don't see how this could work. There is no call-back to the storage pool
> when converting from pool-specific to general access, so how could the pool
> make the conversion?
I'm lost. You said Ada 83 compilers can represent access types as
offsets from some known place. I agree. And I claim Ada 95/2005
compilers can do the same. Nothing to do with storage pools, which did not
exist in Ada 83.
- Bob
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-22 0:07 ` Robert A Duff
@ 2009-09-01 1:57 ` Randy Brukardt
0 siblings, 0 replies; 43+ messages in thread
From: Randy Brukardt @ 2009-09-01 1:57 UTC (permalink / raw)
"Robert A Duff" <bobduff@shell01.TheWorld.com> wrote in message
news:wccmy5semnv.fsf@shell01.TheWorld.com...
> "Randy Brukardt" <randy@rrsoftware.com> writes:
>
>> "Robert A Duff" <bobduff@shell01.TheWorld.com> wrote in message
>> news:wccr5v5xlza.fsf@shell01.TheWorld.com...
>> ...
>>> I think that still works fine in Ada 95/2005 for pool-specific access
>>> types (which is the only kind that existed in Ada 83). The only
>>> relevant language change is that you can convert from pool-specific to
>>> general. So you have to be able to take your offset, and produce a
>>> "full" address, or whatever a general access type is represented as. As
>>> far as I can see, the addition of user-defined storage pools to the
>>> language is irrelevant here.
>>
>> I don't see how this could work. There is no call-back to the storage
>> pool
>> when converting from pool-specific to general access, so how could the
>> pool
>> make the conversion?
>
> I'm lost. You said Ada 83 compilers can represent access types as
> offsets from some known place. I agree. And I claim Ada 95/2005
> compilers can do the same. Nothing to do with storage pools, which did
> not
> exist in Ada 83.
An Ada 83 compiler can represent *all* access types as offsets from some
known place. That's how our old CP/M compilers worked. But since Ada 95
access types can be converted to general access types (without any sort of
conversion function in the case of access types with a storage pool), it
isn't possible to retain such an implementation in general. I suppose you
could use such an implementation for a specific access type with the use of
a special implementation-defined pragma (and then you would have to disallow
conversions to any other access type, which is not Ada 95), but that is
*not* the sort of implementation model that I was thinking of.
Randy.
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-19 19:00 ` Rob Solomon
2009-08-19 19:44 ` sjw
2009-08-19 21:01 ` Adam Beneschan
@ 2009-08-20 6:08 ` Martin Krischik
2009-08-20 20:57 ` Robert A Duff
3 siblings, 0 replies; 43+ messages in thread
From: Martin Krischik @ 2009-08-20 6:08 UTC (permalink / raw)
Rob Solomon schrieb:
> I see that access types are being used the same as pointer types, but
> if I understand correctly, are actually quite different. But I don't
> understand how. ie, how are access types and pointers different?
Access types can be smart pointers containing additional informations
used by garbage collectors. "Can" only JGNAT (targeting JVM) and MGNAT
(targeting CLI) currently feature a garbage collector.
Still there is at least one case where standart GNAT uses smart pointers
as well. Can't remember the details - but it has to to with anonymous
access types used as function parameter (a new feature introduced with
Ada 95). With GNAT this access type consist then of an pointer and
integer sized extra info.
Martin
--
mailto://krischik@users.sourceforge.net
Ada programming at: http://ada.krischik.com
^ permalink raw reply [flat|nested] 43+ messages in thread
* Re: put of access type
2009-08-19 19:00 ` Rob Solomon
` (2 preceding siblings ...)
2009-08-20 6:08 ` Martin Krischik
@ 2009-08-20 20:57 ` Robert A Duff
3 siblings, 0 replies; 43+ messages in thread
From: Robert A Duff @ 2009-08-20 20:57 UTC (permalink / raw)
Rob Solomon <usenet@drrob1-noreply.com> writes:
> I see that access types are being used the same as pointer types, but
> if I understand correctly, are actually quite different. But I don't
> understand how. ie, how are access types and pointers different?
It depends on what you mean by "pointer". Yes, "access types" in Ada
are pretty much the same as "pointer types" in many other languages.
They are used primarily to point to heap-allocated data structures
(linked lists, trees, etc).
There are differences between Ada's access, and Pascal or Modula-2's
pointer. But they are minor. The differences between Ada and C
in this area area larger (in particular, C uses pointers for
by-hand-by-reference parameter passing, and for cursors within
arrays (incrementing a pointer to an array element in C causes
it to point to the next element) -- no such thing in Ada).
Some folks in this thread have emphasized the fact that in Ada, an
access value is not necessarily represented as a (single) machine
address. That's true. But the same is true of many other languages,
including even C.
> What is the difference between integer_address and address?
They're completely different.
I think you're going about this in a wrong way. I presume you want to
learn Ada, and in particular you want to learn how to use Ada's access
types. Is that correct?
If so, you should (at first) avoid any use of "aliased" or 'Access.
You should avoid pretty much everything in chap 13 of the RM,
including Address, Integer_Address, 'Address, operations on
addresses.
Instead, focus on linked lists and trees and other heap-based data
structures. And understand access values by drawing pictures with
boxes and arrows. That's how I learned about pointers in Pascal.
Nothing wrong with printing out an access value for debugging
(or understanding) purposes. I showed you an easy way to do
that in GNAT (Address_Image). But don't focus on that.
Later on, learn about aliased and 'Access and 'Unchecked_Access.
And later still, learn about chap 13 stuff, like type Address.
> I need help with this code:
>
> procedure adr is
>
> c: integer;
> x: aliased integer;
> p1, p2 : access integer;
> str : string (1..255);
>
> Begin
> p1 := x'access;
> p2 := p1;
> str := integer_address'image(to_integer(p1.all'address));
> c := integer(to_integer(p2.all'address));
>
> some put statements
> end adr;
>
> This compiles w/ GNAT under Ubuntu 9.04, but I am getting
> constraint_error, range check failed.
>
> I don't understand why
In Ada, "string (1..255)" means a String of _exactly_ 255 characters.
Not a string of "at most" 255 characters.
- Bob
^ permalink raw reply [flat|nested] 43+ messages in thread