While learning to write LLVM passes and following the precise instructions under http://llvm.org/docs/WritingAnLLVMPass.html,
I got this error when loading the hello pass to run the test program:
opt -load ./Release/lib/Hello.so -hello < test/test.bc > /dev/null
Error opening ‘./Release/lib/Hello.so’: ./Release/lib/Hello.so: undefined symbol: _ZSt16__ostream_insertIcSt11char_traitsIcEERSt13basic_ostreamIT_T0_ES6_PKS3_i
-load request ignored.
opt: Unknown command line argument ‘-hello’. Try: ‘opt --help’
make: *** [run_lib] Error 1
I think I might have missed a LLVM lib file, but can’t figure out which.
I double checked the Makefile, it does have the libLLVMCore.a, libLLVMSystem.a and libLLVMSupport.a specified.
Could people suggest?
All are based on the LLVM 2.5 release, running on Debian4-i386.
Thank you very much
Chuck
Hello.cpp file:
#include “llvm/Pass.h”
#include “llvm/Function.h”
using namespace llvm;
namespace {
struct Hello : public FunctionPass {
static char ID;
Hello() : FunctionPass(&ID) {}
virtual bool runOnFunction(Function &F) {
llvm::cerr << "Hello: " << F.getName() << “\n”;
return false;
}
};
char Hello::ID = 0;
RegisterPass X(“hello”, “Hello World Pass”);
}
Makefile:
Makefile for hello pass
Path to top level of LLVM heirarchy
LEVEL = .
Name of the library to build
LIBRARYNAME = Hello
Make the shared library become a loadable module so the tools can
dlopen/dlsym on the resulting library.
LOADABLE_MODULE = 1
Tell the build system which LLVM libraries your pass needs. You’ll probably
need at least LLVMSystem.a, LLVMSupport.a, LLVMCore.a but possibly several
others too.
LLVMLIBS = LLVMCore.a LLVMSupport.a LLVMSystem.a
Include the makefile implementation stuff
include $(LEVEL)/Makefile.common
Hey Chuck,
I'm afraid I can't reproduce your error but...a problem you may run
into later is that opt will complain with
opt: llvm/lib/VMCore/Pass.cpp:149:
void<unnamed>::PassRegistrar::RegisterPass(const llvm::PassInfo&):
Assertion `Inserted && "Pass registered multiple times!"' failed.
Aborted
I "fixed" this by replacing the LLVMLIBS line in the Makefile with
LINK_COMPONENTS according to this tutorial http://llvm.org/docs/MakefileGuide.html#LoadableModules
and was able to build/run my pass properly.
-shu
Thanks, Shu,
I guess I haven’t updated since my post went out.
There are actually 2 problems:
- mis-compilation:
My LLVM-2.5 turned out to be mis-compiled using gcc-4.4.0 (surprise to me) on Debian4-32b.
I tried a few different compilers, and gcc-4.0.4 (a relatively old one, again surprised me) seems to work out fine.
Question: is there a good/quick/reliable way to figure out whether a certain gcc compiler will mis-compile?
- I ran into exactly the problem you pointed out. (Thank you)
The Makefile needs some update (after careful comparison between the tutorial Makefile and the makefile used for lib/Transformation/Hello), by
commenting out the following line:
#LLVMLIBS = LLVMCore.a LLVMSystem.a LLVMSupport.a
I guess the tutorial needs some update, as with release 2.5 things might have changed a bit.
Thanks for the reply
Chuck
Shuguang Feng wrote:
Question: is there a good/quick/reliable way to figure out whether a
certain gcc compiler will mis-compile?
http://llvm.org/docs/GettingStarted.html#brokengcc lists documented
problems with different versions of gcc.
I use gcc-4.3.2 with ubuntu 8.10 and haven't had any problems
2. I ran into exactly the problem you pointed out. (Thank you)
The Makefile needs some update (after careful comparison between the
tutorial Makefile and the makefile used for lib/Transformation/Hello), by
commenting out the following line:
#LLVMLIBS = LLVMCore.a LLVMSystem.a LLVMSupport.a
I guess the tutorial needs some update, as with release 2.5 things might
have changed a bit.
Yea, I commented out LLVMLIBS at first as well before I came across
the documentation at http://llvm.org/docs/MakefileGuide.html#LoadableModules
. I think LLVMLIBS is supposed to be ignored when compiling a shared
library but somehow isn't. I'm new to LLVM so I could be way off.
Best of luck!
-shu
I'm running into a completely different problem. When I do:
opt -load LowerFastInvoke.o -help
I get the message:
Error opening 'LowerFastInvoke.o': LowerFastInvoke.o: only ET_DYN and
ET_EXEC can be loaded?
Am I missing something?
Assuming the extension is right, you're trying to load an object file,
which isn't allowed; you have to link it first.
-Eli
Oops. Thanks... I totally missed that.
One more thing to follow up:
Does the opt -load option only allow a shared object file (.so) ?
Is it possible to have a normal library as well (e.g., .a file)?
I am asking because current Cygwin build doesn’t seem to generate/support .so/.dll files?
Have anybody tried and succeed in writing an individual pass on Cygwin and managed to get loaded to run from “opt -load” option?
Thank you
Chuck
Kenneth Uildriks wrote: