Dynamic loading, D all the way (dmd 64bit 2.060/Ubuntu 64bit 12.04/x86_64)

Carl Sturtivant sturtivant at gmail.com
Sun Aug 19 20:40:18 PDT 2012


(By dynamic loading I mean using something like the C library function
dlopen to explicitly load a shared object at runtime. I do not mean dynamic
linking in the usual passive sense.)

I just successfully got working a toy example of dynamically loading (from
a D program) a D shared object and then finding and calling functions
defined in the shared object, and not just with C linkage.

The main program, main.d, was compiled and linked somewhat normally, except
for passing the linker via gcc the flags necessary to ensure that the whole
of libphobos2.a is present and that all symbols in the resulting executable
are exposed dynamically.

The shared object source, dload.d was compiled to an object file containing
position independent code by dmd. Then I invoked the linker explicitly and
had it make a shared object without the D runtime system or Phobos. This is
the novel step, and it enables the shared object to resolve its linkage to
the D runtime system and Phobos at the point of being loaded, via callbacks
to the main program. Thus the troubles of D in shared objects are largely
circumvented. There is only one instance of phobos and D-runtime, in the
main program. (Once phobos and druntime are shared objects in the future
somewhere this will work with no code bloat.)

The static initialization code in dload.d is automatically executed when
the shared object libdload.so is loaded by the main program, because the
linker is also passed a flag indicating the static initialization block's
mangled name, dynamically determined from dload.o before linkage to
libdload.so occurs.

Finally, the mangled names of the functions to load are determined by a
call of a function with C linkage in dload.d from main.d that looks up
those names in an associative array initialized in the static
initialization block of dload.d where those mangled names are directly
available, so that full D linkage can be emulated, at least for functions.

One thing: the garbage collector needs to be aware of static and 'global' D
variables in the shared object. Can a technical expert verify that I've
done the right thing to achieve that happy state of affairs in this unusual
context?

So, what's overlooked here? I know that the static initialization code
cannot successfully throw an exception. Yet if a function in the shared
object is called from the main program and throws an exception, all is
well. (Try these.) See my comments in dload.d about this. What is it about
the implementation of exceptions that's problematic here?

All files attached, including a Makefile with the exact options passed to
dmd, gcc and ld.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.puremagic.com/pipermail/digitalmars-d/attachments/20120819/94144da4/attachment.html>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: dload.d
Type: application/octet-stream
Size: 978 bytes
Desc: not available
URL: <http://lists.puremagic.com/pipermail/digitalmars-d/attachments/20120819/94144da4/attachment.obj>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: main.d
Type: application/octet-stream
Size: 862 bytes
Desc: not available
URL: <http://lists.puremagic.com/pipermail/digitalmars-d/attachments/20120819/94144da4/attachment-0001.obj>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: staticCtor.icn
Type: application/octet-stream
Size: 856 bytes
Desc: not available
URL: <http://lists.puremagic.com/pipermail/digitalmars-d/attachments/20120819/94144da4/attachment-0002.obj>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: Makefile
Type: application/octet-stream
Size: 820 bytes
Desc: not available
URL: <http://lists.puremagic.com/pipermail/digitalmars-d/attachments/20120819/94144da4/attachment-0003.obj>


More information about the Digitalmars-d mailing list