[Openmcl-devel] create an executable from openmcl

Gary Byers gb at clozure.com
Fri Apr 18 11:05:49 PDT 2003

On Thu, 17 Apr 2003, Erann Gat wrote:

> On Thu, 17 Apr 2003, Taoufik Dachraoui wrote:
> > Hi,
> >
> > I would like to create a standalone executable program. I do not want
> > to use openmcl to run the program!!
> >
> > Let's say I write a lisp program, then I would like to create a
> > standalone running program without using openmcl.
> >
> > Is there a way to do this? (like when we write a C program than we
> > compile it and link it to create an executable)
> No.
> The fact of the matter is that there is no way to do it with a C program
> either.  That it appears that you can is actually an illusion created by
> the fact that a large number of supporting libraries are ubiquitous and
> well hidden.  Even a statically linked "executable" requires such
> libraries -- they are called the "operating system."
> To run a Lisp "executable" you need additional libraries that are not
> ubiquitous and not well hidden (yet).  That is what makes it appear that
> Lisp is different from C in this regard.  But it isn't.  The Lisp
> libraries have to go somewhere.  You can hide them, just as the C
> libraries are hidden, and give Lisp the appearance of running "standalone
> executables" in exactly the same way that C programs give this appearance.
> But that's the best you can do.
> E.

Commercial MCL tries to address this to some degree: most of the
machine code and readonly data that would otherwise go into a heap
image is distributed in MacOS (PEF/CFM) libraries.  (Mutable data
conceptually could have been kept in libraries as well, but there were
technical limitations - including the lack of copy-on-write - that
made that impractical.)

To the extent that the scheme worked, it worked (and still works)
fairly well.  The biggest limitation (aside from the lack of
copy-on-write) had to do with the way that traditional shared library
technology handles "importing" and "exporting".

When a C program references a library function (such as "printf"),
there'll be an annotation in the executable file indicating that at
one or more locations in the program the address of the library symbol
"printf" should be plugged in to the program's code and/or data in
some way.  There are various schemes for doing this lazily (e.g.,
doing the importing and relocation if and only if "printf" is actually
called) or aggressively ("prebinding" an external reference, in the
expectation that a particular version of a library will be used and
will load at a predictable address.  This sort of thing is what
happens when the OSX installer says that it's going through an
optimization step.)

Regardless of when this importing and relocation takes place, it
depends on the fact that the external entity ("printf") is -named- by
a simple C string.  We might be able to think of meaningful and unique
names for a few types of lisp objects, but I'd rather not have to name
a large mostly static hash table in order to keep a shared hash table
in a library and would rather not have to name a lambda expression in
order to call it ...

What winds up happening in MCL is that each external reference is to
something like "that thing which is N bytes from the start of the
library's code section".  That gets around the naming issue, but
introduces an undesirable lack of flexibility: the value of N depends
on the exact heap address of a particular object that a library's
created (which in turn depends on lots of factors.) MCL's libraries
are timestamped and versioned, and they're usually only built as the
last stage before a release is produced.  (One advantage of the "named
import" scheme is that it's generally possible to import "printf" from
libraries that differ from the version that the application was linked
against, and to continue to do so until there are major ABI changes of
some sort.)

It's tempting to blame this on the limitations of C shared library
technology, but I'm not sure if that'd be accurate.

Perhaps there's less of a problem here than it seems: if "all of the
lisp" - code and data - were in a shared library, perhaps there'd be
other ways of resolving references between the application and that

Openmcl-devel mailing list
Openmcl-devel at clozure.com

More information about the Openmcl-devel mailing list