How to compile gcc with static library? - c

I have static library lib.a and in all tutorials using:
gcc -o main main.o -L. -lib
But I cant, I have errors:
/usr/bin/ld: cannot find -lib
collect2: error: ld returned 1 exit status
I need to use:
gcc -o main main.o -L. -lib.a
Why? What should I do to repair it ?

From the documentation of gcc -l:
-llibrary:
The linker searches a standard list of directories for the library, which is actually a file named liblibrary.a. The linker then uses this file as if it had been specified precisely by name.
...
The only difference between using an -l option and specifying a file name is that -l surrounds library with ‘lib’ and ‘.a’ and searches several directories.
So you cannot use -l with a library named 'lib.a'. Use 'lib.a' without the -l to include it. Of course, you cannot use -L then to set the directories to be searched for this particular library.

Do you have the error with this line ?
gcc -o main main.o -L. -llib
As MicroVirus found in the documentation, you will have to rename your library in liblib.a to use my previous line or just pass your library to gcc like a simple file.

Related

why can my gcc command not have -static parameter

I usually use gcc to compile my C program, it works ok, but when I tried to compile static library with -static parameter it always failed.
Although I tried some solutions on google, but it still didn't get fixed.
My command is as follows:
gcc mycode.c -static -L . -lurl -lcap -o mycode
The error message is:
/usr/bin/ld: cannot find -lc
collect2: error: ld returned 1 exit status
but when I remove -static it works very well.
GCC's -static linkage option directs the linker to ignore shared libraries
during the linkage. So it must find static versions of all the libraries required
by the linkage, including those that are linked by default, such as libc.
You have not installed the static version of libc (which would be /usr/lib/???/libc.a), so:
/usr/bin/ld: cannot find -lc
collect2: error: ld returned 1 exit status
libc.a is installed by the libc development package. The name of the libc
development package and how to install it depends on your distro. E.g. On Debian
or Ubuntu, the package to install is libc6-dev; on Fedora it is glibc-develop.
But before you go to do that, hang on a tick. You said:
I tried to compile static library with -static parameter it always failed.
gcc mycode.c -static -L . -lurl -lcap -o mycode
That sounds rather as if you just wanted to link your program with one or both
static libraries liburl.a, libcap.a, located in ./, and thought you should
do it by passing -static to the linkage.
There is no need to pass -static to link your program with ./liburl.a and/or
./libcap.a. The options:
-L . -lurl -lcap
will direct the linker to search in ./ for either of the files liburl.so (shared library)
or liburl.a (static library) and if it finds one or other of them it will link your
program with that library. If it finds both of them in ./, then it will choose the
shared library liburl.so. So unless you have ./liburl.so as well as ./liburl.a
then:
-L . -lurl
by itself will link your program against ./liburl.a.
And likewise for -lcap. No need for -static. The default shared library libc.so
will be linked automatically. The linker has no problem at all linking your program
with some static libraries and some shared ones. That is what is already happening
with your successful linkage:
gcc mycode.c -L . -lurl -lcap -o mycode
assuming that liburl.a and libcap.a are the only candidates for resolving
-lurl and -lcap in ./.
And even if you do have both ./liburl.a and ./liburl.so - and/or ./libcap.a and ./libcap.so - there is still no
need for a solution as drastic as a fully static linkage. You can just explicitly
tell the linker to find a particular static library if that's what you want, like:
gcc mycode.c -L . -l:liburl.a -l:libcap.a -o mycode

