ChezScheme icon indicating copy to clipboard operation
ChezScheme copied to clipboard

Expose an ABI-friendly embedding interface

Open lambdadog opened this issue 3 years ago • 2 comments

While it's possible to embed Chez Scheme using the generated scheme.h headers, there are problems with this since a significant portion of the interface is increasingly opaque pointer arithmetic macros. If someone wanted to embed the Chez kernel in an application written in a non-C/C++ language they would either have to translate the macros or write some C glue that wraps scheme.h's macros.

This is of course doable, but there are a number of issues with requiring this:

  • The project would need to integrate tooling for compiling and linking C code
  • If the host language doesn't support statically linking C code (common for non-compiled languages, and sometimes the case even for compiled languages) then they now must distribute a tiny dynamic library with their application
  • If the host language furthermore supports run-anywhere distributions, then their distributions no longer "run anywhere" unless they're willing to ship dozens of copies of their dynamic library, which is conditionally loaded based on the platform (when this is even possible)
    • plus they now need infrastructure for compiling the dynamic library for every platform they wish to support

Ideally, instead of jumping through all these hoops, the application could simply load the Chez kernel dynamic library and embed Chez via an ABI-friendly API.

lambdadog avatar Aug 06 '22 03:08 lambdadog

I didn't give much lip service to translating the macros, but this is mostly because I've been trying to do this for the last two weeks in a platform independent way and I find myself chasing obscure and confusing errors constantly -- while it may be possible for someone with enough familiarity with the in-memory layout of scheme values (something difficult to gain without documentation: #654) it shouldn't be the de-facto path to embedding with its barrier to entry.

If bindings were written in this way, of course, it would be nice to have the lower level of indirection, but I can't see it as a starting point.

lambdadog avatar Aug 06 '22 04:08 lambdadog

I've been working on embedding this (as part of embedding racket) and have been approaching it by just wrapping every macro in a function, with the same name, e.g.:

#define Sfixnump(x) (((uptr)(x)&0x7)==0x0)
bool (Sfixnump) (ptr x) { return Sfixnump(x); }

which resolves the linkage issue for me but I imagine does very little for portability. But sharing this here for anyone else trying to do this—it took me a bit to figure out that I could reuse the same name.

porglezomp avatar Apr 13 '24 19:04 porglezomp