10 my @ignore = qw(vserver-packages python-devel-src);
11 my @poldek = (qw(sudo poldek -n th-x86_64-ready), "--cachedir=$pwd/poldekcache",
12 "--skip-installed", "--conf=$pwd/poldekconf/poldek.conf",
13 "-O", "ignore=" . (join " ", @ignore)
16 # if multiple packages provide some funcionality those will be selected:
23 "python-modules" => +1,
24 "python-setuptools" => +1,
30 "libstdc++-devel" => +1,
31 "libusb-compat-devel" => +1,
32 "libjpeg-devel" => +1,
34 "libsamplerate-devel" => +1,
35 "pulseaudio-devel" => +1,
36 "xorg-lib-libXrandr-devel" => +1,
42 # translate package name to provides name
44 "gcc-c++" => "libstdc++-devel",
45 "rarian-compat" => "scrollkeeper",
46 "Mesa-libGL" => "OpenGL",
47 "Mesa-libGL-devel" => "OpenGL-devel",
48 "Mesa-libGLU-devel" => "OpenGL-GLU-devel",
51 my @skip = qw(hostname git svn svnversion mt gawk);
53 @skip{ @skip } = (1) x scalar @skip;
55 # for m4 in *.m4; do R=$(rpm -qf $m4); R=${R%-*-*}; \
56 # awk -vr=$R '/^\s*(AC_DEFUN|AU_ALIAS)/ { gsub(/\].*/,""); gsub(/.*\[/,""); print r " " $0}' $m4; \
57 # done | sort | awk '{print "\t\"" $2 "\" => \"" $1 "\","}'
58 my %ac2br = do "findbr-ac2br";
61 "findkde4:44" => "kde4-kdelibs",
62 "findmsgfmt" => "gettext-devel",
63 "findpythoninterp" => "python",
71 print STDERR "\033[31;1m" . $_ . "\033[0m\n"
75 my $builddir = shift @ARGV;
84 my $msg = shift || $reason;
86 foreach my $p ( @$pkg ) {
94 $pkg = $translate{ $pkg } || $pkg;
96 return if exists $out{ $pkg };
98 print STDERR "\033[33;1madding: $pkg => $msg\033[0m\n";
104 warn "Poldek: $cmd\n";
105 my $pid = open( READ, "-|", @poldek, "--shcmd=".$cmd );
110 return @read if wantarray;
115 my $check_config_log = undef;
122 next if $checked_files{ $_ };
123 $checked_files{ $_ } = 1;
126 return unless @files;
128 my $search = join "; ", map "search -f $_", @files;
129 warn "Reason: $reason\n";
130 my @read = poldek_cmd( $search );
134 while ( $_ = shift @read ) {
135 if ( /(\d+) package\(s\) found:$/ ) {
136 foreach my $i ( 1..$1 ) {
139 $_ =~ /^(.*)-.*?-.*?$/;
145 return unless @found;
147 my $found = $found[0];
150 my %pts = map { ( $_ => ( ($i += 0.001) + ( $preferred{ $_ } || 0 ) ) ) }
152 my @pref = sort { $pts{$b} <=> $pts{$a} } @found;
153 my $pref = join ", ", map "$_ => $pts{$_}", @pref;
154 warn "Multiple found: $pref\n";
158 $found = $translate{ $found } if $translate{ $found };
167 my $read = poldek_cmd( "ls" );
170 next unless /(\S+)-.*?-.*?\.[a-z0-9_]+$/;
172 $pkglist{ lc $pkg } = $pkg;
174 $pkglist = \%pkglist;
179 my $origname = shift;
180 get_pkglist() unless $pkglist;
181 return unless defined $origname;
182 my $name = lc $origname;
191 ".*-lib$name-.*-devel",
195 for my $k ( keys %$pkglist ) {
196 if ( $k =~ /$name/ ) {
200 @select = sort @select;
202 foreach my $try ( @try ) {
203 foreach my $pkg ( @select ) {
204 if ( $pkg =~ /^$try$/ ) {
205 warn "guessed: $origname => $pkglist->{ $pkg }\n";
206 return $pkglist->{ $pkg };
210 warn "$origname not guessed\n";
217 my $cmake_get_call = 0;
218 my $cmake_pkg_list = 0;
219 while ( $_ = shift @lines ) {
221 #next if $checked{ $_ };
225 if ( /^\S+: (\S+): (?:Command )?not found$/ or /.*configure\[\d+\]: (\S+): not found$/
226 or m{which: no (\S+) in \(.*/bin.*\)}
227 or m{\S+: (\S+): command not found$}
228 or m{(?:/usr/bin/)?env: (\S+): No such file or directory}
229 or m{flock: (\S+): No such file or directory}
230 or m{Can't exec "(\S+)": No such file or directory} ) {
232 $exec = $1 if $exec =~ m{^"(.*)"$};
233 next if $skip{ $exec };
234 warn "Looking for executable $exec\n";
235 if ( $exec =~ m#^/# ) {
236 poldek_file( $exec );
238 poldek_file( "/usr/bin/$exec", "/bin/$exec" );
241 if ( /\S+\.[ch](?:pp|xx|c)?:\d+:\d+: error: (\S+): No such file or directory$/ or
242 /\S+\.[ch](?:pp|xx|c)?:\d+:\d+: fatal error: (\S+): No such file or directory$/ ) {
244 warn "Looking for C(++) header $h\n";
245 poldek_file( "/usr/include*/$h" );
247 if ( m{^ImportError: No module named (\S+)$} or
248 m{^ERROR: Cannot find .+: No module named (\S+)$} or
249 m{^ERROR: Failed to import the ".+" module: No module named (\S+)$}
253 warn "Looking for python module $mod\n";
255 "/usr/share/python2*/$mod/__init__.py*",
256 "/usr/share/python2*/$mod.py*",
257 "/usr/lib*/python2*/$mod/__init__.py*",
258 "/usr/lib*/python2*/$mod.py*",
259 "/usr/lib*/python2*/_$mod.so",
260 "/usr/lib*/python2*/$mod.so" );
264 m{^cannot load such file -- (\S+)} or
265 m{in `require': cannot load such file -- (\S+) \(LoadError\)}
268 warn "Looking for ruby module $mod\n";
270 "/usr/share/ruby/*/$mod.rb",
271 "/usr/share/ruby/vendor_ruby/*/$mod.rb",
272 "/usr/lib64/ruby/vendor_ruby/*/$mod.so",
276 if ( /configure(?:\.in|\.ac)?:\d+: error: possibly undefined macro: (\S+)/
277 or m{configure(?:\.in|\.ac)?:\d+: error: m4 macro `(\S+)' is not defined}
278 or m{warning: macro `(\S+)' not found in library} ) {
280 warn "Looking for autotools macro $macro\n";
281 if ( my $br = $ac2br{ $macro } ) {
288 if ( /^No package '(\S+)' found$/ or
289 /Package (\S+) was not found in the pkg-config search path/
290 or m{None of the required '(\S+?)(?:[<>=].*)?' found}
291 or m{--\s+package '(\S+?)(?:[<>=].*)?' not found}
292 or m{ERROR: cannot find a valid pkg-config package for \['(\S+?)(?:[<>=].*)?'\]}
295 warn "Looking for package $pkg\n";
296 poldek_file( "/usr/lib*/pkgconfig/$pkg.pc" );
299 if (/^ocamlfind: Package `(\S+)' not found - required by/
300 or m{Camlp4: Uncaught exception: DynLoader.Error \("(\S+)", "file not found in path"\)}
303 warn "Looking for ocaml package $pkg\n";
304 poldek_file( "/usr/lib*/ocaml/*/$pkg.a", "/usr/lib*/ocaml/*/$pkg");
307 if ( m{^cp: cannot stat `(/.*)': No such file or directory$} ) {
309 warn "Looking for file $f\n";
313 if ( m{^find-lang.sh: Error: international files not found for '}
314 or m{ gettext tools not found}
316 add_br( "gettext-devel" );
320 if ( m{ pkg-config .*not .*found}
321 or m{^checking for pkg-config\.\.\. no}
322 or m{^pkg-config unavailable, build terminated}
324 add_br( "pkgconfig" );
328 if ( m{^Can't locate (.*?\.pm) in \@INC} ) {
330 warn "Looking for perl module $mod\n";
331 poldek_file( "/usr/lib*/perl*/$mod", "/usr/share/perl*/$mod" );
334 if ( m{^(?:/usr/bin/ld: )?cannot find -l(.*?)$} ) {
336 warn "Looking for library $lib\n";
337 poldek_file( "/usr/lib64/lib$lib.so", "/usr/lib/lib$lib.so",
338 "/usr/lib*/lib$lib.so" );
340 if ( m{^error: Couldn't exec (/\S+): No such file or directory$}
341 or m{^Can't open perl script "(/\S+)": No such file or directory$}
342 or m{unable to open (/\S+) \(No such file or directory\)$}
343 or m{GConf-CRITICAL \*\*: No such file `(/.\S+?)'$}
344 or m{make.*: \*\*\* No rule to make target `(/\S+)'}
345 or m{g(?:cc|\+\+): (/\S+): No such file or directory$}
346 or m{env: (/\S+): No such file or directory$}
349 warn "Looking for file $file\n";
350 poldek_file( $file );
353 if ( m{^ValueError: Couldn't find include '(.*\.gir)'} ) {
355 warn "Looking for gir file $file\n";
356 poldek_file( "/usr/share/gir-1.0/" . $file );
359 if ( m{^error: Package `(\S+)' not found in specified Vala API directories or GObject-Introspection GIR directories}
362 warn "Looking for gir file $file\n";
363 poldek_file( "/usr/share/vala/vapi/$file.vapi");
366 if ( m{failed.*http://www\.oasis-open\.org/docbook/xml/([\d\.]+/\S+\.dtd)} ) {
368 warn "Looking for docbook file $dtd\n";
369 poldek_file( "/usr/share/sgml/docbook/xml-dtd-$dtd" );
371 if ( m{http://docbook.sourceforge.net/release/xsl/current/(\S+\.xsl)} ) {
373 next if m{^\s*(/usr/bin/)?xsltproc };
374 warn "Looking for docbook file $db\n";
375 poldek_file( "/usr/share/sgml/*/$db" );
378 if ( m{LaTeX Error: File `(\S+)' not found} ) {
380 warn "Looking for tex file $tex\n";
381 poldek_file( "/usr/share/tex*/$tex" );
383 if ( m{mv: cannot move `\S+' to `(/var/lib/texmf.*?)':} ) {
385 warn "Looking for tex file $tex\n";
389 if ( m{configure: error: C\+\+ preprocessor "/lib/cpp" fails sanity check} ) {
390 add_br( "gcc-c++", "try: %undefine\t__cxx" );
392 if ( m{configure: error: C\+\+ compiler cannot create executables} ) {
393 add_br( "libstdc++-devel", "maybe try: %undefine\t__cxx" );
395 if ( m{configure: error: XML::Parser perl module is required for intltool} ) {
396 add_br( "perl-XML-Parser" );
398 if ( m{iconv: conversion from `\S+' is not supported} ) {
402 if ( m{ (\S+) does not appear in AM_CONDITIONAL$} ) {
404 warn "Looking for autotools macro $macro\n";
405 if ( my $br = $ac2br{ $macro } ) {
413 if ( m{configure\[\d+\]: syntax error: }
414 or m{\./configure\[\d+\]: \S+_\S+: not found}
415 or m{./configure\[\d+\]: .*unexpected}
416 or m{does not appear in AM_CONDITIONAL$}
418 warn "Need to check configure source: $reason\n";
421 if ( m{^configure: error:} ) {
422 $check_config_log = 1 unless defined $check_config_log;
425 if ( m{^CMake Error at (?:\S+/)?(\S+?)\.cmake:(\d+) } ) {
426 my ( $module, $line ) = ( lc $1, $2 );
428 if ( $module eq "findqt4" ) {
431 if ( $l =~ /qmake/ ) {
432 add_br( "qt4-qmake", $l );
433 } elsif ( $l =~ /rcc/ ) {
434 add_br( "qt4-build", $l );
435 } elsif ( $l =~ /Could NOT find (Qt\S+) header/ ) {
436 add_br( "$1-devel", $l );
438 warn "unrecognized Qt requirement: $l\n";
440 } elsif ( $module eq "cmakedeterminecxxcompiler" ) {
441 add_br( "libstdc++-devel",
442 '"try: -DCMAKE_CXX_COMPILER_WORKS=1 -DCMAKE_CXX_COMPILER="%{__cc}"' );
443 } elsif ( $br = $cmake2br{ $module . ":" . $line } ) {
445 } elsif ( $br = $cmake2br{ $module } ) {
447 } elsif ( $br = guess_package( $module =~ /find(.+)/ ) ) {
451 warn "Unrecognized cmake error: $reason\n";
454 if ( m{^\s*ERROR: (?:\S+/)?(\S+?\.cmake) not found} ) {
456 warn "Looking for cmake file: $cmake\n";
457 poldek_file( "/usr/*/cmake/*/$cmake" )
459 if ( $cmake_get_call ) {
460 if ( m{^\s*/\S+/(\S+)\.cmake:(\d+) } ) {
461 my ( $module, $line ) = ( lc $1, $2 );
463 if ( $br = $cmake2br{ $module . ":" . $line } ) {
466 } elsif ( $br = $cmake2br{ $module } ) {
469 } elsif ( $br = guess_package( $module =~ /find(.+)/ ) ) {
475 if ( m{^-- WARNING: you are using the obsolete 'PKGCONFIG' macro} ) {
476 add_br( "pkgconfig" );
478 if ( m{QT_(QT\S+)_LIBRARY \(ADVANCED\)}
479 or m{X11_(\S+)_LIB \(ADVANCED\)}
480 or m{Qt (\S+) library not found} ) {
482 my $pkg = guess_package( $find );
486 warn "Cannot quess qt package: $find\n";
490 if ( m{Unable to find a javac compiler;$} ) {
493 if ( m{Could not find (\S+) Java extension for this JVM$} ) {
495 warn "Looking for jar file: $jar\n";
496 poldek_file( "/usr/share/java/$jar.jar", "*/$jar.jar" )
500 if ( m{^-- The following OPTIONAL packages could NOT be located on your system} ) {
503 if ( $cmake_pkg_list ) {
504 if ( /\s+\* (\S+) / ) {
506 my $pkg = guess_package( $find );
510 warn "Cannot quess optional package: $find\n";
512 } elsif ( /^\s*$/ ) {
517 if ( m{^configure:\d+: checking for (?:"(\S+)"|(\S+))$} ) {
519 if ( @lines and $lines[0] =~ m{^configure:\d+: result: no$} ) {
520 next if $skip{ $exec };
521 warn "Looking for executable $exec\n";
522 poldek_file( $exec ) if $exec =~ m#^/#;
523 poldek_file( "/usr/bin/$exec", "/bin/$exec" );
532 return unless /^configure(\.(?:ac|in|in\.in))?$/;
535 warn "$File::Find::name\n";
540 if ( m{^\s*([A-Za-z0-9_]+)\s*(\(.*)?$} ) {
542 if ( my $br = $ac2br{ $def } ) {
543 add_br( $br, "$file: $_" );
544 } elsif ( $def !~ /^A[CM]_/ and $def =~ /^_?[A-Z]+_[A-Z_0-9a-z]+$/ ) {
545 #warn "Possible macro unrecognized: $def [[[$_]]]\n";
554 find( \&wanted, $builddir );
559 return unless /^config\.log$/;
562 warn "$File::Find::name\n";
568 if ( $check_config_log ) {
569 $check_config_log = 0;
570 find( \&wanted2, $builddir );
571 goto start_check if @lines;
574 foreach my $pkg ( sort keys %out ) {
575 print "$pkg -- $out{$pkg}\n";