This is the mail archive of the guile@cygnus.com mailing list for the guile project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

Re: G-Wrap [Re: Foreign function interface generators.]


   From: chrislee@lavash.ius.cs.cmu.edu
   Cc: guile@cygnus.com
   References: <199711182100.QAA02311@ohanlon.mcl.cs.columbia.edu>
   Date: 18 Nov 1997 17:11:41 -0500
   Lines: 164
   X-Mailer: Gnus v5.3/Emacs 19.34
   Source-Info:  Sender is really chrislee@lavash.ius.cs.cmu.edu
   Sender: owner-guile@cygnus.com
   Precedence: bulk
   Content-Type: text
   Content-Length: 7288

   >>>>> "C" == Clifford Beshers <beshers@ohanlon.mcl.cs.columbia.edu> writes:

       C> I've used g-wrap before and like it for it's simplicity, but it
       C> needs some beefing up.  I find the features of ffi attractive
       C> as well, though they aren't what I need at the moment.

       C> So, I've decided to stick with g-wrap for the moment, modifying
       C> it myself if necessary.  I'd prefer that the entire community
       C> benefitted, thought, and to that end I offer a few minor
       C> comments.  I expect I will have more soon.

   Hi Cliff (and the rest of the Guile folks out there),

   Thanks for your comments.  G-Wrap has indeed not been updated for a
   long time, and I am (too slowly--sorry!) updating it and testing it
   right now, actually.  "Beefing it up" should be very easy due to its
   simplicity, so anyone should contribute their modifications if they
   have useful ones.

