Gentoo Websites Logo
Go to: Gentoo Home Documentation Forums Lists Bugs Planet Store Wiki Get Gentoo!
Bug 430722 - dev-util/pkgconfig: (prefix) libtool uses wrong libglib-2.0.so
Summary: dev-util/pkgconfig: (prefix) libtool uses wrong libglib-2.0.so
Status: RESOLVED OBSOLETE
Alias: None
Product: Gentoo/Alt
Classification: Unclassified
Component: Prefix Support (show other bugs)
Hardware: All Linux
: Normal normal (vote)
Assignee: Gentoo Prefix
URL:
Whiteboard:
Keywords:
Depends on:
Blocks:
 
Reported: 2012-08-10 07:58 UTC by Greg Turner
Modified: 2013-09-23 06:07 UTC (History)
0 users

See Also:
Package list:
Runtime testing required: ---


Attachments
Always eautoreconf pkgconfig (pkgconfig-0.27-eautoreconf-always.patch,1.11 KB, patch)
2012-08-10 08:02 UTC, Greg Turner
Details | Diff

Note You need to log in before you can comment on or make changes to this bug.
Description Greg Turner 2012-08-10 07:58:53 UTC
I discovered this on my (nascent) amd64->i686 cross-prefix.

This is due to the pkgconfig's OOTB libtool m4 gobbldeygook in aclocal.m4 which generates config.lt like so (/goodz/vboxen/i686pfx is my EPREFIX)

sys_lib_search_path_spec='/goodz/vboxen/i686pfx/usr/lib/gcc/i686-pc-linux-gnu/4.6.3 /lib32 /usr/lib32 /goodz/vboxen/i686pfx/usr/i686-pc-linux-gnu/lib /goodz/vboxen/i686pfx/usr/lib'

