comp.lang.ada
 help / color / mirror / Atom feed
* Ada Examples and Problems
@ 2001-04-10 13:38 chris.danx
  2001-04-10 17:53 ` chris.danx
       [not found] ` <ERFA6.2041$FY5.146015@www.newsranger.com>
  0 siblings, 2 replies; 17+ messages in thread
From: chris.danx @ 2001-04-10 13:38 UTC (permalink / raw)


Hi,
    Some of you may remember i was writing a few Ada examples.  I've got one
on streams which is almost complete.  It has a small problem.  I've been all
over the program but can't find the problem.  The error occurs in
display_kernel.adb.

Basically the program should read in the owners from a file, then the dogs.
The file is arranged owner, dog, owner, dog...

It was meant to be an example of streams.  I'd greatly appreciate anyone's
help with this.

you can find the page via http://willow.os-4u.com

Thanks in advance,
Chris Campbell







^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-10 13:38 Ada Examples and Problems chris.danx
@ 2001-04-10 17:53 ` chris.danx
  2001-04-10 17:57   ` chris.danx
       [not found] ` <ERFA6.2041$FY5.146015@www.newsranger.com>
  1 sibling, 1 reply; 17+ messages in thread
From: chris.danx @ 2001-04-10 17:53 UTC (permalink / raw)


Hi folks,

I rewrote the part of the example that reads data from the file.  It works
now but not as i intended.

The program was supposed to read in

    a) owners first
    b) dogs second

    X) then display the output

as an example of non sequential Stream IO.  This means the problem lies with
the read_owners and the read_dogs routines.

Each owner record is followed by a dog record which is followed by a owner
record and so on.

There are five of each, meaning ten records in total.

I got the sizes of each record from the program

dog_type:    56 bytes
owner_type: 41 bytes

starting at 1, i read the first owner.
this means we're now at 42 after the first read.


Add size of dog_type in stream elements, this is byte for GNAT.
this means we're now at 56+42 = 98

add 1
we're now at 99

read next owner.


That's the theory.  The reality is different.

The reads occur at

        1
      97
    193
    289
    385
    481

Which i don't understand.

Does anyone have any ideas?


Thanks,
Chris Campbell

p.s. I got the program to work by doing a read of owner then dog 5 times.  I
wanted to demonstrate non-sequential access and this is the opposite.





^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-10 17:53 ` chris.danx
@ 2001-04-10 17:57   ` chris.danx
  0 siblings, 0 replies; 17+ messages in thread
From: chris.danx @ 2001-04-10 17:57 UTC (permalink / raw)


Sorry mistake!  Should have been

 starting at 1, i read the first owner.
 this means we're now at 42 after the first read.


 Add size of dog_type in stream elements, this is byte for GNAT.
 this means we're now at 56+41 = 97

 add 1
 we're now at 98

 read next owner.


 That's the theory.  The reality is different.

 The reads occur at

         1
       97
     193
     289
     385
     481

 Which i don't understand.

 Does anyone have any ideas?


 Thanks,
 Chris Campbell
>
> p.s. I got the program to work by doing a read of owner then dog 5 times.
I
> wanted to demonstrate non-sequential access and this is the opposite.
>
>





^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
       [not found] ` <ERFA6.2041$FY5.146015@www.newsranger.com>
