opcodes: Fix RPATH not being set for dynamic libbfd dependency
authorMaciej W. Rozycki <macro@embecosm.com>
Wed, 27 Oct 2021 11:21:14 +0000 (12:21 +0100)
committerMaciej W. Rozycki <macro@embecosm.com>
Wed, 27 Oct 2021 11:21:14 +0000 (12:21 +0100)
If built as a shared library, libopcodes has a load-time dependency on
libbfd, which is recorded in the dynamic section, however without a
corresponding RPATH entry for the directory to find libbfd in.  This
causes loading to fail whenever libbfd is only pulled by libopcodes
indirectly and libbfd has been installed in a directory that is not in
the dynamic loader's search path.

It does not happen with the programs included with binutils or GDB,
because they all also pull libbfd when using libopcodes, but it can
happen with external software, e.g.:

$ gdbserver --help
gdbserver: error while loading shared libraries: libbfd-[...].so: cannot open shared object file: No such file or directory
$

(not our `gdbserver').

Indirect dynamic dependencies are handled by libtool automatically by
adding RPATH entries as required, however our setup for libopcodes
prevents this from happening by linking in libbfd with an explicit file
reference sneaked through to the linker directly behind libtool's back
via the `-Wl' linker command-line option rather than via `-l' combined
with a suitable library search path specified via `-L', as it would be
usually the case, or just referring to the relevant .la file in a fully
libtool-enabled configuration such as ours.

According to an observation in the discussion back in 2007[1][2][3] that
has led to the current arrangement it is to prevent libtool from picking
up the wrong version of libbfd.  It does not appear to be needed though,
not at least with our current libtool incarnation, as directly referring
`libbfd.la' does exactly what it should, as previously suggested[4], and
with no link-time reference to the installation directory other than to
set RPATH.  Uninstalled version of libopcodes has libbfd's build-time
location prepended to RPATH too, as also expected.

Use a direct reference to `libbfd.la' then, making the load error quoted
above go away.  Alternatively `-L' and `-l' could be used to the same
effect, but it seems an unnecessary complication and just another way to
circumvent rather than making use of libtool.

References:

[1] "compile failure due to undefined symbol",
    <https://sourceware.org/ml/binutils/2007-08/msg00476.html>

[2] same, <https://sourceware.org/ml/binutils/2007-09/msg00000.html>

[3] same, <https://sourceware.org/ml/binutils/2007-10/msg00019.html>

[4] same, <https://sourceware.org/ml/binutils/2007-10/msg00034.html>

opcodes/
* Makefile.am: Remove obsolete comment.
* configure.ac: Refer `libbfd.la' to link shared BFD library
except for Cygwin.
* Makefile.in: Regenerate.
* configure: Regenerate.

opcodes/ChangeLog
opcodes/Makefile.am
opcodes/Makefile.in
opcodes/configure
opcodes/configure.ac

index 531e6cb5021256dc6bce24743937d1b557688e16..f0e4b72c353c20d35f12e454766874022535e3ba 100644 (file)
@@ -1,3 +1,11 @@
+2021-10-27  Maciej W. Rozycki  <macro@embecosm.com>
+
+       * Makefile.am: Remove obsolete comment.
+       * configure.ac: Refer `libbfd.la' to link shared BFD library
+       except for Cygwin.
+       * Makefile.in: Regenerate.
+       * configure: Regenerate.
+
 2021-09-27  Nick Alcock  <nick.alcock@oracle.com>
 
        * configure: Regenerate.
index c45fc2956656e9fd1aeaebd3586e0b541b93a9bb..e07e360d842790a075a50aaa895ec045abf90772 100644 (file)
@@ -321,12 +321,6 @@ endif
 endif
 
 libopcodes_la_SOURCES =  dis-buf.c disassemble.c dis-init.c
-# It's desirable to list ../bfd/libbfd.la in DEPENDENCIES and LIBADD.
-# Unfortunately this causes libtool to add -L$(libdir), referring to the
-# planned install directory of libbfd.  This can cause us to pick up an
-# old version of libbfd, or to pick up libbfd for the wrong architecture
-# if host != build. So for building with shared libraries we use a
-# hardcoded path to libbfd.so instead of relying on the entries in libbfd.la.
 libopcodes_la_DEPENDENCIES = $(OFILES) @SHARED_DEPENDENCIES@
 libopcodes_la_LIBADD = $(OFILES) @SHARED_LIBADD@
 libopcodes_la_LDFLAGS += -release `cat ../bfd/libtool-soversion` @SHARED_LDFLAGS@
index 8ba01c9f8f9d024ef6b8f0f67d65d2fc883c09c4..942737106abf96814bd2f0cb9d013dcec57d05cf 100644 (file)
@@ -699,12 +699,6 @@ OFILES = @BFD_MACHINES@
 CONFIG_STATUS_DEPENDENCIES = $(BFDDIR)/development.sh
 AM_CPPFLAGS = -I. -I$(srcdir) -I../bfd -I$(INCDIR) -I$(BFDDIR) @HDEFINES@ @INCINTL@
 libopcodes_la_SOURCES = dis-buf.c disassemble.c dis-init.c
-# It's desirable to list ../bfd/libbfd.la in DEPENDENCIES and LIBADD.
-# Unfortunately this causes libtool to add -L$(libdir), referring to the
-# planned install directory of libbfd.  This can cause us to pick up an
-# old version of libbfd, or to pick up libbfd for the wrong architecture
-# if host != build. So for building with shared libraries we use a
-# hardcoded path to libbfd.so instead of relying on the entries in libbfd.la.
 libopcodes_la_DEPENDENCIES = $(OFILES) @SHARED_DEPENDENCIES@
 libopcodes_la_LIBADD = $(OFILES) @SHARED_LIBADD@
 # Allow dependency tracking to work on all the source files.
index 22a9cf926ca92206c3734a2d2e00d93295f30826..acfbdd6ec6fd79441f2994061be2e05080015779 100755 (executable)
@@ -12133,19 +12133,8 @@ if test "$enable_shared" = "yes"; then
       SHARED_LDFLAGS="-no-undefined"
       SHARED_LIBADD="-L`pwd`/../bfd -lbfd -L`pwd`/../libiberty -liberty $SHARED_LIBADD"
       ;;
-   *-*-darwin*)
-     SHARED_LIBADD="-Wl,`pwd`/../bfd/.libs/libbfd.dylib ${SHARED_LIBADD}"
-     SHARED_DEPENDENCIES="../bfd/libbfd.la"
-     ;;
     *)
