Update of /cvsroot/fink/experimental/dmacks/finkinfo
In directory sc8-pr-cvs5.sourceforge.net:/tmp/cvs-serv5709
Added Files:
fink-dyld-link-test.info fink-dyld-link-test.patch
Log Message:
May as well roll this into a package.
--- NEW FILE: fink-dyld-link-test.info ---
Package: fink-dyld-link-test
Version: 1
Revision: 1
Maintainer: Daniel Macks <[EMAIL PROTECTED]>
License: GPL
Description: Script to verify dynamic symbol resolution
DescDetail: <<
This script takes the name of one or more installed packages and
checks that all undefined symbols in the .dylib are defined in other
.dylib files to which it is dynamically linked. Only .dylib that have
an accompanying .a (completely parallel name) can be tested at this
time. Files that report missing symbols are likely to give symbol
resolution errors when they are loaded at runtime by other binaries
that link against them. The usual solution is to add -l flags for the
libraries that supply the missing symbols.
<<
Source: none
Depends: dpkg, dev-tools
PatchScript: <<
cp %a/%n.patch %n
cp %p/share/doc/fink/COPYING .
<<
CompileScript: echo "Nothing to compile"
InstallScript: <<
install -m755 -p -d %i/bin
install -m755 %n %i/bin
<<
DocFiles: COPYING
--- NEW FILE: fink-dyld-link-test.patch ---
#!/usr/bin/perl -w
# Find shared libraries that were probably compiled with some missing
# -l flag(s).
# Copyright 2006 Daniel Macks <[EMAIL PROTECTED]>
# Released under the GNU Public License
use strict;
use File::Temp qw/ tempfile /;
use Data::Dumper;
use constant {
SEP_MAJOR => ('=' x72 . "\n"),
SEP_MINOR => ('-' x72 . "\n"),
};
unless (@ARGV) {
die "Usage: $0 [list of installed packages]\n";
}
print "Preparing...\n";
# make a dummy source file for test compiles
my($src_fh, $src) = tempfile( SUFFIX => '.c', UNLINK => 1);
print $src_fh "int main() { return(0); }\n";
close $src_fh;
my($obj_fh, $obj) = tempfile( SUFFIX => '.o', UNLINK => 1);
close $obj_fh;
unless (&compile_okay(source=>$src, object=>$obj)) {
die "Could not even compile test source without any libs!\n";
}
# store parallel arrays to @ARGV package names so we can keep
# altering the last element during each pass and then dump the
# output in the same order as the given package list
my(@results, @summary);
foreach my $pkg (@ARGV) {
push @results, {}; # hash of results for each library
push @summary, 'Passed'; # one-line summary for each package (worst result)
print SEP_MAJOR;
print "Testing package $pkg...\n";
# find all files in package
my %files = map { chomp; $_ => 1 } (`dpkg -L $pkg`);
if ($?) {
print $results[-1] = 'Could not read file list', "\n";
$summary[-1] = 'Package not tested';
next;
}
foreach my $file (keys %files) {
# find corresponding static/dynamic lib pairs
if ($file =~ s/\.a$//) {
my $dylib;
if (exists $files{"$file.dylib"}) {
$dylib = "$file.dylib"; # normal shared library for linker
# } elsif (exists $files{"$file.so"}) {
# $dylib = "$file.so"; # probably bundle for dlopen() (skip)
} else {
next; # no shared lib for this static one
}
print SEP_MINOR,"Examining $dylib...\n";
# get list of all dynamic libs the dynamic lib links against
my @dyld = `otool -L "$dylib"`;
if ($?) {
print $results[-1]->{$dylib} = 'Could not read dyld links',
"\n";
$summary[-1] = 'Some libs not tested';
next;
}
chomp @dyld;
shift @dyld; # remove otool header
map { s/^\s+(.*?)\s+\(compatibility.*/$1/ } @dyld;
my $okay = &compile_okay(source=>$src, object=>$obj,
static=>["$file.a"], dynamic=>[EMAIL PROTECTED]);
$results[-1]->{$dylib} = $okay
? 'Okay'
: 'Deficient';
$summary[-1] = 'Failed' unless $okay;
}
}
}
# lib-by-lib results
print SEP_MAJOR, "Results:\n", Data::Dumper->Dump([EMAIL PROTECTED], [EMAIL
PROTECTED]);
# package-by-package summary
my $w = 0;
map { $w = length $_ if length $_ > $w } @ARGV; # widest value
print SEP_MAJOR, "Summary:\n";
for (0..$#ARGV) {
printf " %-${w}s %s\n", $ARGV[$_], $summary[$_];
}
sub compile_okay {
my %opts = ( static=>[], dynamic=>[], @_);
die "source undefined!\n" unless defined $opts{source};
die "object undefined!\n" unless defined $opts{object};
my @cmd = (
# assume C++ so we don't have to guess about mangling
# TODO: match to ABI of pkg
'g++',
# here's the magic: fail if any static lib symbol isn't
# defined in the dyld-linked libs, meaning the dynamic lib
# corresponding to the static one is probably missing dyld
# links to the libs that resolve these symbols
'-all_load',
# hide some common noise and test residue
'-multiply_defined', 'suppress',
'-bind_at_load',
# for kicks
#'-Wall',
# source and destination
$opts{source}, '-o', $opts{object},
# the passed libraries
@{$opts{static}}, @{$opts{dynamic}},
);
print "@cmd\n";
return !system(@cmd);
}
-------------------------------------------------------------------------
Take Surveys. Earn Cash. Influence the Future of IT
Join SourceForge.net's Techsay panel and you'll get the chance to share your
opinions on IT & business topics through brief surveys -- and earn cash
http://www.techsay.com/default.php?page=join.php&p=sourceforge&CID=DEVDEV
_______________________________________________
Fink-commits mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/fink-commits