undefined reference to `explain_read' ...... No such file or directory

I need to include libexplain to my project to do certain job. I install it and add the header libexplain/read.h to my code, so far so good and no error reported by the complier. But when I use the function explain_read() provided by libexplain and build the project it says:
/tmp/cc7NjAw0.o: In function `xl45_read(int, unsigned char*)':
connections.cpp:(.text+0x2f): undefined reference to `explain_read'
collect2: error: ld returned 1 exit status
and the build script is:
#!/bin/bash
echo > ./stdafx.h
g++ -O1 -Wall -o ./local_proxy (*.cpp...here is the source file list) -lz -lpthread -lpcap -L/usr/local/lib
actually when I type
whereis libexplain
in terminal, I get
libexplain: /usr/lib/libexplain.so /usr/lib/libexplain.a /usr/include/libexplain
I do a lot of searches and still have no idea what's going wrong. ):
You need to link your object files with libexplain. You can do it using the -l<library name>, like so:
g++ -O1 -Wall -o ./local_proxy *.cpp -lz -lpthread -lpcap -lexplain -L/usr/local/lib
Note the -lexplain flag. For a library with the a file name like libABC.so, you'd use -lABC to refer to that library. The documentation for link options with GCC can shed more light on it.

Error "undefined reference" while linking in MinGW

I have got the object-file from source code using MinGW.
But on linking:
ld -o test.exe test.o
I get errors, for example the following:
undefined reference to printf
First, why are you using ld directly?
The following is an excerpt from the "GCC and Make" tutorial found at http://www3.ntu.edu.sg/home/ehchua/programming/cpp/gcc_make.html.
Compile and Link Separately
The above command compile the source file into object file and link with other object files (system library) into executable in one step. You may separate compile and link in two steps as follows:
// Compile-only with -c option
> g++ -c -Wall -g Hello.cpp
// Link object file(s) into an executable
> g++ -g -o Hello.exe Hello.o
Note g++ (you can substitute gcc if you are using C and not C++) is used both for compiling and linking. ld is not used at all.
The benefit of using g++ or gcc to link is that it will link with default libraries, such as the one you need to link with for printf, automatically.
To link with other libraries, you specify the library name with the -l parameter, as in -lmylib.
We can view commands ran by compiler via command
c99 -v test.o
We'll get some text. All after string which contains "COLLECT_CGG_OPTIONS" will be arguments of ld.
But size of executable file is much more then size of file got by previous way.

Error in creating .so file from .o files generated using multiple .c files

I have created the .o file as follows,
*gcc -I/home/vineeshvs/Dropbox/wel/workspace/Atmel -I /home/vineeshvs/Downloads/libusb-1.0.9 -I /home/vineeshvs/Downloads/libusb-1.0.9/libusb/ usb_comm.c hex2bin.c hex_read.c crc32.c -o vs.o -lusb-1.0*
Then I used the following command to get .so file
*gcc vs.o -shared -o libhello.so*
Then I am getting error as follows
*vs.o: In function `__i686.get_pc_thunk.bx':
(.text+0xaa6): multiple definition of `__i686.get_pc_thunk.bx'
/usr/lib/gcc/i686-linux-gnu/4.6/crtbeginS.o:crtstuff.c:
(.text.__i686.get_pc_thunk.bx[__i686.get_pc_thunk.bx]+0x0): first defined here
vs.o: In function `_fini':
(.fini+0x0): multiple definition of `_fini'
/usr/lib/gcc/i686-linux-gnu/4.6/../../../i386-linux-gnu/crti.o:(.fini+0x0): first defined here
vs.o: In function `__data_start':
(.data+0x4): multiple definition of `__dso_handle'
/usr/lib/gcc/i686-linux-gnu/4.6/crtbeginS.o:(.data.rel+0x0): first defined here
vs.o: In function `_init':
(.init+0x0): multiple definition of `_init'
/usr/lib/gcc/i686-linux-gnu/4.6/../../../i386-linux-gnu/crti.o:(.init+0x0): first defined here
/usr/lib/gcc/i686-linux-gnu/4.6/crtendS.o:(.dtors+0x0): multiple definition of `__DTOR_END__'
vs.o:(.dtors+0x4): first defined here
/usr/bin/ld.bfd.real: error in vs.o(.eh_frame); no .eh_frame_hdr table will be created.
collect2: ld returned 1 exit status
*
What could be the problem? (Thanks for stopping by :))
The problem is that you're linking the object files, not just compiling them.
Make sure that you only compile the files, don't link them! You do that using the -c option. Do not use the -l option, you don't want to link anything at this stage. So:
gcc -c -o usb_comm.o usb_comm.c
gcc -c -o hex2bin.o hex2bin.c
gcc -c -o hex_read.o hex_read.c
gcc -c -o crc32.o crc32.c
(I omitted the -I flags to save space here.)
Then finally link all those object files into a shared library, and link against usb-1.0:
gcc -shared -o libhello.so usb_comm.o hex2bin.o hex_read.o crc32.o -lusb-1.0
You should use a Makefile though for this. Or, even better, use a proper build system, like CMake, which is very easy to use. It's provided by all common Linux distros, so simply install it with the package manager (it it's not installed already), and read a quick tutorial on it.

