Skip to content

Loading…

Runtime.loadLibrary() and unloadLibrary() on POSIX. #211

Closed
wants to merge 1 commit into from

4 participants

@alexrp
D Programming Language member
@MartinNowak
D Programming Language member

We need a full blown library initialization.
We also need a shared runtime instead of a GC proxy.

@alexrp
D Programming Language member

So what is the plan for these functions?

@bithavoc

@alexrp ++
@dawgfoto what do you mean, will this patch work or not? :)

@klickverbot
D Programming Language member

I think the issue is that the patch itself is correct, but not enough to smoothly support shared libraries on Posix, because all kinds of stuff will still break behind your back. Martin already did some work on this in the branch at his repo he linked, but as far as I know, there is still some more to do – you might want to join forces.

@MartinNowak
D Programming Language member

Linking against shared libraries will work soon but loading shared libraries at runtime
will still take a while. There are two major technical issues to solve.

  • Runtime.unloadLibrary will probably have to go. Due to GC one cannot deterministically free all references to a loaded library. The latest idea for this was to put the address range under control of the GC and let him release the library.

  • There is no solution yet for per-thread initialization when you load a C library at runtime that depends on a D library. Basically we need to traverse the dependency DAG of a library but the only feasible solution I found was to poke around in the dlopen handle.

@bithavoc

I get it, that's like others GC'd/managed environments works(AppDomain.Unload in the CLR) and that sounds like a good plan for the future. However, (and this is just a thought) I think that a partial implementation of this feature that at least let the developer load D shared libraries would be very useful.

IMHO, this will be used mostly to load plugins, plugins will modify the environment and do random stuff. From the application point of view it's easier to just restart the process in order to reload the new "catalog" of plugins.

Developers can use dlopen for C shared libraries and loadLibrary for D shared libraries. I don't think unloadLibrary is that necessary at this point, it's always better to just restart the process. In the future, if there will be an implementation of unloadLibrary, it will just mark the library to be unloaded eventually by the Runtime/GC.

So I would vote for a partial implementation of 'loadLibrary' and defer 'unloadLibrary' until we can afford the unload libraries in a safe way by a shared Runtime, etc.

Again, this is just a thought.

@alexrp alexrp referenced this pull request in D-Programming-Language/dmd
Closed

Link to libdl on non-BSD POSIX systems. #941

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Commits on May 17, 2012
Showing with 18 additions and 3 deletions.
  1. +18 −3 src/rt/dmain2.d
View
21 src/rt/dmain2.d
@@ -61,6 +61,11 @@ version (FreeBSD)
import core.stdc.fenv;
}
+version (Posix)
+{
+ import core.sys.posix.dlfcn;
+}
+
extern (C) void _STI_monitor_staticctor();
extern (C) void _STD_monitor_staticdtor();
extern (C) void _STI_critical_init();
@@ -135,11 +140,18 @@ extern (C) void* rt_loadLibrary(in char[] name)
gcSet(gc_getProxy());
}
return ptr;
-
}
else version (Posix)
{
- throw new Exception("rt_loadLibrary not yet implemented on Posix.");
+ if (auto lib = dlopen(name.ptr, RTLD_LAZY))
+ {
+ if (auto fn = cast(gcSetFn)dlsym(lib, "gc_setProxy"))
+ fn(gc_getProxy());
+
+ return lib;
+ }
+ else
+ return null;
}
}
@@ -154,7 +166,10 @@ extern (C) bool rt_unloadLibrary(void* ptr)
}
else version (Posix)
{
- throw new Exception("rt_unloadLibrary not yet implemented on Posix.");
+ if (auto fn = cast(gcClrFn)dlsym(ptr, "gc_clrProxy"))
+ fn();
+
+ return dlclose(ptr) == 0;
}
}
Something went wrong with that request. Please try again.