comp.lang.ada
 help / color / mirror / Atom feed
* What is the best way to define the Imported C function
@ 2008-01-26  5:05 qunying
  2008-01-26 10:15 ` Martin Krischik
                   ` (2 more replies)
  0 siblings, 3 replies; 7+ messages in thread
From: qunying @ 2008-01-26  5:05 UTC (permalink / raw)


Hi,

I am learning Ada and try to test the interface with C.

for this function, what is the best way to define the function in Ada?

int xcb_parse_display(const char *name, char **host, int *display, int
*screen);

function parse_display (Name : String; Host: ??; Display :
Integer_Ptr; Screen : Integer_Ptr) return Integer;
pragma Import (C, parse_display, "xcb_parse_display");

Where Integer_Ptr is access Integer;
How to define the type for char **?  Sould I use "type char_ptr_ptr is
access char_ptr;" where char_ptr is defined in Interfaces.C; or there
is a better way to do it?

Thanks





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

* Re: What is the best way to define the Imported C function
  2008-01-26  5:05 What is the best way to define the Imported C function qunying
@ 2008-01-26 10:15 ` Martin Krischik
  2008-01-26 16:24   ` qunying
  2008-01-26 10:56 ` Dmitry A. Kazakov
  2008-01-27  1:31 ` Jeffrey R. Carter
  2 siblings, 1 reply; 7+ messages in thread
From: Martin Krischik @ 2008-01-26 10:15 UTC (permalink / raw)


qunying wrote:

> Hi,
> 
> I am learning Ada and try to test the interface with C.
> 
> for this function, what is the best way to define the function in Ada?
> 
> int xcb_parse_display(const char *name, char **host, int *display, int
> *screen);

function parse_display (
   Name : in Interfaces.C.Strings.char_array_access;
   Host   : access Interfaces.C.Strings.char_array_access;
   Display : access Interfaces.C.int;
   Screen : access Interfaces.C.int)
return Interfaces.C.int;

See:

http://www.adaic.com/standards/05rm/html/RM-B-3.html

Martin

-- 
mailto://krischik@users.sourceforge.net
Ada programming at: http://ada.krischik.com



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

* Re: What is the best way to define the Imported C function
  2008-01-26  5:05 What is the best way to define the Imported C function qunying
  2008-01-26 10:15 ` Martin Krischik
@ 2008-01-26 10:56 ` Dmitry A. Kazakov
  2008-01-26 12:15   ` Stefan Lucks
  2008-01-27  1:31 ` Jeffrey R. Carter
  2 siblings, 1 reply; 7+ messages in thread
From: Dmitry A. Kazakov @ 2008-01-26 10:56 UTC (permalink / raw)


On Fri, 25 Jan 2008 21:05:02 -0800 (PST), qunying wrote:

> I am learning Ada and try to test the interface with C.
> 
> for this function, what is the best way to define the function in Ada?
> 
> int xcb_parse_display(const char *name, char **host, int *display, int
> *screen);
> 
> function parse_display (Name : String; Host: ??; Display :
> Integer_Ptr; Screen : Integer_Ptr) return Integer;
> pragma Import (C, parse_display, "xcb_parse_display");
> 
> Where Integer_Ptr is access Integer;

   Name : Interfaces.C.char_array

and use To_C in order to pass a String there. Ada's String is not C's
char[]

   Display : access Interfaces.C.int

Firstly Integer is not necessarily int, the built-in package Interfaces.C
provides integer types compatible with C. Secondly in out mode will do the
trick where int * is used as an in-out parameter rather than a pointer to
an array. Unfortunately you have a function, so in out is illegal.
Therefore access Interfaces.C.int instead.

> How to define the type for char **?  Sould I use "type char_ptr_ptr is
> access char_ptr;" where char_ptr is defined in Interfaces.C; or there
> is a better way to do it?

Like with int *, that depends on the semantics. If the idea is to return a
pointer to a string then just tell so:

   Host : access Interfaces.C.Strings.chars_ptr
   Screen : access Interfaces.C.int

Surely, you would like to make a wrapper around the mess to make it more
Ada-friendly:

   type Display_ID is private; -- An opaque handle to
   type Screen_ID is private;
      -- This either does the job or raises an exception
   procedure Parse_Display
          (  Name    : String;
             Host    : out Unbounded_String;
             Display : out Display_ID;
             Screen  : out Screen_ID
          );
...
private
   type Display_ID is new Interfaces.C.int;
   type Screen_ID is new Interfaces.C.int;

...
procedure Parse_Display
          (  Name    : String;
             Host    : out Unbounded_String;
             Display : out Display_ID;
             Screen  : out Screen_ID
          )  is
   function Internal
            (  Name    : Interfaces.C.char_array;
               Host    : access Interfaces.C.Strings.chars_ptr;
               Display : access Display_ID;
               Screen  : access Screen_ID
            )  return Interfaces.C.int;
   pragma Import (C, Internal, "xcb_parse_display");

   Display_Value : aliased Display_ID;
   Screen_Value  : aliased Screen_ID;
   Host_Value    : aliased  Interfaces.C.Strings.chars_ptr;
   Result        : Interfaces.C.int :=
      Internal
      (  Name    => To_C (Name),
         Host    => Host_Value'Access,
         Display => Display_Value'Access,
         Screen  => Screen_Value'Access
      );
begin
   if Result = 0 then
      Host := To_Unbounded_String (To_Ada (Host_Value));
      Display := Display_Value;
      Screen := Screen_Value;
   else
      raise <Something Appropriate>;
   end if;
end Parse_Display;

-- 
Regards,
Dmitry A. Kazakov
http://www.dmitry-kazakov.de



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