Great!

       C> The formats of `new-function', `new-type', and
       C> `define-constant' seem somewhat inconsistent. I believe they
       C> could be slightly modified in form to make them more consistent
       C> with each other, more Scheme-like, and easier to remember.

   This has been pointed-out to me before.  I have been changing it, but
   in the opposite direction than you suggest -- please tell me if you
   have a strong preference either way:

       C> First, I don't think these functions should be passed Scheme
       C> symbols. Rather, they should return Scheme objects which are
       C> associated with a symbol using the standard ``define'' and
       C> ``set!''  forms.  For example, the following:

       C>    (define-constant "VNULL" "NULL" VEC)

       C> would become:

       C>    (define VNULL (gwrap-c-constant "NULL" VEC ))

   I have looked at this, but I don't see a good reason to return an
   object representing such a constant: it has no meaning in the context
   of running the glue-code generation because the interpreter does not
   understand "VEC" at this point, and because it is not needed as a
   parameter-type specifier, as are the objects defined by
   (new-type....). In fact, 'VNULL' is needed as a parameter to tell the
   system what name to use in exporting the constant to the interpreter.

If the functions actually need the symbols, or if at least one does,
then it seems appropriate to pass them.  One could always make a macro
to change to the form I suggested.  

I was think more in terms of an inline pre-processor than a glue
generator, I guess, which is why I wanted the (define foo (g-wrap...))
form.  I think it makes no difference as long as it is consistent.

   Based on input from A. Jaffrey, however, I presently had planned to
   change the interface to
    (define-constant <symbol> <c-string> <type>)
   as in:
    (define-constant 'VNULL  "NULL" 'VEC)  ;; null-vector

   Note that this means that the <type> is now represented as a symbol
   rather than as an object, and so is the symbol being defined.

   This implies a couple things:
    1) Now, defining types is done slightly differently (see bellow)
    2) The glue-code generation will need to be done by the interpreter
       which the code is being generated for.
	 + This is due to the fact that the reader for Guile is not case
	    sensitive (by default), so it can distinguish 'VNULL and
	    'vnull, while SCM does not.

This divide interpreters into two classes, not n classes, right?  That
is, case-sensitive interpreters could generate for case-sensentive and
case-insensitive interpreters (with a flag set), but case-insenstive
interpreters could only target their own class.  This seems fine to
me.  I think most Scheme interpreters have a switch for
case-sensitivity anyway.

	 + Note that this will allow G-Wrap to be used as a Guile module,
	   as I will be assuming that Guile will be running the code for
	   generating wrappers for Guile interpreters.  This should allow
	   similar approaches when glue-code builders for other
	   interpreters are built (I am interested in writing a version
	   for Rscheme because its interpreter is so cool--it has a
	   byte-code interpreter, well-thought-out module system ;),
	   interesting macro system, persistent objects, true real-time
	   non-conservative GC, etc...).

That would be great.  I voted for RScheme as the core of guile...

       C> Specifically, the naming conventions should reflect that the
       C> function is part of g-wrap.  Also, all function names should
       C> make it clear what language is being ``wrapped,'' i.e.,
       C> imported into Scheme.  Hence the prefix ``g-wrap-c'' on all the
       C> functions.

   I do like the idea of using a more consistent naming convention for my
   functions.  I would be willing to use 'gwrap-c-' as a prefix to all
   the function names if anyone else supports this.  It would be
   consistent (but more verbose).  For now, how about `new-constant'
   rather than `define-constant' for the declaration?  This would make
   the names new-constant, new-function, and new-type, which is pretty
   consistent and easy to remember.

Well, I prefer the gwrap prefix to be around somewhere to indicate
what's going on, but it isn't really necessary since these files get
executed in their own interpreter.  Packaged as a module would be the
best, I think.

       C> Similarly:
       C>     (new-function c-name scheme-name ret-type type-list
       C> description)
       C> would become:
       C>     (define scheme-name (gwrap-c-function c-name ret-type
       C> type-list description))

   Similarly (but oppositely to this suggestions) I intend to change this
   to 

   (new-function <scheme-sym> <ret-type-sym> <c-name> <param-list> <descrition>)
   e.g.:

   (new-function 'eig-dsyev
		 'void "eig_dsyev" '((MAT A) (MAT Z) (VEC w))
		 "Calculates eigenvalues Z and eigenvalues w of real
   symmetric matrix A")

I had expect the return type to come after the function name, sort of
a prefix emulation, but keeping the consistency with the C declaration
seems a good idea.  I'm all for simplifying creation of these things.

   - Again, the scheme name is a scheme-symbol, and the types are referred
     to as symbols.
   - Note that the second line reads much more like the original C-function
     declaration (and an emacs macro could do a lot of the formatting by
     default for this).
   - The parameter list will be used to form a consistently-formatted
     header for the description string of the function, such as
     "(eig-dsyev A Z w)
       -- A is a MAT, Z is a MAT, w is a VEC
       -- no return value
      Calculates eigenvalues Z and eigenvalues w of real symmetric matrix A"
   - The description string of the function will actually be used.
     Because I don't currently know how to assign a description to a
     C-function in Guile (although it seems easy for functions written in
     Scheme), I build a assq list of (<name-of-fn> <description-string>)
     pairs that are exported to the interpreter bound as
     `*gw:descriptions*' so that a simple Scheme function can recall a
     description for a function or search for descriptions containing
     some keyword or regular-expression, etc.... 

       C>     (define scheme-name (new-type c-name c-print-name
       C> c-die-name c-eq-name c-gc-name))

   Again similarly (but opposed to this suggestions) I intend to change
   this to

     (new-type <scheme-sym> <c-name> <c-print-fn> <c-free-fn> <c-equal-fn>)
   as in
     (new-type 'VEC "VEC"  "VEC_print"  "v_free"  "VEC_eq")

   An assq list is used to map the symbols to the Scheme object
   containing the code for building the wrapper-code for the type,
   etc....

       C> This new naming scheme is more consistent with the naming of
       C> the auxiliary functions for dealing with C files, e.g.,
       C> c-file-include-local-header. I believe these should be slightly
       C> reworked as well.

   Would something like 'gwrap-c-include-local', 'gwrap-c-include-global'
   make sense?  Any other suggestions?

That's what I had in mind.

       C> Perhaps g-wrap should be a module, but I guess that you would
       C> make it less portable.

   This will probably happen for the next release (soon!).

   Other things in the new release:
    - A capability for automatically generating dynamically-linkable
      Guile modules
      + Note: the Guile directory-structure for looking for these
	dynamically-linked modules is a pain when they begin to rely upon
	one another (ie. for smob information) --- all the paths to the
	modules must be in your LD_LIBRARY_PATH, which seems wrong to me.
    - Automatic support for exporting functions with more than 10 arguments.
    - No longer relies on Slib (slib dependencies removed from output-file.scm)
    - Made generated *.h files more C++ friendly

Cool!  In summary, I think your solutions are fine.  They work and
they are consistent and readable.  Nothing else matters to me.  Fork
me a copy when you want a tester.  I'd cheerfully take it before the
dynamic linking is in.

Cliff