On Monday, 10 March 2014 at 06:38:35 UTC, Steve Teale wrote:
On Sunday, 9 March 2014 at 14:09:28 UTC, Tolga Cakiroglu wrote:


For this, you create an "Interface" that matches to the method declaration of your class. But notice that instead of defining methods, you will define attributes those types' match to that class's methods. I did this before and it works. At least with Posix "dlsym" function's help.

OK, so then what goes wrong here:

module exta;

class ExtA
{
   int n;
   this(int _n) { n = _n; }

   int foo() { return ++n; }
}

ExtA getInstance(int n)
{
   return new ExtA(n);
}

compiled with:
dmd exta.d -c -fPIC -shared
dmd exta.o -shared -defaultlib=libphobos2.so -L-rpath=.

module main;
import core.runtime;
import std.stdio;

extern(C) void* dlsym(void*, const char*);
extern(C) void dlclose(void*);

interface ExtA
{
   int foo();
}

void main() {
   void* lib = Runtime.loadLibrary("exta.so");
   if (lib is null)
   {
      writeln("library not loaded");
      return;
   }
   writeln("loaded");

void* vp = dlsym(lib, "_D4exta11getInstanceFiZC4exta4ExtA\0".ptr);
   if (vp is null)
   {
      writeln("symbol not found");
      return;
   }
   writeln("got symbol");
   ExtA function(int) f = cast(ExtA function(int)) vp;
   ExtA x = f(42);
   if (x is null)
   {
      writeln("no class object");
      return;
   }
   int n = x.foo();
   writefln("n = %d", n);
   Runtime.unloadLibrary(lib);
}

compiled with:
dmd -c main.d
dmd main.o -L-ldl -defaultlib=libphobos2.so -L-rpath=.

output:
loaded
got symbol
n = 9
Segmentation fault (core dumped)

The answer should be 43. The segfault happens on the Runtime.unloadLibrary(lib); call.

Any ideas?

Steve

confusion between main.Exta and exta.ExtA
following worked for me

module exta;

import main;

//===========================================================
class ExtA : ExtA_IF
{
    int n;
    this(int _n) { n = _n; }

    int foo() { return ++n; }
}

ExtA_IF getInstance(int n)
{
    return new ExtA(n);
}
//=============================================================


//==============================================================
module main;
import core.runtime;
import std.stdio;

extern(C) void* dlsym(void*, const char*);
extern(C) void dlclose(void*);

interface ExtA_IF
{
    int foo();
}

void main() {
    void* lib = Runtime.loadLibrary("exta.so");
    if (lib is null)
    {
       writeln("library not loaded");
       return;
    }
    writeln("loaded");

    //use extern (C) to avoid mangling
    void* vp = dlsym(lib,
"_D4exta11getInstanceFiZC4main7ExtA_IF\0".ptr);
    if (vp is null)
    {
       writeln("symbol not found");
       return;
    }
    writeln("got symbol");
    ExtA_IF function(int) f = cast(ExtA_IF function(int)) vp;
    ExtA_IF x = f(42);
    if (x is null)
    {
       writeln("no class object");
       return;
    }
    int n = x.foo();
    writefln("n = %d", n);

    // or free or destroy or whatever it's supposed to be to
    //to avoid the seg fault  (bug?)
    delete x;
    Runtime.unloadLibrary(lib);
}

Reply via email to