(trust me, you don't even /want/ to know what it came up with for sys_lib_dlsearch_path_spec!!)

Anyhow, libtool is gonna search those in order for libglib-2.0.{la,so,a} or something like that, and the first one it finds is /usr/lib32/libglib-2.0.la, which, god help us, contains:

  libdir='/usr/lib'

and so the end result is that libtool is going to put /usr/lib/libglib-2.0.so or some equivalent onto the gcc command-line.

Obviously the libdir in that file is a bug, and most likely, that bug is the one that caused my emerge to fail and got me looking into this in the first place.  Be that as it may, that's not the bug I'm reporting here.

If we eautoreconf pkgconfig instead of elibtoolize, the upgraded libtool.m4(?) gobbledeygook now generates: 

sys_lib_search_path_spec='/goodz/vboxen/i686pfx/lib /goodz/vboxen/i686pfx/usr/lib /goodz/vboxen/i686pfx/usr/lib/gcc/i686-pc-linux-gnu/4.6.3 /lib32 /usr/lib32 /goodz/vboxen/i686pfx/usr/i686-pc-linux-gnu/lib /goodz/vboxen/i686pfx/usr/lib '

which is clearly much more reasonable.

I'd presume/guess that /everybody's/ prefix pkgconfig is being linked against the non-prefix glib2, (when that is present, aka pretty much always), regardless of whether there is one to be found in ${EPREFIX}/usr/lib or not.

If I'm right (and I am, at least for multilib amd64 -> x86 cross-prefixes, but presumably many more) that's a prefix bug.

Reproducible: Always
Comment 1 Greg Turner 2012-08-10 08:02:34 UTC
Created attachment 320844 [details, diff]
Always eautoreconf pkgconfig

one way to fix this... surely there are many more.
Comment 2 Fabian Groffen gentoo-dev 2012-08-10 08:05:07 UTC
not everyone, it seems

ppc-macos:
% otool -L $EPREFIX/usr/bin/pkg-config 
/Volumes/Scratch/gentoo/usr/bin/pkg-config:
        /Volumes/Scratch/gentoo/usr/lib/libglib-2.0.0.dylib (compatibility version 3201.0.0, current version 3201.3.0)
        /usr/lib/libSystem.B.dylib (compatibility version 1.0.0, current version 111.1.7)

x86-solaris:
% ldd  $EPREFIX/usr/bin/pkg-config
        libglib-2.0.so.0 =>      /Library/Gentoo/usr/lib/libglib-2.0.so.0
...

amd64-linux:
% ldd $EPREFIX/usr/bin/pkg-config 
        linux-vdso.so.1 =>  (0x00007fff7a9ff000)
        libglib-2.0.so.0 => /net/sofia.ins.cwi.nl/export/scratch2/fabian/prefix64/usr/lib/libglib-2.0.so.0 (0x00007fb871273000)
Comment 3 Greg Turner 2012-08-10 08:22:35 UTC
(In reply to comment #2)
> not everyone, it seems
> 
> ppc-macos:
> % otool -L $EPREFIX/usr/bin/pkg-config 
> /Volumes/Scratch/gentoo/usr/bin/pkg-config:
>         /Volumes/Scratch/gentoo/usr/lib/libglib-2.0.0.dylib (compatibility
> version 3201.0.0, current version 3201.3.0)
>         /usr/lib/libSystem.B.dylib (compatibility version 1.0.0, current
> version 111.1.7)
> 
> x86-solaris:
> % ldd  $EPREFIX/usr/bin/pkg-config
>         libglib-2.0.so.0 =>      /Library/Gentoo/usr/lib/libglib-2.0.so.0
> ...
> 
> amd64-linux:
> % ldd $EPREFIX/usr/bin/pkg-config 
>         linux-vdso.so.1 =>  (0x00007fff7a9ff000)
>         libglib-2.0.so.0 =>
> /net/sofia.ins.cwi.nl/export/scratch2/fabian/prefix64/usr/lib/libglib-2.0.so.
> 0 (0x00007fb871273000)

Well that's reassuring.

I'm not sure exactly what criteria libtool uses to decide to transform -lfoo into /absolute/path/libfoo.so, but perhaps on systems without the additional multilib libglib .la-file problem, the -lglib-2.0 is left as-is and then the gcc built-in search path does the right thing.

Whether or not that makes this a non-bug I don't know... :)
Comment 4 Greg Turner 2012-08-14 12:04:23 UTC
Maybe I shouldn't have filed this bug, since it's an obscure problem in an off-the-beaten-path prefix scenario and I don't know exactly who the culprit is, much less how best to fix it.

On the other hand, I'm pretty sure this is an instance of a class of bugs that crops up rather frequently in cross-development on multilib host systems, and should be given some more thought before I just say "screw it" and close the bug.

I'd be surprised if the same issue didn't apply to the various cross-emerge wrapper scripts, which means people not trying to break their systems might actually be affected by this :)

Here's some experiments I've tried in order to start narrowing down the etiological landscape:

/usr/lib32/libglib-2.0.la
=========================

  o fixing the broken libdir in this file by hand allows my build to succeed

  o on my system I see only four similar problems:

    $ grep -e "^libdir.*lib\(64\|'\| \)" /usr/lib32/*.la
    /usr/lib32/libgio-2.0.la:libdir='/usr/lib'
    /usr/lib32/libglib-2.0.la:libdir='/usr/lib'
    /usr/lib32/libgthread-2.0.la:libdir='/usr/lib'
    /usr/lib32/libxslt.la:libdir='/usr/lib'

    which suggests that simply fixing the ebuilds generating these .la
    files is a possibility

    however, I see only five .la files in /usr/lib32/ on my box, so
    the problem is effectively ubiquitous, as as of now, insofar as
    these multilib .la files are being deployed at all by portage.

  o it'd be semi-easy to write a QA script checking for this type of problem.
    it'd be harder, but probably feasible, to automatically fix the .la files
    in portage.util.lafilefixer

libtool.lt
==========

 o sys_lib_search_path_spec is, I think, the other culprit here.

 o The code in libtool.m4 shipped with pkgconfig seems to generate this
   by calling

     gcc -print-search-dirs,

   scooping up the libraries this generates, and then calling
 
     gcc -print-multi-os-directory,

   and tacking that on to the end of each of the -print-search-dirs paths
   if it exists (it does all this to $lt_search_path_spec and then
   dumps that into sys_lib_search_path_spec if I understand what I'm seeing).

 o The libtool.m4 created by eautoreconf does exactly the same, but it has
   $EPRFIX/lib $EPREFIX/usr/lib hard-coded and tacked on to the beginning
   of the output sys_lib_search_path_spec.

   At compile time, this saves us because the prefix's .la file is found
   before the broken one in /usr/lib32.

   Normally, none of this would matter because whether libtool finds
   ${EPREFIX}/$(libdir)/libfoo.la or /usr/$(libdir)/libfoo.la, libtool ends up
   emitting -lfoo; but -- I think -- when libtool decides it's supposed to
   link in /usr/lib/libfoo.so and that this is not on the built-in library
   search path, it emits the full library pathname instead of -lfoo.  gcc then
   picks up libfoo.so from the prefix.  This explains Fabian's result above.

 o We could fix this by implementing an elt_patch that kicks in when building
   with an EPREFIX and patches configure to include the hard-coded
   ${EPREFIX}/lib and ${EPREFIX}/usr/lib paths into sys_lib_search_path_spec 

Thoughts?
Comment 5 Greg Turner 2012-08-14 12:10:52 UTC
(In reply to comment #4)
>    Normally, none of this would matter because whether libtool finds
>    ${EPREFIX}/$(libdir)/libfoo.la or /usr/$(libdir)/libfoo.la, libtool ends
> up
>    emitting -lfoo; but -- I think -- when libtool decides it's supposed to
>    link in /usr/lib/libfoo.so and that this is not on the built-in library
>    search path, it emits the full library pathname instead of -lfoo.  gcc
> then
>    picks up libfoo.so from the prefix.  This explains Fabian's result above.

A bit of a thinko above -- this should read:

Normally, none of this would matter because whether libtool finds
${EPREFIX}/$(libdir)/libfoo.la or /usr/$(libdir)/libfoo.la, libtool ends
up emitting -lfoo; gcc then picks up libfoo.so from the prefix, in spite
of libtool's intentions.  This explains Fabian's result above.

But -- I think -- when libtool decides it's supposed to link in
/usr/lib/libfoo.so and determines that this is not on the built-in library
search path, it emits the full library pathname instead of -lfoo, leading
to link failure.
Comment 6 Luca Barbato gentoo-dev 2012-08-14 16:23:26 UTC
remove the .la does that fix your problem?
Comment 7 Greg Turner 2012-08-14 16:51:03 UTC
(In reply to comment #6)
> remove the .la does that fix your problem?

Good question.  It does, which makes sense, because without the .la to tell libtool that the library is in "/usr/lib", the behavior becomes just like the examples Fabian gave -- libtool finds /usr/lib32/libglib-2.0.so, which is on the gcc built-in search path, and therefore libtool emits -lglib-2.0.

However, if the .la happened to contain essential information about library dependencies or linker flags, then of course this "solution" wouldn't work.

It's worth noting, perhaps, that all the other broken /usr/lib32/*.la files contain considerably more information than libglib-2.0.la, which really just has:

  dependency_libs='-lrt'

So in this instance, it's an OK solution so long as everything consuming libglib-2.0 will also get the librt dependency met via some means or another, but I'm not sure how wise a policy of, say, "don't install .la files into multilib dirs other than the ones pointed to by ${EPREFIX}/*/$(libdir)" would be in practice.  In general, I'm aware that .la files tend to be on the superfluous side, but it still seems kinda sloppy.

In fact, I wonder if the fact that portage puts so few .la files into /usr/lib32 isn't itself a bug.  Presumably, every multilib package putting .la files into /usr/lib64 ought to be putting one into /usr/lib32 as well but clearly that isn't the case.

I'm guessing that's because there's a lot of multilib-unaware Makefile code like:

install: $(binaries)
        ...
        $(INSTALL) foo.la $(DESTDIR)$(LIBDIR)foo.la
        ...
Comment 8 Greg Turner 2013-09-23 06:07:20 UTC
closing due to oldness, and being a stupid gigo bug anyhow.