Newsgroups: comp.lang.lisp
Path: utzoo!utgpu!news-server.csri.toronto.edu!rpi!zaphod.mps.ohio-state.edu!think.com!barmar
From: barmar@think.com (Barry Margolin)
Subject: Re: passing Lisp functions to C
Message-ID: <1991Apr26.154656.13177@Think.COM>
Sender: news@Think.COM
Organization: Thinking Machines Corporation, Cambridge MA, USA
References: <sudha.672658705@milton>
Date: Fri, 26 Apr 91 15:46:56 GMT

In article <sudha.672658705@milton> sudha@herodotus.cs.uiuc.edu (Sudhakar Yerramareddy) writes:
>I am calling a C function c_function from LISP.  The c_function has the
>following declarations:
>
>void c_function(a,b,func)
>float *a,*b;
>float (*func)();

>I create a function #'run-time-function at run-time.  I want this function
>to be passed as the third argument to the c_function (via lisp-function).
>
>My call looks like this:
>
>(lisp-function pointer-a pointer-b *what-should-be-here?*)
>
>I am using Lucid Common Lisp.  How do I do this?  Any suggestions
>appreciated.

We have some code that needs to do this, and we use a kludge.  Instead of
passing the function to C, we bind a special variable to the function.
Then we define a foreign callable function whose only purpose is to FUNCALL
the function in the special variable.  It looks something like this

(defvar *callback-function*)

(def-foreign-callable (call-function
			(:language :c)
			(:name "_lisp_callback")
			(:return-type :single-float))
  (...) ; argument descriptions go here
  (funcall *callback-function* ...))

Then the call to lisp-function is done with

(let ((*callback-function* #'run-time-function))
  (lisp-function pointer-a pointer-b))

The other thing you have to do is write the C code that uses lisp_callback
instead of a function passed as an argument.  You can do this in the C code
by having an auxiliary function:

float lisp_callback();

float
lisp_interface_to_c_function (a, b)
float *a, *b;
{
	return c_function (a, b, lisp_callback);
}
--
Barry Margolin, Thinking Machines Corp.

barmar@think.com
{uunet,harvard}!think!barmar
