← Back to team overview

launchpad-users team mailing list archive

Re: library linking error

 

On Tue, Nov 19, 2013 at 8:57 PM, Frank Trampe <frank.trampe@xxxxxxxxx>wrote:

>
>
>
> On Tue, Nov 19, 2013 at 7:31 PM, Andrew Kelley <superjoe30@xxxxxxxxx>wrote:
>
>>
>> On Tue, Nov 19, 2013 at 7:34 PM, Frank Trampe <frank.trampe@xxxxxxxxx>wrote:
>>
>>> As you're running it, gcc is trying to link statically (against
>>> libgroove.a), so the contents of libgroove.so don't mean much. Are you
>>> trying to link dynamically?
>>>
>>
>> Yes I am trying to link dynamically. I'm confused - I thought using -l
>> was dynamic linking and specifying -static and supplying .a files does
>> static linking.
>>
>
> Most gcc installations on Linux try to link dynamically first if the
> shared libraries are available and in the search path (I think) but will
> fall back to static otherwise. Are you sure that the relevant so files are
> in the search paths? Perhaps you could add the path manually via -L or
> LIBRARY_PATH and see if that bypasses the problem.
>

Yes I am sure that the relevant .so files are in the search paths.
libgroove.so should be the only necessary file. Observe:

$ c99 -o test test.c
/tmp/ccdS8adV.o: In function `main':
test.c:(.text+0x41): undefined reference to `groove_init'
test.c:(.text+0x46): undefined reference to `groove_finish'
test.c:(.text+0x55): undefined reference to `groove_set_logging'
test.c:(.text+0x5a): undefined reference to `groove_playlist_create'
test.c:(.text+0x92): undefined reference to `groove_player_create'
test.c:(.text+0xa9): undefined reference to `groove_player_attach'
test.c:(.text+0xd9): undefined reference to `groove_file_open'
(snip)


$ c99 -o test test.c -lgroove
/usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In
function `cleanup_save':
(.text+0x29): undefined reference to `av_free_packet'
/usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In
function `cleanup_save':
(.text+0x39): undefined reference to `avio_closep'
/usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In
function `cleanup_save':
(.text+0x54): undefined reference to `avformat_free_context'
/usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In
function `cleanup_save':
(.text+0xa1): undefined reference to `av_log'
/usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In
function `groove_file_close':
(.text+0xe6): undefined reference to `av_free_packet'
(snip)

 The libav and SDL2 dependencies are internal to libgroove and should be
completely hidden from the end-user of libgroove.


> Either way, you will probably want to adjust the dependencies for the
> package with the static library such that it pulls in the static libraries
> for libsdl and libav at installation.
>

I agree that this is desirable. I searched for how to do this and the
advice that I got was to not do it. Would you be willing to go more into
detail about how to pull in static dependencies so that users who want to
link statically against my library will not have to also link statically
against my dependencies?


>
>
>> Furthermore, when I link the exact same test.c file with the same gcc
>> args against a libgroove installation that was built from source rather
>> than from the PPA, it successfully links and runs. What could explain this
>> behavior?
>>
>>
> Is this on the same machine?
>

Yes. You can try it for yourself if you want:
https://github.com/superjoe30/libgroove/archive/2.0.2.tar.gz


