How do I compile files linked with llvm-link and pass my customized libraries and compiler pass to clang? - c++

Right now I am using the following line:
clang -Xclang -load -Xclang ../pass/pass.so -O2 -I../library/src/include/ -L../library/src/debug/ -DTAG_BITS=15 -lib1 -lib2 example.ll -o example
where I'm using my pass and example.ll is an example file that I linked with a runtime file (needed by the pass) using llvm-link. It does compile, but clang is skipping the libraries and using the built-ins instead:
clang: argument unused during compilation: '-I ../library/src/include/' [-Wunused-command-line-argument]
Why is the library being skipped? If I'm doing this wrong is there some other way I could compile the linked modules?

You've asked clang to compile example.ll which is an LLVM IR text file, and no other files. LLVM IR text doesn't have C-style #include statements, so the -I flag telling clang to look in your ../library/src/include/ directory to resolve files in a #include directive can't affect the compilation.

Related

Use compiled LLVM/clang without gcc

I have been trying to compile LLVM/clang from source, both by myself and using this script. I am compiling clang using gcc 11.2, which itself was also built from source, and hence resides in a non-default location on my system (/scratch/opt/gcc-ml-11.2). Note that it only works with a gcc that was compiled with multilib enabled.
The problem is that I can use the compiled clang and clang++ binaries only if I supply the gcc location as follows: --gcc-toolchain=/scratch/opt/gcc-ml-11.2.0. Without that flag, I run into linker errors:
clang test.c -o test
/usr/bin/ld: cannot find crtbeginS.o: No such file or directory
/usr/bin/ld: cannot find -lgcc
/usr/bin/ld: cannot find -lgcc_s
I do not understand why a clang compiled binary needs to link against some kind of gcc library and why clang does not supply the crtbeginS.O file.
I have also tried using the LLVM linker as well as the LLVM standard library for C++ test applications, i.e., "-fuse-ld=lld -stdlib=libc++. This did not help either.
While I could just export CXXFLAGS=--gcc-toolchain=/scratch/opt/gcc-ml-11.2.0, I am not sure whether this is the right approach. Shouldn't clang/LLVM be able to function without a gcc installation?
I have also tried using my clang installation with the --gcc-toolchain=/scratch/opt/gcc-ml-11.2.0 flag to compile clang again, but the new binary also requires the gcc-toolchain flag.
Should I just globally export the path to my gcc toolchain? Why is this necessary? Isn't clang a standalone compiler that - if supplied with the option to use its own standard library - does not require gcc?
Thank you very much for your help!
Best,
Maxbit

Undefined symbol when loading LLVM plugin

I am developing an LLVM pass and want to run it as a plugin via the Clang LLVM driver:
clang -Xclang -load -Xclang myPlugin.so ...
At first I got an error similar to that described here
undefined symbol for self-built llvm opt?
After applying the flag -D_GLIBCXX_USE_CXX11_ABI=0 as suggested, I'm getting this error:
error: unable to load plugin 'myPlugin.so': 'myPlugin.so: undefined symbol: _ZNK4llvm12FunctionPass17createPrinterPassERNS_11raw_ostreamERKSs
This page suggests that there may be an ABI compatibility issue (which I don't fully understand)
http://clang-developers.42468.n3.nabble.com/Loading-Static-Analyzer-plugin-fails-with-CommandLine-Errors-td4034194.html
My objective is to compile the pass with either GCC or Clang and run it with the system Clang installation (Ubuntu 16.04, LLVM 3.8) rather than building Clang/LLVM from source.
The problem could come from multiple clang installations. The clang version you have used to compile your plugin may be different from the clang called in
clang -Xclang -load -Xclang myPlugin.so ...
If you use cmake to build your plugin, then
cmake -DCMAKE_EXPORT_COMPILE_COMMANDS=ON
will generate the file compile_commands.json that will contain the llvm version you have used. bear make or make -n are alternatives if you don't use cmake for your plugin.
If compile_commands.json contains for example
"command": "c++ -c -I/usr/lib/llvm-4.0/include ..."
and if clang -v is clang version 3.8.0, you are likely to obtain this error message especially if llvm::FunctionPass::createPrinterPass is in llvm-4.0 and not in llvm-3.8.
A solution may be to compile with
clang-xxx -Xclang -load -Xclang myPlugin.so ...
where clang-xxx contains the llvm-xxx that is referenced in compile_commands.json.
I was receiving that error because first argument I passed into the RegisterPass had the same name as the pass itself:
static RegisterPass<MyPass> X("MyPass", "DPVariableNamePass", false, false);
Changing it fixed the issue:
static RegisterPass<MyPass> X("my-pass", "DPVariableNamePass", false, false);
Maybe it helps

clang -cc1 and system includes

I have the following file foo.cpp:
#include <vector>
struct MyClass
{
std::vector<int> v;
};
It can be successfully compiled with clang (I'm using clang 3.3 on Ubuntu 13.04 32bit):
clang++ -c foo.cpp
Now I want to print AST:
clang++ -cc1 -ast-print foo.cpp
and I've got the following error
foo.cpp:1:10: fatal error: 'vector' file not found
#include <vector>
^
struct MyClass {
};
1 error generated.
It looks like clang++ -cc1 doesn't know about system include files etc.
I'm wondering how to set up includes for clang++ -cc1?
You need to set up the right include paths.
on my system I added
-I/usr/include/i386-linux-gnu/c++/4.8 -I/usr/include/c++/4.8
to the compiler flags. The first one was so that it could find
bits/c++config.h
Of course the 4.8 is due to the fact I am using a compiler compatible with g++-4.8
I also added
-std=c++11 -stdlib=libstdc++
as compiler options.
Hope this helps
It's a Frequently Asked Question
#john is correct. For posterity, the relevant portions of the FAQ are (with names tweaked to match the question) :
clang -cc1 is the frontend, clang is the driver. The driver invokes the frontend with options appropriate for your system. To see these options, run:
$ clang++ -### -c foo.cpp
Some clang command line options are driver-only options, some are frontend-only options. Frontend-only options are intended to be used only by clang developers. Users should not run clang -cc1 directly, because -cc1 options are not guaranteed to be stable.
If you want to use a frontend-only option (“a -cc1 option”), for example -ast-dump, then you need to take the clang -cc1 line generated by the driver and add the option you need. Alternatively, you can run clang -Xclang <option> ... to force the driver [to] pass <option> to clang -cc1.
I did the latter (-Xclang) for emitting precompiled headers:
/usr/bin/clang++ -x c++-header foo.hpp -Xclang -emit-pch -o foo.hpp.pch <other options>
^^^^^^^
Without the -Xclang, clang++ ignored the -emit-pch. When I tried -cc1, I had the same problem as the OP — clang++ accepted -emit-pch but didn't have the other options the driver normally provides.

how to read compiler flags from a file

Is it possible to configure clang to read the compiler flags from a file. Is there any flag like:
clang++ test.cpp -flags=flags-file
Such that clang reads the compiler flags from flags-file.
Apparently there is support for reading commands from a file in clang as well as in gcc. The usage is something like:
clang++ test.cpp #file
The compiler will read the command line flags from file.
I could find a link for gcc.
https://developer.apple.com/library/mac/documentation/darwin/reference/manpages/man1/gcc.1.html
It could be achieved with the command:
clang++ test.cpp -flags=`cat flags-file`
as FDinoff suggested in the comments, make seems like the tool for the job though.

If I use g++ as my compiler, how do I scan a c++ file with the clang static analyzer?

I use g++ to compile my C++ project. When I try to use the clang static analyzer (scan-build) to check my code, I get an error:
>> scan-build g++ main.cpp
could not find clang line
How do I use the scan-build tool with g++?
It appears that scan-build is having trouble recognizing "g++" as the compiler command. It expects "clang" or "gcc". If you replace "g++" with "gcc -lstdc++" to build your project, the scan-build tool will work properly.
>> scan-build gcc -lstdc++ main.cpp
main.cpp:7:3: warning: Assigned value is garbage or undefined
int y = x;
^ ~
1 warning generated.
scan-build: 1 bugs found.
scan-build: Run 'scan-view /var/folders/2l/2l6vhCnVFNad-O8ryd5YO++++TI/-Tmp-/scan-build-2011-09-18-2' to examine bug reports.