Add a .a library to cmake project [duplicate] - c

This question already has answers here:
CMake link to external library
(6 answers)
Closed 4 years ago.
I have a libname.a static library that works fine when I use gcc:
gcc -c main.c -o main.o ;
gcc main.o libname.a main
But now I would like to use CMake as the project is getting big, but I got this message and and I don't know how to include it in an appropriate way. (I tried link_target_library and/or link_directories and/or set(CMAKE_CC_FLAGS "absolute_path/libname.a").
Note that I don't have any source code for libname.a.
/usr/bin/ld: cannot find -llibname

As said in my comment target_link_libraries(${PROJECT_NAME} ${CMAKE_SOURCE_DIR}/libname.a) works. I can't really tell what the reason for your problem is (maybe you used target_link_library instead of target_link_libraries ?).

Related

C: An alternative(better) way to compile files? [duplicate]

This question already has answers here:
C++ project organisation (with gtest, cmake and doxygen)
(4 answers)
Closed 6 years ago.
I'm new to C.
I've split my sorting program into three .c files compare_functions.c, insertion_sort.c and main.c, which includes the two.
In order to get the executable, I try the followings: (only related files in the current folder)
gcc -c insertion_sort.c compare_functions.c main.c
gcc *.o -o main.out
In addition to two headers compare_functions.h, insertion_sort.h, finally there are nine files in the folder, after ls them:
compare_functions.c insertion_sort.c main.c
compare_functions.h insertion_sort.h main.o
compare_functions.o insertion_sort.o main.out
Finally the ./main.out just work fine but, say, if I have a program much larger(ie. a hundred of .c file), finally there will be a mess with 100*3 files, is the way described above still suitable?
If you have a lot of source files to compile you might want to check tools like Automake or CMake. They will take care of compiling the right files in the right objects, AND they will only compile the files you edited.

Undefined reference to RSA_generate_key in OpenSSL? [duplicate]

This question already has answers here:
Linking libssl and libcrypto in GCC [duplicate]
(2 answers)
Closed 6 years ago.
I have the following code in the file rsatest.c. I'm trying to generate a RSA key pair.
#include <openssl/rsa.h>
#include <openssl/pem.h>
int main(){
RSA *rsa = RSA_generate_key((const int) 1024,(const int) 3, 0, 0);
return 0;
}
I'm compiling this with
gcc -I../include/ -L . -lcrypto -lssl rsatest.c
and I get the following error.
undefined reference to `RSA_generate_key'
Am I linking the library files in the wrong order? I made the libcrypto.a and libssl.a on windows (64 bit), with msys and mingw, and I'm running the code on the same system.
RSA_generate_key has been declared in rsa.h. Is it not defined in libcrypto.a?
EDIT :
I tried this too,
gcc -I../include rsatest.c -L . -lcrypto -lssl
and I understand that the linker will look for definitions in the libraries going from left to right.
However, I get new undefined references to various functions in
rand_win.o and c_zlib.o
I looked up online and found the missing symbols in the libraries gdi32 and zlib. So I added
-lz and -lgdi32
The compiler did not complain about a missing library, so I assume they are present with mingw. And still, I get the same output.
I also used nm, and found that the symbols were indeed undefined in rand_win.o and c_zlib.o.
Why cant the linker seem to find definitions in these libraries?
Change the order in your gcc command.
gcc -I../include/ rsatest.c -L . -lcrypto -lssl
As far as I know linker has a list of undefined symbols. When it processes libcrypto.a and libssl.a it does not have anything in the list of undefined symbols so he just drops the libraries. Then after processing rsatest it has something in its list but it does not look for symbols in already processed libraries.

Unable to link to libgfortran.a [duplicate]

This question already has answers here:
Why does the order in which libraries are linked sometimes cause errors in GCC?
(9 answers)
Closed 8 years ago.
I have gfortran installed on my system and the file libgfortran.a can be found at /usr/lib/gcc/x86_64-linux-gnu/4.6/. Using nm I made sure that the function _gfortran_compare_string is defined in there:
$ nm /usr/lib/gcc/x86_64-linux-gnu/4.6/libgfortran.a | grep _gfortran_compare_string
Returns
0000000000000000 T _gfortran_compare_string
0000000000000000 T _gfortran_compare_string_char4
But, the linker of my CUDA-C program throws errors:
/usr/local/cuda-6.0/bin/nvcc --cudart static -L/usr/lib/gcc/x86_64-linux-gnu/4.6 -L/home/chung/lapack-3.5.0 -link -o "pQP" ./src/pQP.o -lgfortran -llapacke -llapack -lcublas -lblas -lcurand
nvcc warning : The 'compute_10' and 'sm_10' architectures are deprecated, and may be removed in a future release.
/home/chung/lapack-3.5.0/liblapack.a(ilaenv.o): In function `ilaenv_':
ilaenv.f:(.text+0x81): undefined reference to `_gfortran_compare_string'
and later on another error, again related to libgfortran:
/home/chung/lapack-3.5.0/liblapack.a(xerbla.o): In function `xerbla_':
xerbla.f:(.text+0x49): undefined reference to `_gfortran_st_write'
xerbla.f:(.text+0x54): undefined reference to `_gfortran_string_len_trim'
xerbla.f:(.text+0x66): undefined reference to `_gfortran_transfer_character_write'
xerbla.f:(.text+0x76): undefined reference to `_gfortran_transfer_integer_write'
xerbla.f:(.text+0x7e): undefined reference to `_gfortran_st_write_done'
xerbla.f:(.text+0x87): undefined reference to `_gfortran_stop_string'
But, again using nm, I found that _gfortran_st_write, etc are defined in libgfortran.a.
Links: Complete log and source code.
Note: Lapack makes use of libgfortran. I recently installed lapack and ran all the tests and they all passed.
You need to change the order in which you specify static libraries to the linker. If you do something like this:
nvcc --cudart static -L/usr/lib/gcc/x86_64-linux-gnu/4.6 \
-L/home/chung/lapack-3.5.0 -link -o "pQP" ./src/pQP.o \
-llapacke -llapack -lcublas -lblas -lcurand -lgfortran
You should find it will work.
The underlying reason (and this is a trait of the gcc/gnu toolchain and not anything to do with nvcc) is that linking dependency lists for static libraries are parsed from left to right by the gnu linker. If you specify a static library before any library which depends on it, it will be skipped because it has no dependencies in the link list at the point in processing when it is first encountered.

undefined reference issue in math.h [duplicate]

This question already has answers here:
Undefined reference to `sin` [duplicate]
(4 answers)
Closed 9 years ago.
I have include the math.h in my c file, however it keeps prompts undefined reference to truncand undefined reference to ceil. And I didn't even use trunc in my file. Could anyone tell what was the problem?
If you compile using gcc, you might need to add -lm option to link to the math library (libm) like
gcc test.c -lm
It seems that you will need the info about how C source code are compiled and linked together.
The link contains some basic info:
Compile & Link
You use -I option of gcc to specify where to find headers, and -l option to link standard libraries

How to refresh the file math.h [duplicate]

This question already has answers here:
Closed 12 years ago.
Possible Duplicate:
Why Am I Getting Link Errors When Calling Function in Math.h?
Hello, I have a problem in C (gcc), when I compile a program that includes Math.h and uses functions from there, it says "undefined reference to...". it happens for sqrt, log, but for others not (for instance pow). How can I fix this library or reinstall it ? thanks in advance.
[I am using Ubuntu]
You shold link with -lm option: gcc -o test test.c -lm lm means link math.

Resources