Subject: bug#9941: Handle truncated member names in LIBADD archive libraries

From: "Daniel Richard G." <[email-masked]>
Date: Wed, 02 Nov 2011 16:56:35 -0400

Hello list,

Lately, I've been playing around with an old system (NeXTSTEP 3.3) whose
ar(1) implementation truncates member names to 15 characters. Generally
this hasn't posed a problem, but in building the iODBC libraries with
Libtool 2.4.2, I encountered linking issues traceable to this.

iODBC builds a large library from a couple of smaller libraries using
the Automake _LIBADD directive. I was doing a static build, so ar(1) is
involved. I noticed that after Libtool unpacked the component libraries,
certain members did not appear in the ar(1) invocation to create the
new, combined library.

As it happens, the missing members were those whose filenames were
truncated. When Libtool links the new library, it ignores any file that
does not match *.$objext; the all-important ".o" part was missing from
these members.

Attached is a proposed, first-cut patch against libtool-2.4.2 that
renames truncated members in extracted-library directories, such that no
further special handling is needed. This addresses 15- and 16-character
truncations (per the GNU ar(1) man page, the limitation is usually one
of these two), and explicitly skips a spurious file
"__.SYMDEF SORTED????" that is created when unpacking archive
libraries on this platform. (There may be other examples of the
latter, of course.)

iODBC still doesn't build for me, but at least now it's for reasons
other than a craptastic ar(1) utility.

--Daniel

-- 
Daniel Richard G. || [email-masked]
My ASCII-art .sig got a bad case of Times New Roman.
diff -rbu libtool-2.4.2-orig/libltdl/config/ltmain.m4sh libtool-2.4.2/libltdl/config/ltmain.m4sh
--- libtool-2.4.2-orig/libltdl/config/ltmain.m4sh	2011-10-17 06:17:05.000000000 -0400
+++ libtool-2.4.2/libltdl/config/ltmain.m4sh	2011-11-02 15:04:22.000000000 -0400
@@ -2937,6 +2937,21 @@
     fi
     func_show_eval "(cd \$f_ex_an_ar_dir && $AR x \"\$f_ex_an_ar_oldlib\")" \
 		   'stat=$?; rm -f "$lockfile"; exit $stat'
+    $AR t "$f_ex_an_ar_oldlib" | while read member; do
+      case "$member" in
+      *.$objext|__.SYMDEF*)
+	;;
+      #23456789012345 1234567890123456
+      ??????????????.|???????????????.)
+	func_verbose "fixing truncated member name $member($objext)"
+	(cd $f_ex_an_ar_dir && mv -f $member $member$objext)
+	;;
+      ???????????????|????????????????)
+	func_verbose "fixing truncated member name $member(.$objext)"
+	(cd $f_ex_an_ar_dir && mv -f $member $member.$objext)
+	;;
+      esac
+    done
     if test "$lock_old_archive_extraction" = yes; then
       $opt_dry_run || rm -f "$lockfile"
     fi