>
>
>>
>>> Running nm -g on your static library shows that it includes undefined
>>> static symbols for the functions that you list. If you link against those
>>> libraries (libav and libsdl) when building test.c, this ought to work.
>>>
>>>
>>>
>>> On Tue, Nov 19, 2013 at 11:21 AM, Andrew Kelley <superjoe30@xxxxxxxxx>wrote:
>>>
>>>> Hello -
>>>>
>>>> I just added a library to my ppa:
>>>> https://launchpad.net/~andrewrk/+archive/libgroove
>>>> so far so good, it installs on my system. But when I compile a program
>>>> against it, I get linker errors - undefined symbols from libraries that my
>>>> library depends on. This does not happen when I manually build from source.
>>>>
>>>> Any suggestions?
>>>>
>>>> Here are some more details.
>>>>
>>>> The problem:
>>>>
>>>> andy@andy-bx:~/tmp$ c99 -o test test.c -lgroove
>>>> /usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In function `cleanup_save':
>>>>
>>>> (.text+0x29): undefined reference to `av_free_packet'
>>>> /usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In function `cleanup_save':
>>>>
>>>> (.text+0x39): undefined reference to `avio_closep'
>>>> /usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In function `cleanup_save':
>>>>
>>>> (.text+0x54): undefined reference to `avformat_free_context'
>>>> /usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In function `cleanup_save':
>>>>
>>>> (.text+0xa1): undefined reference to `av_log'
>>>> /usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In function `groove_file_close':
>>>>
>>>> (.text+0xe6): undefined reference to `av_free_packet'
>>>> /usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In function `groove_file_close':
>>>>
>>>> (.text+0x105): undefined reference to `avcodec_close'
>>>> /usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In function `groove_file_close':
>>>>
>>>> (.text+0x12b): undefined reference to `avformat_close_input'
>>>> /usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In function `groove_file_close':
>>>>
>>>> (.text+0x139): undefined reference to `SDL_DestroyMutex'
>>>> /usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In function `groove_file_open':
>>>>
>>>> (.text+0x16f): undefined reference to `av_mallocz'
>>>> /usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In function `groove_file_open':
>>>>
>>>> (.text+0x18f): undefined reference to `SDL_CreateMutex'
>>>> /usr/lib/gcc/x86_64-linux-gnu/4.8/../../../../lib/libgroove.a(file.c.o): In function `groove_file_open':
>>>>
>>>> (.text+0x1a1): undefined reference to `avformat_alloc_context'
>>>> ...(snip)...
>>>>
>>>>
>>>> libav is a static dependency of libgroove, and SDL2 is a dynamic dependency.
>>>> test.c uses only libgroove, it does not depend on libav or SDL2.
>>>>
>>>>
>>>> andy@andy-bx:~$ ldd /usr/lib/libgroove.so.2.0.2
>>>> 	linux-vdso.so.1 =>  (0x00007fff499c9000)
>>>>
>>>>
>>>>
>>>> 	libbz2.so.1.0 => /lib/x86_64-linux-gnu/libbz2.so.1.0 (0x00007fc04ecde000)
>>>>
>>>> 	libz.so.1 => /lib/x86_64-linux-gnu/libz.so.1 (0x00007fc04eac5000)
>>>> 	libmp3lame.so.0 => /usr/lib/x86_64-linux-gnu/libmp3lame.so.0 (0x00007fc04e837000)
>>>>
>>>> 	libpthread.so.0 => /lib/x86_64-linux-gnu/libpthread.so.0 (0x00007fc04e61a000)
>>>> 	libSDL2-2.0.so.0 => /usr/lib/x86_64-linux-gnu/libSDL2-2.0.so.0 (0x00007fc04e346000)
>>>>
>>>> 	libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007fc04df7d000)
>>>> 	libm.so.6 => /lib/x86_64-linux-gnu/libm.so.6 (0x00007fc04dc79000)
>>>>
>>>>
>>>> 	/lib64/ld-linux-x86-64.so.2 (0x00007fc04ff2a000)
>>>> 	libasound.so.2 => /usr/lib/x86_64-linux-gnu/libasound.so.2 (0x00007fc04d989000)
>>>> 	libdl.so.2 => /lib/x86_64-linux-gnu/libdl.so.2 (0x00007fc04d784000)
>>>>
>>>>
>>>>
>>>>
>>>>
>>>>
>>>> 	libpulse-simple.so.0 => /usr/lib/x86_64-linux-gnu/libpulse-simple.so.0 (0x00007fc04d580000)
>>>> 	libpulse.so.0 => /usr/lib/x86_64-linux-gnu/libpulse.so.0 (0x00007fc04d337000)
>>>>
>>>> 	libX11.so.6 => /usr/lib/x86_64-linux-gnu/libX11.so.6 (0x00007fc04d001000)
>>>> 	libXext.so.6 => /usr/lib/x86_64-linux-gnu/libXext.so.6 (0x00007fc04cdef000)
>>>>
>>>> 	libXcursor.so.1 => /usr/lib/x86_64-linux-gnu/libXcursor.so.1 (0x00007fc04cbe5000)
>>>> 	libXinerama.so.1 => /usr/lib/x86_64-linux-gnu/libXinerama.so.1 (0x00007fc04c9e1000)
>>>>
>>>> 	libXi.so.6 => /usr/lib/x86_64-linux-gnu/libXi.so.6 (0x00007fc04c7d1000)
>>>> 	libXrandr.so.2 => /usr/lib/x86_64-linux-gnu/libXrandr.so.2 (0x00007fc04c5c7000)
>>>>
>>>> 	libXss.so.1 => /usr/lib/x86_64-linux-gnu/libXss.so.1 (0x00007fc04c3c2000)
>>>> 	libXxf86vm.so.1 => /usr/lib/x86_64-linux-gnu/libXxf86vm.so.1 (0x00007fc04c1bc000)
>>>>
>>>> 	librt.so.1 => /lib/x86_64-linux-gnu/librt.so.1 (0x00007fc04bfb4000)
>>>> 	libpulsecommon-4.0.so => /usr/lib/x86_64-linux-gnu/pulseaudio/libpulsecommon-4.0.so (0x00007fc04bd4c000)
>>>>
>>>>
>>>>
>>>>
>>>>
>>>>
>>>> 	libjson-c.so.2 => /lib/x86_64-linux-gnu/libjson-c.so.2 (0x00007fc04bb42000)
>>>> 	libdbus-1.so.3 => /lib/x86_64-linux-gnu/libdbus-1.so.3 (0x00007fc04b8fc000)
>>>>
>>>> 	libxcb.so.1 => /usr/lib/x86_64-linux-gnu/libxcb.so.1 (0x00007fc04b6de000)
>>>> 	libXrender.so.1 => /usr/lib/x86_64-linux-gnu/libXrender.so.1 (0x00007fc04b4d4000)
>>>>
>>>> 	libXfixes.so.3 => /usr/lib/x86_64-linux-gnu/libXfixes.so.3 (0x00007fc04b2cd000)
>>>> 	libwrap.so.0 => /lib/x86_64-linux-gnu/libwrap.so.0 (0x00007fc04b0c3000)
>>>>
>>>> 	libsndfile.so.1 => /usr/lib/x86_64-linux-gnu/libsndfile.so.1 (0x00007fc04ae5a000)
>>>> 	libasyncns.so.0 => /usr/lib/x86_64-linux-gnu/libasyncns.so.0 (0x00007fc04ac54000)
>>>>
>>>> 	libXau.so.6 => /usr/lib/x86_64-linux-gnu/libXau.so.6 (0x00007fc04aa50000)
>>>> 	libXdmcp.so.6 => /usr/lib/x86_64-linux-gnu/libXdmcp.so.6 (0x00007fc04a849000)
>>>>
>>>> 	libnsl.so.1 => /lib/x86_64-linux-gnu/libnsl.so.1 (0x00007fc04a62f000)
>>>> 	libFLAC.so.8 => /usr/lib/x86_64-linux-gnu/libFLAC.so.8 (0x00007fc04a3fe000)
>>>>
>>>> 	libvorbisenc.so.2 => /usr/lib/x86_64-linux-gnu/libvorbisenc.so.2 (0x00007fc049f2e000)
>>>> 	libvorbis.so.0 => /usr/lib/x86_64-linux-gnu/libvorbis.so.0 (0x00007fc049d01000)
>>>>
>>>> 	libogg.so.0 => /usr/lib/x86_64-linux-gnu/libogg.so.0 (0x00007fc049af8000)
>>>> 	libresolv.so.2 => /lib/x86_64-linux-gnu/libresolv.so.2 (0x00007fc0498dd000)
>>>>
>>>>
>>>> # libav is not on this list because libgroove depends statically upon it
>>>>
>>>>
>>>>
>>>> here's the difference in linker steps for libgroove.so between the working manual build and the not-working PPA build:
>>>>
>>>> # ppa link step (broken):
>>>>
>>>> /usr/bin/cc  -fPIC -g -O2 -fstack-protector --param=ssp-buffer-size=4 -Wformat -Werror=format-security -D_FORTIFY_SOURCE=2  -O2 -g -DNDEBUG -Wl,-Bsymbolic  -Wl,-z,relro -shared -Wl,-soname,libgroove.so.2 -o libgroove.so.2.0.2 CMakeFiles/groove.dir/src/queue.c.o CMakeFiles/groove.dir/src/loudness_detector.c.o CMakeFiles/groove.dir/src/buffer.c.o CMakeFiles/groove.dir/src/encoder.c.o CMakeFiles/groove.dir/src/file.c.o CMakeFiles/groove.dir/src/playlist.c.o CMakeFiles/groove.dir/src/global.c.o CMakeFiles/groove.dir/src/player.c.o deps/libav/install/lib/libavfilter.a deps/libav/install/lib/libavformat.a deps/libav/install/lib/libavcodec.a deps/libav/install/lib/libavresample.a deps/libav/install/lib/libswscale.a deps/libav/install/lib/libavutil.a -lbz2 -lz -lmp3lame -lpthread -Wl,-Bstatic -lSDL2main -Wl,-Bdynamic -lSDL2 -lpthread -Wl,-Bstatic -lebur128 -lSDL2main -Wl,-Bdynamic -lSDL2 -Wl,-Bstatic -lebur128 -Wl,-Bdynamic
>>>>
>>>>
>>>>
>>>>
>>>>
>>>>
>>>>
>>>> # see full build log: https://launchpadlibrarian.net/156927161/buildlog_ubuntu-saucy-amd64.libgroove_2.0.2-2_UPLOADING.txt.gz
>>>>
>>>>
>>>>
>>>>
>>>>
>>>>
>>>>
>>>>
>>>> # build manually from source link step (works):
>>>>
>>>>
>>>> /usr/bin/cc  -fPIC  -Wl,-Bsymbolic   -shared -Wl,-soname,libgroove.so.2 -o libgroove.so.2.0.0 CMakeFiles/groove.dir/src/global.c.o CMakeFiles/groove.dir/src/loudness_detector.c.o CMakeFiles/groove.dir/src/playlist.c.o CMakeFiles/groove.dir/src/buffer.c.o CMakeFiles/groove.dir/src/encoder.c.o CMakeFiles/groove.dir/src/queue.c.o CMakeFiles/groove.dir/src/file.c.o CMakeFiles/groove.dir/src/player.c.o deps/libav/install/lib/libavfilter.a deps/libav/install/lib/libavformat.a deps/libav/install/lib/libavcodec.a deps/libav/install/lib/libavresample.a deps/libav/install/lib/libswscale.a deps/libav/install/lib/libavutil.a -lbz2 -lz -lmp3lame -lpthread -Wl,-Bstatic -lSDL2main -Wl,-Bdynamic -lSDL2 -lpthread deps/ebur128/libebur128.a -Wl,-Bstatic -lSDL2main -Wl,-Bdynamic -lSDL2
>>>>
>>>>
>>>>
>>>>
>>>>
>>>>
>>>>
>>>> _______________________________________________
>>>> Mailing list: https://launchpad.net/~launchpad-users
>>>> Post to     : launchpad-users@xxxxxxxxxxxxxxxxxxx
>>>> Unsubscribe : https://launchpad.net/~launchpad-users
>>>> More help   : https://help.launchpad.net/ListHelp
>>>>
>>>>
>>>
>>
>

Follow ups

References