comp.lang.ada
 help / color / mirror / Atom feed
From: "John B. Matthews" <nospam@nospam.invalid>
Subject: Re: Ada to C interfacing with access on unconstrained array
Date: Tue, 20 Oct 2009 23:29:45 -0400
Date: 2009-10-20T23:29:45-04:00	[thread overview]
Message-ID: <nospam-586C6A.23294520102009@news.aioe.org> (raw)
In-Reply-To: hbl074$deo$1@aioe.org

In article <hbl074$deo$1@aioe.org>, tmoran@acm.org wrote:

> >  type Nut_Array_Type is array (Positive range <>) of Nut_Type;
>   C has no concept of an unconstrained array - only pointers to the
> start of a length-less array.  The usual way to handle this is to 
> declare the Ada array constrained, but with a "sufficiently large" 
> constraint.  You can pass (a pointer to) such an array between C and 
> Ada.  You lose bounds checking on the Ada side, but you can fudge 
> that by renaming the actual slice.
> So how about:
> 
>    type Nut_Array_Type is array (Positive range <>) of Nut_Type;
>    subtype C_Nut_Array_Type is Nut_Array_Type(Positive);
>    type C_Nut_Array_Access is access C_Nut_Array_Type;
> 
>    type Coco_Type is
>       record
>          X    : Integer;
>          Y    : Integer;
>          Nuts : C_Nut_Array_Access;
>       end record;
> 
>    -- This is the procedure I want to be executed from C
>    procedure Climb (Coco : in Coco_Type);
>    ...
> package body Foo is
> 
>    procedure Climb (Coco : in Coco_Type) is
>      Coco_Nuts : renames Coco.Nuts.all(1 .. actual_length);
>    begin

David: GNAT implements a convenient pragma that's especially helpful for 
this approach. Given a procedure such as

   procedure Climb (Coco_Rec : Coco_Type; Length : Positive);

One can export the procedure

   pragma Convention(C, Climb);
   pragma Export_Procedure(
      Internal        => Climb,
      External        => climb,
      Parameter_Types => (Coco_Type, Positive),
      Mechanism       => (Value, Value));

Then in C, one can write

#define MAX_NUTS 10

struct Nut_Type {
   int Diameter;
   int Weight;
   int Age;
};
struct Nut_Type Nuts[MAX_NUTS];

struct Coco_Type {
   int X;
   int Y;
   struct Nut_Type *Nuts;
} Coco_Rec = { 1, 2, &Nuts[0] };

and invoke

   climb(Coco_Rec, MAX_NUTS);

-- 
John B. Matthews
trashgod at gmail dot com
<http://sites.google.com/site/drjohnbmatthews>



  reply	other threads:[~2009-10-21  3:29 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2009-10-20 13:07 Ada to C interfacing with access on unconstrained array dhenry
2009-10-20 16:11 ` Dmitry A. Kazakov
2009-10-21  9:25   ` dhenry
2009-10-21 12:09     ` Dmitry A. Kazakov
2009-10-21 12:14       ` Dmitry A. Kazakov
2009-10-20 16:24 ` Adam Beneschan
2009-10-20 18:40 ` tmoran
2009-10-21  3:29   ` John B. Matthews [this message]
2009-10-21  9:29     ` dhenry
2009-10-21 14:16       ` John B. Matthews
replies disabled

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