G++ on windows: cannot fild -llua5.1

Good morning,
I'm trying to build luabind using bjam binaries and g++ (mingw).
Lua root is in 'D:\Dev\lua-5.1.4\',
*.a file here: 'D:\Dev\lua-5.1.4\lib\libluadll.dll.a'
*.dll file here: 'D:\Dev\lua-5.1.4\lib\luadll.dll'
All these *.o files were compiled well, but when it started linking it, something went wrong:
gcc.link.dll bin\gcc-mingw-4.4.1\debug\libluabindd.dll.a
d:/programms/codeblocks/mingw/bin/../lib/gcc/mingw32/4.4.1/../../../../mingw32/b
in/ld.exe: cannot find -llibluadll.dll.a
collect2: ld returned 1 exit status
"g++" -L"D:\Dev\lua-5.1.4\lib" "-Wl,--out-implib,bin\gcc-mingw-4.4.1\debug\
libluabindd.dll.a" -o "bin\gcc-mingw-4.4.1\debug\libluabindd.dll" -shared -Wl,-
-start-group "bin\gcc-mingw-4.4.1\debug\src\class.o" "bin\gcc-mingw-4.4.1\debug\
src\class_info.o" "bin\gcc-mingw-4.4.1\debug\src\class_registry.o" "bin\gcc-ming
w-4.4.1\debug\src\class_rep.o" "bin\gcc-mingw-4.4.1\debug\src\create_class.o" "b
in\gcc-mingw-4.4.1\debug\src\error.o" "bin\gcc-mingw-4.4.1\debug\src\exception_h
andler.o" "bin\gcc-mingw-4.4.1\debug\src\function.o" "bin\gcc-mingw-4.4.1\debug\
src\inheritance.o" "bin\gcc-mingw-4.4.1\debug\src\link_compatibility.o" "bin\gcc
-mingw-4.4.1\debug\src\object_rep.o" "bin\gcc-mingw-4.4.1\debug\src\open.o" "bin
\gcc-mingw-4.4.1\debug\src\pcall.o" "bin\gcc-mingw-4.4.1\debug\src\scope.o" "bin
\gcc-mingw-4.4.1\debug\src\stack_content_by_name.o" "bin\gcc-mingw-4.4.1\debug\s
rc\weak_ref.o" "bin\gcc-mingw-4.4.1\debug\src\wrapper_base.o" -Wl,-Bstatic -Wl
,-Bdynamic -llibluadll.dll.a -Wl,--end-group -g
...failed gcc.link.dll bin\gcc-mingw-4.4.1\debug\libluabindd.dll.a bin\gcc-mingw
-4.4.1\debug\libluabindd.dll...
...failed updating 2 targets...
So, I renamed libluadll.dll.a into lua5.1, lua5.1.a, but it's still prints the same error message.
Thanks, beforehand.
Firstly, -l{name} directive searches for lib{name}.dll and lib{name}.a. So, yours should be -llua, not -llibluadll.dll.a.
Secondly, are Lua libraries compiled with g++ too? Object files and libraries compiled by different compilers are incompatible in general.
This part of the g++ command line is wrong:
-llibluadll.dll.a
If you want to link against libfoo.dll, the right linker flag is -lfoo (no lib, no dll).
If you have a static archive and you want a static link, just name the archive, with no -l prefix (and specify a path if it's not found).

Resources