smac89 smac89 - 1 year ago 105
C Question

Properly Linking a static library with the C math library

I have a library which uses the log function from math.h. When I compile and package this library, I get no compilation errors, which is normal (I think).

Now when I try to use the library in an application, gcc gives me linker errors:

Compiling mytestlist using "mytestlist.o":
gcc mytestlist.o -I/student/cmpt332/pthreads -I. -std=c99 -Wall -pedantic -L. -L/student/cmpt332/pthreads/lib/linuxx86_64/ -llist -o mytestlist
./liblist.a(list_adders.o): In function `NodeCreate':
list_adders.c:(.text+0x343): undefined reference to `log'
./liblist.a(list_adders.o): In function `ListCreate':
list_adders.c:(.text+0x62f): undefined reference to `log'
./liblist.a(list_adders.o): In function `ListFree':
list_adders.c:(.text+0xdcc): undefined reference to `log'
list_adders.c:(.text+0xe55): undefined reference to `log'
list_adders.c:(.text+0xefb): undefined reference to `log'
./liblist.a(list_adders.o):list_adders.c:(.text+0xf96): more undefined references to `log' follow
collect2: error: ld returned 1 exit status
Makefile:47: recipe for target 'mytestlist' failed
make: *** [mytestlist] Error 1

Why is this happening? The only solution that works is that I have to supply the
option to gcc when I compile the program that uses the library (even though the program itself makes no use of math.h), however I find this cumbersome to do.

I've also tried supplying the
option when compiling the library, but when the application is compiled using the library, I get the same linker errors.

Is there a way to compile the library with math.h without having to supply
to other programs that make use of the library?

In case you're wondering, I compile each object that makes up the library using:

gcc -std=c99 -Wall -pedantic -static -I. -c list_adders.c -o list_something.o -lm

And the library is packaged using:

ar cvfr liblist.a list_something.o ...

Answer Source

In your gcc -c command, the -lm isn't doing anything. It's a linker option, and -c means "don't link".

The proper place to put -lm is in fact after the -llist whenever you use it. That's how static library dependencies are done. Put it in the documentation for liblist.

If you want something fancier, there's pkg-config. With the appropriate configuration files, pkg-config --static --libs liblist will output -llist -lm.

Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download