Vala: TypeModuleSample(CrossCompilation) and TypeModule/ added.
This commit is contained in:
parent
c5cef9fe2b
commit
52e1edf910
|
@ -0,0 +1,55 @@
|
|||
class MyModule : TypeModule
|
||||
{
|
||||
[CCode (has_target = false)]
|
||||
private delegate Type PluginInitFunc (TypeModule module);
|
||||
|
||||
private GLib.Module module = null;
|
||||
|
||||
private string name = null;
|
||||
|
||||
public MyModule (string name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public override bool load () {
|
||||
string path = Module.build_path (Environment.get_variable ("PWD"), name);
|
||||
module = Module.open (path, GLib.ModuleFlags.BIND_LAZY);
|
||||
if (null == module) {
|
||||
error ("Module not found");
|
||||
}
|
||||
|
||||
void * plugin_init = null;
|
||||
if (! module.symbol ("plugin_init", out plugin_init)) {
|
||||
error ("No such symbol");
|
||||
}
|
||||
|
||||
((PluginInitFunc) plugin_init) (this);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
public override void unload () {
|
||||
if (module != null)
|
||||
message ("Library unloaded");
|
||||
module = null;
|
||||
}
|
||||
}
|
||||
|
||||
// Never unref instance of GTypeModule
|
||||
// http://www.lanedo.com/~mitch/module-system-talk-guadec-2006/Module-System-Talk-Guadec-2006.pdf
|
||||
static TypeModule module = null;
|
||||
|
||||
int main ()
|
||||
{
|
||||
module = new MyModule ("plugin");
|
||||
module.load ();
|
||||
|
||||
var o = GLib.Object.new (Type.from_name ("MyClass"));
|
||||
|
||||
// free last instance, plugin unload
|
||||
o = null;
|
||||
|
||||
module.unload ();
|
||||
|
||||
return 0;
|
||||
}
|
|
@ -0,0 +1,14 @@
|
|||
public class MyClass : Object {
|
||||
construct {
|
||||
message("MyClass init");
|
||||
}
|
||||
|
||||
~MyClass() {
|
||||
message("MyClass deinit");
|
||||
}
|
||||
}
|
||||
|
||||
[ModuleInit]
|
||||
Type plugin_init(GLib.TypeModule type_module) {
|
||||
return typeof(MyClass);
|
||||
}
|
|
@ -0,0 +1,15 @@
|
|||
#!/bin/sh
|
||||
|
||||
# Cross-Platform: Works for GNU/Linux and Windows
|
||||
|
||||
valac -o loader loader.vala --pkg=gmodule-2.0
|
||||
valac --ccode plugin.vala
|
||||
if [[ `uname` == Linux ]]; then
|
||||
libext=so
|
||||
exeext=
|
||||
else
|
||||
libext=dll
|
||||
exeext=.exe
|
||||
fi
|
||||
gcc -fPIC -shared -o libplugin.$libext plugin.c $(pkg-config --libs --cflags gobject-2.0 gmodule-2.0)
|
||||
./loader$exeext
|
|
@ -0,0 +1,45 @@
|
|||
public class PluginRegistrar<T> : Object {
|
||||
|
||||
public string path { get; private set; }
|
||||
|
||||
private Type type;
|
||||
private Module module;
|
||||
|
||||
private delegate Type RegisterPluginFunction (Module module);
|
||||
|
||||
public PluginRegistrar (string name) {
|
||||
assert (Module.supported ());
|
||||
this.path = Module.build_path (Environment.get_variable ("PWD"), name);
|
||||
}
|
||||
|
||||
public bool load () {
|
||||
stdout.printf ("Loading plugin with path: '%s'\n", path);
|
||||
|
||||
module = Module.open (path, ModuleFlags.BIND_LAZY);
|
||||
if (module == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
stdout.printf ("Loaded module: '%s'\n", module.name ());
|
||||
|
||||
void* function;
|
||||
module.symbol ("register_plugin", out function);
|
||||
unowned RegisterPluginFunction register_plugin = (RegisterPluginFunction) function;
|
||||
|
||||
type = register_plugin (module);
|
||||
stdout.printf ("Plugin type: %s\n\n", type.name ());
|
||||
return true;
|
||||
}
|
||||
|
||||
public T new_object () {
|
||||
return Object.new (type);
|
||||
}
|
||||
}
|
||||
|
||||
void main () {
|
||||
var registrar = new PluginRegistrar<TestPlugin> ("plugin");
|
||||
registrar.load ();
|
||||
|
||||
var plugin = registrar.new_object ();
|
||||
plugin.hello ();
|
||||
}
|
|
@ -0,0 +1,3 @@
|
|||
public interface TestPlugin : Object {
|
||||
public abstract void hello ();
|
||||
}
|
|
@ -0,0 +1,11 @@
|
|||
class MyPlugin : Object, TestPlugin {
|
||||
public void hello () {
|
||||
stdout.printf ("Hello world!\n");
|
||||
}
|
||||
}
|
||||
|
||||
public Type register_plugin (Module module) {
|
||||
// types are registered automatically
|
||||
return typeof (MyPlugin);
|
||||
}
|
||||
|
|
@ -0,0 +1,21 @@
|
|||
#!/bin/sh
|
||||
|
||||
# Works under Linux only, not cross-platform
|
||||
|
||||
valac --pkg gmodule-2.0 main.vala plugin-interface.vala -o main
|
||||
if [[ `uname` == Linux ]]; then
|
||||
libext=so
|
||||
exeext=
|
||||
else
|
||||
libext=dll
|
||||
exeext=.exe
|
||||
fi
|
||||
valac --pkg gmodule-2.0 -C plugin.vala plugin-interface.vala
|
||||
if [[ `uname` == Linux ]]; then
|
||||
gcc -shared -fPIC $(pkg-config --cflags --libs glib-2.0 gmodule-2.0) \
|
||||
-o libplugin.$libext plugin.c
|
||||
else
|
||||
gcc -shared -fPIC $(pkg-config --cflags --libs glib-2.0 gmodule-2.0 gobject-2.0) \
|
||||
-o libplugin.$libext plugin.c $(pkg-config --libs glib-2.0 gmodule-2.0 gobject-2.0)
|
||||
fi
|
||||
./main$exeext
|
Loading…
Reference in New Issue