@ 2001-04-11  9:51   ` chris.danx
  2001-04-11 15:34     ` Ted Dennison
  2001-04-12  1:41     ` tmoran
  0 siblings, 2 replies; 17+ messages in thread
From: chris.danx @ 2001-04-11  9:51 UTC (permalink / raw)



> >Basically the program should read in the owners from a file, then the
dogs.
> >The file is arranged owner, dog, owner, dog...
> So what *is* it doing?

I'm a complete numpty!  Sorry!

The program appears to read all the owners from the file.  When it goes to
output them on the screen it print's the first owner ok, but then hit's out
with a constraint error on the second.

The problem definitely comes from the way it reads the file's.  I've tested
the onwer_type completely.  It works on a sequential read but not on a
non-sequential read.

It should read the first record(owner), skip one(dog), read(owner)...

This is what i thought would achieve it.


   procedure read_owners (the_owners : out owner_array_type;
                          file       : in out file_type) is
      count   :   natural := 1;
      strm    :   stream_access;
      offset  :   positive;
   begin
      strm := stream(file);               -- get a stream from a file;

      set_index(file, 1);

      offset :=  (doggies.dog_type'size / 8);   -- calculate the offset of
next owner;


      while count <= 5 and not end_of_file(file) loop
         owners.owner_type'read(strm, the_owners(count));
         set_index(file, index(file) + positive_count(offset+1));
         ada.integer_text_io.put(integer(index(file)));
         ada.text_io.new_line;
         count := count + 1;
      end loop;
   end read_owners;


I reckon that it has something to do with the records size.  I'm not sure
what though.  Is the size of the record the same as the number of bytes
written per record?  Maybe this is it.


This is my first endevour into the world of non-sequential streams and i'm
still trying to get this right.  I just thought of something, I've tried
adding 1, not adding 1, but not taking 1 away.  I'll try that now!


Regards,
Chris





^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-11  9:51   ` chris.danx
@ 2001-04-11 15:34     ` Ted Dennison
  2001-04-11 17:18       ` chris.danx
  2001-04-12  1:41     ` tmoran
  1 sibling, 1 reply; 17+ messages in thread
From: Ted Dennison @ 2001-04-11 15:34 UTC (permalink / raw)


In article <DOVA6.3493$FD1.403553@news6-win.server.ntlworld.com>, chris.danx
says...
>
>
>The program appears to read all the owners from the file.  When it goes to
>output them on the screen it print's the first owner ok, but then hit's out
>with a constraint error on the second.
>
>The problem definitely comes from the way it reads the file's.  I've tested
>the onwer_type completely.  It works on a sequential read but not on a
>non-sequential read.
>
>It should read the first record(owner), skip one(dog), read(owner)...

..
>      while count <= 5 and not end_of_file(file) loop
>         owners.owner_type'read(strm, the_owners(count));
>         set_index(file, index(file) + positive_count(offset+1));
>         ada.integer_text_io.put(integer(index(file)));
>         ada.text_io.new_line;
>         count := count + 1;
>      end loop;
>   end read_owners;

Ahhhh. You are using indexing to move the file pointer around. You do of course
realize that this is completely non-portable, unless you wrote your own
Dog_Type'Write and Dog_Type'Read routines? There's no LRM guarantee for how many
storage units that the compiler will decide to use for each Dog_Type. 

In fact, my suspicion would be that it indeed does not use the same number of
storage units as you think it does for Dog_Type (1, if I read your code right).
The best way to check is to use "od" to view the data in the file. If you are
using Windoze instead of Unix, go get Cygwin (see my website for the URL). It
should have a copy of od in it. A wild guess would be that your system uses a
byte for a storage unit, and Dog_Type is 4 of them (assuming its some kind of
enumeration or integer). But I'd check it out for sure.

---
T.E.D.    homepage   - http://www.telepath.com/dennison/Ted/TED.html
          home email - mailto:dennison@telepath.com



^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-11 15:34     ` Ted Dennison
@ 2001-04-11 17:18       ` chris.danx
  2001-04-11 17:43         ` chris.danx
  2001-04-12 15:28         ` Ted Dennison
  0 siblings, 2 replies; 17+ messages in thread
From: chris.danx @ 2001-04-11 17:18 UTC (permalink / raw)



"Ted Dennison" <dennison@telepath.com> wrote in message
news:nQ_A6.3185$FY5.218929@www.newsranger.com...
> In article <DOVA6.3493$FD1.403553@news6-win.server.ntlworld.com>,
chris.danx
> says...
> >
> >
> >The program appears to read all the owners from the file.  When it goes
to
> >output them on the screen it print's the first owner ok, but then hit's
out
> >with a constraint error on the second.
> >
> >The problem definitely comes from the way it reads the file's.  I've
tested
> >the onwer_type completely.  It works on a sequential read but not on a
> >non-sequential read.
> >
> >It should read the first record(owner), skip one(dog), read(owner)...
>
> ..
> >      while count <= 5 and not end_of_file(file) loop
> >         owners.owner_type'read(strm, the_owners(count));
> >         set_index(file, index(file) + positive_count(offset+1));
> >         ada.integer_text_io.put(integer(index(file)));
> >         ada.text_io.new_line;
> >         count := count + 1;
> >      end loop;
> >   end read_owners;
>
> Ahhhh. You are using indexing to move the file pointer around. You do of
course
> realize that this is completely non-portable, unless you wrote your own
> Dog_Type'Write and Dog_Type'Read routines?

I did do this.

> There's no LRM guarantee for how many
> storage units that the compiler will decide to use for each Dog_Type.

That's not suprising but it is a bugger.

> In fact, my suspicion would be that it indeed does not use the same number
of
> storage units as you think it does for Dog_Type (1, if I read your code
right).

Ok.  I think i'll try working out the size (should be 30+4+4+size of enum
sex_type).

> The best way to check is to use "od" to view the data in the file. If you
are
> using Windoze instead of Unix, go get Cygwin (see my website for the URL).
It
> should have a copy of od in it. A wild guess would be that your system
uses a
> byte for a storage unit, and Dog_Type is 4 of them (assuming its some
> kind of
> enumeration or integer). But I'd check it out for sure.

I'll take a look and see.  Thanks for the info.


If what you've said is correct how then can i write the code so that i don't
need to count each individual entry and hardwire it into the program.  It'd
be much nicer if when i changed the types, i could just recompile the
modules without changing the values for the sizes of records.

I should go to eat something, that was totally incomprehensible.

Cheers,
Chris





^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-11 17:18       ` chris.danx
@ 2001-04-11 17:43         ` chris.danx
  2001-04-11 19:01           ` Marc A. Criley
  2001-04-12 15:28         ` Ted Dennison
  1 sibling, 1 reply; 17+ messages in thread
From: chris.danx @ 2001-04-11 17:43 UTC (permalink / raw)


I'm not impressed.  I've spent 2 or 3 days on this and it's drove me nuts.
2 minutes after i read your post I got it working.

The size of the record dog_type is 56 but the size of it's contents is 53.
Just 3 bytes of padding and 3 bytes that drove me nuts.

This is something i'm going to have to watch out for in future.  I've got an
idea about how to limit the chances of me running into this again.  I'm
going to put a function for every type i might write to a stream (that's not
dynamic in size) that gives the size of it's contents.

-- a function that returns the total size of all fields in type X;
--
function size_of_fields(t : in X) return natural;

Not the best option but certainly better than hardwiring it into the
file/stream handling routines.


Thanks to Ted and everyone else who's helped me with this.

Regards,
Chris





^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-11 17:43         ` chris.danx
@ 2001-04-11 19:01           ` Marc A. Criley
  2001-04-11 19:56             ` chris.danx
  0 siblings, 1 reply; 17+ messages in thread
