Hello, any theoric example of buffer i can find is always tied to an specific type. I'm looking for any example of ravenscar buffer able for using any type of data at the same time. I suppose it will need to serialize all data and manipulate it as a group of bytes. Does any body knows any example of this written in Ada?
On 04/07/2020 19:00, Daniel wrote: > I'm looking for any example of ravenscar buffer able for using any type of data at the same time. > > I suppose it will need to serialize all data and manipulate it as a group of bytes. > > Does any body knows any example of this written in Ada? Ring buffer of indefinite elements would be OK. As an element you can use this: type Item (Size : Stream_Element_Count) is record Data : Stream_Element_Array (1..Size); end record; Instantiate the generic buffer with this type. Use stream attributes to serialize/deserialize. Alternatively you can do it with Storage_Element in the above and use a fake storage pool to store/restore objects. Or a combination "for X'Address use Y" with pragma Import (Ada, X); If the type set is somewhat statically known you can use a variant record as an element too. In some cases you can have a ring buffer of type tags and a set of ring buffers. For each type tag you would keep values in a separate ring buffer. -- Regards, Dmitry A. Kazakov http://www.dmitry-kazakov.de
"Dmitry A. Kazakov" <mailbox@dmitry-kazakov.de> writes:
> Ring buffer of indefinite elements would be OK. As an element you can
> use this:
>
> type Item (Size : Stream_Element_Count) is record
> Data : Stream_Element_Array (1..Size);
> end record;
For the Size, see ARM 13.13.2(2).
Simon Wright <simon@pushface.org> writes:
> For the Size, see ARM 13.13.2(2).
13.13.2(1.2), sorry
On 7/5/20 11:52 AM, Simon Wright wrote: > Simon Wright <simon@pushface.org> writes: > >> For the Size, see ARM 13.13.2(2). > > 13.13.2(1.2), sorry That only works for elementary types. For any type, a better approach is generic package Ada.Storage_IO, ARM A.9 (http://www.ada-auth.org/standards/rm12_w_tc1/html/RM-A-9.html). -- Jeff Carter "C++: The power, elegance and simplicity of a hand grenade." Ole-Hjalmar Kristensen 90
"Jeffrey R. Carter" <spam.jrcarter.not@spam.not.acm.org> writes:
> On 7/5/20 11:52 AM, Simon Wright wrote:
>> Simon Wright <simon@pushface.org> writes:
>>
>>> For the Size, see ARM 13.13.2(2).
>>
>> 13.13.2(1.2), sorry
>
> That only works for elementary types. For any type, a better approach
> is generic package Ada.Storage_IO, ARM A.9
> (http://www.ada-auth.org/standards/rm12_w_tc1/html/RM-A-9.html).
As you say, this has the advantage of actually working.
On 05/07/2020 17:36, Simon Wright wrote: > "Jeffrey R. Carter" <spam.jrcarter.not@spam.not.acm.org> writes: > >> On 7/5/20 11:52 AM, Simon Wright wrote: >>> Simon Wright <simon@pushface.org> writes: >>> >>>> For the Size, see ARM 13.13.2(2). >>> >>> 13.13.2(1.2), sorry >> >> That only works for elementary types. For any type, a better approach >> is generic package Ada.Storage_IO, ARM A.9 >> (http://www.ada-auth.org/standards/rm12_w_tc1/html/RM-A-9.html). > > As you say, this has the advantage of actually working. I see no difference. In both cases some kind of type tag need to be written and the object's size with it if not derived from the tag. Whether stream Read/Write or storage elements copy is then used changes little. P.S. I never used Storage_IO, I did storage pools instead. With a ring buffer you go as follows. Make a LIFO of Storage_Elements. It could be a descendant of Root_Storage_Pool or else if true parent type is already spent (Ada has no full multiple inheritance) use an access discriminant in a mix-in: type LIFO_Pool (Buffer : not null access LIFO'Class) with null record; The implementation of Allocate with reserve place in Buffer. Allocate already has parameter Size_In_Storage_Elements. You should only pay attention to Alignment and to atomic kicking off old elements when new allocation overlaps old elements in the buffer. So the element sizes must be stored in the LIFO. Writing into the LIFO will become: procedure Push (Buffer : in out LIFO'Class S : String) is Pool : LIFO_Pool (Buffer'Unchecked_Access); type String_Ptr is access String; for String_Ptr'Storage_Pool use Pool; Ptr : String_Ptr; begin Ptr := new String'("Some text"); end Push; P.P.S. Beware Ada finalization design bug ARM 7.6.1 (11.1/3): no controlled types, also. -- Regards, Dmitry A. Kazakov http://www.dmitry-kazakov.de
"Dmitry A. Kazakov" <mailbox@dmitry-kazakov.de> writes:
> On 05/07/2020 17:36, Simon Wright wrote:
>> "Jeffrey R. Carter" <spam.jrcarter.not@spam.not.acm.org> writes:
>>
>>> On 7/5/20 11:52 AM, Simon Wright wrote:
>>>> Simon Wright <simon@pushface.org> writes:
>>>>
>>>>> For the Size, see ARM 13.13.2(2).
>>>>
>>>> 13.13.2(1.2), sorry
>>>
>>> That only works for elementary types. For any type, a better approach
>>> is generic package Ada.Storage_IO, ARM A.9
>>> (http://www.ada-auth.org/standards/rm12_w_tc1/html/RM-A-9.html).
>>
>> As you say, this has the advantage of actually working.
>
> I see no difference. In both cases some kind of type tag need to be
> written and the object's size with it if not derived from the tag.
I was talking about the fact that 'Storage_Size only works for elementary
types.
"Jeffrey R. Carter" <spam.jrcarter.not@spam.not.acm.org> writes:
> For any type, a better approach is generic package Ada.Storage_IO, ARM
> A.9 (http://www.ada-auth.org/standards/rm12_w_tc1/html/RM-A-9.html).
Any *definite* type. I don't remember whether that would suit the
original requirement in this thread.
On 7/6/20 10:11 AM, Simon Wright wrote:
>
> Any *definite* type. I don't remember whether that would suit the
> original requirement in this thread.
I don't think "requirement" applies. "Circular buffer of untyped values" is at
best a design decision. Trying to bypass the type system is usually an
indication of a design problem, in my experience.
--
Jeff Carter
"In the frozen land of Nador they were forced to
eat Robin's minstrels, and there was much rejoicing."
Monty Python & the Holy Grail
70
"Jeffrey R. Carter" <spam.jrcarter.not@spam.not.acm.org> writes:
> On 7/6/20 10:11 AM, Simon Wright wrote:
>>
>> Any *definite* type. I don't remember whether that would suit the
>> original requirement in this thread.
>
> I don't think "requirement" applies. "Circular buffer of untyped
> values" is at best a design decision. Trying to bypass the type system
> is usually an indication of a design problem, in my experience.
Yes. There would have to be some mechanism for the receiving end to
decide what to do with the next lot of bytes!
On 06/07/2020 12:34, Simon Wright wrote: > "Jeffrey R. Carter" <spam.jrcarter.not@spam.not.acm.org> writes: > >> On 7/6/20 10:11 AM, Simon Wright wrote: >>> >>> Any *definite* type. I don't remember whether that would suit the >>> original requirement in this thread. >> >> I don't think "requirement" applies. "Circular buffer of untyped >> values" is at best a design decision. Trying to bypass the type system >> is usually an indication of a design problem, in my experience. > > Yes. There would have to be some mechanism for the receiving end to > decide what to do with the next lot of bytes! Sure. An example would be implementation of interprocess RPC. The parameters of a RPC would be passed via some pipe implemented as a ring buffer with stream interface on top of it. Since RPC parameters could be of almost any type, here you go. -- Regards, Dmitry A. Kazakov http://www.dmitry-kazakov.de
On Saturday, 4 July 2020 22:30:28 UTC+5:30, Daniel wrote:
> Hello, any theoric
> example of buffer i can find is always tied to an specific type.
>
> I'm looking for any example of ravenscar buffer able for using any type of data at the same time.
>
> I suppose it will need to serialize all data and manipulate it as a group of bytes.
>
> Does any body knows any example of this written in Ada?
On Saturday, 4 July 2020 22:30:28 UTC+5:30, Daniel wrote:
> Hello, any theoric
> example of buffer i can find is always tied to an specific type.
>
> I'm looking for any example of ravenscar buffer able for using any type of data at the same time.
>
> I suppose it will need to serialize all data and manipulate it as a group of bytes.
>
> Does any body knows any example of this written in Ada?
Le 24/09/2020 à 06:10, nimaopatel121@gmail.com a écrit : > On Saturday, 4 July 2020 22:30:28 UTC+5:30, Daniel wrote: >> Hello, any theoric >> example of buffer i can find is always tied to an specific type. >> >> I'm looking for any example of ravenscar buffer able for using any type of data at the same time. >> >> I suppose it will need to serialize all data and manipulate it as a group of bytes. >> >> Does any body knows any example of this written in Ada? > Hmmm, you know, Ada is a strongly typed language, therefore what you put in a buffer must have a well defined type. There are two possibilities: 1) If you can accept several buffers, one for each type, make it generic and instantiate it as many times as you need 2) Make a buffer of Stream_Elements, and use the streaming attributes ('Read, 'Write) to turn any type into stream elements. Ada.Streams.Stream_IO can also be handy in some cases. -- J-P. Rosen Adalog 2 rue du Docteur Lombard, 92441 Issy-les-Moulineaux CEDEX Tel: +33 1 45 29 21 52, Fax: +33 1 45 29 25 00 http://www.adalog.fr
Daniel <danielnorberto@gmail.com> writes: > Hello, any theoric > example of buffer i can find is always tied to an specific type. > > I'm looking for any example of ravenscar buffer able for using any > type of data at the same time. > > I suppose it will need to serialize all data and manipulate it as a > group of bytes. As J-P has said, you could use 'Write and 'Read (or better, 'Output and 'Input) to write to a stream. The beginnings of an alternative, which I last worked on a while ago, is at [1]; it's an Ada implementation of part of MessagePack[2] (boolean, integer, float, string). Still a way to go! Writing arbitrary data to a stream using 'Write/'Output suffers from the disadvantage that the reading side won't know what to expect unless you have some protocol in place. This Message_Pack doesn't eliminate this at all. For a while, I supported a scheme where all the data to be transmitted had to be instances of a tagged type e.g. Base; as far as I can remember, you output the data using Base'Class'Output and read it in using Base'Class'Input. [1] https://sourceforge.net/u/simonjwright/msgpack-ada/code/ci/master/tree/ [2] https://en.wikipedia.org/wiki/MessagePack