1. Wrapping a C library.

This is something I've been thinking about doing for a while, but to be honest I find C a bit intimidating and have never used any of Euphoria's "wrapping" functions. I'd like to use the Gnuplot plotting program directly from Eu (to create graphs on the fly) and there's a simple C library - http://ndevilla.free.fr/gnuplot/ which should do the job.

To be honest, I'm clueless as to where to start. Do I need to know C to do this stuff? I've been looking at the simple example on calling C functions in the demo folder and it seems easy enough, but do I need to compile the C code into a shared library first? Any advice appreciated.

new topic     » topic index » view message » categorize

2. Re: Wrapping a C library.

Davy said...

This is something I've been thinking about doing for a while, but to be honest I find C a bit intimidating and have never used any of Euphoria's "wrapping" functions. I'd like to use the Gnuplot plotting program directly from Eu (to create graphs on the fly) and there's a simple C library - http://ndevilla.free.fr/gnuplot/ which should do the job.


Did you look at

http://rapideuphoria.com/cgi-bin/asearch.exu?dos=on&win=on&lnx=on&gen=on&keywords=plot

?

useless

new topic     » goto parent     » topic index » view message » categorize

3. Re: Wrapping a C library.

Hi useless, thanks but Gnuplot is much more powerful and I'm already familiar with it. Actually it occurred to me I might be able to use the pipeio routines instead of wrapping the C code.

new topic     » goto parent     » topic index » view message » categorize

4. Re: Wrapping a C library.

Davy said...

This is something I've been thinking about doing for a while, but to be honest I find C a bit intimidating and have never used any of Euphoria's "wrapping" functions. I'd like to use the Gnuplot plotting program directly from Eu (to create graphs on the fly) and there's a simple C library - http://ndevilla.free.fr/gnuplot/ which should do the job.

To be honest, I'm clueless as to where to start. Do I need to know C to do this stuff? I've been looking at the simple example on calling C functions in the demo folder and it seems easy enough, but do I need to compile the C code into a shared library first? Any advice appreciated.

Yes, you'll need to compile that yourself, although it looks fairly simple. I tried downloading it, and it's a single file. After extracting it, I went into the source directory and did:

gnuplot_i-2.10/src$ gcc -fPIC gnuplot_i.c -shared -o gnuplot_i.so 
That built the shared library for me, and should work for you. One note: if you're on a 64-bit system, but using 32-bit euphoria, you'll want to tell gcc to use the -m32 flag:
gnuplot_i-2.10/src$ gcc -m32 -fPIC gnuplot_i.c -shared -o gnuplot_i.so 

Then you should be able to wrap the library. Looking at the API, it mostly takes pointers to values (which is what the asterisks mean in C), so make sure that you're allocating and passing pointers. If you have specific questions, please ask!

Matt

new topic     » goto parent     » topic index » view message » categorize

5. Re: Wrapping a C library.

This was an easy one. smile As Matt said above, I compiled the code into a shared library and built a simple Euphoria wrapper around it. I also put together a make file to easily make && make install, as well as test the library (make test) and build the zip files I posted here (make binzip && make srczip).

Get it here:

Edit 1: I just realized that I left out the last two functions, and I make an example program using a simple example in the documentation.

Edit 2: Renamed project to eugnuplot, moved from Dropbox to BitBucket.

Please test it and let me know if it breaks. If this works for you, then I'll post it to the Archive for others to download.

-Greg

new topic     » goto parent     » topic index » view message » categorize

6. Re: Wrapping a C library.

Wow Greg, that took you 5 hours.

Now go away and write me an wrapper, and a complete set of dlls and a manual for Luxinia

http://www.luxinia.de/index.php/Main/HomePage

I'll give you 24 hours for this one!

Chris

new topic     » goto parent     » topic index » view message » categorize

7. Re: Wrapping a C library.

Wow, I just came here to ask a question and see that it's already been written.

thanks a million Greg!

It works just fine. smile

And thanks also to Matt. I think I'll try to write the wrapper myself anyway. Now I can read Greg's code if I get stuck.

new topic     » goto parent     » topic index » view message » categorize

8. Re: Wrapping a C library.

ChrisB said...

Wow Greg, that took you 5 hours.

Now go away and write me an wrapper, and a complete set of dlls and a manual for Luxinia

http://www.luxinia.de/index.php/Main/HomePage

I'll give you 24 hours for this one!