* Re: What is the best way to define the Imported C function
  2008-01-26 10:56 ` Dmitry A. Kazakov
@ 2008-01-26 12:15   ` Stefan Lucks
  0 siblings, 0 replies; 7+ messages in thread
From: Stefan Lucks @ 2008-01-26 12:15 UTC (permalink / raw)


On Sat, 26 Jan 2008, Dmitry A. Kazakov wrote:

> Surely, you would like to make a wrapper around the mess to make it more
> Ada-friendly:

Such a wrapper looks like a typical "please inline me" function:

>   type Display_ID is private; -- An opaque handle to
>   type Screen_ID is private;
>      -- This either does the job or raises an exception
>   procedure Parse_Display ( [...] );
     pragma inline (Parse_Display); -- *** this seems to make sense ***

> private
> ...
> procedure Parse_Display ( [...] )  is
>   function Internal ( [...] )  return Interfaces.C.int;
>   pragma Import (C, Internal, "xcb_parse_display");
     [...]
>   Result        : Interfaces.C.int := Internal ( [...] );
> begin
>   if Result = 0 then
       [...]
>   else
>     raise [...];
>   end if;
> end Parse_Display;


-- 
Stefan Lucks      (moved to Bauhaus-University Weimar, Germany)
 		       <Stefan.Lucks at medien.uni-weimar.de>
------  I  love  the  taste  of  Cryptanalysis  in  the  morning!  ------





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

* Re: What is the best way to define the Imported C function
  2008-01-26 10:15 ` Martin Krischik
@ 2008-01-26 16:24   ` qunying
  0 siblings, 0 replies; 7+ messages in thread
From: qunying @ 2008-01-26 16:24 UTC (permalink / raw)


Thanks for all the helps.  You are awesome!  I hope I could produced
something out ^_^  I'm trying to do a XCB binding to Ada, also have to
mangle with the xml/xslt thing.  Seems there is still quite some road
for me to go.



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

* Re: What is the best way to define the Imported C function
  2008-01-26  5:05 What is the best way to define the Imported C function qunying
  2008-01-26 10:15 ` Martin Krischik
  2008-01-26 10:56 ` Dmitry A. Kazakov
@ 2008-01-27  1:31 ` Jeffrey R. Carter
  2008-01-28 17:18   ` Adam Beneschan
  2 siblings, 1 reply; 7+ messages in thread
From: Jeffrey R. Carter @ 2008-01-27  1:31 UTC (permalink / raw)


qunying wrote:
> 
> I am learning Ada and try to test the interface with C.

I would suggest that you learn Ada before trying to interface it to C. But if 
you are going to do it, use the types in Interfaces.C and its children, or types 
declared Convention C, not String and Integer; and don't pass explicit pointer 
values when Ada's interfacing rules will do the right thing for you.

> for this function, what is the best way to define the function in Ada?
> 
> int xcb_parse_display(const char *name, char **host, int *display, int
> *screen);

I can't help you (and really, neither can those who have replied to you) because 
the C specification isn't a specification; it doesn't tell us how the function 
uses its parameters. Without that information, we can't tell how to interface to it.

The problem is that C uses the same construct for many conceptually different 
things. For example:

void f (char* c);

may represent something that is conceptually equivalent to Ada's

procedure F (C : in Character); [unlikely, but possible]
procedure F (C : in out Character);
procedure F (C : out Character);
procedure F (C : in String);
procedure F (C : in out String);
procedure F (C : out String);

Given the common practice of using "char" to represent what Ada calls a 
Storage_Element, and "char[]" or "char*" for Storage_Array, this single C 
declaration may mean any of 12 different things.

-- 
Jeff Carter
"C++ is like jamming a helicopter inside a Miata
and expecting some sort of improvement."
Drew Olbrich
51



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

* Re: What is the best way to define the Imported C function
  2008-01-27  1:31 ` Jeffrey R. Carter
@ 2008-01-28 17:18   ` Adam Beneschan
  0 siblings, 0 replies; 7+ messages in thread
From: Adam Beneschan @ 2008-01-28 17:18 UTC (permalink / raw)


On Jan 26, 5:31 pm, "Jeffrey R. Carter"
<spam.jrcarter....@acm.nospam.org> wrote:

> I can't help you (and really, neither can those who have replied to you) because
> the C specification isn't a specification; it doesn't tell us how the function
> uses its parameters. Without that information, we can't tell how to interface to it.
>
> The problem is that C uses the same construct for many conceptually different
> things. For example:
>
> void f (char* c);
>
> may represent something that is conceptually equivalent to Ada's
>
> procedure F (C : in Character); [unlikely, but possible]
> procedure F (C : in out Character);
> procedure F (C : out Character);
> procedure F (C : in String);
> procedure F (C : in out String);
> procedure F (C : out String);
>
> Given the common practice of using "char" to represent what Ada calls a
> Storage_Element, and "char[]" or "char*" for Storage_Array, this single C
> declaration may mean any of 12 different things.

It's probably worse than that, because even when char * refers to a
structure with multiple characters rather than a single character, you
don't know whether it's supposed to be a null-terminated string, or an
array of characters whose size is given somewhere else, or what.

                               -- Adam





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

end of thread, other threads:[~2008-01-28 17:18 UTC | newest]

Thread overview: 7+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2008-01-26  5:05 What is the best way to define the Imported C function qunying
2008-01-26 10:15 ` Martin Krischik
2008-01-26 16:24   ` qunying
2008-01-26 10:56 ` Dmitry A. Kazakov
2008-01-26 12:15   ` Stefan Lucks
2008-01-27  1:31 ` Jeffrey R. Carter
2008-01-28 17:18   ` Adam Beneschan

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