-      case "$host_vendor" in
-        hp)
-          SHARED_LIBADD="-Wl,`pwd`/../bfd/.libs/libbfd.sl ${SHARED_LIBADD}"
-         ;;
-       *)
-          SHARED_LIBADD="-Wl,`pwd`/../bfd/.libs/libbfd.so ${SHARED_LIBADD}"
-         ;;
-      esac
+      SHARED_LIBADD="../bfd/libbfd.la ${SHARED_LIBADD}"
       SHARED_DEPENDENCIES="../bfd/libbfd.la"
       ;;
   esac
index 4853b9e32d709df97e8fb90792dcb46743872255..757ce10fbe24c63bcfa87a33a813910e3439f3e5 100644 (file)
@@ -193,19 +193,8 @@ if test "$enable_shared" = "yes"; then
       SHARED_LDFLAGS="-no-undefined"
       SHARED_LIBADD="-L`pwd`/../bfd -lbfd -L`pwd`/../libiberty -liberty $SHARED_LIBADD"
       ;;
-   *-*-darwin*)
-     SHARED_LIBADD="-Wl,`pwd`/../bfd/.libs/libbfd.dylib ${SHARED_LIBADD}"
-     SHARED_DEPENDENCIES="../bfd/libbfd.la"
-     ;;
     *)
-      case "$host_vendor" in
-        hp)
-          SHARED_LIBADD="-Wl,`pwd`/../bfd/.libs/libbfd.sl ${SHARED_LIBADD}"
-         ;;
-       *)
-          SHARED_LIBADD="-Wl,`pwd`/../bfd/.libs/libbfd.so ${SHARED_LIBADD}"
-         ;;
-      esac
+      SHARED_LIBADD="../bfd/libbfd.la ${SHARED_LIBADD}"
       SHARED_DEPENDENCIES="../bfd/libbfd.la"
       ;;
   esac