[llvm-dev] symbol resolution on statically-compiled JIT

12 views
Skip to first unread message

Eli Baum via llvm-dev

unread,
Mar 11, 2019, 11:16:12 PM3/11/19
to llvm...@lists.llvm.org
Hi!

I am using LLVM to create a JIT – I have followed the excellent Kaleidoscope tutorial, and am now starting to build off of it.

Down the line, I plan to use this JIT for my research into computer architecture, which means that I will need to run the JIT itself within a simulated CPU and bare-bones linux system. To make that research easier, I am trying to statically compile my JIT. Everything works with the normal compilation (clang ... -rdynamic) but when switched to static (clang ... -static), I can no longer execute externally defined C functions. I suspect this is something to do with the symbol loader not being properly set up for static linking, but I don't know much about that.

Here are some more details:

In the normally-compiled kaleidoscope JIT, I can run something like this:
kld> extern printd(x);
kld> printd(10);
10.000000

printd was one of the C functions defined within the main program:
/// printd - printf that takes a double prints it as "%f\n", returning 0.
extern "C" DLLEXPORT double printd(double X) {
  fprintf(stderr, "%f\n", X);
  return X;
}

However, in the static linked version, the JIT cannot find the symbol:
kld> extern printd(x);
kld> printd(1);
kaleidoscope error: Symbols not found: { printd }

But the symbol is there:
$ llvm-nm kld_s | grep printd
0000000000497e30 T printd
$ llvm-nm kld | grep printd
00000000006b1820 T printd

(kld_s is the static version)

How can I begin to debug this issue? Does something different happen to the symbol loader when I compile statically?

My two make scripts look like
$ make kld
clang++ -v  kld.cpp libkld.o /home/eli/sproj-git/passes/test/libTestPass.o `llvm-config --cxxflags --ldflags --system-libs --libs core orcjit native ` -fuse-ld=gold -g3 -o kld -rdynamic

$ make kld_s
clang++ -v  kld.cpp libkld.o /home/eli/sproj-git/passes/test/libTestPass.o `llvm-config --cxxflags --ldflags --system-libs --libs core orcjit native ` -fuse-ld=gold -g3 -o kld_s -static

The only difference is in the final flag (bold). libkld.o and libTestPass.o are unrelated object files I am linking from other parts of my project.

If the clang option -static behaves like gcc's, the man page does say that it "... prevents linking with the shared libraries", which I suppose is not precisely what I want. 

I previously emailed llvm-dev a few months ago about a similar issue, where extern functions were not working at all (even dynamically). I resolved that issue by downgrading to LLVM 6, and recently, by upgrading to LLVM 9. Now the issue has returned, I suppose, in slightly different form.

If anyone has any ideas, please let me know!

Thank you so much,
Eli Baum

Lang Hames via llvm-dev

unread,
Mar 29, 2019, 8:15:57 PM3/29/19
to Eli Baum, LLVM Developers Mailing List
Hi Eli,

You will need to add the process symbols explicitly to the search space using:

  sys::DynamicLibrary::LoadLibraryPermanently(nullptr);

If you are on linux, you will also need to make sure that process symbols are exported by passing -Wl,--export-dynamic to clang, and ensure that any symbols that you want to call are not dead-stripped by the linker.

Hope that helps!

Cheers,
Lang.

_______________________________________________
LLVM Developers mailing list
llvm...@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev
Reply all
Reply to author
Forward
0 new messages