From: Marc A. Criley @ 2001-04-11 19:01 UTC (permalink / raw)


"chris.danx" wrote:
> 
> This is something i'm going to have to watch out for in future.  I've got an
> idea about how to limit the chances of me running into this again.  I'm
> going to put a function for every type i might write to a stream (that's not
> dynamic in size) that gives the size of it's contents.
> 
> -- a function that returns the total size of all fields in type X;
> --
> function size_of_fields(t : in X) return natural;
> 
> Not the best option but certainly better than hardwiring it into the
> file/stream handling routines.

This just reminded me of a thread that was raging here for awhile last
year regarding the 'Size of types and objects versus the number of bytes
objects occupy in a stream (stream meaning the Stream_IO kind of
stream).

Bottom line:  There is _no_ required correspondence between those sizes.

This can be frustrating at times, and did engender some smoke and fire
in the newsgroup.  There are situations where one wants to know ahead of
time how many bytes something is going to occupy in a stream, but Ada
does not require that an ability to make that determination for all
types be available.

Marc A. Criley
Senior Staff Engineer
Quadrus Corporation
www.quadruscorp.com



^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-11 19:01           ` Marc A. Criley
@ 2001-04-11 19:56             ` chris.danx
  2001-04-12  1:41               ` tmoran
  0 siblings, 1 reply; 17+ messages in thread
From: chris.danx @ 2001-04-11 19:56 UTC (permalink / raw)



> This just reminded me of a thread that was raging here for awhile last
> year regarding the 'Size of types and objects versus the number of bytes
> objects occupy in a stream (stream meaning the Stream_IO kind of
> stream).
>
> Bottom line:  There is _no_ required correspondence between those sizes.
>
> This can be frustrating at times, and did engender some smoke and fire
> in the newsgroup.  There are situations where one wants to know ahead of
> time how many bytes something is going to occupy in a stream, but Ada
> does not require that an ability to make that determination for all
> types be available.

Maybe this would be a good idea for addition in Ada 0y.  An attribute that
gives the total number of bytes/bits occupied by the fields not the record
size.

T'save_me_a_headache

or

T'field_bytes


Bye,
Chris







^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-11 19:56             ` chris.danx
@ 2001-04-12  1:41               ` tmoran
  0 siblings, 0 replies; 17+ messages in thread
From: tmoran @ 2001-04-12  1:41 UTC (permalink / raw)



>Maybe this would be a good idea for addition in Ada 0y.  An attribute that
>gives the total number of bytes/bits occupied by the fields not the record
>size.
>T'field_bytes
  The size in memory does not necessarily relate to the size in 'write.
It would be legal (if weird) for the 'write to write the bytes values
as comma separated integers, each expressed in Roman numerals.

>> time how many bytes something is going to occupy in a stream, but Ada
>> does not require that an ability to make that determination for all
>> types be available.
  You can determine it at run time by creating a dummy stream with
your own
procedure Write(Stream : in out My_Type; Item : in Stream_Element_Array);
and having that note Item'length for 'Writes on various things.



^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-11  9:51   ` chris.danx
  2001-04-11 15:34     ` Ted Dennison
@ 2001-04-12  1:41     ` tmoran
  2001-04-12 10:15       ` chris.danx
  1 sibling, 1 reply; 17+ messages in thread
From: tmoran @ 2001-04-12  1:41 UTC (permalink / raw)


>It works on a sequential read but not on a non-sequential read.
  "For direct access, the file is viewed as a set of elements
occupying consecutive positions in linear order;..."  LRM A.8(3)
So each element of a direct access file must be the same size.
Since you have owner, dog, owner, dog... where owner and dog are
different size records, that won't work.  But "Pair" in
  type Pair is
    Person : Owner;
    Animal : Dog;
  end record;
is a constant size record.  If you want the N-th owner, or N-th dog,
  Set_Index(The_File, N);
That seems easier than taking the individual byte as the constant
size element and then doing arithmetic that you hope gets you to
the correct byte position.



^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-12  1:41     ` tmoran
@ 2001-04-12 10:15       ` chris.danx
  0 siblings, 0 replies; 17+ messages in thread
From: chris.danx @ 2001-04-12 10:15 UTC (permalink / raw)



> >It works on a sequential read but not on a non-sequential read.
>   "For direct access, the file is viewed as a set of elements
> occupying consecutive positions in linear order;..."  LRM A.8(3)
> So each element of a direct access file must be the same size.
> Since you have owner, dog, owner, dog... where owner and dog are
> different size records, that won't work.  But "Pair" in
>   type Pair is
>     Person : Owner;
>     Animal : Dog;
>   end record;
> is a constant size record.  If you want the N-th owner, or N-th dog,
>   Set_Index(The_File, N);
> That seems easier than taking the individual byte as the constant
> size element and then doing arithmetic that you hope gets you to
> the correct byte position.

Thanks for that I'll use it in future.

The reason i did it with two different sized records was because I'm writing
a driver for a file system.  It's contigouous which means i've got to do all
sorts of mad calculations and access the stream.  It's not fun.

Thanks again,
Chris Campbell
http://willow.os-4u.com








^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-11 17:18       ` chris.danx
  2001-04-11 17:43         ` chris.danx
@ 2001-04-12 15:28         ` Ted Dennison
  2001-04-12 18:56           ` chris.danx
  1 sibling, 1 reply; 17+ messages in thread
From: Ted Dennison @ 2001-04-12 15:28 UTC (permalink / raw)


In article <sl0B6.3907$Ow3.824242@news2-win.server.ntlworld.com>, chris.danx
says...
>
>
>"Ted Dennison" <dennison@telepath.com> wrote in message
>news:nQ_A6.3185$FY5.218929@www.newsranger.com...
>> Ahhhh. You are using indexing to move the file pointer around. You do of
>course
>> realize that this is completely non-portable, unless you wrote your own
>> Dog_Type'Write and Dog_Type'Read routines?
>
>I did do this.

Oh. So you actually wrote code to convert Dog_Type into Stream_Elements and send
it to Ada.Streams.Write? That changes things significantly. In that case you do
know exactly how many stream elements Dog_Type uses. So its just a simple matter
of updating the file index by that many elements (probably *not* 1 though).


>If what you've said is correct how then can i write the code so that i don't
>need to count each individual entry and hardwire it into the program.  It'd
>be much nicer if when i changed the types, i could just recompile the
>modules without changing the values for the sizes of records.

You've already hit upon the answer: Write your own 'Write and 'Read routines,
and then your code can properly size itself automaticly. (If this isn't what you
did, tell me. I probably can dig up an example of this to post).

---
T.E.D.    homepage   - http://www.telepath.com/dennison/Ted/TED.html
          home email - mailto:dennison@telepath.com



^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-12 15:28         ` Ted Dennison
@ 2001-04-12 18:56           ` chris.danx
  2001-04-12 19:01             ` chris.danx
  2001-04-12 21:47             ` Ted Dennison
  0 siblings, 2 replies; 17+ messages in thread
From: chris.danx @ 2001-04-12 18:56 UTC (permalink / raw)


Hi,

> Oh. So you actually wrote code to convert Dog_Type into Stream_Elements
and send
> it to Ada.Streams.Write? That changes things significantly. In that case
you > do know exactly how many stream elements Dog_Type uses.

Ok maybe i'm confused as to what you meant.

I wrote the following

    procedure owner_write (s      : access ...
                                          item : in owner_type) is
    begin
        owner_name_type'write (s, item.name);
        integer'write                   (s, item.age);
        sex_type'write                (s, item.sex);
    end  owner_write;

but i get the feeling that's not what you meant.  Is it?


> So its just a simple matter
> of updating the file index by that many elements (probably *not* 1
though).

I've got a small problem with sex_type which is a single bit.  I thought
about

for sex_type'size use 8;

I'll make this change soon.


> >If what you've said is correct how then can i write the code so that i
don't
> >need to count each individual entry and hardwire it into the program.
It'd
> >be much nicer if when i changed the types, i could just recompile the
> >modules without changing the values for the sizes of records.
>
> You've already hit upon the answer: Write your own 'Write and 'Read
routines,
> and then your code can properly size itself automaticly. (If this isn't
what you
> did, tell me. I probably can dig up an example of this to post).

I don't know if i did what you suggested or not.  Are you suggesting using
(I don't recall this properly i saw it in the LRM) something like
stream_element_array?

Even if my read write routines are correct, how can my code adjust
automatically.  I want to skip records in the stream, to do that i need to
know the size of the block i'm jumping over.  I don't want to read the block
in order to skip it.  I want to just jump over it.  I must be missing
something somewhere (like my brains')!


Thanks,
Chris.









^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-12 18:56           ` chris.danx
@ 2001-04-12 19:01             ` chris.danx
  2001-04-12 21:47             ` Ted Dennison
  1 sibling, 0 replies; 17+ messages in thread
