Eliminate hardcode_libdir_flag_spec_ld tag variable. (was: [OMPI devel] make check (libtool) failure on Linux/ppc w/ XLC (1.5rc5 and 1.4.3rc1))

2010-10-16 Thread Ralf Wildenhues
[ moving to the libtool-patches list from here:
  http://www.open-mpi.org/community/lists/devel/2010/08/8399.php ]

* Ralf Wildenhues wrote on Thu, Oct 14, 2010 at 08:56:19PM CEST:
 this bug has been addressed in upstream Libtool commit
 v2.2.6-59-gb7dbec6:
 http://git.savannah.gnu.org/cgit/libtool.git/commit/?id=v2.2.6-59-gb7dbec6
 
 It is not wholly fixed yet, but for all cases interesting to OpenMPI.
 (A libtoolized package using only Fortran but no C compiler may still
 have issues.)

Not totally true; since C will be enabled by libtool anyway, we are
fairly safe here (as the test will be run with the C compiler then, and
not rerun with Fortran due to caching).

However, we should fix setting hardcode_libdir_flag_spec for XL Fortran
on GNU/Linux anyway, and for that we need to ensure $wl is unset in the
shared library creation code in ltmain.  The patch below does that and
eliminates the need for hardcode_libdir_flag_spec_ld in the process.
This should also help when hardcoding flags in programs created by this
compiler.

The idea is that, if $archive_cmds contains the string `$LD ' literally,
then we are going to link with ld, and $wl can be nullified.

Warning 1: this also nullifies $wl for all following tag variable
expansions in the ltmain code.  I *think* this is safe, as by this time
all we're going to do is create a shared library; but I'm not 100% sure.
(OTOH, the number of systems where $LD is used for linking is pretty low
in practice by now.)

Warning 2: we might be creating the library with either one of
  archive_cmds
  archive_expsym_cmds
  module_cmds
  module_expsym_cmds

but the code only checks the former, rather the one that really will be
selected later.  Should I fix that, for future-proofness in case we ever
have the case where module creation differs from archive creation in
whether $LD is used directly for linking?  (Sounds fairly remote,
right?)

Tested on GNU/Linux/ppc with the XL compiler suite, as well as on
HP-UX 10.20 (no regressions in the latter).

OK to commit and add Paul to THANKS?

Thanks,
Ralf

Eliminate hardcode_libdir_flag_spec_ld tag variable.

* libltdl/config/ltmain.m4sh (func_mode_link): Set $wl to empty
if $LD is used for creating shared libraries.  Do not use
hardcode_libdir_flag_spec_ld any more.
* libltdl/m4/libtool.m4 (_LT_LINKER_SHLIBS, _LT_LANG_CXX_CONFIG)
(_LT_LANG_F77_CONFIG, _LT_LANG_FC_CONFIG, _LT_SYS_DYNAMIC_LINKER)
hardcode_libdir_flag_spec_ld: Remove all instances of the tag
variable.
(_LT_LINKER_SHLIBS) [linux, xlf] hardcode_libdir_flag_spec:
Set variable, including ${wl}.  Fixes hardcoding in programs
created by XL Fortran on GNU/Linux.
* NEWS, THANKS: Update.
Report by Paul H. Hargrove.

diff --git a/NEWS b/NEWS
index d8d692e..9c12714 100644
--- a/NEWS
+++ b/NEWS
@@ -9,6 +9,15 @@ New in 2.4.2 2010-12-??: git version 2.4.1a, Libtool team:
   - The bug that leaked developer tool paths into the release tarballs
 from ./bootstrap is fixed.
 
+* Important incompatible changes:
+
+  - The undocumented hardcode_libdir_flag_spec_ld tag variable has been
+removed in favor of using hardcode_libdir_flag_spec with $wl set to empty.
+
+* Changes in supported systems or compilers:
+
+  - Fixes for gfortran on Darwin, XL Fortran on GNU/Linux.
+
 New in 2.4 2010-09-22: git version 2.2.11a, Libtool team:
 
 * New features:
diff --git a/libltdl/config/ltmain.m4sh b/libltdl/config/ltmain.m4sh
index af46cb8..aff8a1c 100644
--- a/libltdl/config/ltmain.m4sh
+++ b/libltdl/config/ltmain.m4sh
@@ -7237,6 +7237,11 @@ EOF
 
   # Test again, we may have decided not to build it any more
   if test $build_libtool_libs = yes; then
+   # Remove ${wl} instances when linking with ld.
+   # FIXME: should test the right _cmds variable.
+   case $archive_cmds in
+ *\$LD\ *) wl= ;;
+esac
if test $hardcode_into_libs = yes; then
  # Hardcode the library paths
  hardcode_libdirs=
@@ -7275,11 +7280,7 @@ EOF
  if test -n $hardcode_libdir_separator 
 test -n $hardcode_libdirs; then
libdir=$hardcode_libdirs
-   if test -n $hardcode_libdir_flag_spec_ld; then
- eval dep_rpath=\$hardcode_libdir_flag_spec_ld\
-   else
- eval dep_rpath=\$hardcode_libdir_flag_spec\
-   fi
+   eval dep_rpath=\$hardcode_libdir_flag_spec\
  fi
  if test -n $runpath_var  test -n $perm_rpath; then
# We should set the runpath_var.
diff --git a/libltdl/m4/libtool.m4 b/libltdl/m4/libtool.m4
index d8b3a4d..419ffe1 100644
--- a/libltdl/m4/libtool.m4
+++ b/libltdl/m4/libtool.m4
@@ -4522,7 +4522,6 @@ m4_if([$1], [CXX], [
   _LT_TAGVAR(hardcode_direct, $1)=no
   _LT_TAGVAR(hardcode_direct_absolute, $1)=no
   _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=
-  _LT_TAGVAR(hardcode_libdir_flag_spec_ld, $1)=
   _LT_TAGVAR(hardcode_libdir_separator, $1)=
   _LT_TAGVAR(hardcode_minus_L, $1)=no
   

LD_LIBRARY_PATH_64 on Solaris (was: [OMPI devel] make check (libtool?) failure on Solaris/SPARC (1.5rc5 and 1.4.3rc1))

2010-10-16 Thread Ralf Wildenhues
[ moving from open-mpi-devel to libtool-patches ]

Hello Paul, all,

this took quite a bit longer than I expected, and it also turned out
to be quite a bit longer than I initially expected.  ;-)

 * Paul H. Hargrove wrote on Thu, Aug 26, 2010 at 10:14:22PM CEST:
   I just had a thought on this one:  In my environment on this
  platform I have LD_LIBRARY_PATH_32 and LD_LIBRARY_PATH_64 set.  It
  seems possible to me that this is causing the loader to ignore the
  LD_LIBRARY_PATH setting that libtool's wrapper script sets when
  executing uninstalled programs in the build directory, as during
  make check.
   So, I tried removing these from my environment and editing
  ~/.bashrc not to set them.  The result is a SUCCESSful make check!

Yep.  Quoting ld.so.1(1) from Solaris 10 (Sparc):

 Each environment variable can be specified with a _32 or _64
 suffix.   This  makes  the  environment  variable  specific,
 respectively, to 32-bit or 64-bit processes.  This  environ-
 ment  variable  overrides  any  non-suffixed  version of the
 environment variable that may  be  in  effect.   Environment
 variables  specified without a value, that have a _32 or _64
 suffix, effectively cancel any associated  generic  environ-
 ment variable setting.

Here's what I think are the semantics relevant to Libtool:

- programs executed by libtool might be 32 or 64 bits, so in the most
general case we need the settings from up to two of the three variables
LD_LIBRARY_PATH LD_LIBRARY_PATH_32 LD_LIBRARY_PATH_64, in the following
named L, L32, and L64.

- we cannot assume L, L32, and L64 are set the same at configure time as
they are at, say, runtime of uninstalled executables.

- we cannot blindly append :$L to L32 if L32 is already set, because the
entries from L could actually contain old libraries not to be used (for
all programs not from us, we want to ensure an error is still an error).
Or they could contain unwanted 64bit libraries.  Same of course with 32
and 64 roles swapped.

- we cannot prepend $L32: to L and then unset L32, because those
directories could also contain bogus 64bit libraries then loaded by
64bit helper programs.  Likewise with roles swapped.

- a quick test shows that if you have a directory with 64bit liba.so.1
and one later with 32bit liba.so.1, then if both directories are in one
of the paths, the runtime linker will load the right one and not print
complaints about the wrong one found earlier.  Good.


Taken together, that means it should be possible to implement one of
these alternative strategies for a 32-bit build (analogous for 64bit of
course):

1) if L32 is already set, prepend to L32 in addition to prepending to L.

2) if L32 is already set, prepend to L32 instead of prepending to L.

(1) seems a bit safer for the case that we detect the bitness wrongly,
or the link editor behaves differently than the runtime linker;
(2) increases the environment less.

An actual implementation could thus be a new libtool variable
aux_shlibpath_var; if nonempty, we check whether the variable it names
is set, and if yes, we prepend to that instead of or additionally.


Now, how about other multi-ABI systems?

I checked IRIX, which has very similar runtime linker semantics
regarding the variables LD_LIBRARY64_PATH and LD_LIBRARYN32_PATH.

Hmm, IRIX also has _RLD_ROOT, _RLD64_ROOT and _RLDN32_ROOT, which in
hierarchy sit even before DT_RPATH, so could be (ab)used as alternate
shlibpath_var settings that override the runpath (unlike LD_LIBRARY_PATH
and sisters on this system) ...

HP-UX/hppa64, according to documentation, has in addition to SHLIB_PATH
also LD_LIBRARY_PATH.  The latter takes precedence over the former, but
does not turn the former off.  Of course either are only enabled when +s
has been used for linking (which we don't deal with quite correctly
yet).

OS X has DYLD_FALLBACK_LIBRARY_PATH, but it has lower precedence.

Note that this is not intended for systems which have environment
variables which differ in whether they override DT_RPATH (run path
entries encoded in the executable or library).


So, I've worked on a patch for this, and this is what I've come up with
so far.  I say so far, because the patch could probably do with a few
more testsuite additions and maybe some factoring, but I'm at a stage
where I'd like some preliminary review that what I'm doing is sensible
and will be welcome when finished.  It implements approach (2) above.

The two patches (well, slightly previous versions of them) have been
tested on IRIX, HP-UX/hppa64, Solaris/i386 with both the shlibpath_var
and the aux_shlibpath_var unset (no regression to previous test
results).  They have also been tested with LD_LIBRARY_PATH_32 set on
Solaris/i386, fixing all of several previous test failures.

I would test the final version again before pushing.

I'm a bit worried whether $host_cpu is a good indicator for bitness on
Solaris (it will be wrong if -m64 is put in CFLAGS rather than CC).
Better