Actually it only took about an hour. 90% of it was already written, I just glued it all together. With all this recent discussion on wrapping C libraries, I think I'm going to start compiling a good how-to on the subject. I'm also thinking about writing an app that will assist with the process of wrapping a large library, which would be useful for Luxinia, or even wxEuphoria.

Davy said...

Wow, I just came here to ask a question and see that it's already been written.

thanks a million Greg!

It works just fine. smile

And thanks also to Matt. I think I'll try to write the wrapper myself anyway. Now I can read Greg's code if I get stuck.

It hadn't already been written, I built it somewhere in the time between your post and Matt's post. blink

This is actually a good example of a very simple wrapper. Unfortunately it's not always this easy.

-Greg

new topic     » goto parent     » topic index » view message » categorize

9. Re: Wrapping a C library.

ghaberek said...

With all this recent discussion on wrapping C libraries, I think I'm going to start compiling a good how-to on the subject. -Greg

That would be awesome. After I've got the hang of it, there's another library I want to wrap; it's a simple and lightweight GUI toolkit. At the moment I'm using EuWinGui with Wine, but it would be nice to have a "EuLinGui" for Linux.

new topic     » goto parent     » topic index » view message » categorize

10. Re: Wrapping a C library.

Davy said...

That would be awesome. After I've got the hang of it, there's another library I want to wrap; it's a simple and lightweight GUI toolkit. At the moment I'm using EuWinGui with Wine, but it would be nice to have a "EuLinGui" for Linux.

Do you mean FLTK? (Fast, Light Toolkit)

Have you had a look at wxEuphoria at all? It's really quite simple to use.

-Greg

new topic     » goto parent     » topic index » view message » categorize

11. Re: Wrapping a C library.

ghaberek said...

Do you mean FLTK? (Fast, Light Toolkit)

Have you had a look at wxEuphoria at all? It's really quite simple to use.

-Greg

I was thinking of EZWGL. But I think it would be a fairly ambitious project, even for someone with experience. I'll take a look at wxEuphoria, but what I like about EuWingui is that unlike most GUIs it doesn't involve objects, events and callbacks; you only need to use simple procedural coding.

new topic     » goto parent     » topic index » view message » categorize

12. Re: Wrapping a C library.

Davy said...

I was thinking of EZWGL.

EZWGL V1.50 is released on Dec 6, 1999 

I'm not sure it's worth wrapping a toolkit which was last updated over 12 years ago. getlost

Davy said...

But I think it would be a fairly ambitious project, even for someone with experience. I'll take a look at wxEuphoria, but what I like about EuWingui is that unlike most GUIs it doesn't involve objects, events and callbacks; you only need to use simple procedural coding.

I've honestly never used EuWinGUI. I started with Win32Lib and then got into wxEuphoria early on. To use Win32Lib or wxEuphoria is quite simple: create() your controls, set up your event handlers setHandler()/set_event_handler(), and then call your main function WinMain()/wxMain(). I think EuWinGui works the same way, doesn't it? FLTK might be worth a good look, and Jeremy recently wrapped IUP as well.

-Greg

new topic     » goto parent     » topic index » view message » categorize

13. Re: Wrapping a C library.

ghaberek said...

I'm not sure it's worth wrapping a toolkit which was last updated over 12 years ago. getlost -Greg

I see what you mean. EuWinGui IS a bit limited, and there's always irv's EuGTK, which looks fairly easy to use.

new topic     » goto parent     » topic index » view message » categorize

14. Re: Wrapping a C library.

Greg,

I'm getting a type check error when I use the gnuplot_plot_xy() function.

Looking at the include file, I see that the parameters x and y are atoms, however, writing the euphoria equivalent of the example given in the documentation:

 gnuplot_ctrl    *h ; 
    double          x[50] ; 
    double          y[50] ; 
    int             i ; 
 
    h = gnuplot_init() ; 
    for (i=0 ; i<50 ; i++) { 
        x[i] = (double)(i)/10.0 ; 
        y[i] = x[i] * x[i] ; 
    } 
    gnuplot_plot_xy(h, x, y, 50, "parabola") ; 
    sleep(2) ; 
    gnuplot_close(h) ; 

was when I got the error.

I took it that x and y being arrays here, then in the corresponding Eu code x and y would be sequences.

I think this is something to do with the fact that x and y are not actually arrays, but pointers to arrays. Unfortunately my knowledge of C is nil so I'm just confused...

Here is the code generating the error -

include "gnuplot_i.e" 
include std/console.e 
sequence x, y  
 
x = {} 
y = {} 
gnuplot_ctrl g = gnuplot_init() 
 
for i = 0.1 to 5 by 0.1 do 
    x &= i 
    y &= i*i 
end for 
 
gnuplot_plot_xy(g, x, y, 50, "parabola") 
 
any_key() 
gnuplot_close( g ) 
new topic     » goto parent     » topic index » view message » categorize

15. Re: Wrapping a C library.

Davy said...

I'm getting a type check error when I use the gnuplot_plot_xy() function.

Looking at the include file, I see that the parameters x and y are atoms, however, writing the euphoria equivalent of the example given in the documentation:

...

I took it that x and y being arrays here, then in the corresponding Eu code x and y would be sequences.

I think this is something to do with the fact that x and y are not actually arrays, but pointers to arrays. Unfortunately my knowledge of C is nil so I'm just confused...

Yes, a C array is really just a pointer. To use it, you'll need to allocate some memory and poke and peek the data (there should be an easier way coming in 4.1). So, something like this:

include std/convert.e 
include std/machine.e 
 
sequence x = repeat( 0, 50 ) 
atom x_array = allocate( length( x ) * 8 ) -- doubles are 8 bytes each 
 
-- write your sequence into an array: 
for i = 1 to length( x ) do 
    poke( x_array + (i-1) * 8, atom_to_float64( x[i] ) ) 
end for 
 
-- read the array in memory into a sequence: 
for i = 1 to length( x ) do 
    x[i] = float64_to_atom( peek( { x_array + (i-1) * 8, 8 } ) 
end for 

Ideally, you'd probably put that sort of thing into functions/procedures, and use them as needed.

Matt

new topic     » goto parent     » topic index » view message » categorize

16. Re: Wrapping a C library.

Ah, thanks Matt. I'll do what you suggest and add the appropriate code to gnuplot_i.e, then I can use sequences in the gnuplot function calls.

new topic     » goto parent     » topic index » view message » categorize

17. Re: Wrapping a C library.

Whoops, my bad! I'll get that updated in my code later today.

-Greg

new topic     » goto parent     » topic index » view message » categorize

18. Re: Wrapping a C library.

Okay, I've made the necessary changes, added a second example program, and posted the code to my BitBucket repository. I also renamed this project to eugnuplot so it's easier to identify.

https://bitbucket.org/ghaberek/eugnuplot

Oh, and here's the routine I used for allocating an array of float64 values.

function allocate_float64_array( object data, integer count=-1 ) 
 
    -- make sure we have an array of values 
    if atom( data ) then 
        data = {data} 
    end if 
 
    -- auto-detect the array length, if necessary 
    if count = -1 then 
        count = length( data ) 
    end if 
 
    -- allocate the block of memory 
    atom ptr = allocate( count * 8 ) 
 
    -- poke the values into memory 
    for i = 1 to count do 
        poke( ptr + (i-1) * 8, atom_to_float64( data[i] ) ) 
    end for 
 
    -- return the data pointer 
    return ptr 
end function 

-Greg

new topic     » goto parent     » topic index » view message » categorize

19. Re: Wrapping a C library.

Awesome! thanks,Greg.

new topic     » goto parent     » topic index » view message » categorize

20. Re: Wrapping a C library.

Greg, sorry to be a pain, but I want to use gnuplot_i.e with an older program written in 3.1.1; I'm not sure which statements I need to remove to make the include file backwards compatible. I'm still finding my way around ver 4.x, but obviously I need to remove the "override" functions and references to the standard library.
Forked into: 3.1.1 backwards compatibility

new topic     » goto parent     » topic index » view message » categorize

21. Re: Wrapping a C library.

Davy said...

Greg, sorry to be a pain, but I want to use gnuplot_i.e with an older program written in 3.1.1; I'm not sure which statements I need to remove to make the include file backwards compatible. I'm still finding my way around ver 4.x, but obviously I need to remove the "override" functions and references to the standard library.

Is this a test? blink No problem. Get it here:

-Greg

new topic     » goto parent     » topic index » view message » categorize

22. Re: Wrapping a C library.

Once again Greg, many thanks for your time and effort. I'm sure there will be others who haven't yet made the switch to 4.x who will appreciate it.

One error found in the new include file: "public" should be changed to "global" in the constant declaration. Apart from that, perfect!

new topic     » goto parent     » topic index » view message » categorize

Search



Quick Links

User menu

Not signed in.

Misc Menu