From: chris.danx @ 2001-04-12 19:01 UTC (permalink / raw)


Oh i forgot the

for owner_type'write use owner_write;


Sorry,
Chris

told you i'd lost my brains didn't i?





^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-12 18:56           ` chris.danx
  2001-04-12 19:01             ` chris.danx
@ 2001-04-12 21:47             ` Ted Dennison
  2001-04-13  8:40               ` chris.danx
  1 sibling, 1 reply; 17+ messages in thread
From: Ted Dennison @ 2001-04-12 21:47 UTC (permalink / raw)


In article <oTmB6.7485$FD1.924788@news6-win.server.ntlworld.com>, chris.danx
says...
>Ok maybe i'm confused as to what you meant.
>
>I wrote the following
>
>    begin
>        owner_name_type'write (s, item.name);
>        integer'write                   (s, item.age);
>        sex_type'write                (s, item.sex);
>    end  owner_write;
>
>but i get the feeling that's not what you meant.  Is it?

Not quite. Ada allows you to override 'Write and 'Read with your own routines.
Now you can do that, then just write the above. But now you still don't know the
size of all the little 'Writes. However, if you Unchecked_Convert the entire
structure into a stream element array, then pass it into Ada.Streams.Write
directly, then obviously you now know exactly how many stream elements it uses. 

