[LLVMdev] LLVM ERROR: Program used external function 'printd' which could not be resolved!

OvermindDL1 overminddl1 at gmail.com
Mon Oct 4 12:53:57 PDT 2010


On Mon, Oct 4, 2010 at 3:22 AM, Anton Korobeynikov
<anton at korobeynikov.info> wrote:
>>>> Any help will be much appreciated. Thanks!
>>> Windows does not support dynamic linking. You will need to resolve
>>> externals by hand.
>>
>> Why would it not support dynamic linking?  What about loadlibrary and
>> its kin are not sufficient to handle this?
> Well, you cannot easily export stuff from an executable and this is
> the main issue here.
> (And you cannot e.g. import stuff from executable into dynamic library
> as you can on linux/darwin)
>
>> Perhaps a work-around can be developed.
> Maybe. Patches are welcome!

Boost has worked around that same issue (which actually causes an
issue in Boost.Serialization because for it to work on Windows it has
to export the entire serialization tree of the user's program, which
can be on the order of *bloody massive* at times, it is fascinating
how it managed to pull this off without causing edits to the user code
though), by defining a specific macro that is clear on non-windows but
is the proper dllexport statement on Windows, could do the same thing
while encapsulating things in a "C" export to keep the names simple
for easy import.  If that is really the only issue, I could easily fix
it.  I figured it was something more complex...

And yes, you can import stuff from the executable into a dynamic
library in Windows, GetModuleHandle being passed null/0/etc... will
give a module link to the primary running executable, upon which you
can then pull in things it exports with ease.  LoadLibrary will link
in a dynamic library if it is not already linked in, then calls
GetModuleHandle on it, then returns what GetModuleHandle returns on
that.  GetModuleHandle by itself just looks in the linked in library
list (of which the executable is part of), and returns a handle to it.
 GetProcAddress operates on that handle to return a function pointer.

For example, from within the executable itself, if you want to link in
something that is exported from itself, you can do this:

export "C" {
  void printInt(int i) { printf("%i", i); }

  typedef void(*printIntType)(int);
}

int main(void) {
  HMODULE self = GetModuleHandle(0);
  printIntType printIntPtr = (AddFunc)GetProcAddress(self, "printInt");
  (*printIntPtr)(42);
}

And if you want to check for something exported from any currently
loaded module, EnumProcessModules can be used for that to get all
modules loaded into the current process.

So is this really all that is needed to get linking working on
Windows?  If so then I can easily do it.  Maybe a few pointers to show
me where in LLVM/clang source the equivalent *nix code is so I can
special case it?




More information about the llvm-dev mailing list