[Ecls-list] Embedding ECL - how?

Dr. Edmund Weitz edi at agharta.de
Tue Jan 22 00:21:01 UTC 2002


First of all thanks for your fast and informative reply. And good luck
with your IKEA furniture - I know how hard this can be sometimes... :)

Let me also add that I would want to volunteer for writing a tutorial
or extend the developer documentation once I've completely understood
the stuff myself. But first of all, I still have a couple of
questions. Here's what I did:

I wrote a small C snippet and called it 'lib.c':

  #include <stdio.h>
  
  void print_something () {
    printf("This is a test.\n");
  }

Then I built my little library...
  
  gcc -c -o lib lib.c
  ar -q libmylib.a lib
  
...and an image according to your guidelines:

  (c::build-program "myimage" :ld-flags '("-L. -lmylib") :prologue-code "print_something();")
  
Calling 'myimage' did exactly what I expected: The line 'This is a
test.' was printed and then I was thrown into the REPL.

Afterward I did...

  (c::build-program "myimage" :ld-flags '("-L. -lmylib") :epilogue-code "print_something();")

...and also got what I expected: Only the above-mentioned line was
printed, no REPL. Fine.

Now, what I actually wanted to have was a way to call into ECL
non-interactively, i.e. without a REPL. So I tried something like this:
  
  #include "/usr/local/lib/ecl/h/ecl.h"
  
  void call_into_lisp () {
    clLprint(1, MAKE_FIXNUM(3));
  }

then
  
  gcc -c -o lib lib.c
  rm libmylib.a
  ar -q libmylib.a lib

and

  (c::build-program "myimage" :ld-flags '("-L. -lmylib") :prologue-code "call_into_lisp();")

which resulted in a segmentation fault when calling 'myimage'. No
surprise here, 'cause obviously ECL didn't have a chance to set up its
environment yet.

So, I changed the call to

  (c::build-program "myimage" :ld-flags '("-L. -lmylib") :epilogue-code "call_into_lisp();")

everything worked fine - the number 3 was printed, and the program
exited.

So far, so good. Now, how do I call my own functions? If I
COMPILE-FILE a file with my own Lisp definitions, these functions
obviously are not compiled into functions whose resemble the
conventions described in the developer documentation. Instead of, say,
'clLfac' I get something like 'L1' or 'L2'. So, I though I should try
EVAL to call these function (although I'd rather call them directly of
course.)

I followed one of the examples from the developer documentation and
wrote this little C function:
  
  #include "/usr/local/lib/ecl/h/ecl.h"
  
  void call_into_lisp () {
    cl_object form;
    cl_object buffer;
  
    form = c_string_to_object("(print 3)");
    buffer = OBJNULL;
    eval(form, &buffer, Cnil);
    eval(form, &buffer, Cnil); 
  }

and, after building my library, did:
  
  (c::build-program "myimage" :ld-flags '("-L. -lmylib") :epilogue-code "call_into_lisp();")
  
This resulted in

  edi at bird:~> ./myimage 
  Segmentation violation.
  Wrong type argument to a compiled function.
  Top level.
  > 
  
Hmm... What's wrong with that? Will EVAL only work inside of the REPL?
I decided to give it another try and call 'clLeval' directly, like so:

  #include "/usr/local/lib/ecl/h/ecl.h"
  
  void eval_string (char *string) {
    cl_object form;
  
    form = c_string_to_object(string);
    clLeval(0, form);
  }

and
  
  (c::build-program "myimage" :ld-flags '("-L. -lmylib") :epilogue-code "eval_string(\"(print 3)\");")

This time I got:
  
  edi at bird:~> ./myimage 
  Function SI:TOP-LEVEL requires one argument,
  but only zero were supplied.
  Top level.
  > 
  
So this is basically where I'm stuck now. I actually want to write a
couple of Lisp functions, COMPILE-FILE them and want to be able to
call them non-interactively from a C program, but I guess I'm not
there yet. Is this possible at all with ECL?

Thanks in advance for your help,
Edi.





More information about the ecl-devel mailing list