>Even if my read write routines are correct, how can my code adjust
>automatically.  I want to skip records in the stream, to do that i need to

If you do your own conversion to an array of stream elements, rather than
letting Ada do it for you, then calculating the length of the array required is
fairly easy (you'll have to do it to get the unchecked_Conversion to work
anyway). Since you now know that length, you can just increment the file pointer
by that length to skip the entire object in the stream (file).

---
T.E.D.    homepage   - http://www.telepath.com/dennison/Ted/TED.html
          home email - mailto:dennison@telepath.com



^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: Ada Examples and Problems
  2001-04-12 21:47             ` Ted Dennison
@ 2001-04-13  8:40               ` chris.danx
  0 siblings, 0 replies; 17+ messages in thread
From: chris.danx @ 2001-04-13  8:40 UTC (permalink / raw)


Thankyou Ted


chris





^ permalink raw reply	[flat|nested] 17+ messages in thread

end of thread, other threads:[~2001-04-13  8:40 UTC | newest]

Thread overview: 17+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2001-04-10 13:38 Ada Examples and Problems chris.danx
2001-04-10 17:53 ` chris.danx
2001-04-10 17:57   ` chris.danx
     [not found] ` <ERFA6.2041$FY5.146015@www.newsranger.com>
2001-04-11  9:51   ` chris.danx
2001-04-11 15:34     ` Ted Dennison
2001-04-11 17:18       ` chris.danx
2001-04-11 17:43         ` chris.danx
2001-04-11 19:01           ` Marc A. Criley
2001-04-11 19:56             ` chris.danx
2001-04-12  1:41               ` tmoran
2001-04-12 15:28         ` Ted Dennison
2001-04-12 18:56           ` chris.danx
2001-04-12 19:01             ` chris.danx
2001-04-12 21:47             ` Ted Dennison
2001-04-13  8:40               ` chris.danx
2001-04-12  1:41     ` tmoran
2001-04-12 10:15       ` chris.danx

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox