darksky darksky - 1 year ago 42
C Question

Static Library Include Issue in C

I followed the following tutorials to create a static library.




I generated a static library in C using the

tool. The library is from a different directory. I am generating the library properly, and I'm using it to compile with my program as follows:

gcc -lpthreads main.c -o server -L thread-pool -lthreadpool

The library under the current directory is called
which contains

According to the tutorials, I need to include my
file as follows in
#include "threadpool.h"
. GCC is throwing an error saying
is not found. That is obvious since it's in a different directory.

When I include is as:
#include threadpool/threadpool.h"
it compiles but doesn't actually work. It still does not recognise the functions. I'm not sure why this is happening. I thought when compiling a static library, you do not need to actually send the
file or any source as a matter of fact.

What is the issue here? How can I overcome this?


I know .h files are not the same as static libraries. I'm not sure why what I said above make it seem as if I'm confused between both.

Anyway, so when one uses a static library, does it mean we also need the
file and include it into the source, and not just compile the program with the static library?

Answer Source

As Michael Burr said, the #include of the .h file, and the linking with the library file, are two different (but related) things.

When you build a C program that consists of several parts, such as several .c source files, or libraries, the process is done in two steps. First the individual source .c files are compiled, that is, translated from the C source to modules of executable machine instructions. Then all the modules and libraries needed for the program are linked together, building the executable file.

The difference between static and dynamic linking is just when the linking is done. Conceptually they are the same thing, but static linking (with a static library) is done in advance, forming an executable file that can be run at a later time, and dynamic linking is done immediately before execution.

The type of linking (static or dynamic) doesn't at all affect the compilation step.

During compilation of an individual source file, the compiler needs to generate code for the calls to the library functions. For example, if a library contains a function f that takes a double as argument, and the source file contains the code f(7), the compiler needs to know that there is a function called f, and that it expects a double as argument, so the compiler can generate code that converts the integer 7 to a double, before actually calling the function f.

This is done by putting function declarations in a .h file, which is then included in your .c source file. For example, that declaration might look like this:

void f(double);

This makes the compiler able to generate the correct code, and also to give the correct warnings and error messages if there is something wrong.

The library, on the other hand, contains the compiled function definition, which is the actual code for the function that does something.

Note that the compilation step has very little to do with the library file, and nothing to do with the difference between static or dynamic linking. To be able to #include the .h file, the compiler needs to know where to find the .h file. That may be in a completely different place from the actual library file. The library file doesn't even have to be present on the same computer, or even exist at all. When the #include is performed, the actual functions in the library might not have been written yet.

One source of confusion could be that the gcc command,

gcc -lpthreads main.c -o server -L thread-pool -lthreadpool

looks like it performs both compilation and linking. It does, but that is just for convenience, and behind the scenes it is still done in two separate steps.