From 38488004c207508834543e02e991e6129669bc8c Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 30 Aug 2012 07:20:32 -0500 Subject: changes for REQUIRES in SBos for 14, and many cleanups, fixes, enhancements --- SBO-Lib/lib/SBO/Lib.pm | 699 ++++++++++++++++++++++++++++--------------------- sbocheck | 17 +- sboclean | 30 +-- sboconfig | 63 +++-- sbofind | 53 ++-- sboinstall | 14 +- sbosnap | 16 +- sboupgrade | 323 ++++++++++------------- t/SBO/Lib.pm | 668 ++++++++++++++++++++++++++++++++++++++++++++++ t/SBO/Lib.pm~ | 643 +++++++++++++++++++++++++++++++++++++++++++++ t/do_tests.sh | 4 + t/prep.pl | 46 ++++ t/test.t | 95 +++++++ t/test.t~ | 95 +++++++ 14 files changed, 2190 insertions(+), 576 deletions(-) create mode 100644 t/SBO/Lib.pm create mode 100644 t/SBO/Lib.pm~ create mode 100755 t/do_tests.sh create mode 100755 t/prep.pl create mode 100755 t/test.t create mode 100755 t/test.t~ diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 7dc19aa..3db3133 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -2,19 +2,23 @@ # # vim: set ts=4:noet # -# sbolib.sh +# Lib.pm # shared functions for the sbo_ scripts. # # author: Jacob Pipkin # date: Setting Orange, the 37th day of Discord in the YOLD 3178 # license: WTFPL -package SBO::Lib 0.7; -my $version = "0.7"; +use 5.16.0; +use warnings FATAL => 'all'; +use strict; + +package SBO::Lib 1.0; +my $version = "1.0"; require Exporter; -@ISA = qw(Exporter); -@EXPORT = qw( +our @ISA = qw(Exporter); +our @EXPORT = qw( script_error open_fh open_read @@ -29,10 +33,13 @@ require Exporter; make_distclean do_upgradepkg get_sbo_location + get_from_info + get_tmp_extfn + get_tmp_perlfn ); -use warnings FATAL => 'all'; -use strict; +$< == 0 or die "This script requires root privileges.\n"; + use Tie::File; use Sort::Versions; use Digest::MD5; @@ -41,31 +48,30 @@ use File::Path qw(make_path remove_tree); use Fcntl; use File::Find; use File::Temp qw(tempdir tempfile); - -$< == 0 or die "This script requires root privileges.\n"; +use Data::Dumper; +use Fcntl qw(F_SETFD F_GETFD); our $tempdir = tempdir (CLEANUP => 1); # subroutine for throwing internal script errors -sub script_error { - unless (exists $_[0]) { - die "A fatal script error has occured. Exiting.\n"; - } else { - die "A fatal script error has occured:\n$_[0]\nExiting.\n"; - } +sub script_error (;$) { + exists $_[0] ? die "A fatal script error has occured:\n$_[0]\nExiting.\n" + : die "A fatal script error has occured. Exiting.\n"; } # sub for opening files, second arg is like '<','>', etc -sub open_fh { - exists $_[1] or script_error ('open_fh requires two arguments'); - script_error ('open_fh first argument not a file') unless -f $_[0]; +sub open_fh ($$) { + exists $_[1] or script_error 'open_fh requires two arguments'; + unless ($_[1] eq '>') { + -f $_[0] or script_error 'open_fh first argument not a file'; + } my ($file, $op) = @_; open my $fh, $op, $file or die "Unable to open $file.\n"; return $fh; } -sub open_read { - return open_fh (shift, '<'); +sub open_read ($) { + return open_fh shift, '<'; } # pull in configuration, set sane defaults, etc. @@ -82,7 +88,7 @@ our %config = ( # if the conf file exists, pull all the $key=$value pairs into a hash my %conf_values; if (-f $conf_file) { - my $fh = open_read ($conf_file); + my $fh = open_read $conf_file; my $text = do {local $/; <$fh>}; %conf_values = $text =~ /^(\w+)=(.*)$/mg; close $fh; @@ -91,28 +97,26 @@ if (-f $conf_file) { for my $key (keys %config) { $config{$key} = $conf_values{$key} if exists $conf_values{$key}; } -#$config{$_} = $conf_values{$_} for keys %config; $config{JOBS} = 'FALSE' unless $config{JOBS} =~ /^\d+$/; $config{SBO_HOME} = '/usr/sbo' if $config{SBO_HOME} eq 'FALSE'; +# some stuff we'll need later. my $distfiles = "$config{SBO_HOME}/distfiles"; my $slackbuilds_txt = "$config{SBO_HOME}/SLACKBUILDS.TXT"; - my $name_regex = '\ASLACKBUILD\s+NAME:\s+'; -sub show_version { - print "sbotools version $version\n"; - print "licensed under the WTFPL\n"; - print "\n"; +sub show_version () { + say "sbotools version $version"; + say 'licensed under the WTFPL'; + say ''; } # %supported maps what's in /etc/slackware-version to what's at SBo -sub get_slack_version { - my %supported = ( - '13.37.0' => '13.37', - '14.0' => '13.37', - ); - my $fh = open_read ('/etc/slackware-version'); +# which is now not needed since this version drops support < 14.0 +# but it's already future-proofed, so leave it. +sub get_slack_version () { + my %supported = ('14.0' => '14.0'); + my $fh = open_read '/etc/slackware-version'; chomp (my $line = <$fh>); close $fh; my $version = ($line =~ /\s+(\d+[^\s]+)$/)[0]; @@ -121,13 +125,13 @@ sub get_slack_version { return $supported{$version}; } -sub check_slackbuilds_txt { - return 1 if -f $slackbuilds_txt; - return; +# does the SLACKBUILDS.TXT file exist in the sbo tree? +sub chk_slackbuilds_txt () { + return -f $slackbuilds_txt ? 1 : 0; } # check for the validity of new $config{SBO_HOME} -sub check_home { +sub check_home () { my $sbo_home = $config{SBO_HOME}; if (-d $sbo_home) { opendir (my $home_handle, $sbo_home); @@ -136,62 +140,63 @@ sub check_home { die "$sbo_home exists and is not empty. Exiting.\n"; } } else { - make_path ($sbo_home) or die "Unable to create $sbo_home. Exiting.\n"; + make_path ($sbo_home) or die "Unable to create $sbo_home.\n"; } } -sub rsync_sbo_tree { - my $slk_version = get_slack_version (); +# rsync the sbo tree from slackbuilds.org to $config{SBO_HOME} +sub rsync_sbo_tree () { + my $slk_version = get_slack_version; my @arg = ('rsync', '-a', '--exclude=*.tar.gz', '--exclude=*.tar.gz.asc'); push @arg, "rsync://slackbuilds.org/slackbuilds/$slk_version/*"; - push @arg, $config{SBO_HOME}; - system @arg; - print "Finished.\n" and return 1; + my $out = system @arg, $config{SBO_HOME}; + say 'Finished.' and return $out; } -sub fetch_tree { - check_home (); - print "Pulling SlackBuilds tree...\n"; - rsync_sbo_tree (), return 1; +# wrappers for differing checks and output +sub fetch_tree () { + check_home; + say 'Pulling SlackBuilds tree...'; + rsync_sbo_tree, return $?; } -sub update_tree { - fetch_tree (), return unless check_slackbuilds_txt (); - print "Updating SlackBuilds tree...\n"; - rsync_sbo_tree (), return 1; +sub update_tree () { + fetch_tree, return unless chk_slackbuilds_txt; + say 'Updating SlackBuilds tree...'; + rsync_sbo_tree, return $?; } # if the SLACKBUILDS.TXT is not in $config{SBO_HOME}, we assume the tree has # not been populated there; prompt the user to automagickally pull the tree. -sub slackbuilds_or_fetch { - unless (check_slackbuilds_txt () ) { - print "It looks like you haven't run \"sbosnap fetch\" yet.\n"; - print "Would you like me to do this now? [y] "; - =~ /^[Yy\n]/ ? fetch_tree () : +sub slackbuilds_or_fetch () { + unless (chk_slackbuilds_txt) { + say 'It looks like you haven\'t run "sbosnap fetch" yet.'; + print 'Would you like me to do this now? [y] '; + =~ /^[Yy\n]/ ? fetch_tree : die "Please run \"sbosnap fetch\"\n"; } return 1; } # pull an array of hashes, each hash containing the name and version of an sbo -# currently installed. starting to think it might be better to only pull an -# array of names, and have another sub to pull the versions. -sub get_installed_sbos { +# currently installed. +sub get_installed_sbos () { my @installed; + # $1 == name, $2 == version + my $regex = qr#/([^/]+)-([^-]+)-[^-]+-[^-]+$#; for my $path () { - my ($name, $version) = - ($path =~ qr#/([^/]+)-([^-]+)-[^-]+-[^-]+$#)[0,1]; + my ($name, $version) = ($path =~ $regex)[0,1]; push @installed, {name => $name, version => $version}; } - return @installed; + return \@installed; } # search the SLACKBUILDS.TXT for a given sbo's directory -sub get_sbo_location { - exists $_[0] or script_error ('get_sbo_location requires an argument.'); +sub get_sbo_location ($) { + exists $_[0] or script_error 'get_sbo_location requires an argument.'; my $sbo = shift; my $regex = qr#LOCATION:\s+\.(/[^/]+/$sbo)$#; - my $fh = open_read ($slackbuilds_txt); + my $fh = open_read $slackbuilds_txt; while (my $line = <$fh>) { if (my $loc = ($line =~ $regex)[0]) { return "$config{SBO_HOME}$loc"; @@ -200,105 +205,144 @@ sub get_sbo_location { return; } +# pull the sbo name from a $location: $config{SBO_HOME}/system/wine, etc. +sub get_sbo_from_loc ($) { + exists $_[0] or script_error 'get_sbo_from_loc requires an argument.'; + return (shift =~ qr#/([^/]+)$#)[0]; +} + +# pull piece(s) of data, GET, from the $sbo.info file under LOCATION. +sub get_from_info (%) { + my %args = ( + LOCATION => '', + GET => '', + @_ + ); + unless ($args{LOCATION} && $args{GET}) { + script_error 'get_from_info requires LOCATION and GET.'; + } + state $vars = {PRGNAM => ['']}; + my $sbo = get_sbo_from_loc $args{LOCATION}; + return $$vars{$args{GET}} if $$vars{PRGNAM}[0] eq $sbo; + # if we're here, we haven't read in the .info file yet. + my $fh = open_read "$args{LOCATION}/$sbo.info"; + # suck it all in, clean it all up, stuff it all in $vars. + my $contents = do {local $/; <$fh>}; + $contents =~ s/("|\\\n)//g; + $vars = {$contents =~ /^(\w+)=(.*)$/mg}; + # fill the hash with array refs - even for single values, + # since consistency here is a lot easier than sorting it out later + for my $key (keys %$vars) { + if ($$vars{$key} =~ /\s/) { + my @array = split ' ', $$vars{$key}; + $$vars{$key} = \@array; + } else { + $$vars{$key} = [$$vars{$key}]; + } + } + return exists $$vars{$args{GET}} ? $$vars{$args{GET}} : 0; +} + +# find the version in the tree for a given sbo (provided a location) +sub get_sbo_version ($) { + exists $_[0] or script_error 'get_sbo_version requires an argument.'; + my $version = get_from_info (LOCATION => shift, GET => 'VERSION'); + return $$version[0] ? $$version[0] : 0; +} + # for each installed sbo, find out whether or not the version in the tree is # newer, and compile an array of hashes containing those which are -sub get_available_updates { +sub get_available_updates () { my @updates; - my @pkg_list = get_installed_sbos (); - FIRST: for my $key (keys @pkg_list) { - my $location = get_sbo_location ($pkg_list[$key]{name}); + my $pkg_list = get_installed_sbos; + FIRST: for my $key (keys @$pkg_list) { + my $location = get_sbo_location $$pkg_list[$key]{name}; # if we can't find a location, assume invalid and skip next FIRST unless defined $location; - my $regex = qr/^VERSION="([^"]+)"/; - my $fh = open_read ("$location/$pkg_list[$key]{name}.info"); - SECOND: while (my $line = <$fh>) { - if (my $sbo_version = ($line =~ $regex)[0]) { - if (versioncmp ($sbo_version, $pkg_list[$key]{version}) == 1) { - push @updates, {name => $pkg_list[$key]{name}, - installed => $pkg_list[$key]{version}, - update => $sbo_version}; - } - last SECOND; - } + my $version = get_sbo_version $location; + if (versioncmp ($version, $$pkg_list[$key]{version}) == 1) { + push @updates, { + name => $$pkg_list[$key]{name}, + installed => $$pkg_list[$key]{version}, + update => $version + }; } - close $fh; } - return @updates; -} - -# pull links or md5sums (type - 'download','md5sum') from a given sbo's .info -# file, first checking for x86_64-specific info we are told to -sub find_download_info { - exists $_[3] or script_error - ('find_download_info requires four arguments.'); - my ($sbo, $location, $type, $x64) = @_; - my @return; - $type =~ tr/a-z/A-Z/; - $type = $x64 ? "${type}_x86_64" : $type; - my $regex = qr/$type="([^"\s]*)("|\s)/; - my $empty_regex = qr/=""$/; - # may be > 1 lines for a given key. - my $back_regex = qr/\\$/; - my $un_regex = qr/^UN(SUPPOR|TES)TED$/; - my $more = 'FALSE'; - my $fh = open_read ("$location/$sbo.info"); - FIRST: while (my $line = <$fh>) { - if ($more eq 'FALSE') { - if ($line =~ $regex) { - last FIRST if $line =~ $empty_regex; - # some sbos have UNSUPPORTED for the x86_64 info - $1 =~ $un_regex ? last FIRST : push @return, $1; - $more = 'TRUE' if $line =~ $back_regex; - } - } else { - $more = 'FALSE' unless $line =~ $back_regex; - # we can assume anything we need will be at least 6 chars long - push @return, ($line =~ /([^\s"]{6,})/)[0]; + return \@updates; +} + +# get downloads and md5sums from an sbo's .info file, first +# checking for x86_64-specific info if we are told to +sub get_download_info (%) { + my %args = ( + LOCATION => 0, + X64 => 1, + @_ + ); + $args{LOCATION} or script_error 'get_download_info requires LOCATION.'; + my ($get, $downs, $md5s, %return); + $get = ($args{X64} ? 'DOWNLOAD_x86_64' : 'DOWNLOAD'); + $downs = get_from_info (LOCATION => $args{LOCATION}, GET => $get); + # did we get nothing back, or UNSUPPORTED/UNTESTED? + if ($args{X64}) { + my $nothing; + if (! $$downs[0]) { + $nothing = 1; + } elsif ($$downs[0] =~ qr/^UN(SUPPOR|TES)TED$/) { + $nothing = 1; + } + if ($nothing) { + $args{X64} = 0; + $downs = get_from_info (LOCATION => $args{LOCATION}, + GET => 'DOWNLOAD'); } } - close $fh; - return @return if exists $return[0]; - return; + # if we still don't have any links, something is really wrong. + return unless $$downs[0]; + # grab the md5s and build a hash + $get = $args{X64} ? 'MD5SUM_x86_64' : 'MD5SUM'; + $md5s = get_from_info (LOCATION => $args{LOCATION}, GET => $get); + return unless $$md5s[0]; + $return{$$downs[$_]} = $$md5s[$_] for (keys @$downs); + return %return; } -sub get_arch { +sub get_arch () { chomp (my $arch = `uname -m`); return $arch; } -# assemble an array of hashes containing links and md5sums for a given sbo, -# with the option of only checking for 32-bit links, for -compat32 packaging -sub get_sbo_downloads { - exists $_[2] or script_error - ('get_sbo_downloads requires three arguments.'); - -d $_[1] or script_error ('get_sbo_downloads given a non-directory.'); - my ($sbo, $location, $only32) = @_; - my $arch = get_arch (); - my (@links, @md5s); +# TODO: should probably combine this with get_download_info +sub get_sbo_downloads (%) { + my %args = ( + LOCATION => '', + 32 => 0, + @_ + ); + $args{LOCATION} or script_error 'get_sbo_downloads requires LOCATION.'; + my $location = $args{LOCATION}; + -d $location or script_error 'get_sbo_downloads given a non-directory.'; + my $arch = get_arch; + my %dl_info; if ($arch eq 'x86_64') { - unless ($only32 eq 'TRUE') { - @links = find_download_info ($sbo, $location, 'download', 1); - @md5s = find_download_info ($sbo, $location, 'md5sum', 1); - } - } - unless (exists $links[0]) { - @links = find_download_info ($sbo, $location, 'download', 0); - @md5s = find_download_info ($sbo, $location, 'md5sum', 0); + %dl_info = get_download_info (LOCATION => $location) unless $args{32}; + } + unless (keys %dl_info > 0) { + %dl_info = get_download_info (LOCATION => $location, X64 => 0); } - my @downloads; - push @downloads, {link => $links[$_], md5sum => $md5s[$_]} for keys @links; - return @downloads; + return %dl_info; } -sub get_filename_from_link { - exists $_[0] or script_error - ('get_filename_from_link requires an argument'); +# given a link, grab the filename from the end of it +sub get_filename_from_link ($) { + exists $_[0] or script_error 'get_filename_from_link requires an argument'; return "$distfiles/". (shift =~ qr#/([^/]+)$#)[0]; } -sub compute_md5sum { - -f $_[0] or script_error ('compute_md5sum requires a file argument.'); - my $fh = open_read (shift); +# for a given file, computer its md5sum +sub compute_md5sum ($) { + -f $_[0] or script_error 'compute_md5sum requires a file argument.'; + my $fh = open_read shift; my $md5 = Digest::MD5->new; $md5->addfile ($fh); my $md5sum = $md5->hexdigest; @@ -306,82 +350,67 @@ sub compute_md5sum { return $md5sum; } +sub compare_md5s ($$) { + exists $_[1] or script_error 'compare_md5s requires two arguments.'; + my ($first, $second) = @_; + return $first eq $second ? 1 : 0; +} + # for a given distfile, see whether or not it exists, and if so, if its md5sum # matches the sbo's .info file -sub check_distfile { - exists $_[1] or script_error ('check_distfile requires two arguments.'); +sub verify_distfile ($$) { + exists $_[1] or script_error 'check_distfile requires two arguments.'; my ($link, $info_md5sum) = @_; - my $filename = get_filename_from_link ($link); + my $filename = get_filename_from_link $link; return unless -d $distfiles; return unless -f $filename; - my $md5sum = compute_md5sum ($filename); - return unless $info_md5sum eq $md5sum; - return 1; + my $md5sum = compute_md5sum $filename; + return compare_md5s $info_md5sum, $md5sum; } # for a given distfile, attempt to retrieve it and, if successful, check its # md5sum against that in the sbo's .info file -sub get_distfile { - exists $_[1] or script_error ('get_distfile requires an argument'); - my ($link, $expected_md5sum) = @_; - my $filename = get_filename_from_link ($link); - mkdir ($distfiles) unless -d $distfiles; - chdir ($distfiles); +sub get_distfile ($$) { + exists $_[1] or script_error 'get_distfile requires an argument'; + my ($link, $exp_md5) = @_; + my $filename = get_filename_from_link $link; + mkdir $distfiles unless -d $distfiles; + chdir $distfiles; system ("wget --no-check-certificate $link") == 0 or die "Unable to wget $link\n"; - my $md5sum = compute_md5sum ($filename); - $md5sum eq $expected_md5sum or die "md5sum failure for $filename.\n"; + my $md5sum = compute_md5sum $filename; + # can't do anything if the link in the .info doesn't lead to a good d/l + compare_md5s $md5sum, $exp_md5 or die "md5sum failure for $filename.\n"; return 1; } -# find the version in the tree for a given sbo -sub get_sbo_version { - exists $_[1] or script_error ('get_sbo_version requires two arguments.'); - my ($sbo, $location) = @_; - my $version; - my $fh = open_read ("$location/$sbo.info"); - my $version_regex = qr/^VERSION="([^"]+)"/; - FIRST: while (my $line = <$fh>) { - last FIRST if $version = ($line =~ $version_regex)[0]; - } - close $fh; - return $version; -} - -# for a given distfile, what will be the full path of the symlink? -sub get_symlink_from_filename { +# for a given distfile, figure out what the full path to its symlink will be +sub get_symlink_from_filename ($$) { exists $_[1] or script_error - ('get_symlink_from_filename requires two arguments'); + 'get_symlink_from_filename requires two arguments'; -f $_[0] or script_error - ('get_symlink_from_filename first argument is not a file'); + 'get_symlink_from_filename first argument is not a file'; my ($filename, $location) = @_; - my @split = split ('/', reverse ($filename), 2); - return "$location/". reverse ($split[0]); + return "$location/". ($filename =~ qr#/([^/]+)$#)[0]; } # determine whether or not a given sbo is 32-bit only -sub check_x32 { - exists $_[1] or script_error ('check_x32 requires two arguments.'); - my ($sbo, $location) = @_; - my $fh = open_read ("$location/$sbo.info"); - my $regex = qr/^DOWNLOAD_x86_64="UN(SUPPOR|TES)TED"/; - while (my $line = <$fh>) { - return 1 if $line =~ $regex; - } - close $fh; - return; +sub check_x32 ($) { + exists $_[0] or script_error 'check_x32 requires an argument.'; + my $dl = get_from_info (LOCATION => shift, GET => 'DOWNLOAD_x86_64'); + return $$dl[0] =~ /UN(SUPPOR|TES)TED/ ? 1 : 0; } # can't do 32-bit on x86_64 without this file, so we'll use it as the test to # to determine whether or not an x86_64 system is setup for multilib -sub check_multilib { +sub check_multilib () { return 1 if -f '/etc/profile.d/32dev.sh'; return; } # make a backup of the existent SlackBuild, and rewrite the original as needed -sub rewrite_slackbuild { - exists $_[1] or script_error ('rewrite_slackbuild requires two arguments.'); +sub rewrite_slackbuild ($$%) { + exists $_[1] or script_error 'rewrite_slackbuild requires two arguments.'; my ($slackbuild, $tempfn, %changes) = @_; copy ($slackbuild, "$slackbuild.orig") or die "Unable to backup $slackbuild to $slackbuild.orig\n"; @@ -389,7 +418,8 @@ sub rewrite_slackbuild { my $makepkg_regex = qr/makepkg/; my $libdir_regex = qr/^\s*LIBDIRSUFFIX="64"\s*$/; my $make_regex = qr/^\s*make(| \Q||\E exit 1)$/; - my $arch_out_regex = qr/\$VERSION-\$ARCH-\$BUILD/; + my $arch_regex = qr/\$VERSION-\$ARCH-\$BUILD/; + # tie the slackbuild, because this is the easiest way to handle this. tie my @sb_file, 'Tie::File', $slackbuild; for my $line (@sb_file) { # get the output of the tar and makepkg commands. hope like hell that v @@ -397,16 +427,15 @@ sub rewrite_slackbuild { if ($line =~ $tar_regex || $line =~ $makepkg_regex) { $line = "$line | tee -a $tempfn"; } - while (my ($key, $value) = each %changes) { - if ($key eq 'libdirsuffix') { - $line =~ s/64/$value/ if $line =~ $libdir_regex; - } - if ($key eq 'make') { - $line =~ s/make/make $value/ if $line =~ $make_regex; - } - if ($key eq 'arch_out') { - $line =~ s/\$ARCH/$value/ if $line =~ $arch_out_regex; - } + # then check for and apply any other %changes + if (exists $changes{libdirsuffix}) { + $line =~ s/64/$changes{libdirsuffix}/ if $line =~ $libdir_regex; + } + if (exists $changes{make}) { + $line =~ s/make/make $changes{make}/ if $line =~ $make_regex; + } + if (exists $changes{arch_out}) { + $line =~ s/\$ARCH/$changes{arch_out}/ if $line =~ $arch_regex; } } untie @sb_file; @@ -414,8 +443,8 @@ sub rewrite_slackbuild { } # move a backed-up .SlackBuild file back into place -sub revert_slackbuild { - exists $_[0] or script_error ('revert_slackbuild requires an argument'); +sub revert_slackbuild ($) { + exists $_[0] or script_error 'revert_slackbuild requires an argument'; my $slackbuild = shift; if (-f "$slackbuild.orig") { unlink $slackbuild if -f $slackbuild; @@ -424,141 +453,199 @@ sub revert_slackbuild { return 1; } +# for each $download, see if we have it, and if the copy we have is good, +# otherwise download a new copy +sub check_distfiles (%) { + exists $_[0] or script_error 'check_distfiles requires an argument.'; + my %dists = @_; + for my $link (keys %dists) { + my $md5sum = $dists{$link}; + unless (verify_distfile $link, $md5sum) { + die unless get_distfile $link, $md5sum; + } + } + return 1; +} + # given a location and a list of download links, assemble a list of symlinks, # and create them. -sub create_symlinks { - exists $_[1] or script_error ('create_symlinks requires two arguments.'); - my ($location, @downloads) = @_; +sub create_symlinks ($%) { + exists $_[1] or script_error 'create_symlinks requires two arguments.'; + my ($location, %downloads) = @_; my @symlinks; - for my $key (keys @downloads) { - my $link = $downloads[$key]{link}; - my $md5sum = $downloads[$key]{md5sum}; - my $filename = get_filename_from_link ($link); - unless (check_distfile ($link, $md5sum) ) { - die unless get_distfile ($link, $md5sum); - } - my $symlink = get_symlink_from_filename ($filename, $location); + for my $link (keys %downloads) { + my $filename = get_filename_from_link $link; + my $symlink = get_symlink_from_filename $filename, $location; push @symlinks, $symlink; - symlink ($filename, $symlink); + symlink $filename, $symlink; } return @symlinks; } -# make a .SlackBuild executable. -sub prep_sbo_file { - exists $_[1] or script_error ('prep_sbo_file requires two arguments'); - my ($sbo, $location) = @_; - chdir ($location); - chmod (0755, "$location/$sbo.SlackBuild"); - return 1; -} - # pull the untarred source directory or created package name from the temp # file (the one we tee'd to) -sub grok_temp_file { - exists $_[1] or script_error ('grok_temp_file requires two arguments'); - my ($tempfn, $find) = @_; +sub grok_temp_file (%) { + my %args = ( + FH => '', + REGEX => '', + CAPTURE => 0, + @_ + ); + unless ($args{FH} && $args{REGEX}) { + script_error 'grok_temp_file requires two arguments'; + } + my $fh = $args{FH}; + seek $fh, 0, 0; my $out; - my $pkg_regex = qr/^Slackware\s+package\s+([^\s]+)\s+created\.$/; - my $src_regex = qr#^([^/]+)/.*$#; - my $fh = open_read ($tempfn); FIRST: while (my $line = <$fh>) { - if ($find eq 'pkg') { - last FIRST if $out = ($line =~ $pkg_regex)[0]; - } elsif ($find eq 'src') { - last FIRST if $out = ($line =~ $src_regex)[0]; + if ($line =~ $args{REGEX}) { + $out = ($line =~ $args{REGEX})[$args{CAPTURE}]; + last FIRST; } } - close $fh; +# close $fh; return $out; } # wrappers around grok_temp_file -sub get_src_dir { - exists $_[0] or script_error ('get_src_dir requires an argument'); - return grok_temp_file (shift, 'src'); +sub get_src_dir ($) { + exists $_[0] or script_error 'get_src_dir requires an argument'; + return grok_temp_file (FH => shift, REGEX => qr#^([^/]+)/#); +} + +sub get_pkg_name ($) { + exists $_[0] or script_error 'get_pkg_name requires an argument'; + return grok_temp_file (FH => shift, + REGEX => qr/^Slackware\s+package\s+([^\s]+)\s+created\.$/); +} + +sub clear_coe_bit ($) { + exists $_[0] or script_error 'clear_coe_bit requires an argument'; + my $fh = shift; + fcntl ($fh, F_SETFD, 0) or die "no unset exec-close thingy\n"; + return $fh; } -sub get_pkg_name { - exists $_[0] or script_error ('get_pkg_name requires an argument'); - return grok_temp_file (shift, 'pkg'); +sub get_tmp_extfn ($) { + exists $_[0] or script_error 'get_tmp_extfn requires an argument.'; + my $fh = clear_coe_bit shift; + return '/dev/fd/'. fileno $fh; +} + +sub get_tmp_perlfn ($) { + exists $_[0] or script_error 'get_tmp_perlfn requires an argument.'; + my $fh = clear_coe_bit shift; + return '+<=&'. fileno $fh; } # prep and run .SlackBuild -sub perform_sbo { - exists $_[6] or script_error ('perform_sbo requires seven arguments'); - my ($opts, $jobs, $sbo, $location, $arch, $c32, $x32) = @_; - prep_sbo_file ($sbo, $location); +sub perform_sbo (%) { + my %args = ( + OPTS => 0, + JOBS => 0, + LOCATION => '', + ARCH => '', + C32 => 0, + X32 => 0, + @_ + ); + unless ($args{LOCATION} && $args{ARCH}) { + script_error 'perform_sbo requires LOCATION and ARCH.'; + } + my $location = $args{LOCATION}; + my $sbo = get_sbo_from_loc $location; my ($cmd, %changes); - $jobs eq 'FALSE' or $changes{make} = "-j $jobs"; - if ($arch eq 'x86_64' and ($c32 eq 'TRUE' || $x32) ) { - if ($c32 eq 'TRUE') { + # figure out any changes we need to make to the .SlackBuild + $changes{make} = "-j $args{JOBS}" if $args{JOBS}; + if ($args{ARCH} eq 'x86_64' and ($args{C32} || $args{X32})) { + if ($args{C32}) { $changes{libdirsuffix} = ''; - } elsif ($x32) { + } elsif ($args{X32}) { $changes{arch_out} = 'i486'; } - $cmd = ". /etc/profile.d/32dev.sh && $location/$sbo.SlackBuild"; - } else { - $cmd = "$location/$sbo.SlackBuild"; + $cmd = ". /etc/profile.d/32dev.sh &&"; } - $cmd = "$opts $cmd" unless $opts eq 'FALSE'; - my ($tempfh, $tempfn) = tempfile (DIR => $tempdir); - close $tempfh; - rewrite_slackbuild ("$location/$sbo.SlackBuild", $tempfn, %changes); - my $out = system $cmd; - revert_slackbuild ("$location/$sbo.SlackBuild"); + $cmd .= "/bin/sh $location/$sbo.SlackBuild"; + $cmd = "$args{OPTS} $cmd" if $args{OPTS}; + my $tempfh = tempfile (DIR => $tempdir); + my $fn = get_tmp_extfn $tempfh; + rewrite_slackbuild "$location/$sbo.SlackBuild", $fn, %changes; + chdir $location, my $out = system $cmd; + revert_slackbuild "$location/$sbo.SlackBuild"; die unless $out == 0; - my $src = get_src_dir ($tempfn); - my $pkg = get_pkg_name ($tempfn); - unlink $tempfn; + my $pkg = get_pkg_name $tempfh; + my $src = get_src_dir $tempfh; return $pkg, $src; } +# run convertpkg on a package to turn it into a -compat32 thing +sub do_convertpkg ($) { + exists $_[0] or script_error 'do_convertpkg requires an argument.'; + my $pkg = shift; + my $tempfh = tempfile (DIR => $tempdir); + my $fn = get_tmp_extfn $tempfh; + my $cmd = "/usr/sbin/convertpkg-compat32 -i $pkg -d /tmp | tee $fn"; + system ($cmd) == 0 or die; + unlink $pkg; + return get_pkg_name $tempfh; +} + # "public interface", sort of thing. -sub do_slackbuild { - exists $_[4] or script_error ('do_slackbuild requires five arguments.'); - my ($opts, $jobs, $sbo, $location, $compat32) = @_; - my $arch = get_arch (); - my $version = get_sbo_version ($sbo, $location); - my @downloads = get_sbo_downloads ($sbo, $location, $compat32); +sub do_slackbuild (%) { + my %args = ( + OPTS => 0, + JOBS => 0, + LOCATION => '', + COMPAT32 => 0, + @_ + ); + $args{LOCATION} or script_error 'do_slackbuild requires LOCATION.'; + my $location = $args{LOCATION}; + my $sbo = get_sbo_from_loc $location; + my $arch = get_arch; + my $multi = check_multilib; + my $version = get_sbo_version $location; my $x32; - if ($compat32 eq 'TRUE') { - unless ($arch eq 'x86_64') { - die "You can only create compat32 packages on x86_64 systems.\n"; - } else { - die "This system does not appear to be setup for multilib.\n" - unless check_multilib (); - die "compat32 pkgs require /usr/sbin/convertpkg-compat32.\n" + # ensure x32 stuff is set correctly, or that we're setup for it + if ($args{COMPAT32}) { + die "compat32 only works on x86_64.\n" unless $arch eq 'x86_64'; + die "compat32 requires multilib.\n" unless $multi; + die "compat32 requires /usr/sbin/convertpkg-compat32.\n" unless -f '/usr/sbin/convertpkg-compat32'; - } } else { if ($arch eq 'x86_64') { - $x32 = check_x32 ($sbo, $location); - if ($x32 && ! check_multilib () ) { - die "$sbo is 32-bit, but this system does not seem to be setup for multilib.\n"; + $x32 = check_x32 $args{LOCATION}; + if ($x32 && ! $multi) { + die "$sbo is 32-bit which requires multilib on x86_64.\n"; } } } - my @symlinks = create_symlinks ($location, @downloads); - my ($pkg, $src) = perform_sbo - ($opts, $jobs, $sbo, $location, $arch, $compat32, $x32); - if ($compat32 eq 'TRUE') { - my ($tempfh, $tempfn) = tempfile (DIR => $tempdir); - close $tempfh; - my $cmd = "/usr/sbin/convertpkg-compat32 -i $pkg -d /tmp | tee $tempfn"; - system ($cmd) == 0 or die; - unlink $pkg; - $pkg = get_pkg_name ($tempfn); - } + # get a hash of downloads and md5sums, ensure we have 'em, symlink 'em + my %downloads = get_sbo_downloads ( + LOCATION => $location, + 32 => $args{COMPAT32} + ); + check_distfiles %downloads; + my @symlinks = create_symlinks $args{LOCATION}, %downloads; + # setup and run the .SlackBuild itself + my ($pkg, $src) = perform_sbo ( + OPTS => $args{OPTS}, + JOBS => $args{JOBS}, + LOCATION => $location, + ARCH => $arch, + C32 => $args{COMPAT32}, + X32 => $x32, + ); + do_convertpkg $pkg if $args{COMPAT32}; unlink $_ for @symlinks; return $version, $pkg, $src; } # remove work directories (source and packaging dirs under /tmp/SBo) -sub make_clean { - exists $_[1] or script_error ('make_clean requires two arguments.'); +sub make_clean ($$$) { + exists $_[2] or script_error 'make_clean requires three arguments.'; my ($sbo, $src, $version) = @_; - print "Cleaning for $sbo-$version...\n"; + say "Cleaning for $sbo-$version..."; my $tmpsbo = "/tmp/SBo"; remove_tree ("$tmpsbo/$src") if -d "$tmpsbo/$src"; remove_tree ("$tmpsbo/package-$sbo") if -d "$tmpsbo/package-$sbo"; @@ -566,23 +653,31 @@ sub make_clean { } # remove distfiles -sub make_distclean { - exists $_[3] or script_error ('make_distclean requires four arguments.'); - my ($sbo, $src, $version, $location) = @_; - make_clean ($sbo, $src, $version); - print "Distcleaning for $sbo-$version...\n"; - my @downloads = get_sbo_downloads ($sbo, $location, 0); - for my $key (keys @downloads) { - my $filename = get_filename_from_link ($downloads[$key]{link}); +sub make_distclean (%) { + my %args = ( + SRC => '', + VERSION => '', + LOCATION => '', + @_ + ); + unless ($args{SRC} && $args{VERSION} && $args{LOCATION}) { + script_error 'make_distclean requires four arguments.'; + } + my $sbo = get_sbo_from_loc $args{LOCATION}; + make_clean $sbo, $args{SRC}, $args{VERSION}; + say "Distcleaning for $sbo-$args{VERSION}..."; + # remove any distfiles for this particular SBo. + my %downloads = get_sbo_downloads (LOCATION => $args{LOCATION}); + for my $key (keys %downloads) { + my $filename = get_filename_from_link $key; unlink $filename if -f $filename; } return 1; } # run upgradepkg for a created package -sub do_upgradepkg { - exists $_[0] or script_error ('do_upgradepkg requires an argument.'); +sub do_upgradepkg ($) { + exists $_[0] or script_error 'do_upgradepkg requires an argument.'; system ('/sbin/upgradepkg', '--reinstall', '--install-new', shift); return 1; } - diff --git a/sbocheck b/sbocheck index 6e748a2..9d228a6 100755 --- a/sbocheck +++ b/sbocheck @@ -9,6 +9,7 @@ # date: Sweetmorn, the 38th day of Discord in the YOLD 3178 # license: WTFPL +use 5.16.0; use SBO::Lib; use File::Basename; use Getopt::Std; @@ -22,18 +23,18 @@ my $self = basename ($0); my %options; getopts ('v',\%options); -show_version () && exit (0) if (exists $options{v}); +show_version && exit 0 if (exists $options{v}); -update_tree (); +update_tree; print "Checking for updated SlackBuilds...\n"; -my @updates = get_available_updates (); +my $updates = get_available_updates; # pretty formatting. my @listing; -for my $key (keys @updates) { - my $string = "$updates[$key]{name}-$updates[$key]{installed}"; - $string .= " < needs updating (SBo has $updates[$key]{update})\n"; +for my $key (keys @$updates) { + my $string = "$$updates[$key]{name}-$$updates[$key]{installed}"; + $string .= " < needs updating (SBo has $$updates[$key]{update})\n"; push @listing, $string; } @@ -41,9 +42,9 @@ if (exists $listing[0]) { my $tab = new Text::Tabulate (); $tab->configure (tab => '\s'); my $output = $tab->format (@listing); - print "\n". $output ."\n"; + say "\n". $output; } else { - print "\nNo updates available.\n"; + say "\nNo updates available."; } exit 0; diff --git a/sboclean b/sboclean index 3e4da48..3154bd1 100755 --- a/sboclean +++ b/sboclean @@ -9,6 +9,7 @@ # date: Boomtime, the 6th day of Confusion in the YOLD 3178 # license: WTFPL +use 5.16.0; use SBO::Lib; use File::Basename; use Getopt::Std; @@ -19,7 +20,7 @@ use warnings FATAL => 'all'; my %config = %SBO::Lib::config; my $self = basename ($0); -sub show_usage { +sub show_usage () { print < =~ /^[Yy]/; } @@ -64,7 +64,7 @@ sub remove_stuff { } } -remove_stuff ($config{SBO_HOME} . '/distfiles') if $clean_dist eq 'TRUE'; -remove_stuff ('/tmp/SBo') if $clean_work eq 'TRUE'; +remove_stuff $config{SBO_HOME} .'/distfiles' if $clean_dist; +remove_stuff '/tmp/SBo' if $clean_work; exit 0; diff --git a/sboconfig b/sboconfig index 829d7a3..b5c1d6d 100755 --- a/sboconfig +++ b/sboconfig @@ -9,6 +9,7 @@ # date: Pungenday, the 40th day of Discord in the YOLD 3178 # license: WTFPL +use 5.16.0; use strict; use warnings FATAL => 'all'; use SBO::Lib; @@ -21,7 +22,7 @@ use File::Temp qw(tempfile);; my %config = %SBO::Lib::config; my $self = basename ($0); -sub show_usage { +sub show_usage () { print < 'NOCLEAN', @@ -66,7 +59,17 @@ my %valid_confs = ( p => 'PKG_DIR', s => 'SBO_HOME', ); - + +my %params = reverse %valid_confs; + +if (exists $options{l}) { + my @keys = sort {$a cmp $b} keys %config; + say "sboconfig -$params{$_}:\n $_=$config{$_}" for @keys; + exit 0; +} + +show_usage and exit 0 unless %options; + # setup what's being changed. my %changes; while (my ($key, $value) = each %valid_confs) { @@ -77,52 +80,48 @@ if (exists $changes{JOBS}) { ($changes{JOBS} =~ /^\d+$/ || $changes{JOBS} eq 'FALSE'); } -my $conf_dir = $SBO::Lib::conf_dir;; +my $conf_dir = $SBO::Lib::conf_dir; my $conf_file = $SBO::Lib::conf_file; # safely modify our conf file; copy to a temp location, edit the temp file, # move the edited file into place -sub config_write { - exists $_[1] or script_error ('config_write requires two arguments.'); +sub config_write ($$) { + exists $_[1] or script_error 'config_write requires two arguments.'; my ($key, $val) = @_; if (! -d $conf_dir) { - mkdir ($conf_dir) or die "Unable to create $conf_dir. Exiting.\n"; + mkdir $conf_dir or die "Unable to create $conf_dir. Exiting.\n"; } if (-f $conf_file) { - my ($fh, $filename) = tempfile (DIR => $SBO::Lib::tempdir); - close $fh; - copy ($conf_file, $filename); + my $tempfh = tempfile (DIR => $SBO::Lib::tempdir); + my $tempfn = get_tmp_perlfn $tempfh; + copy ($conf_file, $tempfn); # tie the file so that if $key is already there, we just change that # line and untie it - tie my @temp, 'Tie::File', $filename; - my $has = 'FALSE'; + tie my @temp, 'Tie::File', $tempfn; + my $has = 0; my $regex = qr/\A\Q$key\E=/; FIRST: for my $tmpline (@temp) { - if ($tmpline =~ $regex) { - $has = 'TRUE'; - $tmpline = "$key=$val"; - last FIRST; - } + $has++, $tmpline = "$key=$val", last FIRST if $tmpline =~ $regex;; } untie @temp; # otherwise, append our new $key=$value pair - if ($has eq 'FALSE') { - my $fh = open_fh ($filename, '>>'); + unless ($has) { + my $fh = open_fh ($tempfn, '>>'); print {$fh} "$key=$val\n"; close $fh; } - move ($filename, $conf_file); + move ($tempfn, $conf_file); } else { # no config file, easiest case of all. - my $fh = open_fh ($conf_file, '>'); - print {$fh} "$key=$val\n"; + my $fh = open_fh $conf_file, '>'; + say {$fh} "$key=$val"; close $fh; } } while (my ($key, $value) = each %changes) { print "Setting $key to $value...\n"; - config_write ($key, $value); + config_write $key, $value; } exit 0; diff --git a/sbofind b/sbofind index 5e8931d..e00f8de 100755 --- a/sbofind +++ b/sbofind @@ -9,6 +9,7 @@ # date: Boomtime, the 39th day of Discord in the YOLD 3178 # license: WTFPL +use 5.16.0; use SBO::Lib; use File::Basename; use Getopt::Std; @@ -18,7 +19,7 @@ use warnings FATAL => 'all'; my %config = %SBO::Lib::config; my $self = basename ($0); -sub show_usage { +sub show_usage () { print <) { - if ($found eq 'FALSE') { - $found = 'TRUE', next FIRST if $name = ($line =~ $name_regex)[0]; + unless ($found) { + $found++, next FIRST if $name = ($line =~ $name_regex)[0]; } else { if (my ($location) = ($line =~ $loc_regex)[0]) { - $found = 'FALSE'; + $found = 0; $location =~ s#^\.##; - push @findings, {$name => $config{SBO_HOME} . $location}; + push @$findings, {$name => $config{SBO_HOME} . $location}; } } } -sub get_file_contents { - exists $_[0] or script_error ('get_file_contents requires an argument'); - -f $_[0] or script_error ('get_file_contents argument is not a file'); - my $fh = open_read (shift); +sub get_file_contents ($) { + exists $_[0] or script_error 'get_file_contents requires an argument'; + -f $_[0] or return "$_[0] doesn't exist.\n"; + my $fh = open_read shift; my $contents = do {local $/; <$fh>}; $contents =~ s/\n/\n /g; $contents =~ s/ $//g; @@ -78,22 +79,22 @@ sub get_file_contents { } # pretty formatting -if (exists $findings[0]) { +if (exists $$findings[0]) { my @listing = ("\n"); - for my $hash (@findings) { - while (my ($key, $value) = each %{$hash}) { + for my $hash (@$findings) { + while (my ($key, $value) = each %$hash) { push @listing, "SBo: $key\n"; push @listing, "Path: $value\n"; - push @listing, "info: ". get_file_contents ("$value/$key.info") - if $show_info eq 'TRUE'; - push @listing, "README: ". get_file_contents ("$value/README") - if $show_readme eq 'TRUE'; + push @listing, "info: ". get_file_contents "$value/$key.info" + if $show_info; + push @listing, "README: ". get_file_contents "$value/README" + if $show_readme; push @listing, "\n"; } } print $_ for @listing; } else { - print "Nothing found for search term: $search\n"; + say "Nothing found for search term: $search"; } exit 0; diff --git a/sboinstall b/sboinstall index 76cfa9f..3637207 100755 --- a/sboinstall +++ b/sboinstall @@ -9,6 +9,7 @@ # date: Pungenday, the 40th day of Discord in the YOLD 3178 # license: WTFPL +use 5.16.0; use SBO::Lib; use Getopt::Std; use File::Basename; @@ -17,7 +18,7 @@ use warnings FATAL => 'all'; my $self = basename ($0); -sub show_usage { +sub show_usage () { print < 'all'; use strict; @@ -23,7 +23,7 @@ my %config = %SBO::Lib::config; my $sbo_home = $config{SBO_HOME}; my $self = basename ($0); -sub show_usage { +sub show_usage () { print < +use 5.16.0; use SBO::Lib; use File::Basename; use Getopt::Std; @@ -19,7 +20,7 @@ use warnings FATAL => 'all'; my %config = %SBO::Lib::config; my $self = basename ($0); -sub show_usage { +sub show_usage () { print < =~ /^[Yy\n]/) { - my @args = ("/usr/sbin/sboupgrade", '-oN'); - # populate args so that they carry over correctly - push @args, "-c" if exists $options{c}; - push @args, "-d" if exists $options{d}; - push @args, "-j $options{j}" if exists $options{j}; - push @args, "-p" if $compat32 eq 'TRUE'; - push @args, $need; - system (@args) == 0 or - die "Requirement failure, unable to proceed.\n"; +# for a ref to an array of hashes of installed packages, return an array ref +# consisting of just their names +sub get_inst_names ($) { + exists $_[0] or script_error 'get_inst_names requires an argument.'; + my $inst = shift; + my $installed; + push @$installed, $$_{name} for @$inst; + return $installed; +} + +# pull list of requirements, offer to install them +sub grok_requirements ($$$) { + exists $_[1] or script_error 'grok_requirements requires an argument.'; + my ($sbo, $location, $readme) = @_; + my $requires = get_from_info (LOCATION => $location, GET => 'REQUIRES'); + return unless $$requires[0]; + for my $req (@$requires) { + my $inst = get_installed_sbos; + my $inst_names= get_inst_names $inst;; + unless ($req ~~ @$inst_names) { + say $readme; + say "$sbo has $req listed as a requirement."; + print "Shall I attempt to install it first? [y] "; + if ( =~ /^[Yy\n]/) { + my @cmd = ('/usr/sbin/sboupgrade', '-oN', $req); + system (@cmd) == 0 or die "$req failed to install.\n"; + } } } - return; + return 1; } # look for any (user|group)add commands in the README -sub grok_user_group { - exists $_[0] or script_error ('grok_user_group requires an argument'); +sub grok_user_group ($) { + exists $_[0] or script_error 'grok_user_group requires an argument'; my $readme = shift; - my @readme_array = split /\n/, $readme; - my @cmds; + my $readme_array = [split /\n/, $readme]; my $cmd_regex = qr/^\s*#\s+((user|group)add.*)/; - push @cmds, ($_ =~ $cmd_regex)[0] for @readme_array; + my @cmds; + push @cmds, ($_ =~ $cmd_regex)[0] for @$readme_array; return unless exists $cmds[0]; - print "\n". $readme ."\n";; + say "\n". $readme; print "\nIt looks like this slackbuild requires the following command(s)"; - print " to be run first:\n"; - print " # $_\n" for @cmds; + say " to be run first:"; + say " # $_" for @cmds; print "Shall I run it/them now? [y] "; if ( =~ /^[Yy\n]/) { for my $cmd (@cmds) { @@ -170,73 +139,81 @@ sub grok_user_group { } # see if the README mentions any options -sub grok_options { - exists $_[0] or script_error ('grok_options requires an argument'); +sub grok_options ($) { + exists $_[0] or script_error 'grok_options requires an argument'; my $readme = shift; - return 7 unless $readme =~ /[A-Z]+=[^\s]/; - my @readme_array = split /\n/, $readme; - print "\n". $readme; + return unless $readme =~ /[A-Z]+=[^\s]/; + say "\n". $readme; print "\nIt looks this slackbuilds has options; would you like to set any"; print " when the slackbuild is run? [n] "; if ( =~ /^[Yy]/) { - my $ask = sub { + my $ask = sub () { print "\nPlease supply any options here, or enter to skip: "; chomp (my $opts = ); - return 7 if $opts =~ /^$/; - return $opts; }; + return if $opts =~ /^$/; + return $opts; + }; my $kv_regex = qr/[A-Z]+=[^\s]+(|\s([A-Z]+=[^\s]+){0,})/; - my $opts = &$ask (); + my $opts = &$ask; FIRST: while ($opts !~ $kv_regex) { warn "Invalid input received.\n"; - $opts = &$ask (); - return 7 if $opts eq "7"; + $opts = &$ask; } return $opts; } - return 7; + return; } -# prompt for the readme, and grok the readme at this time also. -sub readme_prompt { - exists $_[0] or script_error ('readme_prompt requires an argument.'); - my $sbo = shift; - my $fh = open_read (get_readme_path ($sbo) ); +# prompt for the readme +sub readme_prompt ($$) { + exists $_[0] or script_error 'readme_prompt requires an argument.'; + my ($sbo, $location) = @_; + my $fh = open_read (get_readme_path $sbo); my $readme = do {local $/; <$fh>}; close $fh; - grok_requirements ($sbo, $readme); - grok_user_group ($readme); - my $opts = grok_options ($readme); - print "\n". $readme if ($opts eq "7" || ! $opts); - my $name = $compat32 eq 'TRUE' ? "$sbo-compat32" : $sbo; + # check for requirements, useradd/groupadd, options + grok_requirements $sbo, $location, $readme; + grok_user_group $readme; + my $opts = grok_options $readme; + print "\n". $readme unless $opts; + # present the name as -compat32 if appropriate + my $name = $compat32 ? "$sbo-compat32" : $sbo; print "\nProceed with $name? [y]: "; exit 0 unless =~ /^[Yy\n]/; - return $opts if defined $opts; - return 1; + return $opts; } # do the things with the provided sbos - whether upgrades or new installs. sub process_sbos { - exists $_[0] or script_error ('process_sbos requires an argument.'); - my @todo = @_; + exists $_[0] or script_error 'process_sbos requires an argument.'; + my $todo = shift; my @failures; - FIRST: for my $sbo (@todo) { + FIRST: for my $sbo (keys %$todo) { my $opts = 0; - $opts = readme_prompt ($sbo) unless $no_readme eq 'TRUE'; - $opts = 'FALSE' if ($opts =~ /\d+/ || ! $opts); + $opts = readme_prompt $sbo, $$todo{$sbo} unless $no_readme; # switch compat32 on if upgrading a -compat32 - $compat32 = 'TRUE' if $sbo =~ /-compat32$/; + $compat32 = 1 if $sbo =~ /-compat32$/; my ($version, $pkg, $src); - my @sb_args = ($opts, $jobs, $sbo, $locations{$sbo}, $compat32); - eval { ($version, $pkg, $src) = do_slackbuild (@sb_args); }; + eval { ($version, $pkg, $src) = do_slackbuild ( + OPTS => $opts, + JOBS => $jobs, + LOCATION => $locations{$sbo}, + COMPAT32 => $compat32, + ); }; if ($@) { push @failures, $sbo; } else { unless ($distclean eq 'TRUE') { - make_clean ($sbo, $src, $version) if $noclean eq 'FALSE'; + make_clean $sbo, $src, $version unless $noclean eq 'TRUE'; } else { - make_distclean ($sbo, $src, $version, $locations{$sbo}); + make_distclean ( + SBO => $sbo, + SRC => $src, + VERSION => $version, + LOCATION => $locations{$sbo}, + ); } - do_upgradepkg ($pkg) unless $no_install eq 'TRUE'; + do_upgradepkg $pkg unless $no_install; # move package to $config{PKG_DIR} if defined unless ($config{PKG_DIR} eq 'FALSE') { my $dir = $config{PKG_DIR}; @@ -244,7 +221,7 @@ sub process_sbos { mkdir ($dir) or warn "Unable to create $dir\n"; } if (-d $dir) { - move ($pkg, $dir), print "$pkg stored in $dir\n"; + move ($pkg, $dir), say "$pkg stored in $dir"; } else { warn "$pkg left in /tmp\n"; } @@ -256,80 +233,68 @@ sub process_sbos { return @failures; } -my @failed; - -sub print_failures { - if (exists $failed[0]) { - print "Failures:\n"; - print " $_\n" for @failed; +sub print_failures (;@) { + if (exists $_[0]) { + say "Failures:"; + say " $_" for @_; exit 1; } } # deal with any updates prior to any new installs. # no reason to bother if only_new is specified, ie running from sboinstall. -unless ($only_new eq 'TRUE') { - # doesn't matter what's updatable and what's not if force is specified - my @updates unless $force eq 'TRUE'; - unless ($force eq 'TRUE') { - my @updates_array = get_available_updates (); - push @updates, $updates_array[$_]{name} for keys @updates_array; +goto INSTALL_NEW if $only_new; + +# doesn't matter what's updatable and what's not if force is specified +my @updates unless $force; +unless ($force) { + my $updates = get_available_updates; + push @updates, $$_{name} for @$updates; +} +my $todo_upgrade; +# but without force, we only want to update what there are updates for +unless ($force) { + for my $sbo (@ARGV) { + $$todo_upgrade{$sbo} = $locations{$sbo} if $sbo ~~ @updates; } - my @todo_upgrade; - # but without force, we only want to update what there are updates for - unless ($force eq 'TRUE') { - for my $sbo (@ARGV) { - push @todo_upgrade, $sbo if $sbo ~~ @updates; - } - } else { - my @inst = get_installed_sbos (); - FIRST: for my $sbo (@ARGV) { - SECOND: for my $key (keys @inst) { - if ($sbo eq $inst[$key]{name}) { - push @todo_upgrade, $sbo; - last SECOND; - } - } +} else { + my $inst = get_installed_sbos; + my $inst_names= get_inst_names $inst;; + FIRST: for my $sbo (@ARGV) { + if ($sbo ~~ @$inst_names) { + $$todo_upgrade{$sbo} = $locations{$sbo}; } } - @failed = process_sbos (@todo_upgrade) if exists $todo_upgrade[0]; - print_failures () unless $install_new eq 'TRUE'; } +my @failures = process_sbos $todo_upgrade if keys %$todo_upgrade > 0; +print_failures @failures; -if ($install_new eq 'TRUE') { - my @todo_install; - FIRST: for my $sbo (@ARGV) { - my $has = 'FALSE'; - my $name = $compat32 eq 'TRUE' ? "$sbo-compat32" : $sbo; - my @inst = get_installed_sbos (); - SECOND: for my $key (keys @inst) { - $has = 'TRUE', last SECOND if $name eq $inst[$key]{name}; - } - # if compat32 is TRUE, we need to see if the non-compat version exists. - if ($compat32 eq 'TRUE') { - my $has64 = 'FALSE'; - my @inst = get_installed_sbos (); - THIRD: for my $key (keys @inst) { - $has64 = 'TRUE', last THIRD if $sbo eq $inst[$key]{name}; - } - unless ($has64 eq 'TRUE') { - print "\nYou are attempting to install $sbo-compat32, however,"; - print " $sbo is not yet installed. Shall I install it first?"; - print " [y] "; - if ( =~ /^[Yy\n]/) { - my @args = ('/usr/sbin/sboupgrade', '-oN', $sbo); - system (@args) == 0 or exit 1; - } else { - print "Please install $sbo\n" and exit 0; - } +INSTALL_NEW: +exit 0 unless $install_new; +my $todo_install; +FIRST: for my $sbo (@ARGV) { + my $name = $compat32 ? "$sbo-compat32" : $sbo; + my $inst = get_installed_sbos; + my $inst_names = get_inst_names $inst;; + warn "$name already installed\n", next FIRST if $name ~~ @$inst_names; + # if compat32 is TRUE, we need to see if the non-compat version exists. + if ($compat32) { + my $inst = get_installed_sbos; + my $inst_names = get_inst_names $inst; + unless ($sbo ~~ @$inst_names) { + print "\nYou are attempting to install $name, however, $sbo is not"; + print " yet installed. Shall I install it first? [y] "; + if ( =~ /^[Yy\n]/) { + my @args = ('/usr/sbin/sboupgrade', '-oN', $sbo); + system (@args) == 0 or exit 1; + } else { + warn "Please install $sbo\n" and exit 0; } } - $has eq 'TRUE' ? warn "$name already installed.\n" : - push @todo_install, $sbo; } - @failed = process_sbos (@todo_install) if exists $todo_install[0]; - print_failures (); + $$todo_install{$sbo} = $locations{$sbo}; } +@failures = process_sbos $todo_install if keys %$todo_install > 0; +print_failures @failures; -exit 1 if exists $failed[0]; exit 0; diff --git a/t/SBO/Lib.pm b/t/SBO/Lib.pm new file mode 100644 index 0000000..398e6a3 --- /dev/null +++ b/t/SBO/Lib.pm @@ -0,0 +1,668 @@ +#!/usr/bin/env perl +# +# vim: set ts=4:noet +# +# Lib.pm +# shared functions for the sbo_ scripts. +# +# author: Jacob Pipkin +# date: Setting Orange, the 37th day of Discord in the YOLD 3178 +# license: WTFPL + +use 5.16.0; +use warnings FATAL => 'all'; +use strict; + +package SBO::Lib 1.0; +my $version = "1.0"; + +require Exporter; +our @ISA = qw(Exporter); +our @EXPORT = qw(get_slack_version chk_slackbuilds_txt check_home rsync_sbo_tree get_sbo_from_loc get_sbo_version get_download_info get_arch get_sbo_downloads get_filename_from_link compute_md5sum compare_md5s verify_distfile get_distfile get_symlink_from_filename check_x32 check_multilib rewrite_slackbuild revert_slackbuild check_distfiles create_symlinks grok_temp_file get_src_dir get_pkg_name perform_sbo do_convertpkg + script_error + open_fh + open_read + show_version + slackbuilds_or_fetch + fetch_tree + update_tree + get_installed_sbos + get_available_updates + do_slackbuild + make_clean + make_distclean + do_upgradepkg + get_sbo_location + get_from_info + get_tmp_fn +); + +#$< == 0 or die "This script requires root privileges.\n"; + +use Tie::File; +use Sort::Versions; +use Digest::MD5; +use File::Copy; +use File::Path qw(make_path remove_tree); +use Fcntl; +use File::Find; +use File::Temp qw(tempdir tempfile); +use Data::Dumper; +use Fcntl qw(F_SETFD F_GETFD); + +our $tempdir = tempdir (CLEANUP => 1); + +# subroutine for throwing internal script errors +sub script_error (;$) { + exists $_[0] ? die "A fatal script error has occured:\n$_[0]\nExiting.\n" + : die "A fatal script error has occured. Exiting.\n"; +} + +# sub for opening files, second arg is like '<','>', etc +sub open_fh ($$) { + exists $_[1] or script_error 'open_fh requires two arguments'; + -f $_[0] or script_error 'open_fh first argument not a file'; + my ($file, $op) = @_; + open my $fh, $op, $file or die "Unable to open $file.\n"; + return $fh; +} + +sub open_read ($) { + return open_fh shift, '<'; +} + +# pull in configuration, set sane defaults, etc. +our $conf_dir = '/etc/sbotools'; +our $conf_file = "$conf_dir/sbotools.conf"; +our %config = ( + NOCLEAN => 'FALSE', + DISTCLEAN => 'FALSE', + JOBS => 'FALSE', + PKG_DIR => 'FALSE', + SBO_HOME => 'FALSE', +); + +# if the conf file exists, pull all the $key=$value pairs into a hash +my %conf_values; +if (-f $conf_file) { + my $fh = open_read $conf_file; + my $text = do {local $/; <$fh>}; + %conf_values = $text =~ /^(\w+)=(.*)$/mg; + close $fh; +} + +for my $key (keys %config) { + $config{$key} = $conf_values{$key} if exists $conf_values{$key}; +} +$config{JOBS} = 'FALSE' unless $config{JOBS} =~ /^\d+$/; +$config{SBO_HOME} = '/usr/sbo' if $config{SBO_HOME} eq 'FALSE'; + +# some stuff we'll need later. +my $distfiles = "$config{SBO_HOME}/distfiles"; +my $slackbuilds_txt = "$config{SBO_HOME}/SLACKBUILDS.TXT"; +my $name_regex = '\ASLACKBUILD\s+NAME:\s+'; + +sub show_version () { + say "sbotools version $version"; + say 'licensed under the WTFPL'; + say ''; +} + +# %supported maps what's in /etc/slackware-version to what's at SBo +# which is now not needed since this version drops support < 14.0 +# but it's already future-proofed, so leave it. +sub get_slack_version () { + my %supported = ('14.0' => '14.0'); + my $fh = open_read '/etc/slackware-version'; + chomp (my $line = <$fh>); + close $fh; + my $version = ($line =~ /\s+(\d+[^\s]+)$/)[0]; + die "Unsupported Slackware version: $version\n" + unless $version ~~ %supported; + return $supported{$version}; +} + +# does the SLACKBUILDS.TXT file exist in the sbo tree? +sub chk_slackbuilds_txt () { + return -f $slackbuilds_txt ? 1 : 0; +} + +# check for the validity of new $config{SBO_HOME} +sub check_home () { + my $sbo_home = $config{SBO_HOME}; + if (-d $sbo_home) { + opendir (my $home_handle, $sbo_home); + FIRST: while (readdir $home_handle) { + next FIRST if /^\.[\.]{0,1}$/; + die "$sbo_home exists and is not empty. Exiting.\n"; + } + } else { + make_path ($sbo_home) or die "Unable to create $sbo_home.\n"; + } +} + +# rsync the sbo tree from slackbuilds.org to $config{SBO_HOME} +sub rsync_sbo_tree () { + my $slk_version = get_slack_version; + my @arg = ('rsync', '-a', '--exclude=*.tar.gz', '--exclude=*.tar.gz.asc'); + push @arg, "rsync://slackbuilds.org/slackbuilds/$slk_version/*"; + my $out = system @arg, $config{SBO_HOME}; + say 'Finished.' and return $out; +} + +# wrappers for differing checks and output +sub fetch_tree () { + check_home; + say 'Pulling SlackBuilds tree...'; + rsync_sbo_tree, return $?; +} + +sub update_tree () { + fetch_tree, return unless chk_slackbuilds_txt; + say 'Updating SlackBuilds tree...'; + rsync_sbo_tree, return $?; +} + +# if the SLACKBUILDS.TXT is not in $config{SBO_HOME}, we assume the tree has +# not been populated there; prompt the user to automagickally pull the tree. +sub slackbuilds_or_fetch () { + unless (chk_slackbuilds_txt) { + say 'It looks like you haven\'t run "sbosnap fetch" yet.'; + print 'Would you like me to do this now? [y] '; + =~ /^[Yy\n]/ ? fetch_tree : + die "Please run \"sbosnap fetch\"\n"; + } + return 1; +} + +# pull an array of hashes, each hash containing the name and version of an sbo +# currently installed. +sub get_installed_sbos () { + my @installed; + # $1 == name, $2 == version + my $regex = qr#/([^/]+)-([^-]+)-[^-]+-[^-]+$#; + for my $path () { + my ($name, $version) = ($path =~ $regex)[0,1]; + push @installed, {name => $name, version => $version}; + } + return \@installed; +} + +# search the SLACKBUILDS.TXT for a given sbo's directory +sub get_sbo_location ($) { + exists $_[0] or script_error 'get_sbo_location requires an argument.'; + my $sbo = shift; + my $regex = qr#LOCATION:\s+\.(/[^/]+/$sbo)$#; + my $fh = open_read $slackbuilds_txt; + while (my $line = <$fh>) { + if (my $loc = ($line =~ $regex)[0]) { + return "$config{SBO_HOME}$loc"; + } + } + return; +} + +# pull the sbo name from a $location: $config{SBO_HOME}/system/wine, etc. +sub get_sbo_from_loc ($) { + exists $_[0] or script_error 'get_sbo_from_loc requires an argument.'; + return (shift =~ qr#/([^/]+)$#)[0]; +} + +# pull piece(s) of data, GET, from the $sbo.info file under LOCATION. +sub get_from_info (%) { + my %args = ( + LOCATION => '', + GET => '', + @_ + ); + unless ($args{LOCATION} && $args{GET}) { + script_error 'get_from_info requires LOCATION and GET.'; + } + state $vars = {PRGNAM => ['']}; + my $sbo = get_sbo_from_loc $args{LOCATION}; + return $$vars{$args{GET}} if $$vars{PRGNAM}[0] eq $sbo; + # if we're here, we haven't read in the .info file yet. + my $fh = open_read "$args{LOCATION}/$sbo.info"; + # suck it all in, clean it all up, stuff it all in $vars. + my $contents = do {local $/; <$fh>}; + $contents =~ s/("|\\\n)//g; + $vars = {$contents =~ /^(\w+)=(.*)$/mg}; + # fill the hash with array refs - even for single values, + # since consistency here is a lot easier than sorting it out later + for my $key (keys %$vars) { + if ($$vars{$key} =~ /\s/) { + my @array = split ' ', $$vars{$key}; + $$vars{$key} = \@array; + } else { + $$vars{$key} = [$$vars{$key}]; + } + } + return exists $$vars{$args{GET}} ? $$vars{$args{GET}} : 0; +} + +# find the version in the tree for a given sbo (provided a location) +sub get_sbo_version ($) { + exists $_[0] or script_error 'get_sbo_version requires an argument.'; + my $version = get_from_info (LOCATION => shift, GET => 'VERSION'); + return $$version[0] ? $$version[0] : 0; +} + +# for each installed sbo, find out whether or not the version in the tree is +# newer, and compile an array of hashes containing those which are +sub get_available_updates () { + my @updates; + my $pkg_list = get_installed_sbos; + FIRST: for my $key (keys @$pkg_list) { + my $location = get_sbo_location $$pkg_list[$key]{name}; + # if we can't find a location, assume invalid and skip + next FIRST unless defined $location; + my $version = get_sbo_version $location; + if (versioncmp ($version, $$pkg_list[$key]{version}) == 1) { + push @updates, { + name => $$pkg_list[$key]{name}, + installed => $$pkg_list[$key]{version}, + update => $version + }; + } + } + return \@updates; +} + +# get downloads and md5sums from an sbo's .info file, first +# checking for x86_64-specific info if we are told to +sub get_download_info (%) { + my %args = ( + LOCATION => 0, + X64 => 1, + @_ + ); + $args{LOCATION} or script_error 'get_download_info requires LOCATION.'; + my ($get, $downs, $md5s, %return); + $get = ($args{X64} ? 'DOWNLOAD_x86_64' : 'DOWNLOAD'); + $downs = get_from_info (LOCATION => $args{LOCATION}, GET => $get); + # did we get nothing back, or UNSUPPORTED/UNTESTED? + if ($args{X64}) { + my $nothing; + if (! $$downs[0]) { + $nothing = 1; + } elsif ($$downs[0] =~ qr/^UN(SUPPOR|TES)TED$/) { + $nothing = 1; + } + if ($nothing) { + $args{X64} = 0; + $downs = get_from_info (LOCATION => $args{LOCATION}, + GET => 'DOWNLOAD'); + } + } + # if we still don't have any links, something is really wrong. + return unless $$downs[0]; + # grab the md5s and build a hash + $get = $args{X64} ? 'MD5SUM_x86_64' : 'MD5SUM'; + $md5s = get_from_info (LOCATION => $args{LOCATION}, GET => $get); + return unless $$md5s[0]; + $return{$$downs[$_]} = $$md5s[$_] for (keys @$downs); + return %return; +} + +sub get_arch () { + chomp (my $arch = `uname -m`); + return $arch; +} + +# TODO: should probably combine this with get_download_info +sub get_sbo_downloads (%) { + my %args = ( + LOCATION => '', + 32 => 0, + @_ + ); + $args{LOCATION} or script_error 'get_sbo_downloads requires LOCATION.'; + my $location = $args{LOCATION}; + -d $location or script_error 'get_sbo_downloads given a non-directory.'; + my $arch = get_arch; + my %dl_info; + if ($arch eq 'x86_64') { + %dl_info = get_download_info (LOCATION => $location) unless $args{32}; + } + unless (keys %dl_info > 0) { + %dl_info = get_download_info (LOCATION => $location, X64 => 0); + } + return %dl_info; +} + +# given a link, grab the filename from the end of it +sub get_filename_from_link ($) { + exists $_[0] or script_error 'get_filename_from_link requires an argument'; + return "$distfiles/". (shift =~ qr#/([^/]+)$#)[0]; +} + +# for a given file, computer its md5sum +sub compute_md5sum ($) { + -f $_[0] or script_error 'compute_md5sum requires a file argument.'; + my $fh = open_read shift; + my $md5 = Digest::MD5->new; + $md5->addfile ($fh); + my $md5sum = $md5->hexdigest; + close $fh; + return $md5sum; +} + +sub compare_md5s ($$) { + exists $_[1] or script_error 'compare_md5s requires two arguments.'; + my ($first, $second) = @_; + return $first eq $second ? 1 : 0; +} + +# for a given distfile, see whether or not it exists, and if so, if its md5sum +# matches the sbo's .info file +sub verify_distfile ($$) { + exists $_[1] or script_error 'check_distfile requires two arguments.'; + my ($link, $info_md5sum) = @_; + my $filename = get_filename_from_link $link; + return unless -d $distfiles; + return unless -f $filename; + my $md5sum = compute_md5sum $filename; + return compare_md5s $info_md5sum, $md5sum; +} + +# for a given distfile, attempt to retrieve it and, if successful, check its +# md5sum against that in the sbo's .info file +sub get_distfile ($$) { + exists $_[1] or script_error 'get_distfile requires an argument'; + my ($link, $exp_md5) = @_; + my $filename = get_filename_from_link $link; + mkdir $distfiles unless -d $distfiles; + chdir $distfiles; + system ("wget --no-check-certificate $link") == 0 or + die "Unable to wget $link\n"; + my $md5sum = compute_md5sum $filename; + # can't do anything if the link in the .info doesn't lead to a good d/l + compare_md5s $md5sum, $exp_md5 or die "md5sum failure for $filename.\n"; + return 1; +} + +# for a given distfile, figure out what the full path to its symlink will be +sub get_symlink_from_filename ($$) { + exists $_[1] or script_error + 'get_symlink_from_filename requires two arguments'; + -f $_[0] or script_error + 'get_symlink_from_filename first argument is not a file'; + my ($filename, $location) = @_; + return "$location/". ($filename =~ qr#/([^/]+)$#)[0]; +} + +# determine whether or not a given sbo is 32-bit only +sub check_x32 ($) { + exists $_[0] or script_error 'check_x32 requires an argument.'; + my $dl = get_from_info (LOCATION => shift, GET => 'DOWNLOAD_x86_64'); + return $$dl[0] =~ /UN(SUPPOR|TES)TED/ ? 1 : 0; +} + +# can't do 32-bit on x86_64 without this file, so we'll use it as the test to +# to determine whether or not an x86_64 system is setup for multilib +sub check_multilib () { + return 1 if -f '/etc/profile.d/32dev.sh'; + return; +} + +# make a backup of the existent SlackBuild, and rewrite the original as needed +sub rewrite_slackbuild ($$%) { + exists $_[1] or script_error 'rewrite_slackbuild requires two arguments.'; + my ($slackbuild, $tempfn, %changes) = @_; + copy ($slackbuild, "$slackbuild.orig") or + die "Unable to backup $slackbuild to $slackbuild.orig\n"; + my $tar_regex = qr/(un|)tar .*$/; + my $makepkg_regex = qr/makepkg/; + my $libdir_regex = qr/^\s*LIBDIRSUFFIX="64"\s*$/; + my $make_regex = qr/^\s*make(| \Q||\E exit 1)$/; + my $arch_regex = qr/\$VERSION-\$ARCH-\$BUILD/; + # tie the slackbuild, because this is the easiest way to handle this. + tie my @sb_file, 'Tie::File', $slackbuild; + for my $line (@sb_file) { + # get the output of the tar and makepkg commands. hope like hell that v + # is specified among tar's arguments + if ($line =~ $tar_regex || $line =~ $makepkg_regex) { + $line = "$line | tee -a $tempfn"; + } + # then check for and apply any other %changes + if (exists $changes{libdirsuffix}) { + $line =~ s/64/$changes{libdirsuffix}/ if $line =~ $libdir_regex; + } + if (exists $changes{make}) { + $line =~ s/make/make $changes{make}/ if $line =~ $make_regex; + } + if (exists $changes{arch_out}) { + $line =~ s/\$ARCH/$changes{arch_out}/ if $line =~ $arch_regex; + } + } + untie @sb_file; + return 1; +} + +# move a backed-up .SlackBuild file back into place +sub revert_slackbuild ($) { + exists $_[0] or script_error 'revert_slackbuild requires an argument'; + my $slackbuild = shift; + if (-f "$slackbuild.orig") { + unlink $slackbuild if -f $slackbuild; + rename ("$slackbuild.orig", $slackbuild); + } + return 1; +} + +# for each $download, see if we have it, and if the copy we have is good, +# otherwise download a new copy +sub check_distfiles (%) { + exists $_[0] or script_error 'check_distfiles requires an argument.'; + my %dists = @_; + for my $link (keys %dists) { + my $md5sum = $dists{$link}; + unless (verify_distfile $link, $md5sum) { + die unless get_distfile $link, $md5sum; + } + } + return 1; +} + +# given a location and a list of download links, assemble a list of symlinks, +# and create them. +sub create_symlinks ($%) { + exists $_[1] or script_error 'create_symlinks requires two arguments.'; + my ($location, %downloads) = @_; + my @symlinks; + for my $link (keys %downloads) { + my $filename = get_filename_from_link $link; + my $symlink = get_symlink_from_filename $filename, $location; + push @symlinks, $symlink; + symlink $filename, $symlink; + } + return @symlinks; +} + +# pull the untarred source directory or created package name from the temp +# file (the one we tee'd to) +sub grok_temp_file (%) { + my %args = ( + FH => '', + REGEX => '', + CAPTURE => 0, + @_ + ); + unless ($args{FH} && $args{REGEX}) { + script_error 'grok_temp_file requires two arguments'; + } + my $fh = $args{FH}; + seek $fh, 0, 0; + my $out; + FIRST: while (my $line = <$fh>) { + if ($line =~ $args{REGEX}) { + $out = ($line =~ $args{REGEX})[$args{CAPTURE}]; + last FIRST; + } + } +# close $fh; + return $out; +} + +# wrappers around grok_temp_file +sub get_src_dir ($) { + exists $_[0] or script_error 'get_src_dir requires an argument'; + return grok_temp_file (FH => shift, REGEX => qr#^([^/]+)/#); +} + +sub get_pkg_name ($) { + exists $_[0] or script_error 'get_pkg_name requires an argument'; + return grok_temp_file (FH => shift, + REGEX => qr/^Slackware\s+package\s+([^\s]+)\s+created\.$/); +} + +sub get_tmp_fn ($) { + exists $_[0] or script_error 'get_tmp_fn requires an argument.'; + my $fh = shift; + fcntl ($fh, F_SETFD, 0) or die "no unset exec-close thingy\n"; + return "/dev/fd/". fileno $fh; +} + +# prep and run .SlackBuild +sub perform_sbo (%) { + my %args = ( + OPTS => 0, + JOBS => 0, + LOCATION => '', + ARCH => '', + C32 => 0, + X32 => 0, + @_ + ); + unless ($args{LOCATION} && $args{ARCH}) { + script_error 'perform_sbo requires LOCATION and ARCH.'; + } + my $location = $args{LOCATION}; + my $sbo = get_sbo_from_loc $location; + my ($cmd, %changes); + # figure out any changes we need to make to the .SlackBuild + $changes{make} = "-j $args{JOBS}" if $args{JOBS}; + if ($args{ARCH} eq 'x86_64' and ($args{C32} || $args{X32})) { + if ($args{C32}) { + $changes{libdirsuffix} = ''; + } elsif ($args{X32}) { + $changes{arch_out} = 'i486'; + } + $cmd = ". /etc/profile.d/32dev.sh &&"; + } + $cmd .= "/bin/sh $location/$sbo.SlackBuild"; + $cmd = "$args{OPTS} $cmd" if $args{OPTS}; + my $tempfh = tempfile (DIR => $tempdir); + my $fn = get_tmp_fn $tempfh; + rewrite_slackbuild "$location/$sbo.SlackBuild", $fn, %changes; + chdir $location, my $out = system $cmd; + revert_slackbuild "$location/$sbo.SlackBuild"; + die unless $out == 0; + my $pkg = get_pkg_name $tempfh; + my $src = get_src_dir $tempfh; + return $pkg, $src; +} + +# run convertpkg on a package to turn it into a -compat32 thing +sub do_convertpkg ($) { + exists $_[0] or script_error 'do_convertpkg requires an argument.'; + my $pkg = shift; + my $tempfh = tempfile (DIR => $tempdir); + my $fn = get_tmp_fn $tempfh; + my $cmd = "/usr/sbin/convertpkg-compat32 -i $pkg -d /tmp | tee $fn"; + system ($cmd) == 0 or die; + unlink $pkg; + return get_pkg_name $tempfh; +} + +# "public interface", sort of thing. +sub do_slackbuild (%) { + my %args = ( + OPTS => 0, + JOBS => 0, + LOCATION => '', + COMPAT32 => 0, + @_ + ); + $args{LOCATION} or script_error 'do_slackbuild requires LOCATION.'; + my $location = $args{LOCATION}; + my $sbo = get_sbo_from_loc $location; + my $arch = get_arch; + my $multi = check_multilib; + my $version = get_sbo_version $location; + my $x32; + # ensure x32 stuff is set correctly, or that we're setup for it + if ($args{COMPAT32}) { + die "compat32 only works on x86_64.\n" unless $arch eq 'x86_64'; + die "compat32 requires multilib.\n" unless $multi; + die "compat32 requires /usr/sbin/convertpkg-compat32.\n" + unless -f '/usr/sbin/convertpkg-compat32'; + } else { + if ($arch eq 'x86_64') { + $x32 = check_x32 $args{LOCATION}; + if ($x32 && ! $multi) { + die "$sbo is 32-bit which requires multilib on x86_64.\n"; + } + } + } + # get a hash of downloads and md5sums, ensure we have 'em, symlink 'em + my %downloads = get_sbo_downloads ( + LOCATION => $location, + 32 => $args{COMPAT32} + ); + check_distfiles %downloads; + my @symlinks = create_symlinks $args{LOCATION}, %downloads; + # setup and run the .SlackBuild itself + my ($pkg, $src) = perform_sbo ( + OPTS => $args{OPTS}, + JOBS => $args{JOBS}, + LOCATION => $location, + ARCH => $arch, + C32 => $args{COMPAT32}, + X32 => $x32, + ); + do_convertpkg $pkg if $args{COMPAT32}; + unlink $_ for @symlinks; + return $version, $pkg, $src; +} + +# remove work directories (source and packaging dirs under /tmp/SBo) +sub make_clean ($$$) { + exists $_[2] or script_error 'make_clean requires three arguments.'; + my ($sbo, $src, $version) = @_; + say "Cleaning for $sbo-$version..."; + my $tmpsbo = "/tmp/SBo"; + remove_tree ("$tmpsbo/$src") if -d "$tmpsbo/$src"; + remove_tree ("$tmpsbo/package-$sbo") if -d "$tmpsbo/package-$sbo"; + return 1; +} + +# remove distfiles +sub make_distclean (%) { + my %args = ( + SRC => '', + VERSION => '', + LOCATION => '', + @_ + ); + unless ($args{SRC} && $args{VERSION} && $args{LOCATION}) { + script_error 'make_distclean requires four arguments.'; + } + my $sbo = get_sbo_from_loc $args{LOCATION}; + make_clean $sbo, $args{SRC}, $args{VERSION}; + say "Distcleaning for $sbo-$args{VERSION}..."; + # remove any distfiles for this particular SBo. + my %downloads = get_sbo_downloads (LOCATION => $args{LOCATION}); + for my $key (keys %downloads) { + my $filename = get_filename_from_link $key; + unlink $filename if -f $filename; + } + return 1; +} + +# run upgradepkg for a created package +sub do_upgradepkg ($) { + exists $_[0] or script_error 'do_upgradepkg requires an argument.'; + system ('/sbin/upgradepkg', '--reinstall', '--install-new', shift); + return 1; +} diff --git a/t/SBO/Lib.pm~ b/t/SBO/Lib.pm~ new file mode 100644 index 0000000..be29986 --- /dev/null +++ b/t/SBO/Lib.pm~ @@ -0,0 +1,643 @@ +#!/usr/bin/env perl +# +# vim: set ts=4:noet +# +# Lib.pm +# shared functions for the sbo_ scripts. +# +# author: Jacob Pipkin +# date: Setting Orange, the 37th day of Discord in the YOLD 3178 +# license: WTFPL + +use 5.16.0; +use warnings FATAL => 'all'; +use strict; + +package SBO::Lib 1.0; +my $version = "1.0"; + +require Exporter; +our @ISA = qw(Exporter); +our @EXPORT = qw(get_slack_version chk_slackbuilds_txt check_home rsync_sbo_tree get_sbo_from_loc get_sbo_version get_download_info get_arch get_sbo_downloads get_filename_from_link compute_md5sum compare_md5s check_distfile get_distfile get_symlink_from_filename check_x32 check_multilib rewrite_slackbuild revert_slackbuild create_symlinks grok_temp_file get_src_dir get_pkg_name perform_sbo + script_error + open_fh + open_read + show_version + slackbuilds_or_fetch + fetch_tree + update_tree + get_installed_sbos + get_available_updates + do_slackbuild + make_clean + make_distclean + do_upgradepkg + get_sbo_location + get_from_info +); + +#$< == 0 or die "This script requires root privileges.\n"; + +use Tie::File; +use Sort::Versions; +use Digest::MD5; +use File::Copy; +use File::Path qw(make_path remove_tree); +use Fcntl; +use File::Find; +use File::Temp qw(tempdir tempfile); +use Data::Dumper; + +our $tempdir = tempdir (CLEANUP => 1); + +# subroutine for throwing internal script errors +sub script_error (;$) { + exists $_[0] ? die "A fatal script error has occured:\n$_[0]\nExiting.\n" + : die "A fatal script error has occured. Exiting.\n"; +} + +# sub for opening files, second arg is like '<','>', etc +sub open_fh ($$) { + exists $_[1] or script_error 'open_fh requires two arguments'; + -f $_[0] or script_error 'open_fh first argument not a file'; + my ($file, $op) = @_; + open my $fh, $op, $file or die "Unable to open $file.\n"; + return $fh; +} + +sub open_read ($) { + return open_fh shift, '<'; +} + +# pull in configuration, set sane defaults, etc. +our $conf_dir = '/etc/sbotools'; +our $conf_file = "$conf_dir/sbotools.conf"; +our %config = ( + NOCLEAN => 'FALSE', + DISTCLEAN => 'FALSE', + JOBS => 'FALSE', + PKG_DIR => 'FALSE', + SBO_HOME => 'FALSE', +); + +# if the conf file exists, pull all the $key=$value pairs into a hash +my %conf_values; +if (-f $conf_file) { + my $fh = open_read $conf_file; + my $text = do {local $/; <$fh>}; + %conf_values = $text =~ /^(\w+)=(.*)$/mg; + close $fh; +} + +for my $key (keys %config) { + $config{$key} = $conf_values{$key} if exists $conf_values{$key}; +} +$config{JOBS} = 'FALSE' unless $config{JOBS} =~ /^\d+$/; +$config{SBO_HOME} = '/usr/sbo' if $config{SBO_HOME} eq 'FALSE'; + +# some stuff we'll need later. +my $distfiles = "$config{SBO_HOME}/distfiles"; +my $slackbuilds_txt = "$config{SBO_HOME}/SLACKBUILDS.TXT"; +my $name_regex = '\ASLACKBUILD\s+NAME:\s+'; + +sub show_version () { + print "sbotools version $version\n"; + print "licensed under the WTFPL\n"; + print "\n"; +} + +# %supported maps what's in /etc/slackware-version to what's at SBo +# which is now not needed since this version drops support < 14.0 +# but it's already future-proofed, so leave it. +sub get_slack_version () { + my %supported = ('14.0' => '14.0'); + my $fh = open_read '/etc/slackware-version'; + chomp (my $line = <$fh>); + close $fh; + my $version = ($line =~ /\s+(\d+[^\s]+)$/)[0]; + die "Unsupported Slackware version: $version\n" + unless $version ~~ %supported; + return $supported{$version}; +} + +# does the SLACKBUILDS.TXT file exist in the sbo tree? +sub chk_slackbuilds_txt () { + return -f $slackbuilds_txt ? 1 : 0; +} + +# check for the validity of new $config{SBO_HOME} +sub check_home () { + my $sbo_home = $config{SBO_HOME}; + if (-d $sbo_home) { + opendir (my $home_handle, $sbo_home); + FIRST: while (readdir $home_handle) { + next FIRST if /^\.[\.]{0,1}$/; + die "$sbo_home exists and is not empty. Exiting.\n"; + } + } else { + make_path ($sbo_home) or die "Unable to create $sbo_home.\n"; + } +} + +# rsync the sbo tree from slackbuilds.org to $config{SBO_HOME} +sub rsync_sbo_tree () { + my $slk_version = get_slack_version; + my @arg = ('rsync', '-a', '--exclude=*.tar.gz', '--exclude=*.tar.gz.asc'); + push @arg, "rsync://slackbuilds.org/slackbuilds/$slk_version/*"; + my $out = system @arg, $config{SBO_HOME}; + print "Finished.\n" and return $out; +} + +# wrappers for differing checks and output +sub fetch_tree () { + check_home; + print "Pulling SlackBuilds tree...\n"; + rsync_sbo_tree, return $?; +} + +sub update_tree () { + fetch_tree, return unless chk_slackbuilds_txt; + print "Updating SlackBuilds tree...\n"; + rsync_sbo_tree, return $?; +} + +# if the SLACKBUILDS.TXT is not in $config{SBO_HOME}, we assume the tree has +# not been populated there; prompt the user to automagickally pull the tree. +sub slackbuilds_or_fetch () { + unless (chk_slackbuilds_txt) { + print "It looks like you haven't run \"sbosnap fetch\" yet.\n"; + print "Would you like me to do this now? [y] "; + =~ /^[Yy\n]/ ? fetch_tree : + die "Please run \"sbosnap fetch\"\n"; + } + return 1; +} + +# pull an array of hashes, each hash containing the name and version of an sbo +# currently installed. +sub get_installed_sbos () { + my @installed; + # $1 == name, $2 == version + my $regex = qr#/([^/]+)-([^-]+)-[^-]+-[^-]+$#; + for my $path () { + my ($name, $version) = ($path =~ $regex)[0,1]; + push @installed, {name => $name, version => $version}; + } + return \@installed; +} + +# search the SLACKBUILDS.TXT for a given sbo's directory +sub get_sbo_location ($) { + exists $_[0] or script_error 'get_sbo_location requires an argument.'; + my $sbo = shift; + my $regex = qr#LOCATION:\s+\.(/[^/]+/$sbo)$#; + my $fh = open_read $slackbuilds_txt; + while (my $line = <$fh>) { + if (my $loc = ($line =~ $regex)[0]) { + return "$config{SBO_HOME}$loc"; + } + } + return; +} + +# pull the sbo name from a $location: $config{SBO_HOME}/system/wine, etc. +sub get_sbo_from_loc ($) { + exists $_[0] or script_error 'get_sbo_from_loc requires an argument.'; + return (shift =~ qr#/([^/]+)$#)[0]; +} + +# pull piece(s) of data, GET, from the $sbo.info file under LOCATION. +sub get_from_info { + warn " * * * * * * * * * * in get_from_info sub * * * * * * * * * *\n"; + my %args = ( + LOCATION => '', + GET => '', + @_ + ); + unless ($args{LOCATION} && $args{GET}) { + script_error 'get_from_info requires LOCATION and GET.'; + } + state $vars = {PKGNAM => ['']}; + my $sbo = get_sbo_from_loc $args{LOCATION}; + print Dumper ($vars); + return $$vars{$args{GET}} if $$vars{PKGNAM}[0] eq $sbo; + # if we haven't read in the .info file yet, do so now. + warn " * * * * * * * * * * parsing $sbo.info file * * * * * * * * * *\n"; + my $fh = open_read "$args{LOCATION}/$sbo.info"; + # suck it all in and join up the \ lines... + my $contents = do {local $/; <$fh>}; + $contents =~ s/("|\\\n)//g; + my %tmp = $contents =~ /^(\w+)=(.*)$/mg; + $vars = \%tmp; + # fill the hash with array refs - even for single values, + # since consistency here is a lot easier than sorting it out later + for my $key (keys %$vars) { + if ($$vars{$key} =~ /\s/) { + my @array = split ' ', $$vars{$key}; + $$vars{$key} = \@array; + } else { + $$vars{$key} = [$$vars{$key}]; + } + } + return $$vars{$args{GET}}; +} + +# find the version in the tree for a given sbo (provided a location) +sub get_sbo_version ($) { + exists $_[0] or script_error 'get_sbo_version requires an argument.'; + my $version = get_from_info (LOCATION => shift, GET => 'VERSION'); + return $$version[0] ? $$version[0] : 0; +} + +# for each installed sbo, find out whether or not the version in the tree is +# newer, and compile an array of hashes containing those which are +sub get_available_updates () { + my @updates; + my $pkg_list = get_installed_sbos; + FIRST: for my $key (keys @$pkg_list) { + my $location = get_sbo_location $$pkg_list[$key]{name}; + # if we can't find a location, assume invalid and skip + next FIRST unless defined $location; + my $version = get_sbo_version $location; + if (versioncmp ($version, $$pkg_list[$key]{version}) == 1) { + push @updates, { + name => $$pkg_list[$key]{name}, + installed => $$pkg_list[$key]{version}, + update => $version + }; + } + } + return \@updates; +} + +# get downloads and md5sums from an sbo's .info file, first +# checking for x86_64-specific info if we are told to +sub get_download_info { + my %args = ( + LOCATION => 0, + X64 => 1, + @_ + ); + $args{LOCATION} or script_error 'get_download_info requires LOCATION.'; + my ($get, $downs, $md5s, %return); + $get = ($args{X64} ? 'DOWNLOAD_x86_64' : 'DOWNLOAD'); + $downs = get_from_info (LOCATION => $args{LOCATION}, GET => $get); + # did we get nothing back, or UNSUPPORTED/UNTESTED? + if ($args{X64}) { + my $nothing; + if (! $$downs[0]) { + $nothing = 1; + } elsif ($$downs[0] =~ qr/^UN(SUPPOR|TES)TED$/) { + $nothing = 1; + } + if ($nothing) { + $args{X64} = 0; + $downs = get_from_info (LOCATION => $args{LOCATION}, + GET => 'DOWNLOAD'); + } + } + # if we still don't have any links, something is really wrong. + return unless $$downs[0]; + # grab the md5s and build a hash + $get = $args{X64} ? 'MD5SUM_x86_64' : 'MD5SUM'; + $md5s = get_from_info (LOCATION => $args{LOCATION}, GET => $get); + return unless $$md5s[0]; + $return{$$downs[$_]} = $$md5s[$_] for (keys @$downs); + return %return; +} + +sub get_arch () { + chomp (my $arch = `uname -m`); + return $arch; +} + +# TODO: should probably combine this with get_download_info +sub get_sbo_downloads { + my %args = ( + LOCATION => '', + 32 => 0, + @_ + ); + $args{LOCATION} or script_error 'get_sbo_downloads requires LOCATION.'; + my $location = $args{LOCATION}; + -d $location or script_error 'get_sbo_downloads given a non-directory.'; + my $arch = get_arch; + my %dl_info; + if ($arch eq 'x86_64') { + %dl_info = get_download_info (LOCATION => $location) unless $args{32}; + } + unless (keys %dl_info > 0) { + %dl_info = get_download_info (LOCATION => $location, X64 => 0); + } + return %dl_info; +} + +# given a link, grab the filename from the end of it +sub get_filename_from_link ($) { + exists $_[0] or script_error 'get_filename_from_link requires an argument'; + return "$distfiles/". (shift =~ qr#/([^/]+)$#)[0]; +} + +# for a given file, computer its md5sum +sub compute_md5sum ($) { + -f $_[0] or script_error 'compute_md5sum requires a file argument.'; + my $fh = open_read shift; + my $md5 = Digest::MD5->new; + $md5->addfile ($fh); + my $md5sum = $md5->hexdigest; + close $fh; + return $md5sum; +} + +sub compare_md5s ($$) { + exists $_[1] or script_error 'compare_md5s requires two arguments.'; + my ($first, $second) = @_; + return $first eq $second ? 1 : 0; +} + +# for a given distfile, see whether or not it exists, and if so, if its md5sum +# matches the sbo's .info file +sub check_distfile ($$) { + exists $_[1] or script_error 'check_distfile requires two arguments.'; + my ($link, $info_md5sum) = @_; + my $filename = get_filename_from_link $link; + return unless -d $distfiles; + return unless -f $filename; + my $md5sum = compute_md5sum $filename; + return compare_md5s $info_md5sum, $md5sum; +} + +# for a given distfile, attempt to retrieve it and, if successful, check its +# md5sum against that in the sbo's .info file +sub get_distfile ($$) { + exists $_[1] or script_error 'get_distfile requires an argument'; + my ($link, $exp_md5) = @_; + my $filename = get_filename_from_link $link; + mkdir $distfiles unless -d $distfiles; + chdir $distfiles; + system ("wget --no-check-certificate $link") == 0 or + die "Unable to wget $link\n"; + my $md5sum = compute_md5sum $filename; + # can't do anything if the link in the .info doesn't lead to a good d/l + compare_md5s $md5sum, $exp_md5 or die "md5sum failure for $filename.\n"; + return 1; +} + +# for a given distfile, figure out what the full path to its symlink will be +sub get_symlink_from_filename ($$) { + exists $_[1] or script_error + 'get_symlink_from_filename requires two arguments'; + -f $_[0] or script_error + 'get_symlink_from_filename first argument is not a file'; + my ($filename, $location) = @_; + return "$location/". ($filename =~ qr#/([^/]+)$#)[0]; +} + +# determine whether or not a given sbo is 32-bit only +sub check_x32 ($) { + exists $_[0] or script_error 'check_x32 requires an argument.'; + my $dl = get_from_info (LOCATION => shift, GET => 'DOWNLOAD_x86_64'); + return $$dl[0] =~ /UN(SUPPOR|TES)TED/ ? 1 : 0; +} + +# can't do 32-bit on x86_64 without this file, so we'll use it as the test to +# to determine whether or not an x86_64 system is setup for multilib +sub check_multilib () { + return 1 if -f '/etc/profile.d/32dev.sh'; + return; +} + +# make a backup of the existent SlackBuild, and rewrite the original as needed +sub rewrite_slackbuild ($$%) { + exists $_[1] or script_error 'rewrite_slackbuild requires two arguments.'; + my ($slackbuild, $tempfn, %changes) = @_; + copy ($slackbuild, "$slackbuild.orig") or + die "Unable to backup $slackbuild to $slackbuild.orig\n"; + my $tar_regex = qr/(un|)tar .*$/; + my $makepkg_regex = qr/makepkg/; + my $libdir_regex = qr/^\s*LIBDIRSUFFIX="64"\s*$/; + my $make_regex = qr/^\s*make(| \Q||\E exit 1)$/; + my $arch_regex = qr/\$VERSION-\$ARCH-\$BUILD/; + # tie the slackbuild, because this is the easiest way to handle this. + tie my @sb_file, 'Tie::File', $slackbuild; + for my $line (@sb_file) { + # get the output of the tar and makepkg commands. hope like hell that v + # is specified among tar's arguments + if ($line =~ $tar_regex || $line =~ $makepkg_regex) { + $line = "$line | tee -a $tempfn"; + } + # then check for and apply any other %changes + if (exists $changes{libdirsuffix}) { + $line =~ s/64/$changes{libdirsuffix}/ if $line =~ $libdir_regex; + } + if (exists $changes{make}) { + $line =~ s/make/make $changes{make}/ if $line =~ $make_regex; + } + if (exists $changes{arch_out}) { + $line =~ s/\$ARCH/$changes{arch_out}/ if $line =~ $arch_regex; + } + } + untie @sb_file; + return 1; +} + +# move a backed-up .SlackBuild file back into place +sub revert_slackbuild ($) { + exists $_[0] or script_error 'revert_slackbuild requires an argument'; + my $slackbuild = shift; + if (-f "$slackbuild.orig") { + unlink $slackbuild if -f $slackbuild; + rename ("$slackbuild.orig", $slackbuild); + } + return 1; +} + +# given a location and a list of download links, assemble a list of symlinks, +# and create them. +sub create_symlinks ($%) { + exists $_[1] or script_error 'create_symlinks requires two arguments.'; + my ($location, %downloads) = @_; + my @symlinks; + for my $link (keys %downloads) { + my $md5sum = $downloads{$link}; + unless (check_distfile $link, $md5sum) { + die unless get_distfile $link, $md5sum; + } + my $filename = get_filename_from_link $link; + my $symlink = get_symlink_from_filename $filename, $location; + push @symlinks, $symlink; + symlink $filename, $symlink; + } + return @symlinks; +} + +# pull the untarred source directory or created package name from the temp +# file (the one we tee'd to) +sub grok_temp_file { + my %args = ( + TEMPFN => '', + REGEX => '', + CAPTURE => 0, + @_ + ); + unless ($args{TEMPFN} && $args{REGEX}) { + script_error 'grok_temp_file requires two arguments'; + } + my $out; + my $fh = open_read $args{TEMPFN}; + FIRST: while (my $line = <$fh>) { + if ($line =~ $args{REGEX}) { + $out = ($line =~ $args{REGEX})[$args{CAPTURE}]; + last FIRST; + } + } + close $fh; + return $out; +} + +# wrappers around grok_temp_file +sub get_src_dir ($) { + exists $_[0] or script_error 'get_src_dir requires an argument'; + return grok_temp_file (TEMPFN => shift, REGEX => qr#^([^/]+)/#); +} + +sub get_pkg_name ($) { + exists $_[0] or script_error 'get_pkg_name requires an argument'; + return grok_temp_file (TEMPFN => shift, + REGEX => qr/^Slackware\s+package\s+([^\s]+)\s+created\.$/); +} + +# prep and run .SlackBuild +sub perform_sbo { + my %args = ( + OPTS => 0, + JOBS => 0, + LOCATION => '', + ARCH => '', + C32 => 0, + X32 => 0, + @_ + ); + unless ($args{LOCATION} && $args{ARCH}) { + script_error 'perform_sbo requires LOCATION and ARCH.'; + } + my $location = $args{LOCATION}; + my $sbo = get_sbo_from_loc $location; + my ($cmd, %changes); + $changes{make} = "-j $args{JOBS}" if $args{JOBS}; + if ($args{ARCH} eq 'x86_64' and ($args{C32} || $args{X32}) ) { + if ($args{C32}) { + $changes{libdirsuffix} = ''; + } elsif ($args{X32}) { + $changes{arch_out} = 'i486'; + } + $cmd = ". /etc/profile.d/32dev.sh &&"; + } + $cmd .= "/bin/sh $location/$sbo.SlackBuild"; + $cmd = "$args{OPTS} $cmd" if $args{OPTS}; + my ($tempfh, $tempfn) = tempfile (DIR => $tempdir); + close $tempfh; + rewrite_slackbuild "$location/$sbo.SlackBuild", $tempfn, %changes; + chdir $location, my $out = system $cmd; + revert_slackbuild "$location/$sbo.SlackBuild"; + die unless $out == 0; + my $src = get_src_dir $tempfn; + my $pkg = get_pkg_name $tempfn; + unlink $tempfn; + return $pkg, $src; +} + +# "public interface", sort of thing. +sub do_slackbuild { + my %args = ( + OPTS => 0, + JOBS => 0, + LOCATION => '', + COMPAT32 => 0, + @_ + ); + $args{LOCATION} or script_error 'do_slackbuild requires LOCATION.'; + my $location = $args{LOCATION}; + my $sbo = get_sbo_from_loc $location; + my $arch = get_arch; + my $multi = check_multilib; + my $version = get_sbo_version $location; + my $x32; + if ($args{COMPAT32}) { + die "compat32 only works on x86_64.\n" unless $arch eq 'x86_64'; + die "compat32 requires multilib.\n" unless $multi; + die "compat32 requires /usr/sbin/convertpkg-compat32.\n" + unless -f '/usr/sbin/convertpkg-compat32'; + } else { + if ($arch eq 'x86_64') { + $x32 = check_x32 $args{LOCATION}; + if ($x32 && ! $multi) { + die "$sbo is 32-bit which requires multilib on x86_64.\n"; + } + } + } + my %downloads = get_sbo_downloads ( + LOCATION => $location, + 32 => $args{COMPAT32} + ); + my @symlinks = create_symlinks $args{LOCATION}, %downloads; + my ($pkg, $src) = perform_sbo ( + OPTS => $args{OPTS}, + JOBS => $args{JOBS}, + LOCATION => $location, + ARCH => $arch, + C32 => $args{COMPAT32}, + X32 => $x32, + ); + if ($args{COMPAT32}) { + my ($tempfh, $tempfn) = tempfile (DIR => $tempdir); + close $tempfh; + my $cmd = "/usr/sbin/convertpkg-compat32 -i $pkg -d /tmp | tee $tempfn"; + system ($cmd) == 0 or die; + unlink $pkg; + $pkg = get_pkg_name $tempfn; + } + unlink $_ for @symlinks; + return $version, $pkg, $src; +} + +# remove work directories (source and packaging dirs under /tmp/SBo) +sub make_clean ($$$) { + exists $_[2] or script_error 'make_clean requires three arguments.'; + my ($sbo, $src, $version) = @_; + print "Cleaning for $sbo-$version...\n"; + my $tmpsbo = "/tmp/SBo"; + remove_tree ("$tmpsbo/$src") if -d "$tmpsbo/$src"; + remove_tree ("$tmpsbo/package-$sbo") if -d "$tmpsbo/package-$sbo"; + return 1; +} + +# remove distfiles +sub make_distclean { + my %args = ( + SRC => '', + VERSION => '', + LOCATION => '', + @_ + ); + unless ($args{SRC} && $args{VERSION} && $args{LOCATION}) { + script_error 'make_distclean requires four arguments.'; + } + my $sbo = get_sbo_from_loc $args{LOCATION}; + make_clean $sbo, $args{SRC}, $args{VERSION}; + print "Distcleaning for $sbo-$args{VERSION}...\n"; + # remove any distfiles for this particular SBo. + my %downloads = get_sbo_downloads (LOCATION => $args{LOCATION}); + for my $key (keys %downloads) { + my $filename = get_filename_from_link $key; + unlink $filename if -f $filename; + } + return 1; +} + +# run upgradepkg for a created package +sub do_upgradepkg ($) { + exists $_[0] or script_error 'do_upgradepkg requires an argument.'; + system ('/sbin/upgradepkg', '--reinstall', '--install-new', shift); + return 1; +} diff --git a/t/do_tests.sh b/t/do_tests.sh new file mode 100755 index 0000000..54222db --- /dev/null +++ b/t/do_tests.sh @@ -0,0 +1,4 @@ +#!/usr/bin/env bash + +./prep.pl +./test.t diff --git a/t/prep.pl b/t/prep.pl new file mode 100755 index 0000000..e2fe9bf --- /dev/null +++ b/t/prep.pl @@ -0,0 +1,46 @@ +#!/usr/bin/perl + +use strict; +use warnings FATAL => 'all'; +use File::Copy; +use Tie::File; + +chomp (my $pwd = `pwd`); +mkdir "$pwd/SBO" unless -d "$pwd/SBO"; +copy ('/home/d4wnr4z0r/projects/sbotools/SBO-Lib/lib/SBO/Lib.pm', "$pwd/SBO"); +my @subs; +open my $file_h, '<', "$pwd/SBO/Lib.pm"; +my $regex = qr/^sub\s+([^\s]+)\s+/; +while (my $line = <$file_h>) { + if (my $sub = ($line =~ $regex)[0]) { + push @subs, $sub; + } +} + +seek $file_h, 0, 0; +my @not_exported; +FIRST: for my $sub (@subs) { + my $found = 'FALSE'; + my $has = 'FALSE'; + SECOND: while (my $line = <$file_h>) { + if ($found eq 'FALSE') { + $found = 'TRUE', next SECOND if $line =~ /\@EXPORT/; + } else { + last SECOND if $line =~ /^\);$/; + $has = 'TRUE', last SECOND if $line =~ /$sub/; + } + } + push @not_exported, $sub unless $has eq 'TRUE'; + seek $file_h, 0, 0; +} + +close $file_h; +tie my @file, 'Tie::File', "$pwd/SBO/Lib.pm"; +FIRST: for my $line (@file) { + if ($line =~ /\@EXPORT/) { + $line = "our \@EXPORT = qw(". join ' ', @not_exported; + } + $line = "#$line" if $line =~ /root privileges/; +} + + diff --git a/t/test.t b/t/test.t new file mode 100755 index 0000000..71eca1d --- /dev/null +++ b/t/test.t @@ -0,0 +1,95 @@ +#!/usr/bin/perl -I/home/d4wnr4z0r/projects/sbotools/t + +use 5.16.0; +use strict; +use warnings FATAL => 'all'; +use File::Temp qw(tempdir tempfile); +use Test::More tests => 39; +use SBO::Lib; + +ok (defined $SBO::Lib::tempdir, '$tempdir is defined'); + +my $fh = open_read ('/home/d4wnr4z0r/projects/sbotools/t/test.t'); +ok (ref ($fh) eq 'GLOB', 'open_read works'); +close $fh; + +ok ($SBO::Lib::config{DISTCLEAN} eq 'FALSE', 'config{DISTCLEAN} is good'); +ok ($SBO::Lib::config{JOBS} == 2, 'config{JOBS} is good'); +ok ($SBO::Lib::config{NOCLEAN} eq 'TRUE', 'config{NOCLEAN} is good'); +ok ($SBO::Lib::config{PKG_DIR} eq 'FALSE', 'config{PKG_DIR} is good'); +ok ($SBO::Lib::config{SBO_HOME} eq '/usr/sbo', 'config{SBO_HOME} is good'); + +ok (show_version == 1, 'show_version is good'); +ok (get_slack_version eq '14.0', 'get_slack_version is good'); +ok (chk_slackbuilds_txt == 1, 'check_slackbuilds_txt is good'); +#ok (rsync_sbo_tree == 1, 'rsync_sbo_tree is good'); +#ok (update_tree == 1, 'update_tree is good'); +ok (slackbuilds_or_fetch == 1, 'slackbuilds_or_fetch is good'); + +print "pseudo-random sampling of get_installed_sbos output...\n"; +my $installed = get_installed_sbos; +for my $key (keys @$installed) { + is ($$installed[$key]{version}, '1.13') if $$installed[$key]{name} eq 'OpenAL'; + is ($$installed[$key]{version}, '9.5.1_enu') if $$installed[$key]{name} eq 'adobe-reader'; + is ($$installed[$key]{version}, '4.1.3') if $$installed[$key]{name} eq 'libdvdnav'; + is ($$installed[$key]{version}, '0.8.8.4') if $$installed[$key]{name} eq 'libmodplug'; + is ($$installed[$key]{version}, '3.12.4') if $$installed[$key]{name} eq 'mozilla-nss'; + is ($$installed[$key]{version}, '2.5.0') if $$installed[$key]{name} eq 'zdoom'; +} +print "completed pseudo-random testing of get_installed_sbos \n"; + +is (get_sbo_location 'nginx', '/usr/sbo/network/nginx', 'get_sbo_location is good'); + +my $updates = get_available_updates; +for my $key (keys @$updates) { + is ($$updates[$key]{installed}, '1.15', '$$updates[$key]{installed} good for mutagen') if $$updates[$key]{name} eq 'mutagen'; + is ($$updates[$key]{update}, '1.20', '$$updates[$key]{update} good for mutagen') if $$updates[$key]{name} eq 'mutagen'; +} + +ok (get_arch eq 'x86_64', 'get_arch is good'); + +my %dl_info = get_download_info (LOCATION => '/usr/sbo/system/wine', X64 => 0); +my $link = 'http://downloads.sf.net/wine/source/1.4/wine-1.4.1.tar.bz2'; +is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', 'get_download_info test 01 good.'); +$link = 'http://www.unrealize.co.uk/source/dibeng-max-2010-11-12.zip'; +is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', 'get_download_info test 02 good.'); + +%dl_info = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine'); +$link = 'http://downloads.sf.net/wine/source/1.4/wine-1.4.1.tar.bz2'; +is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', 'get_sbo_downloads test 01 good.'); +$link = 'http://www.unrealize.co.uk/source/dibeng-max-2010-11-12.zip'; +is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', 'get_sbo_downloads test 02 good.'); + +my %downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/ifuse'); +$link = 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2'; +is ($downloads{$link}, '8d528a79de024b91f12f8ac67965c37c', 'get_sbo_downloads test 03 good.'); + +is (get_filename_from_link 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2', '/usr/sbo/distfiles/ifuse-1.1.1.tar.bz2', 'get_file_from_link good'); +is (compute_md5sum '/usr/sbo/distfiles//laptop-mode-tools_1.61.tar.gz', '6685af5dbb34c3d51ca27933b58f484e', 'compute_md5sum good'); +is ((verify_distfile '/usr/sbo/distfiles/laptop-mode-tools_1.61.tar.gz', '6685af5dbb34c3d51ca27933b58f484e'), 1, 'verify_distfile good'); +is (get_sbo_version '/usr/sbo/system/wine', '1.4.1', 'get_sbo_version good'); +is ((get_symlink_from_filename '/usr/sbo/distfiles/laptop-mode-tools_1.61.tar.gz', '/usr/sbo/system/laptop-mode-tools'), '/usr/sbo/system/laptop-mode-tools/laptop-mode-tools_1.61.tar.gz', 'get_symlink_from_filename good'); +ok (check_x32 '/usr/sbo/system/wine', 'check_x32 true for 32-bit only wine'); +ok (!(check_x32 '/usr/sbo/system/ifuse'), 'check_x32 false for not-32-bit-only ifuse'); +ok (check_multilib, 'check_multilib good'); + +# TODO: find a way to write a test for rewrite_slackbuild, revert_slackbuild. + +%downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine', 32 => 1); +my @symlinks = create_symlinks '/usr/sbo/system/wine', %downloads; +is ($symlinks[0], '/usr/sbo/system/wine/wine-1.4.1.tar.bz2', '$symlinks[0] good for create_symlinks'); +is ($symlinks[1], '/usr/sbo/system/wine/dibeng-max-2010-11-12.zip', '$symlinks[1] good for create_symlinks'); + +my $tempdir = tempdir (CLEANUP => 1); +my $tempfh = tempfile (DIR => $tempdir); +my $lmt = 'laptop-mode-tools_1.60'; +print {$tempfh} "$lmt/COPYING\n"; +print {$tempfh} "$lmt/Documentation/\n"; +print {$tempfh} "$lmt/README\n"; +print {$tempfh} "Slackware package skype-2.2.0.35-i486-1_SBo.tgz created.\n"; +#close $tempfh; +is (get_src_dir $tempfh, 'laptop-mode-tools_1.60', 'get_src_dir good'); +is (get_pkg_name $tempfh, 'skype-2.2.0.35-i486-1_SBo.tgz', 'get_pkg_name good'); +%downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine', 32 => 1); +is ((check_distfiles %downloads), 1, 'check_distfiles good'); +#is (do_convertpkg ($package), "$package-compat32", 'do_convertpkg good'); diff --git a/t/test.t~ b/t/test.t~ new file mode 100755 index 0000000..9b0a256 --- /dev/null +++ b/t/test.t~ @@ -0,0 +1,95 @@ +#!/usr/bin/perl -I/home/d4wnr4z0r/projects/sbotools/t + +use 5.16.0; +use strict; +use warnings FATAL => 'all'; +use File::Temp qw(tempdir tempfile); +use Test::More tests => 39; +use SBO::Lib; + +ok (defined $SBO::Lib::tempdir, '$tempdir is defined'); + +my $fh = open_read ('/home/d4wnr4z0r/projects/sbotools/t/test.t'); +ok (ref ($fh) eq 'GLOB', 'open_read works'); +close $fh; + +ok ($SBO::Lib::config{DISTCLEAN} eq 'FALSE', 'config{DISTCLEAN} is good'); +ok ($SBO::Lib::config{JOBS} == 2, 'config{JOBS} is good'); +ok ($SBO::Lib::config{NOCLEAN} eq 'TRUE', 'config{NOCLEAN} is good'); +ok ($SBO::Lib::config{PKG_DIR} eq 'FALSE', 'config{PKG_DIR} is good'); +ok ($SBO::Lib::config{SBO_HOME} eq '/usr/sbo', 'config{SBO_HOME} is good'); + +ok (show_version == 1, 'show_version is good'); +ok (get_slack_version eq '14.0', 'get_slack_version is good'); +ok (chk_slackbuilds_txt == 1, 'check_slackbuilds_txt is good'); +#ok (rsync_sbo_tree == 1, 'rsync_sbo_tree is good'); +#ok (update_tree == 1, 'update_tree is good'); +ok (slackbuilds_or_fetch == 1, 'slackbuilds_or_fetch is good'); + +print "pseudo-random sampling of get_installed_sbos output...\n"; +my $installed = get_installed_sbos; +for my $key (keys @$installed) { + is ($$installed[$key]{version}, '1.13') if $$installed[$key]{name} eq 'OpenAL'; + is ($$installed[$key]{version}, '9.5.1_enu') if $$installed[$key]{name} eq 'adobe-reader'; + is ($$installed[$key]{version}, '4.1.3') if $$installed[$key]{name} eq 'libdvdnav'; + is ($$installed[$key]{version}, '0.8.8.4') if $$installed[$key]{name} eq 'libmodplug'; + is ($$installed[$key]{version}, '3.12.4') if $$installed[$key]{name} eq 'mozilla-nss'; + is ($$installed[$key]{version}, '2.5.0') if $$installed[$key]{name} eq 'zdoom'; +} +print "completed pseudo-random testing of get_installed_sbos \n"; + +is (get_sbo_location 'nginx', '/usr/sbo/network/nginx', 'get_sbo_location is good'); + +my $updates = get_available_updates; +for my $key (keys @$updates) { + is ($$updates[$key]{installed}, '1.15', '$$updates[$key]{installed} good for mutagen') if $$updates[$key]{name} eq 'mutagen'; + is ($$updates[$key]{update}, '1.20', '$$updates[$key]{update} good for mutagen') if $$updates[$key]{name} eq 'mutagen'; +} + +ok (get_arch eq 'x86_64', 'get_arch is good'); + +my %dl_info = get_download_info (LOCATION => '/usr/sbo/system/wine', X64 => 0); +my $link = 'http://downloads.sf.net/wine/source/1.4/wine-1.4.1.tar.bz2'; +is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', 'get_download_info test 01 good.'); +$link = 'http://www.unrealize.co.uk/source/dibeng-max-2010-11-12.zip'; +is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', 'get_download_info test 02 good.'); + +%dl_info = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine'); +$link = 'http://downloads.sf.net/wine/source/1.4/wine-1.4.1.tar.bz2'; +is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', 'get_sbo_downloads test 01 good.'); +$link = 'http://www.unrealize.co.uk/source/dibeng-max-2010-11-12.zip'; +is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', 'get_sbo_downloads test 02 good.'); + +my %downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/ifuse'); +$link = 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2'; +is ($downloads{$link}, '8d528a79de024b91f12f8ac67965c37c', 'get_sbo_downloads test 03 good.'); + +is (get_filename_from_link 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2', '/usr/sbo/distfiles/ifuse-1.1.1.tar.bz2', 'get_file_from_link good'); +is (compute_md5sum '/usr/sbo/distfiles//laptop-mode-tools_1.61.tar.gz', '6685af5dbb34c3d51ca27933b58f484e', 'compute_md5sum good'); +is ((verify_distfile '/usr/sbo/distfiles/laptop-mode-tools_1.61.tar.gz', '6685af5dbb34c3d51ca27933b58f484e'), 1, 'verify_distfile good'); +is (get_sbo_version '/usr/sbo/system/wine', '1.4.1', 'get_sbo_version good'); +is ((get_symlink_from_filename '/usr/sbo/distfiles/laptop-mode-tools_1.61.tar.gz', '/usr/sbo/system/laptop-mode-tools'), '/usr/sbo/system/laptop-mode-tools/laptop-mode-tools_1.61.tar.gz', 'get_symlink_from_filename good'); +ok (check_x32 '/usr/sbo/system/wine', 'check_x32 true for 32-bit only wine'); +ok (!(check_x32 '/usr/sbo/system/ifuse'), 'check_x32 false for not-32-bit-only ifuse'); +ok (check_multilib, 'check_multilib good'); + +# TODO: find a way to write a test for rewrite_slackbuild, revert_slackbuild. + +%downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine', 32 => 1); +my @symlinks = create_symlinks '/usr/sbo/system/wine', %downloads; +is ($symlinks[0], '/usr/sbo/system/wine/wine-1.4.1.tar.bz2', '$symlinks[0] good for create_symlinks'); +is ($symlinks[1], '/usr/sbo/system/wine/dibeng-max-2010-11-12.zip', '$symlinks[1] good for create_symlinks'); + +my $tempdir = tempdir (CLEANUP => 1); +my $tempfh = tempfile (DIR => $tempdir); +my $lmt = 'laptop-mode-tools_1.60'; +print {$tempfh} "$lmt/COPYING\n"; +print {$tempfh} "$lmt/Documentation/\n"; +print {$tempfh} "$lmt/README\n"; +print {$tempfh} "Slackware package skype-2.2.0.35-i486-1_SBo.tgz created.\n"; +#close $tempfh; +is (get_src_dir $tempfh, 'laptop-mode-tools_1.60', 'get_src_dir good'); +is (get_pkg_name $tempfh, 'skype-2.2.0.35-i486-1_SBo.tgz', 'get_pkg_name good'); +%downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine', 32 => 1); +is (check_distfiles %downloads, 1, 'check_distfiles good'); +#is (do_convertpkg ($package), "$package-compat32", 'do_convertpkg good'); -- cgit v1.2.3 From dd031840dcb5d295b26b15ad7aac694b1d300072 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 30 Aug 2012 10:18:47 -0500 Subject: more enhancements and cleanups --- SBO-Lib/lib/SBO/Lib.pm | 12 +++++++----- sboupgrade | 26 +++++++++++--------------- 2 files changed, 18 insertions(+), 20 deletions(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 3db3133..8d3441b 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -48,7 +48,6 @@ use File::Path qw(make_path remove_tree); use Fcntl; use File::Find; use File::Temp qw(tempdir tempfile); -use Data::Dumper; use Fcntl qw(F_SETFD F_GETFD); our $tempdir = tempdir (CLEANUP => 1); @@ -157,13 +156,13 @@ sub rsync_sbo_tree () { sub fetch_tree () { check_home; say 'Pulling SlackBuilds tree...'; - rsync_sbo_tree, return $?; + rsync_sbo_tree, return 1; } sub update_tree () { fetch_tree, return unless chk_slackbuilds_txt; say 'Updating SlackBuilds tree...'; - rsync_sbo_tree, return $?; + rsync_sbo_tree, return 1; } # if the SLACKBUILDS.TXT is not in $config{SBO_HOME}, we assume the tree has @@ -448,7 +447,7 @@ sub revert_slackbuild ($) { my $slackbuild = shift; if (-f "$slackbuild.orig") { unlink $slackbuild if -f $slackbuild; - rename ("$slackbuild.orig", $slackbuild); + rename "$slackbuild.orig", $slackbuild; } return 1; } @@ -503,7 +502,6 @@ sub grok_temp_file (%) { last FIRST; } } -# close $fh; return $out; } @@ -519,6 +517,7 @@ sub get_pkg_name ($) { REGEX => qr/^Slackware\s+package\s+([^\s]+)\s+created\.$/); } +# clear the close-on-exec bit from a temp file handle sub clear_coe_bit ($) { exists $_[0] or script_error 'clear_coe_bit requires an argument'; my $fh = shift; @@ -526,12 +525,14 @@ sub clear_coe_bit ($) { return $fh; } +# return a filename from a temp fh for use externally sub get_tmp_extfn ($) { exists $_[0] or script_error 'get_tmp_extfn requires an argument.'; my $fh = clear_coe_bit shift; return '/dev/fd/'. fileno $fh; } +# return a filename from a temp fh for use internally sub get_tmp_perlfn ($) { exists $_[0] or script_error 'get_tmp_perlfn requires an argument.'; my $fh = clear_coe_bit shift; @@ -681,3 +682,4 @@ sub do_upgradepkg ($) { system ('/sbin/upgradepkg', '--reinstall', '--install-new', shift); return 1; } + diff --git a/sboupgrade b/sboupgrade index cf4468a..b5208e9 100755 --- a/sboupgrade +++ b/sboupgrade @@ -89,9 +89,7 @@ sub get_readme_path ($) { sub get_inst_names ($) { exists $_[0] or script_error 'get_inst_names requires an argument.'; my $inst = shift; - my $installed; - push @$installed, $$_{name} for @$inst; - return $installed; + return [$$_{name} for @$inst]; } # pull list of requirements, offer to install them @@ -184,13 +182,13 @@ sub readme_prompt ($$) { } # do the things with the provided sbos - whether upgrades or new installs. -sub process_sbos { +sub process_sbos ($) { exists $_[0] or script_error 'process_sbos requires an argument.'; my $todo = shift; my @failures; - FIRST: for my $sbo (keys %$todo) { + FIRST: for my $sbo (@$todo) { my $opts = 0; - $opts = readme_prompt $sbo, $$todo{$sbo} unless $no_readme; + $opts = readme_prompt $sbo, $locations{$sbo} unless $no_readme; # switch compat32 on if upgrading a -compat32 $compat32 = 1 if $sbo =~ /-compat32$/; my ($version, $pkg, $src); @@ -226,7 +224,7 @@ sub process_sbos { warn "$pkg left in /tmp\n"; } } elsif ($distclean eq 'TRUE') { - unlink ($pkg); + unlink $pkg; } } } @@ -255,18 +253,16 @@ my $todo_upgrade; # but without force, we only want to update what there are updates for unless ($force) { for my $sbo (@ARGV) { - $$todo_upgrade{$sbo} = $locations{$sbo} if $sbo ~~ @updates; + push $$todo_upgrades, $sbo if $sbo ~~ @updates; } } else { my $inst = get_installed_sbos; - my $inst_names= get_inst_names $inst;; + my $inst_names= get_inst_names $inst; FIRST: for my $sbo (@ARGV) { - if ($sbo ~~ @$inst_names) { - $$todo_upgrade{$sbo} = $locations{$sbo}; - } + push $todo_upgrade, $sbo if $sbo ~~ @$inst_names; } } -my @failures = process_sbos $todo_upgrade if keys %$todo_upgrade > 0; +my @failures = process_sbos $todo_upgrade if exists $todo_upgrade[0]; print_failures @failures; INSTALL_NEW: @@ -292,9 +288,9 @@ FIRST: for my $sbo (@ARGV) { } } } - $$todo_install{$sbo} = $locations{$sbo}; + push $todo_install, $sbo; } -@failures = process_sbos $todo_install if keys %$todo_install > 0; +@failures = process_sbos $todo_install if exists $todo_install[0]; print_failures @failures; exit 0; -- cgit v1.2.3 From 5ca399e0e9ab12063f15c4ab14443ba762877634 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 30 Aug 2012 14:03:49 -0500 Subject: bugfixes++ --- sboclean | 2 +- sboconfig | 2 +- sboupgrade | 5 ++++- 3 files changed, 6 insertions(+), 3 deletions(-) diff --git a/sboclean b/sboclean index 3154bd1..fd6f5c8 100755 --- a/sboclean +++ b/sboclean @@ -49,7 +49,7 @@ unless ($clean_dist || $clean_work) { sub remove_stuff ($) { exists $_[0] or script_error 'remove_stuff requires an argument'; - say "Nothing to do." and return 1 unless -d $_[0]; + -d $[0] or say "Nothing to do." and return 1; my $dir = shift; opendir (my $dh, $dir); FIRST: while (my $ls = readdir $dh) { diff --git a/sboconfig b/sboconfig index b5c1d6d..9c2682f 100755 --- a/sboconfig +++ b/sboconfig @@ -101,7 +101,7 @@ sub config_write ($$) { my $has = 0; my $regex = qr/\A\Q$key\E=/; FIRST: for my $tmpline (@temp) { - $has++, $tmpline = "$key=$val", last FIRST if $tmpline =~ $regex;; + $has++, $tmpline = "$key=$val", last FIRST if $tmpline =~ $regex; } untie @temp; # otherwise, append our new $key=$value pair diff --git a/sboupgrade b/sboupgrade index b5208e9..be2fc5a 100755 --- a/sboupgrade +++ b/sboupgrade @@ -63,6 +63,7 @@ if (exists $options{j}) { ($options{j} =~ /^\d+$/ || $options{j} eq 'FALSE'); } my $jobs = exists $options{j} ? $options{j} : $config{JOBS}; +$jobs = 0 if $jobs eq 'FALSE'; show_usage and exit 1 unless exists $ARGV[0]; @@ -89,7 +90,9 @@ sub get_readme_path ($) { sub get_inst_names ($) { exists $_[0] or script_error 'get_inst_names requires an argument.'; my $inst = shift; - return [$$_{name} for @$inst]; + my @installed; + push @installed, $$_{name} for @$inst; + return \@installed; } # pull list of requirements, offer to install them -- cgit v1.2.3 From f8c22cc9dd4828416555f0081c154a6adff9e80b Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 30 Aug 2012 14:13:18 -0500 Subject: um? --- t/SBO/Lib.pm | 43 ++++++++++++++++++--------- t/prep.pl | 2 +- t/test.t | 24 +++++++-------- t/test.t~ | 95 ------------------------------------------------------------ 4 files changed, 43 insertions(+), 121 deletions(-) delete mode 100755 t/test.t~ diff --git a/t/SBO/Lib.pm b/t/SBO/Lib.pm index 398e6a3..c2b9ef5 100644 --- a/t/SBO/Lib.pm +++ b/t/SBO/Lib.pm @@ -18,7 +18,7 @@ my $version = "1.0"; require Exporter; our @ISA = qw(Exporter); -our @EXPORT = qw(get_slack_version chk_slackbuilds_txt check_home rsync_sbo_tree get_sbo_from_loc get_sbo_version get_download_info get_arch get_sbo_downloads get_filename_from_link compute_md5sum compare_md5s verify_distfile get_distfile get_symlink_from_filename check_x32 check_multilib rewrite_slackbuild revert_slackbuild check_distfiles create_symlinks grok_temp_file get_src_dir get_pkg_name perform_sbo do_convertpkg +our @EXPORT = qw(get_slack_version chk_slackbuilds_txt check_home rsync_sbo_tree get_sbo_from_loc get_sbo_version get_download_info get_arch get_sbo_downloads get_filename_from_link compute_md5sum compare_md5s verify_distfile get_distfile get_symlink_from_filename check_x32 check_multilib rewrite_slackbuild revert_slackbuild check_distfiles create_symlinks grok_temp_file get_src_dir get_pkg_name clear_coe_bit perform_sbo do_convertpkg script_error open_fh open_read @@ -34,7 +34,8 @@ our @EXPORT = qw(get_slack_version chk_slackbuilds_txt check_home rsync_sbo_tree do_upgradepkg get_sbo_location get_from_info - get_tmp_fn + get_tmp_extfn + get_tmp_perlfn ); #$< == 0 or die "This script requires root privileges.\n"; @@ -47,7 +48,6 @@ use File::Path qw(make_path remove_tree); use Fcntl; use File::Find; use File::Temp qw(tempdir tempfile); -use Data::Dumper; use Fcntl qw(F_SETFD F_GETFD); our $tempdir = tempdir (CLEANUP => 1); @@ -61,7 +61,9 @@ sub script_error (;$) { # sub for opening files, second arg is like '<','>', etc sub open_fh ($$) { exists $_[1] or script_error 'open_fh requires two arguments'; - -f $_[0] or script_error 'open_fh first argument not a file'; + unless ($_[1] eq '>') { + -f $_[0] or script_error 'open_fh first argument not a file'; + } my ($file, $op) = @_; open my $fh, $op, $file or die "Unable to open $file.\n"; return $fh; @@ -154,13 +156,13 @@ sub rsync_sbo_tree () { sub fetch_tree () { check_home; say 'Pulling SlackBuilds tree...'; - rsync_sbo_tree, return $?; + rsync_sbo_tree, return 1; } sub update_tree () { fetch_tree, return unless chk_slackbuilds_txt; say 'Updating SlackBuilds tree...'; - rsync_sbo_tree, return $?; + rsync_sbo_tree, return 1; } # if the SLACKBUILDS.TXT is not in $config{SBO_HOME}, we assume the tree has @@ -445,7 +447,7 @@ sub revert_slackbuild ($) { my $slackbuild = shift; if (-f "$slackbuild.orig") { unlink $slackbuild if -f $slackbuild; - rename ("$slackbuild.orig", $slackbuild); + rename "$slackbuild.orig", $slackbuild; } return 1; } @@ -500,7 +502,6 @@ sub grok_temp_file (%) { last FIRST; } } -# close $fh; return $out; } @@ -516,11 +517,26 @@ sub get_pkg_name ($) { REGEX => qr/^Slackware\s+package\s+([^\s]+)\s+created\.$/); } -sub get_tmp_fn ($) { - exists $_[0] or script_error 'get_tmp_fn requires an argument.'; +# clear the close-on-exec bit from a temp file handle +sub clear_coe_bit ($) { + exists $_[0] or script_error 'clear_coe_bit requires an argument'; my $fh = shift; fcntl ($fh, F_SETFD, 0) or die "no unset exec-close thingy\n"; - return "/dev/fd/". fileno $fh; + return $fh; +} + +# return a filename from a temp fh for use externally +sub get_tmp_extfn ($) { + exists $_[0] or script_error 'get_tmp_extfn requires an argument.'; + my $fh = clear_coe_bit shift; + return '/dev/fd/'. fileno $fh; +} + +# return a filename from a temp fh for use internally +sub get_tmp_perlfn ($) { + exists $_[0] or script_error 'get_tmp_perlfn requires an argument.'; + my $fh = clear_coe_bit shift; + return '+<=&'. fileno $fh; } # prep and run .SlackBuild @@ -553,7 +569,7 @@ sub perform_sbo (%) { $cmd .= "/bin/sh $location/$sbo.SlackBuild"; $cmd = "$args{OPTS} $cmd" if $args{OPTS}; my $tempfh = tempfile (DIR => $tempdir); - my $fn = get_tmp_fn $tempfh; + my $fn = get_tmp_extfn $tempfh; rewrite_slackbuild "$location/$sbo.SlackBuild", $fn, %changes; chdir $location, my $out = system $cmd; revert_slackbuild "$location/$sbo.SlackBuild"; @@ -568,7 +584,7 @@ sub do_convertpkg ($) { exists $_[0] or script_error 'do_convertpkg requires an argument.'; my $pkg = shift; my $tempfh = tempfile (DIR => $tempdir); - my $fn = get_tmp_fn $tempfh; + my $fn = get_tmp_extfn $tempfh; my $cmd = "/usr/sbin/convertpkg-compat32 -i $pkg -d /tmp | tee $fn"; system ($cmd) == 0 or die; unlink $pkg; @@ -666,3 +682,4 @@ sub do_upgradepkg ($) { system ('/sbin/upgradepkg', '--reinstall', '--install-new', shift); return 1; } + diff --git a/t/prep.pl b/t/prep.pl index e2fe9bf..08efc61 100755 --- a/t/prep.pl +++ b/t/prep.pl @@ -7,7 +7,7 @@ use Tie::File; chomp (my $pwd = `pwd`); mkdir "$pwd/SBO" unless -d "$pwd/SBO"; -copy ('/home/d4wnr4z0r/projects/sbotools/SBO-Lib/lib/SBO/Lib.pm', "$pwd/SBO"); +copy ('/home/d4wnr4z0r/projects/slack14/sbotools/SBO-Lib/lib/SBO/Lib.pm', "$pwd/SBO"); my @subs; open my $file_h, '<', "$pwd/SBO/Lib.pm"; my $regex = qr/^sub\s+([^\s]+)\s+/; diff --git a/t/test.t b/t/test.t index 71eca1d..9ebd5fc 100755 --- a/t/test.t +++ b/t/test.t @@ -1,4 +1,4 @@ -#!/usr/bin/perl -I/home/d4wnr4z0r/projects/sbotools/t +#!/usr/bin/perl -I/home/d4wnr4z0r/projects/slack14/sbotools/t use 5.16.0; use strict; @@ -10,21 +10,21 @@ use SBO::Lib; ok (defined $SBO::Lib::tempdir, '$tempdir is defined'); my $fh = open_read ('/home/d4wnr4z0r/projects/sbotools/t/test.t'); -ok (ref ($fh) eq 'GLOB', 'open_read works'); +is (ref $fh, 'GLOB', 'open_read works'); close $fh; -ok ($SBO::Lib::config{DISTCLEAN} eq 'FALSE', 'config{DISTCLEAN} is good'); -ok ($SBO::Lib::config{JOBS} == 2, 'config{JOBS} is good'); -ok ($SBO::Lib::config{NOCLEAN} eq 'TRUE', 'config{NOCLEAN} is good'); -ok ($SBO::Lib::config{PKG_DIR} eq 'FALSE', 'config{PKG_DIR} is good'); -ok ($SBO::Lib::config{SBO_HOME} eq '/usr/sbo', 'config{SBO_HOME} is good'); +is ($SBO::Lib::config{DISTCLEAN}, 'FALSE', 'config{DISTCLEAN} is good'); +is ($SBO::Lib::config{JOBS}, 2, 'config{JOBS} is good'); +is ($SBO::Lib::config{NOCLEAN}, 'FALSE', 'config{NOCLEAN} is good'); +is ($SBO::Lib::config{PKG_DIR}, 'FALSE', 'config{PKG_DIR} is good'); +is ($SBO::Lib::config{SBO_HOME}, '/usr/sbo', 'config{SBO_HOME} is good'); -ok (show_version == 1, 'show_version is good'); -ok (get_slack_version eq '14.0', 'get_slack_version is good'); -ok (chk_slackbuilds_txt == 1, 'check_slackbuilds_txt is good'); +is (show_version, 1, 'show_version is good'); +is (get_slack_version, '14.0', 'get_slack_version is good'); +is (chk_slackbuilds_txt, 1, 'check_slackbuilds_txt is good'); #ok (rsync_sbo_tree == 1, 'rsync_sbo_tree is good'); #ok (update_tree == 1, 'update_tree is good'); -ok (slackbuilds_or_fetch == 1, 'slackbuilds_or_fetch is good'); +is (slackbuilds_or_fetch, 1, 'slackbuilds_or_fetch is good'); print "pseudo-random sampling of get_installed_sbos output...\n"; my $installed = get_installed_sbos; @@ -46,7 +46,7 @@ for my $key (keys @$updates) { is ($$updates[$key]{update}, '1.20', '$$updates[$key]{update} good for mutagen') if $$updates[$key]{name} eq 'mutagen'; } -ok (get_arch eq 'x86_64', 'get_arch is good'); +is (get_arch, 'x86_64', 'get_arch is good'); my %dl_info = get_download_info (LOCATION => '/usr/sbo/system/wine', X64 => 0); my $link = 'http://downloads.sf.net/wine/source/1.4/wine-1.4.1.tar.bz2'; diff --git a/t/test.t~ b/t/test.t~ deleted file mode 100755 index 9b0a256..0000000 --- a/t/test.t~ +++ /dev/null @@ -1,95 +0,0 @@ -#!/usr/bin/perl -I/home/d4wnr4z0r/projects/sbotools/t - -use 5.16.0; -use strict; -use warnings FATAL => 'all'; -use File::Temp qw(tempdir tempfile); -use Test::More tests => 39; -use SBO::Lib; - -ok (defined $SBO::Lib::tempdir, '$tempdir is defined'); - -my $fh = open_read ('/home/d4wnr4z0r/projects/sbotools/t/test.t'); -ok (ref ($fh) eq 'GLOB', 'open_read works'); -close $fh; - -ok ($SBO::Lib::config{DISTCLEAN} eq 'FALSE', 'config{DISTCLEAN} is good'); -ok ($SBO::Lib::config{JOBS} == 2, 'config{JOBS} is good'); -ok ($SBO::Lib::config{NOCLEAN} eq 'TRUE', 'config{NOCLEAN} is good'); -ok ($SBO::Lib::config{PKG_DIR} eq 'FALSE', 'config{PKG_DIR} is good'); -ok ($SBO::Lib::config{SBO_HOME} eq '/usr/sbo', 'config{SBO_HOME} is good'); - -ok (show_version == 1, 'show_version is good'); -ok (get_slack_version eq '14.0', 'get_slack_version is good'); -ok (chk_slackbuilds_txt == 1, 'check_slackbuilds_txt is good'); -#ok (rsync_sbo_tree == 1, 'rsync_sbo_tree is good'); -#ok (update_tree == 1, 'update_tree is good'); -ok (slackbuilds_or_fetch == 1, 'slackbuilds_or_fetch is good'); - -print "pseudo-random sampling of get_installed_sbos output...\n"; -my $installed = get_installed_sbos; -for my $key (keys @$installed) { - is ($$installed[$key]{version}, '1.13') if $$installed[$key]{name} eq 'OpenAL'; - is ($$installed[$key]{version}, '9.5.1_enu') if $$installed[$key]{name} eq 'adobe-reader'; - is ($$installed[$key]{version}, '4.1.3') if $$installed[$key]{name} eq 'libdvdnav'; - is ($$installed[$key]{version}, '0.8.8.4') if $$installed[$key]{name} eq 'libmodplug'; - is ($$installed[$key]{version}, '3.12.4') if $$installed[$key]{name} eq 'mozilla-nss'; - is ($$installed[$key]{version}, '2.5.0') if $$installed[$key]{name} eq 'zdoom'; -} -print "completed pseudo-random testing of get_installed_sbos \n"; - -is (get_sbo_location 'nginx', '/usr/sbo/network/nginx', 'get_sbo_location is good'); - -my $updates = get_available_updates; -for my $key (keys @$updates) { - is ($$updates[$key]{installed}, '1.15', '$$updates[$key]{installed} good for mutagen') if $$updates[$key]{name} eq 'mutagen'; - is ($$updates[$key]{update}, '1.20', '$$updates[$key]{update} good for mutagen') if $$updates[$key]{name} eq 'mutagen'; -} - -ok (get_arch eq 'x86_64', 'get_arch is good'); - -my %dl_info = get_download_info (LOCATION => '/usr/sbo/system/wine', X64 => 0); -my $link = 'http://downloads.sf.net/wine/source/1.4/wine-1.4.1.tar.bz2'; -is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', 'get_download_info test 01 good.'); -$link = 'http://www.unrealize.co.uk/source/dibeng-max-2010-11-12.zip'; -is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', 'get_download_info test 02 good.'); - -%dl_info = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine'); -$link = 'http://downloads.sf.net/wine/source/1.4/wine-1.4.1.tar.bz2'; -is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', 'get_sbo_downloads test 01 good.'); -$link = 'http://www.unrealize.co.uk/source/dibeng-max-2010-11-12.zip'; -is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', 'get_sbo_downloads test 02 good.'); - -my %downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/ifuse'); -$link = 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2'; -is ($downloads{$link}, '8d528a79de024b91f12f8ac67965c37c', 'get_sbo_downloads test 03 good.'); - -is (get_filename_from_link 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2', '/usr/sbo/distfiles/ifuse-1.1.1.tar.bz2', 'get_file_from_link good'); -is (compute_md5sum '/usr/sbo/distfiles//laptop-mode-tools_1.61.tar.gz', '6685af5dbb34c3d51ca27933b58f484e', 'compute_md5sum good'); -is ((verify_distfile '/usr/sbo/distfiles/laptop-mode-tools_1.61.tar.gz', '6685af5dbb34c3d51ca27933b58f484e'), 1, 'verify_distfile good'); -is (get_sbo_version '/usr/sbo/system/wine', '1.4.1', 'get_sbo_version good'); -is ((get_symlink_from_filename '/usr/sbo/distfiles/laptop-mode-tools_1.61.tar.gz', '/usr/sbo/system/laptop-mode-tools'), '/usr/sbo/system/laptop-mode-tools/laptop-mode-tools_1.61.tar.gz', 'get_symlink_from_filename good'); -ok (check_x32 '/usr/sbo/system/wine', 'check_x32 true for 32-bit only wine'); -ok (!(check_x32 '/usr/sbo/system/ifuse'), 'check_x32 false for not-32-bit-only ifuse'); -ok (check_multilib, 'check_multilib good'); - -# TODO: find a way to write a test for rewrite_slackbuild, revert_slackbuild. - -%downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine', 32 => 1); -my @symlinks = create_symlinks '/usr/sbo/system/wine', %downloads; -is ($symlinks[0], '/usr/sbo/system/wine/wine-1.4.1.tar.bz2', '$symlinks[0] good for create_symlinks'); -is ($symlinks[1], '/usr/sbo/system/wine/dibeng-max-2010-11-12.zip', '$symlinks[1] good for create_symlinks'); - -my $tempdir = tempdir (CLEANUP => 1); -my $tempfh = tempfile (DIR => $tempdir); -my $lmt = 'laptop-mode-tools_1.60'; -print {$tempfh} "$lmt/COPYING\n"; -print {$tempfh} "$lmt/Documentation/\n"; -print {$tempfh} "$lmt/README\n"; -print {$tempfh} "Slackware package skype-2.2.0.35-i486-1_SBo.tgz created.\n"; -#close $tempfh; -is (get_src_dir $tempfh, 'laptop-mode-tools_1.60', 'get_src_dir good'); -is (get_pkg_name $tempfh, 'skype-2.2.0.35-i486-1_SBo.tgz', 'get_pkg_name good'); -%downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine', 32 => 1); -is (check_distfiles %downloads, 1, 'check_distfiles good'); -#is (do_convertpkg ($package), "$package-compat32", 'do_convertpkg good'); -- cgit v1.2.3 From 12a1c8c4530ddb9ab83fec1f9b5bf61a25764e6b Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 31 Aug 2012 08:00:07 -0500 Subject: better testing, more still to come --- SBO-Lib/lib/SBO/Lib.pm | 39 +-- sboupgrade | 17 +- t/SBO/Lib.pm | 685 ------------------------------------------------- t/test.t | 169 ++++++++++-- 4 files changed, 179 insertions(+), 731 deletions(-) delete mode 100644 t/SBO/Lib.pm diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 8d3441b..886c19c 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -46,7 +46,6 @@ use Digest::MD5; use File::Copy; use File::Path qw(make_path remove_tree); use Fcntl; -use File::Find; use File::Temp qw(tempdir tempfile); use Fcntl qw(F_SETFD F_GETFD); @@ -73,7 +72,7 @@ sub open_read ($) { return open_fh shift, '<'; } -# pull in configuration, set sane defaults, etc. +# global config variables our $conf_dir = '/etc/sbotools'; our $conf_file = "$conf_dir/sbotools.conf"; our %config = ( @@ -84,20 +83,23 @@ our %config = ( SBO_HOME => 'FALSE', ); -# if the conf file exists, pull all the $key=$value pairs into a hash -my %conf_values; -if (-f $conf_file) { - my $fh = open_read $conf_file; - my $text = do {local $/; <$fh>}; - %conf_values = $text =~ /^(\w+)=(.*)$/mg; - close $fh; +# subroutine to suck in config in order to facilitate unit testing +sub read_config () { + my %conf_values; + if (-f $conf_file) { + my $fh = open_read $conf_file; + my $text = do {local $/; <$fh>}; + %conf_values = $text =~ /^(\w+)=(.*)$/mg; + close $fh; + } + for my $key (keys %config) { + $config{$key} = $conf_values{$key} if exists $conf_values{$key}; + } + $config{JOBS} = 'FALSE' unless $config{JOBS} =~ /^\d+$/; + $config{SBO_HOME} = '/usr/sbo' if $config{SBO_HOME} eq 'FALSE'; } -for my $key (keys %config) { - $config{$key} = $conf_values{$key} if exists $conf_values{$key}; -} -$config{JOBS} = 'FALSE' unless $config{JOBS} =~ /^\d+$/; -$config{SBO_HOME} = '/usr/sbo' if $config{SBO_HOME} eq 'FALSE'; +read_config; # some stuff we'll need later. my $distfiles = "$config{SBO_HOME}/distfiles"; @@ -141,6 +143,7 @@ sub check_home () { } else { make_path ($sbo_home) or die "Unable to create $sbo_home.\n"; } + return 1; } # rsync the sbo tree from slackbuilds.org to $config{SBO_HOME} @@ -286,9 +289,9 @@ sub get_download_info (%) { if ($args{X64}) { my $nothing; if (! $$downs[0]) { - $nothing = 1; + $nothing++; } elsif ($$downs[0] =~ qr/^UN(SUPPOR|TES)TED$/) { - $nothing = 1; + $nothing++; } if ($nothing) { $args{X64} = 0; @@ -335,7 +338,9 @@ sub get_sbo_downloads (%) { # given a link, grab the filename from the end of it sub get_filename_from_link ($) { exists $_[0] or script_error 'get_filename_from_link requires an argument'; - return "$distfiles/". (shift =~ qr#/([^/]+)$#)[0]; + my $fn = shift; + my $regex = qr#/([^/]+)$#; + return $fn =~ $regex ? $distfiles .'/'. ($fn =~ $regex)[0] : undef; } # for a given file, computer its md5sum diff --git a/sboupgrade b/sboupgrade index be2fc5a..cdc2ca2 100755 --- a/sboupgrade +++ b/sboupgrade @@ -101,20 +101,29 @@ sub grok_requirements ($$$) { my ($sbo, $location, $readme) = @_; my $requires = get_from_info (LOCATION => $location, GET => 'REQUIRES'); return unless $$requires[0]; + # do nothing if a req list contains %README% + return if '%README%' ~~ @$requires; + # do nothing if there's a circular requirement + FIRST: for my $req (@$requires) { + my $req_req = get_from_info (LOCATION => get_sbo_location $req, + GET => 'REQUIRES'); + return if $sbo ~~ @$req_req; + } + # else proceed for my $req (@$requires) { my $inst = get_installed_sbos; - my $inst_names= get_inst_names $inst;; + my $inst_names= get_inst_names $inst; unless ($req ~~ @$inst_names) { say $readme; say "$sbo has $req listed as a requirement."; print "Shall I attempt to install it first? [y] "; if ( =~ /^[Yy\n]/) { - my @cmd = ('/usr/sbin/sboupgrade', '-oN', $req); - system (@cmd) == 0 or die "$req failed to install.\n"; + system ('/usr/sbin/sboupgrade', '-oN', $req) == 0 or + die "$req failed to install.\n"; } } } - return 1; + return; } # look for any (user|group)add commands in the README diff --git a/t/SBO/Lib.pm b/t/SBO/Lib.pm deleted file mode 100644 index c2b9ef5..0000000 --- a/t/SBO/Lib.pm +++ /dev/null @@ -1,685 +0,0 @@ -#!/usr/bin/env perl -# -# vim: set ts=4:noet -# -# Lib.pm -# shared functions for the sbo_ scripts. -# -# author: Jacob Pipkin -# date: Setting Orange, the 37th day of Discord in the YOLD 3178 -# license: WTFPL - -use 5.16.0; -use warnings FATAL => 'all'; -use strict; - -package SBO::Lib 1.0; -my $version = "1.0"; - -require Exporter; -our @ISA = qw(Exporter); -our @EXPORT = qw(get_slack_version chk_slackbuilds_txt check_home rsync_sbo_tree get_sbo_from_loc get_sbo_version get_download_info get_arch get_sbo_downloads get_filename_from_link compute_md5sum compare_md5s verify_distfile get_distfile get_symlink_from_filename check_x32 check_multilib rewrite_slackbuild revert_slackbuild check_distfiles create_symlinks grok_temp_file get_src_dir get_pkg_name clear_coe_bit perform_sbo do_convertpkg - script_error - open_fh - open_read - show_version - slackbuilds_or_fetch - fetch_tree - update_tree - get_installed_sbos - get_available_updates - do_slackbuild - make_clean - make_distclean - do_upgradepkg - get_sbo_location - get_from_info - get_tmp_extfn - get_tmp_perlfn -); - -#$< == 0 or die "This script requires root privileges.\n"; - -use Tie::File; -use Sort::Versions; -use Digest::MD5; -use File::Copy; -use File::Path qw(make_path remove_tree); -use Fcntl; -use File::Find; -use File::Temp qw(tempdir tempfile); -use Fcntl qw(F_SETFD F_GETFD); - -our $tempdir = tempdir (CLEANUP => 1); - -# subroutine for throwing internal script errors -sub script_error (;$) { - exists $_[0] ? die "A fatal script error has occured:\n$_[0]\nExiting.\n" - : die "A fatal script error has occured. Exiting.\n"; -} - -# sub for opening files, second arg is like '<','>', etc -sub open_fh ($$) { - exists $_[1] or script_error 'open_fh requires two arguments'; - unless ($_[1] eq '>') { - -f $_[0] or script_error 'open_fh first argument not a file'; - } - my ($file, $op) = @_; - open my $fh, $op, $file or die "Unable to open $file.\n"; - return $fh; -} - -sub open_read ($) { - return open_fh shift, '<'; -} - -# pull in configuration, set sane defaults, etc. -our $conf_dir = '/etc/sbotools'; -our $conf_file = "$conf_dir/sbotools.conf"; -our %config = ( - NOCLEAN => 'FALSE', - DISTCLEAN => 'FALSE', - JOBS => 'FALSE', - PKG_DIR => 'FALSE', - SBO_HOME => 'FALSE', -); - -# if the conf file exists, pull all the $key=$value pairs into a hash -my %conf_values; -if (-f $conf_file) { - my $fh = open_read $conf_file; - my $text = do {local $/; <$fh>}; - %conf_values = $text =~ /^(\w+)=(.*)$/mg; - close $fh; -} - -for my $key (keys %config) { - $config{$key} = $conf_values{$key} if exists $conf_values{$key}; -} -$config{JOBS} = 'FALSE' unless $config{JOBS} =~ /^\d+$/; -$config{SBO_HOME} = '/usr/sbo' if $config{SBO_HOME} eq 'FALSE'; - -# some stuff we'll need later. -my $distfiles = "$config{SBO_HOME}/distfiles"; -my $slackbuilds_txt = "$config{SBO_HOME}/SLACKBUILDS.TXT"; -my $name_regex = '\ASLACKBUILD\s+NAME:\s+'; - -sub show_version () { - say "sbotools version $version"; - say 'licensed under the WTFPL'; - say ''; -} - -# %supported maps what's in /etc/slackware-version to what's at SBo -# which is now not needed since this version drops support < 14.0 -# but it's already future-proofed, so leave it. -sub get_slack_version () { - my %supported = ('14.0' => '14.0'); - my $fh = open_read '/etc/slackware-version'; - chomp (my $line = <$fh>); - close $fh; - my $version = ($line =~ /\s+(\d+[^\s]+)$/)[0]; - die "Unsupported Slackware version: $version\n" - unless $version ~~ %supported; - return $supported{$version}; -} - -# does the SLACKBUILDS.TXT file exist in the sbo tree? -sub chk_slackbuilds_txt () { - return -f $slackbuilds_txt ? 1 : 0; -} - -# check for the validity of new $config{SBO_HOME} -sub check_home () { - my $sbo_home = $config{SBO_HOME}; - if (-d $sbo_home) { - opendir (my $home_handle, $sbo_home); - FIRST: while (readdir $home_handle) { - next FIRST if /^\.[\.]{0,1}$/; - die "$sbo_home exists and is not empty. Exiting.\n"; - } - } else { - make_path ($sbo_home) or die "Unable to create $sbo_home.\n"; - } -} - -# rsync the sbo tree from slackbuilds.org to $config{SBO_HOME} -sub rsync_sbo_tree () { - my $slk_version = get_slack_version; - my @arg = ('rsync', '-a', '--exclude=*.tar.gz', '--exclude=*.tar.gz.asc'); - push @arg, "rsync://slackbuilds.org/slackbuilds/$slk_version/*"; - my $out = system @arg, $config{SBO_HOME}; - say 'Finished.' and return $out; -} - -# wrappers for differing checks and output -sub fetch_tree () { - check_home; - say 'Pulling SlackBuilds tree...'; - rsync_sbo_tree, return 1; -} - -sub update_tree () { - fetch_tree, return unless chk_slackbuilds_txt; - say 'Updating SlackBuilds tree...'; - rsync_sbo_tree, return 1; -} - -# if the SLACKBUILDS.TXT is not in $config{SBO_HOME}, we assume the tree has -# not been populated there; prompt the user to automagickally pull the tree. -sub slackbuilds_or_fetch () { - unless (chk_slackbuilds_txt) { - say 'It looks like you haven\'t run "sbosnap fetch" yet.'; - print 'Would you like me to do this now? [y] '; - =~ /^[Yy\n]/ ? fetch_tree : - die "Please run \"sbosnap fetch\"\n"; - } - return 1; -} - -# pull an array of hashes, each hash containing the name and version of an sbo -# currently installed. -sub get_installed_sbos () { - my @installed; - # $1 == name, $2 == version - my $regex = qr#/([^/]+)-([^-]+)-[^-]+-[^-]+$#; - for my $path () { - my ($name, $version) = ($path =~ $regex)[0,1]; - push @installed, {name => $name, version => $version}; - } - return \@installed; -} - -# search the SLACKBUILDS.TXT for a given sbo's directory -sub get_sbo_location ($) { - exists $_[0] or script_error 'get_sbo_location requires an argument.'; - my $sbo = shift; - my $regex = qr#LOCATION:\s+\.(/[^/]+/$sbo)$#; - my $fh = open_read $slackbuilds_txt; - while (my $line = <$fh>) { - if (my $loc = ($line =~ $regex)[0]) { - return "$config{SBO_HOME}$loc"; - } - } - return; -} - -# pull the sbo name from a $location: $config{SBO_HOME}/system/wine, etc. -sub get_sbo_from_loc ($) { - exists $_[0] or script_error 'get_sbo_from_loc requires an argument.'; - return (shift =~ qr#/([^/]+)$#)[0]; -} - -# pull piece(s) of data, GET, from the $sbo.info file under LOCATION. -sub get_from_info (%) { - my %args = ( - LOCATION => '', - GET => '', - @_ - ); - unless ($args{LOCATION} && $args{GET}) { - script_error 'get_from_info requires LOCATION and GET.'; - } - state $vars = {PRGNAM => ['']}; - my $sbo = get_sbo_from_loc $args{LOCATION}; - return $$vars{$args{GET}} if $$vars{PRGNAM}[0] eq $sbo; - # if we're here, we haven't read in the .info file yet. - my $fh = open_read "$args{LOCATION}/$sbo.info"; - # suck it all in, clean it all up, stuff it all in $vars. - my $contents = do {local $/; <$fh>}; - $contents =~ s/("|\\\n)//g; - $vars = {$contents =~ /^(\w+)=(.*)$/mg}; - # fill the hash with array refs - even for single values, - # since consistency here is a lot easier than sorting it out later - for my $key (keys %$vars) { - if ($$vars{$key} =~ /\s/) { - my @array = split ' ', $$vars{$key}; - $$vars{$key} = \@array; - } else { - $$vars{$key} = [$$vars{$key}]; - } - } - return exists $$vars{$args{GET}} ? $$vars{$args{GET}} : 0; -} - -# find the version in the tree for a given sbo (provided a location) -sub get_sbo_version ($) { - exists $_[0] or script_error 'get_sbo_version requires an argument.'; - my $version = get_from_info (LOCATION => shift, GET => 'VERSION'); - return $$version[0] ? $$version[0] : 0; -} - -# for each installed sbo, find out whether or not the version in the tree is -# newer, and compile an array of hashes containing those which are -sub get_available_updates () { - my @updates; - my $pkg_list = get_installed_sbos; - FIRST: for my $key (keys @$pkg_list) { - my $location = get_sbo_location $$pkg_list[$key]{name}; - # if we can't find a location, assume invalid and skip - next FIRST unless defined $location; - my $version = get_sbo_version $location; - if (versioncmp ($version, $$pkg_list[$key]{version}) == 1) { - push @updates, { - name => $$pkg_list[$key]{name}, - installed => $$pkg_list[$key]{version}, - update => $version - }; - } - } - return \@updates; -} - -# get downloads and md5sums from an sbo's .info file, first -# checking for x86_64-specific info if we are told to -sub get_download_info (%) { - my %args = ( - LOCATION => 0, - X64 => 1, - @_ - ); - $args{LOCATION} or script_error 'get_download_info requires LOCATION.'; - my ($get, $downs, $md5s, %return); - $get = ($args{X64} ? 'DOWNLOAD_x86_64' : 'DOWNLOAD'); - $downs = get_from_info (LOCATION => $args{LOCATION}, GET => $get); - # did we get nothing back, or UNSUPPORTED/UNTESTED? - if ($args{X64}) { - my $nothing; - if (! $$downs[0]) { - $nothing = 1; - } elsif ($$downs[0] =~ qr/^UN(SUPPOR|TES)TED$/) { - $nothing = 1; - } - if ($nothing) { - $args{X64} = 0; - $downs = get_from_info (LOCATION => $args{LOCATION}, - GET => 'DOWNLOAD'); - } - } - # if we still don't have any links, something is really wrong. - return unless $$downs[0]; - # grab the md5s and build a hash - $get = $args{X64} ? 'MD5SUM_x86_64' : 'MD5SUM'; - $md5s = get_from_info (LOCATION => $args{LOCATION}, GET => $get); - return unless $$md5s[0]; - $return{$$downs[$_]} = $$md5s[$_] for (keys @$downs); - return %return; -} - -sub get_arch () { - chomp (my $arch = `uname -m`); - return $arch; -} - -# TODO: should probably combine this with get_download_info -sub get_sbo_downloads (%) { - my %args = ( - LOCATION => '', - 32 => 0, - @_ - ); - $args{LOCATION} or script_error 'get_sbo_downloads requires LOCATION.'; - my $location = $args{LOCATION}; - -d $location or script_error 'get_sbo_downloads given a non-directory.'; - my $arch = get_arch; - my %dl_info; - if ($arch eq 'x86_64') { - %dl_info = get_download_info (LOCATION => $location) unless $args{32}; - } - unless (keys %dl_info > 0) { - %dl_info = get_download_info (LOCATION => $location, X64 => 0); - } - return %dl_info; -} - -# given a link, grab the filename from the end of it -sub get_filename_from_link ($) { - exists $_[0] or script_error 'get_filename_from_link requires an argument'; - return "$distfiles/". (shift =~ qr#/([^/]+)$#)[0]; -} - -# for a given file, computer its md5sum -sub compute_md5sum ($) { - -f $_[0] or script_error 'compute_md5sum requires a file argument.'; - my $fh = open_read shift; - my $md5 = Digest::MD5->new; - $md5->addfile ($fh); - my $md5sum = $md5->hexdigest; - close $fh; - return $md5sum; -} - -sub compare_md5s ($$) { - exists $_[1] or script_error 'compare_md5s requires two arguments.'; - my ($first, $second) = @_; - return $first eq $second ? 1 : 0; -} - -# for a given distfile, see whether or not it exists, and if so, if its md5sum -# matches the sbo's .info file -sub verify_distfile ($$) { - exists $_[1] or script_error 'check_distfile requires two arguments.'; - my ($link, $info_md5sum) = @_; - my $filename = get_filename_from_link $link; - return unless -d $distfiles; - return unless -f $filename; - my $md5sum = compute_md5sum $filename; - return compare_md5s $info_md5sum, $md5sum; -} - -# for a given distfile, attempt to retrieve it and, if successful, check its -# md5sum against that in the sbo's .info file -sub get_distfile ($$) { - exists $_[1] or script_error 'get_distfile requires an argument'; - my ($link, $exp_md5) = @_; - my $filename = get_filename_from_link $link; - mkdir $distfiles unless -d $distfiles; - chdir $distfiles; - system ("wget --no-check-certificate $link") == 0 or - die "Unable to wget $link\n"; - my $md5sum = compute_md5sum $filename; - # can't do anything if the link in the .info doesn't lead to a good d/l - compare_md5s $md5sum, $exp_md5 or die "md5sum failure for $filename.\n"; - return 1; -} - -# for a given distfile, figure out what the full path to its symlink will be -sub get_symlink_from_filename ($$) { - exists $_[1] or script_error - 'get_symlink_from_filename requires two arguments'; - -f $_[0] or script_error - 'get_symlink_from_filename first argument is not a file'; - my ($filename, $location) = @_; - return "$location/". ($filename =~ qr#/([^/]+)$#)[0]; -} - -# determine whether or not a given sbo is 32-bit only -sub check_x32 ($) { - exists $_[0] or script_error 'check_x32 requires an argument.'; - my $dl = get_from_info (LOCATION => shift, GET => 'DOWNLOAD_x86_64'); - return $$dl[0] =~ /UN(SUPPOR|TES)TED/ ? 1 : 0; -} - -# can't do 32-bit on x86_64 without this file, so we'll use it as the test to -# to determine whether or not an x86_64 system is setup for multilib -sub check_multilib () { - return 1 if -f '/etc/profile.d/32dev.sh'; - return; -} - -# make a backup of the existent SlackBuild, and rewrite the original as needed -sub rewrite_slackbuild ($$%) { - exists $_[1] or script_error 'rewrite_slackbuild requires two arguments.'; - my ($slackbuild, $tempfn, %changes) = @_; - copy ($slackbuild, "$slackbuild.orig") or - die "Unable to backup $slackbuild to $slackbuild.orig\n"; - my $tar_regex = qr/(un|)tar .*$/; - my $makepkg_regex = qr/makepkg/; - my $libdir_regex = qr/^\s*LIBDIRSUFFIX="64"\s*$/; - my $make_regex = qr/^\s*make(| \Q||\E exit 1)$/; - my $arch_regex = qr/\$VERSION-\$ARCH-\$BUILD/; - # tie the slackbuild, because this is the easiest way to handle this. - tie my @sb_file, 'Tie::File', $slackbuild; - for my $line (@sb_file) { - # get the output of the tar and makepkg commands. hope like hell that v - # is specified among tar's arguments - if ($line =~ $tar_regex || $line =~ $makepkg_regex) { - $line = "$line | tee -a $tempfn"; - } - # then check for and apply any other %changes - if (exists $changes{libdirsuffix}) { - $line =~ s/64/$changes{libdirsuffix}/ if $line =~ $libdir_regex; - } - if (exists $changes{make}) { - $line =~ s/make/make $changes{make}/ if $line =~ $make_regex; - } - if (exists $changes{arch_out}) { - $line =~ s/\$ARCH/$changes{arch_out}/ if $line =~ $arch_regex; - } - } - untie @sb_file; - return 1; -} - -# move a backed-up .SlackBuild file back into place -sub revert_slackbuild ($) { - exists $_[0] or script_error 'revert_slackbuild requires an argument'; - my $slackbuild = shift; - if (-f "$slackbuild.orig") { - unlink $slackbuild if -f $slackbuild; - rename "$slackbuild.orig", $slackbuild; - } - return 1; -} - -# for each $download, see if we have it, and if the copy we have is good, -# otherwise download a new copy -sub check_distfiles (%) { - exists $_[0] or script_error 'check_distfiles requires an argument.'; - my %dists = @_; - for my $link (keys %dists) { - my $md5sum = $dists{$link}; - unless (verify_distfile $link, $md5sum) { - die unless get_distfile $link, $md5sum; - } - } - return 1; -} - -# given a location and a list of download links, assemble a list of symlinks, -# and create them. -sub create_symlinks ($%) { - exists $_[1] or script_error 'create_symlinks requires two arguments.'; - my ($location, %downloads) = @_; - my @symlinks; - for my $link (keys %downloads) { - my $filename = get_filename_from_link $link; - my $symlink = get_symlink_from_filename $filename, $location; - push @symlinks, $symlink; - symlink $filename, $symlink; - } - return @symlinks; -} - -# pull the untarred source directory or created package name from the temp -# file (the one we tee'd to) -sub grok_temp_file (%) { - my %args = ( - FH => '', - REGEX => '', - CAPTURE => 0, - @_ - ); - unless ($args{FH} && $args{REGEX}) { - script_error 'grok_temp_file requires two arguments'; - } - my $fh = $args{FH}; - seek $fh, 0, 0; - my $out; - FIRST: while (my $line = <$fh>) { - if ($line =~ $args{REGEX}) { - $out = ($line =~ $args{REGEX})[$args{CAPTURE}]; - last FIRST; - } - } - return $out; -} - -# wrappers around grok_temp_file -sub get_src_dir ($) { - exists $_[0] or script_error 'get_src_dir requires an argument'; - return grok_temp_file (FH => shift, REGEX => qr#^([^/]+)/#); -} - -sub get_pkg_name ($) { - exists $_[0] or script_error 'get_pkg_name requires an argument'; - return grok_temp_file (FH => shift, - REGEX => qr/^Slackware\s+package\s+([^\s]+)\s+created\.$/); -} - -# clear the close-on-exec bit from a temp file handle -sub clear_coe_bit ($) { - exists $_[0] or script_error 'clear_coe_bit requires an argument'; - my $fh = shift; - fcntl ($fh, F_SETFD, 0) or die "no unset exec-close thingy\n"; - return $fh; -} - -# return a filename from a temp fh for use externally -sub get_tmp_extfn ($) { - exists $_[0] or script_error 'get_tmp_extfn requires an argument.'; - my $fh = clear_coe_bit shift; - return '/dev/fd/'. fileno $fh; -} - -# return a filename from a temp fh for use internally -sub get_tmp_perlfn ($) { - exists $_[0] or script_error 'get_tmp_perlfn requires an argument.'; - my $fh = clear_coe_bit shift; - return '+<=&'. fileno $fh; -} - -# prep and run .SlackBuild -sub perform_sbo (%) { - my %args = ( - OPTS => 0, - JOBS => 0, - LOCATION => '', - ARCH => '', - C32 => 0, - X32 => 0, - @_ - ); - unless ($args{LOCATION} && $args{ARCH}) { - script_error 'perform_sbo requires LOCATION and ARCH.'; - } - my $location = $args{LOCATION}; - my $sbo = get_sbo_from_loc $location; - my ($cmd, %changes); - # figure out any changes we need to make to the .SlackBuild - $changes{make} = "-j $args{JOBS}" if $args{JOBS}; - if ($args{ARCH} eq 'x86_64' and ($args{C32} || $args{X32})) { - if ($args{C32}) { - $changes{libdirsuffix} = ''; - } elsif ($args{X32}) { - $changes{arch_out} = 'i486'; - } - $cmd = ". /etc/profile.d/32dev.sh &&"; - } - $cmd .= "/bin/sh $location/$sbo.SlackBuild"; - $cmd = "$args{OPTS} $cmd" if $args{OPTS}; - my $tempfh = tempfile (DIR => $tempdir); - my $fn = get_tmp_extfn $tempfh; - rewrite_slackbuild "$location/$sbo.SlackBuild", $fn, %changes; - chdir $location, my $out = system $cmd; - revert_slackbuild "$location/$sbo.SlackBuild"; - die unless $out == 0; - my $pkg = get_pkg_name $tempfh; - my $src = get_src_dir $tempfh; - return $pkg, $src; -} - -# run convertpkg on a package to turn it into a -compat32 thing -sub do_convertpkg ($) { - exists $_[0] or script_error 'do_convertpkg requires an argument.'; - my $pkg = shift; - my $tempfh = tempfile (DIR => $tempdir); - my $fn = get_tmp_extfn $tempfh; - my $cmd = "/usr/sbin/convertpkg-compat32 -i $pkg -d /tmp | tee $fn"; - system ($cmd) == 0 or die; - unlink $pkg; - return get_pkg_name $tempfh; -} - -# "public interface", sort of thing. -sub do_slackbuild (%) { - my %args = ( - OPTS => 0, - JOBS => 0, - LOCATION => '', - COMPAT32 => 0, - @_ - ); - $args{LOCATION} or script_error 'do_slackbuild requires LOCATION.'; - my $location = $args{LOCATION}; - my $sbo = get_sbo_from_loc $location; - my $arch = get_arch; - my $multi = check_multilib; - my $version = get_sbo_version $location; - my $x32; - # ensure x32 stuff is set correctly, or that we're setup for it - if ($args{COMPAT32}) { - die "compat32 only works on x86_64.\n" unless $arch eq 'x86_64'; - die "compat32 requires multilib.\n" unless $multi; - die "compat32 requires /usr/sbin/convertpkg-compat32.\n" - unless -f '/usr/sbin/convertpkg-compat32'; - } else { - if ($arch eq 'x86_64') { - $x32 = check_x32 $args{LOCATION}; - if ($x32 && ! $multi) { - die "$sbo is 32-bit which requires multilib on x86_64.\n"; - } - } - } - # get a hash of downloads and md5sums, ensure we have 'em, symlink 'em - my %downloads = get_sbo_downloads ( - LOCATION => $location, - 32 => $args{COMPAT32} - ); - check_distfiles %downloads; - my @symlinks = create_symlinks $args{LOCATION}, %downloads; - # setup and run the .SlackBuild itself - my ($pkg, $src) = perform_sbo ( - OPTS => $args{OPTS}, - JOBS => $args{JOBS}, - LOCATION => $location, - ARCH => $arch, - C32 => $args{COMPAT32}, - X32 => $x32, - ); - do_convertpkg $pkg if $args{COMPAT32}; - unlink $_ for @symlinks; - return $version, $pkg, $src; -} - -# remove work directories (source and packaging dirs under /tmp/SBo) -sub make_clean ($$$) { - exists $_[2] or script_error 'make_clean requires three arguments.'; - my ($sbo, $src, $version) = @_; - say "Cleaning for $sbo-$version..."; - my $tmpsbo = "/tmp/SBo"; - remove_tree ("$tmpsbo/$src") if -d "$tmpsbo/$src"; - remove_tree ("$tmpsbo/package-$sbo") if -d "$tmpsbo/package-$sbo"; - return 1; -} - -# remove distfiles -sub make_distclean (%) { - my %args = ( - SRC => '', - VERSION => '', - LOCATION => '', - @_ - ); - unless ($args{SRC} && $args{VERSION} && $args{LOCATION}) { - script_error 'make_distclean requires four arguments.'; - } - my $sbo = get_sbo_from_loc $args{LOCATION}; - make_clean $sbo, $args{SRC}, $args{VERSION}; - say "Distcleaning for $sbo-$args{VERSION}..."; - # remove any distfiles for this particular SBo. - my %downloads = get_sbo_downloads (LOCATION => $args{LOCATION}); - for my $key (keys %downloads) { - my $filename = get_filename_from_link $key; - unlink $filename if -f $filename; - } - return 1; -} - -# run upgradepkg for a created package -sub do_upgradepkg ($) { - exists $_[0] or script_error 'do_upgradepkg requires an argument.'; - system ('/sbin/upgradepkg', '--reinstall', '--install-new', shift); - return 1; -} - diff --git a/t/test.t b/t/test.t index 9ebd5fc..aabb5fa 100755 --- a/t/test.t +++ b/t/test.t @@ -4,28 +4,45 @@ use 5.16.0; use strict; use warnings FATAL => 'all'; use File::Temp qw(tempdir tempfile); -use Test::More tests => 39; +use Test::More tests => 61; +use File::Copy; +use Text::Diff; use SBO::Lib; -ok (defined $SBO::Lib::tempdir, '$tempdir is defined'); +my $sbo_home = '/home/d4wnr4z0r/sbo.git/slackbuilds'; -my $fh = open_read ('/home/d4wnr4z0r/projects/sbotools/t/test.t'); +# 1, open_read, open_fh tests +my $fh = open_read ('./test.t'); is (ref $fh, 'GLOB', 'open_read works'); close $fh; +# 2-7, config settings tests; +ok (defined $SBO::Lib::tempdir, '$tempdir is defined'); is ($SBO::Lib::config{DISTCLEAN}, 'FALSE', 'config{DISTCLEAN} is good'); is ($SBO::Lib::config{JOBS}, 2, 'config{JOBS} is good'); is ($SBO::Lib::config{NOCLEAN}, 'FALSE', 'config{NOCLEAN} is good'); is ($SBO::Lib::config{PKG_DIR}, 'FALSE', 'config{PKG_DIR} is good'); -is ($SBO::Lib::config{SBO_HOME}, '/usr/sbo', 'config{SBO_HOME} is good'); +is ($SBO::Lib::config{SBO_HOME}, "$sbo_home", 'config{SBO_HOME} is good'); +# 8, show_version test is (show_version, 1, 'show_version is good'); + +# 9, get_slack_version test is (get_slack_version, '14.0', 'get_slack_version is good'); -is (chk_slackbuilds_txt, 1, 'check_slackbuilds_txt is good'); + +# 10-11, chk_slackbuilds_txt tests +is (chk_slackbuilds_txt, 1, 'chk_slackbuilds_txt is good'); +move ("$sbo_home/SLACKBUILDS.TXT", "$sbo_home/SLACKBUILDS.TXT.moved"); +is (chk_slackbuilds_txt, 0, 'chk_slackbuilds_txt returns false with no SLACKBUILDS.TXT'); +move ("$sbo_home/SLACKBUILDS.TXT.moved", "$sbo_home/SLACKBUILDS.TXT"); + #ok (rsync_sbo_tree == 1, 'rsync_sbo_tree is good'); #ok (update_tree == 1, 'update_tree is good'); + +# 12, slackbuilds_or_fetch test is (slackbuilds_or_fetch, 1, 'slackbuilds_or_fetch is good'); +# 13-18, get_installed_sbos test print "pseudo-random sampling of get_installed_sbos output...\n"; my $installed = get_installed_sbos; for my $key (keys @$installed) { @@ -38,48 +55,67 @@ for my $key (keys @$installed) { } print "completed pseudo-random testing of get_installed_sbos \n"; -is (get_sbo_location 'nginx', '/usr/sbo/network/nginx', 'get_sbo_location is good'); +# 19-20, get_sbo_location tests +is (get_sbo_location 'nginx', "$sbo_home/network/nginx", 'get_sbo_location is good'); +is (get_sbo_location 'omgwtfbbq', undef, 'get_sbo_location returns false with not-an-sbo input'); +# 21-22, get_available_updates tests my $updates = get_available_updates; for my $key (keys @$updates) { is ($$updates[$key]{installed}, '1.15', '$$updates[$key]{installed} good for mutagen') if $$updates[$key]{name} eq 'mutagen'; is ($$updates[$key]{update}, '1.20', '$$updates[$key]{update} good for mutagen') if $$updates[$key]{name} eq 'mutagen'; } +# 23, get_arch test is (get_arch, 'x86_64', 'get_arch is good'); -my %dl_info = get_download_info (LOCATION => '/usr/sbo/system/wine', X64 => 0); +# 24-25, get_download_info tests +my %dl_info = get_download_info (LOCATION => "$sbo_home/system/wine", X64 => 0); my $link = 'http://downloads.sf.net/wine/source/1.4/wine-1.4.1.tar.bz2'; is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', 'get_download_info test 01 good.'); $link = 'http://www.unrealize.co.uk/source/dibeng-max-2010-11-12.zip'; is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', 'get_download_info test 02 good.'); -%dl_info = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine'); +# 26-28, get_sbo_downloads tests +%dl_info = get_sbo_downloads (LOCATION => "$sbo_home/system/wine"); $link = 'http://downloads.sf.net/wine/source/1.4/wine-1.4.1.tar.bz2'; is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', 'get_sbo_downloads test 01 good.'); $link = 'http://www.unrealize.co.uk/source/dibeng-max-2010-11-12.zip'; is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', 'get_sbo_downloads test 02 good.'); - -my %downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/ifuse'); +my %downloads = get_sbo_downloads (LOCATION => "$sbo_home/system/ifuse"); $link = 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2'; is ($downloads{$link}, '8d528a79de024b91f12f8ac67965c37c', 'get_sbo_downloads test 03 good.'); -is (get_filename_from_link 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2', '/usr/sbo/distfiles/ifuse-1.1.1.tar.bz2', 'get_file_from_link good'); -is (compute_md5sum '/usr/sbo/distfiles//laptop-mode-tools_1.61.tar.gz', '6685af5dbb34c3d51ca27933b58f484e', 'compute_md5sum good'); -is ((verify_distfile '/usr/sbo/distfiles/laptop-mode-tools_1.61.tar.gz', '6685af5dbb34c3d51ca27933b58f484e'), 1, 'verify_distfile good'); -is (get_sbo_version '/usr/sbo/system/wine', '1.4.1', 'get_sbo_version good'); -is ((get_symlink_from_filename '/usr/sbo/distfiles/laptop-mode-tools_1.61.tar.gz', '/usr/sbo/system/laptop-mode-tools'), '/usr/sbo/system/laptop-mode-tools/laptop-mode-tools_1.61.tar.gz', 'get_symlink_from_filename good'); -ok (check_x32 '/usr/sbo/system/wine', 'check_x32 true for 32-bit only wine'); -ok (!(check_x32 '/usr/sbo/system/ifuse'), 'check_x32 false for not-32-bit-only ifuse'); -ok (check_multilib, 'check_multilib good'); +# 29, get_filename_from_link test +is (get_filename_from_link 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2', "$sbo_home/distfiles/ifuse-1.1.1.tar.bz2", 'get_file_from_link good'); +is (get_filename_from_link 'adf;lkajsdfaksjdfalsdjfalsdkfjdsfj', undef, 'get_filename_from_link good with invalid input'); + +# 31, compute_md5sum test +is (compute_md5sum "$sbo_home/distfiles/laptop-mode-tools_1.61.tar.gz", '6685af5dbb34c3d51ca27933b58f484e', 'compute_md5sum good'); -# TODO: find a way to write a test for rewrite_slackbuild, revert_slackbuild. +# 32, verify_distfile test +is ((verify_distfile "$sbo_home/distfiles/laptop-mode-tools_1.61.tar.gz", '6685af5dbb34c3d51ca27933b58f484e'), 1, 'verify_distfile good'); -%downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine', 32 => 1); -my @symlinks = create_symlinks '/usr/sbo/system/wine', %downloads; -is ($symlinks[0], '/usr/sbo/system/wine/wine-1.4.1.tar.bz2', '$symlinks[0] good for create_symlinks'); -is ($symlinks[1], '/usr/sbo/system/wine/dibeng-max-2010-11-12.zip', '$symlinks[1] good for create_symlinks'); +# 33, get_sbo_version test +is (get_sbo_version "$sbo_home/system/wine", '1.4.1', 'get_sbo_version good'); +# 34, get_symlink_from_filename test +is ((get_symlink_from_filename "$sbo_home/distfiles/laptop-mode-tools_1.61.tar.gz", "$sbo_home/system/laptop-mode-tools"), "$sbo_home/system/laptop-mode-tools/laptop-mode-tools_1.61.tar.gz", 'get_symlink_from_filename good'); + +# 35-36, check_x32 tests +ok (check_x32 "$sbo_home/system/wine", 'check_x32 true for 32-bit only wine'); +ok (!(check_x32 "$sbo_home/system/ifuse"), 'check_x32 false for not-32-bit-only ifuse'); + +# 37, check_multilib tests +ok (check_multilib, 'check_multilib good'); + +# 38-39, create_symlinks tests +%downloads = get_sbo_downloads (LOCATION => "$sbo_home/system/wine", 32 => 1); +my @symlinks = create_symlinks "$sbo_home/system/wine", %downloads; +is ($symlinks[0], "$sbo_home/system/wine/wine-1.4.1.tar.bz2", '$symlinks[0] good for create_symlinks'); +is ($symlinks[1], "$sbo_home/system/wine/dibeng-max-2010-11-12.zip", '$symlinks[1] good for create_symlinks'); + +# 40-41, grok_temp_file, get_src_dir/get_pkg_name tests my $tempdir = tempdir (CLEANUP => 1); my $tempfh = tempfile (DIR => $tempdir); my $lmt = 'laptop-mode-tools_1.60'; @@ -87,9 +123,92 @@ print {$tempfh} "$lmt/COPYING\n"; print {$tempfh} "$lmt/Documentation/\n"; print {$tempfh} "$lmt/README\n"; print {$tempfh} "Slackware package skype-2.2.0.35-i486-1_SBo.tgz created.\n"; -#close $tempfh; is (get_src_dir $tempfh, 'laptop-mode-tools_1.60', 'get_src_dir good'); is (get_pkg_name $tempfh, 'skype-2.2.0.35-i486-1_SBo.tgz', 'get_pkg_name good'); -%downloads = get_sbo_downloads (LOCATION => '/usr/sbo/system/wine', 32 => 1); +close $tempfh; + +# 42, check_distfiles test +%downloads = get_sbo_downloads (LOCATION => "$sbo_home/system/wine", 32 => 1); is ((check_distfiles %downloads), 1, 'check_distfiles good'); + +# 43-45, check_home tests +system ('sudo /usr/sbin/sboconfig -s /home/d4wnr4z0r/opt_sbo') == 0 or die "unable to set sboconfig -s\n"; +read_config; +ok (check_home, 'check_home returns true with new non-existent directory'); +ok (-d '/home/d4wnr4z0r/opt_sbo', 'check_home creates $config{SBO_HOME}'); +ok (check_home, 'check_home returns true with new existent empty directory'); +system ("sudo /usr/sbin/sboconfig -s $sbo_home") == 0 or die "unable to reset sboconfig -s\n"; +read_config; +rmdir "/home/d4wnr4z0r/opt_sbo"; + +# 46-47 get_sbo_from_loc tests +is (get_sbo_from_loc '/home/d4wnr4z0r/sbo.git/system/ifuse', 'ifuse', 'get_sbo_from_loc returns correctly with valid input'); +ok (! get_sbo_from_loc 'omg_wtf_bbq', 'get_sbo_from_loc returns false with invalid input'); + +# 48-49, compare_md5s tests +is (compare_md5s ('omgwtf123456789', 'omgwtf123456789'), 1, 'compare_md5s returns true for matching parameters'); +is (compare_md5s ('omgwtf123456788', 'somethingelsebbq'), 0, 'compare_md5s returns false for not-matching parameters'); + +# 50, get_distfile tests +my $distfile = "$sbo_home/distfiles/Sort-Versions-1.5.tar.gz"; +unlink $distfile if -f $distfile; +is (get_distfile ('http://search.cpan.org/CPAN/authors/id/E/ED/EDAVIS/Sort-Versions-1.5.tar.gz', '5434f948fdea6406851c77bebbd0ed19'), 1, 'get_distfile is good'); +unlink $distfile; + +# 51-58, rewrite_slackbuilds/revert_slackbuild tests +my $rewrite_dir = tempdir (CLEANUP => 1); +copy ("$sbo_home/system/ifuse/ifuse.SlackBuild", $rewrite_dir); +my $slackbuild = "$rewrite_dir/ifuse.SlackBuild"; +$tempfh = tempfile (DIR => $rewrite_dir); +my $tempfn = get_tmp_extfn $tempfh; +my %changes; +is (rewrite_slackbuild ($slackbuild, $tempfn, %changes), 1, 'rewrite_slackbuild with no %changes good'); +ok (-f "$slackbuild.orig", 'rewrite_slackbuild backing up original is good.'); +my $expected_out = "67c67 +< tar xvf \$CWD/\$PRGNAM-\$VERSION.tar.bz2 +--- +> tar xvf \$CWD/\$PRGNAM-\$VERSION.tar.bz2 | tee -a $tempfn +103c103 +< /sbin/makepkg -l y -c n \$OUTPUT/\$PRGNAM-\$VERSION-\$ARCH-\$BUILD\$TAG.\${PKGTYPE:-tgz} +--- +> /sbin/makepkg -l y -c n \$OUTPUT/\$PRGNAM-\$VERSION-\$ARCH-\$BUILD\$TAG.\${PKGTYPE:-tgz} | tee -a $tempfn +"; +is (diff ("$slackbuild.orig", $slackbuild, {STYLE => 'OldStyle'}), $expected_out, 'tar line rewritten correctly'); +is (revert_slackbuild $slackbuild, 1, 'revert_slackbuild is good'); +$changes{libdirsuffix} = ''; +$changes{make} = '-j 5'; +$changes{arch_out} = 'i486'; +is (rewrite_slackbuild ($slackbuild, $tempfn, %changes), 1, 'rewrite_slackbuild with all %changes good'); +ok (-f "$slackbuild.orig", 'rewrite_slackbuild backing up original is good.'); +$expected_out = "55c55 +< LIBDIRSUFFIX=\"64\" +--- +> LIBDIRSUFFIX=\"\" +67c67 +< tar xvf \$CWD/\$PRGNAM-\$VERSION.tar.bz2 +--- +> tar xvf \$CWD/\$PRGNAM-\$VERSION.tar.bz2 | tee -a $tempfn +87c87 +< make +--- +> make -j 5 +103c103 +< /sbin/makepkg -l y -c n \$OUTPUT/\$PRGNAM-\$VERSION-\$ARCH-\$BUILD\$TAG.\${PKGTYPE:-tgz} +--- +> /sbin/makepkg -l y -c n \$OUTPUT/\$PRGNAM-\$VERSION-i486-\$BUILD\$TAG.\${PKGTYPE:-tgz} | tee -a $tempfn +"; +is (diff ("$slackbuild.orig", $slackbuild, {STYLE => 'OldStyle'}), $expected_out, 'all changed lines rewritten correctly'); +is (revert_slackbuild $slackbuild, 1, 'revert_slackbuild is good again'); + +# 59-61, get_from_info tests +my $test_loc = "$sbo_home/system/ifuse"; +my %params = (LOCATION => $test_loc); +my $info = get_from_info (%params, GET => 'VERSION'); +is ($$info[0], '1.1.1', 'get_from_info GET => VERSION is good'); +$info = get_from_info (%params, GET => 'HOMEPAGE'); +is ($$info[0], 'http://www.libimobiledevice.org', 'get_from_info GET => HOMEPAGE is good'); +$info = get_from_info (%params, GET => 'DOWNLOAD_x86_64'); +is ($$info[0], "", 'get_from_info GET => DOWNLOAD_x86_64 is good'); + + #is (do_convertpkg ($package), "$package-compat32", 'do_convertpkg good'); -- cgit v1.2.3 From d55dbdf17977ed9b1dfd91c98a4a569960b851cd Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 31 Aug 2012 15:53:21 -0500 Subject: epic changes and fixes and much further testing --- SBO-Lib/lib/SBO/Lib.pm | 11 +- sbocheck | 43 ++-- sboclean | 2 +- sboconfig | 9 +- sbofind | 33 ++- sboupgrade | 87 ++++--- t/SBO/Lib.pm~ | 643 ------------------------------------------------- t/prep.pl | 44 ++++ t/test.t | 73 +++++- 9 files changed, 227 insertions(+), 718 deletions(-) delete mode 100644 t/SBO/Lib.pm~ diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 886c19c..94ce3be 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -464,9 +464,7 @@ sub check_distfiles (%) { my %dists = @_; for my $link (keys %dists) { my $md5sum = $dists{$link}; - unless (verify_distfile $link, $md5sum) { - die unless get_distfile $link, $md5sum; - } + get_distfile $link, $md5sum unless verify_distfile $link, $md5sum; } return 1; } @@ -561,7 +559,7 @@ sub perform_sbo (%) { my $location = $args{LOCATION}; my $sbo = get_sbo_from_loc $location; my ($cmd, %changes); - # figure out any changes we need to make to the .SlackBuild + # set any changes we need to make to the .SlackBuild, setup the command $changes{make} = "-j $args{JOBS}" if $args{JOBS}; if ($args{ARCH} eq 'x86_64' and ($args{C32} || $args{X32})) { if ($args{C32}) { @@ -578,7 +576,7 @@ sub perform_sbo (%) { rewrite_slackbuild "$location/$sbo.SlackBuild", $fn, %changes; chdir $location, my $out = system $cmd; revert_slackbuild "$location/$sbo.SlackBuild"; - die unless $out == 0; + die "$sbo.SlackBuild returned non-zero ext status\n" unless $out == 0; my $pkg = get_pkg_name $tempfh; my $src = get_src_dir $tempfh; return $pkg, $src; @@ -591,7 +589,8 @@ sub do_convertpkg ($) { my $tempfh = tempfile (DIR => $tempdir); my $fn = get_tmp_extfn $tempfh; my $cmd = "/usr/sbin/convertpkg-compat32 -i $pkg -d /tmp | tee $fn"; - system ($cmd) == 0 or die; + system ($cmd) == 0 or + die "convertpkg-compt32 returned non-zero exit status\n"; unlink $pkg; return get_pkg_name $tempfh; } diff --git a/sbocheck b/sbocheck index 9d228a6..d2e6f91 100755 --- a/sbocheck +++ b/sbocheck @@ -27,24 +27,35 @@ show_version && exit 0 if (exists $options{v}); update_tree; -print "Checking for updated SlackBuilds...\n"; -my $updates = get_available_updates; - -# pretty formatting. -my @listing; -for my $key (keys @$updates) { - my $string = "$$updates[$key]{name}-$$updates[$key]{installed}"; - $string .= " < needs updating (SBo has $$updates[$key]{update})\n"; - push @listing, $string; +# retrieve and format list of available updates +sub get_update_list () { + print "Checking for updated SlackBuilds...\n"; + my $updates = get_available_updates; + # pretty formatting. + my @listing; + for my $update (@$updates) { + my $string = "$$update{name}-$$update{installed}"; + $string .= " < needs updating (SBo has $$update{update})\n"; + push @listing, $string; + } + return \@listing; } -if (exists $listing[0]) { - my $tab = new Text::Tabulate (); - $tab->configure (tab => '\s'); - my $output = $tab->format (@listing); - say "\n". $output; -} else { - say "\nNo updates available."; +# Text::Tabulate and print list of updates +sub print_output ($) { + exists $_[0] or script_error 'print_output requires an argument'; + my $listing = shift; + if (exists $$listing[0]) { + my $tab = new Text::Tabulate (); + $tab->configure (tab => '\s'); + my $output = $tab->format (@$listing); + say "\n". $output; + } else { + say "\nNo updates available."; + } } +my $output = get_update_list; +print_output $output; + exit 0; diff --git a/sboclean b/sboclean index fd6f5c8..558272b 100755 --- a/sboclean +++ b/sboclean @@ -49,7 +49,7 @@ unless ($clean_dist || $clean_work) { sub remove_stuff ($) { exists $_[0] or script_error 'remove_stuff requires an argument'; - -d $[0] or say "Nothing to do." and return 1; + -d $_[0] or say "Nothing to do." and return 1; my $dir = shift; opendir (my $dh, $dir); FIRST: while (my $ls = readdir $dh) { diff --git a/sboconfig b/sboconfig index 9c2682f..2065a27 100755 --- a/sboconfig +++ b/sboconfig @@ -98,7 +98,7 @@ sub config_write ($$) { # tie the file so that if $key is already there, we just change that # line and untie it tie my @temp, 'Tie::File', $tempfn; - my $has = 0; + my $has; my $regex = qr/\A\Q$key\E=/; FIRST: for my $tmpline (@temp) { $has++, $tmpline = "$key=$val", last FIRST if $tmpline =~ $regex; @@ -110,18 +110,19 @@ sub config_write ($$) { print {$fh} "$key=$val\n"; close $fh; } - move ($tempfn, $conf_file); + move ($tempfn, $conf_file) || return; } else { # no config file, easiest case of all. - my $fh = open_fh $conf_file, '>'; + my $fh = open_fh $conf_file, '>' || return; say {$fh} "$key=$val"; close $fh; } + return 1; } while (my ($key, $value) = each %changes) { print "Setting $key to $value...\n"; - config_write $key, $value; + config_write $key, $value or warn "Unable to write to $conf_file\n"; } exit 0; diff --git a/sbofind b/sbofind index e00f8de..16ad1b1 100755 --- a/sbofind +++ b/sbofind @@ -51,23 +51,28 @@ my $search = $ARGV[0]; slackbuilds_or_fetch; # find anything with $search in its name -my ($findings, $name); -my $found = 0; -my $name_regex = qr/NAME:\s+(.*\Q$search\E.*)$/i; -my $loc_regex = qr/LOCATION:\s+(.*)$/; -my $fh = open_read "$config{SBO_HOME}/SLACKBUILDS.TXT"; -FIRST: while (my $line = <$fh>) { - unless ($found) { - $found++, next FIRST if $name = ($line =~ $name_regex)[0]; - } else { - if (my ($location) = ($line =~ $loc_regex)[0]) { - $found = 0; - $location =~ s#^\.##; - push @$findings, {$name => $config{SBO_HOME} . $location}; +sub perform_search ($) { + exists $_[0] or script_error 'perform_search requires an argument.'; + my $search = shift; + my (@findings, $name, $found); + my $name_regex = qr/NAME:\s+(.*\Q$search\E.*)$/i; + my $loc_regex = qr/LOCATION:\s+(.*)$/; + my $fh = open_read "$config{SBO_HOME}/SLACKBUILDS.TXT"; + FIRST: while (my $line = <$fh>) { + unless ($found) { + $found++, next FIRST if $name = ($line =~ $name_regex)[0]; + } else { + if (my ($location) = ($line =~ $loc_regex)[0]) { + $found = 0; + $location =~ s#^\.##; + push @findings, {$name => $config{SBO_HOME} . $location}; + } } } + return \@findings; } +# pull the contents of a file into a variable and format it for output sub get_file_contents ($) { exists $_[0] or script_error 'get_file_contents requires an argument'; -f $_[0] or return "$_[0] doesn't exist.\n"; @@ -78,6 +83,8 @@ sub get_file_contents ($) { return $contents; } +perform_search $search; + # pretty formatting if (exists $$findings[0]) { my @listing = ("\n"); diff --git a/sboupgrade b/sboupgrade index cdc2ca2..6633834 100755 --- a/sboupgrade +++ b/sboupgrade @@ -95,10 +95,10 @@ sub get_inst_names ($) { return \@installed; } -# pull list of requirements, offer to install them -sub grok_requirements ($$$) { - exists $_[1] or script_error 'grok_requirements requires an argument.'; - my ($sbo, $location, $readme) = @_; +# pull list of requirements +sub get_requires ($$) { + exists $_[1] or script_error 'get_requires requires an argument.'; + my ($sbo, $location) = @_; my $requires = get_from_info (LOCATION => $location, GET => 'REQUIRES'); return unless $$requires[0]; # do nothing if a req list contains %README% @@ -109,7 +109,13 @@ sub grok_requirements ($$$) { GET => 'REQUIRES'); return if $sbo ~~ @$req_req; } - # else proceed + return $requires; +} + +# ask to install any requirements found +sub ask_requires ($$$) { + exists $_[2] or script_error 'ask_requires requires three arguments.'; + my ($requires, $readme, $sbo) = shift; for my $req (@$requires) { my $inst = get_installed_sbos; my $inst_names= get_inst_names $inst; @@ -123,36 +129,43 @@ sub grok_requirements ($$$) { } } } - return; } # look for any (user|group)add commands in the README -sub grok_user_group ($) { +sub get_user_group ($) { exists $_[0] or script_error 'grok_user_group requires an argument'; my $readme = shift; - my $readme_array = [split /\n/, $readme]; - my $cmd_regex = qr/^\s*#\s+((user|group)add.*)/; - my @cmds; - push @cmds, ($_ =~ $cmd_regex)[0] for @$readme_array; - return unless exists $cmds[0]; + my @cmds = $readme =~ /^\s*#*\s*(useradd.*|groupadd.*)/mg; + return @cmds; +} + +# offer to run any user/group add commands +sub ask_user_group ($$) { + exists $_[1] or script_error 'ask_user_group requires two arguments'; + my ($cmds, $readme) = shift; say "\n". $readme; - print "\nIt looks like this slackbuild requires the following command(s)"; - say " to be run first:"; - say " # $_" for @cmds; + print "\nIt looks like this slackbuild requires the following"; + say " command(s) to be run first:"; + say " # $_" for @$cmds; print "Shall I run it/them now? [y] "; if ( =~ /^[Yy\n]/) { - for my $cmd (@cmds) { - system ($cmd == 0) or warn "\"$cmd\" exited non-zero\n"; + for my $cmd (@$cmds) { + system ($cmd) == 0 or warn "\"$cmd\" exited non-zero\n"; } } - return 1; } # see if the README mentions any options -sub grok_options ($) { +sub get_opts ($) { exists $_[0] or script_error 'grok_options requires an argument'; my $readme = shift; - return unless $readme =~ /[A-Z]+=[^\s]/; + return $readme =~ /[A-Z]+=[^\s]/ ? 1 : undef; +} + +# provide an opportunity to set options +sub ask_opts ($) { + exists $_[0] or script_error 'ask_opts requires an argument'; + my $readme = shift; say "\n". $readme; print "\nIt looks this slackbuilds has options; would you like to set any"; print " when the slackbuild is run? [n] "; @@ -181,10 +194,15 @@ sub readme_prompt ($$) { my $fh = open_read (get_readme_path $sbo); my $readme = do {local $/; <$fh>}; close $fh; - # check for requirements, useradd/groupadd, options - grok_requirements $sbo, $location, $readme; - grok_user_group $readme; - my $opts = grok_options $readme; + # check for requirements, offer to install any found + my $requires = get_requires $sbo, $location; + ask_requires $requires, $readme, $sbo if ref $requires eq 'ARRAY'; + # check for user/group add commands, offer to run any found + my $user_group = get_user_group $readme; + ask_user_group $user_group, $readme if ref $user_group eq 'ARRAY'; + # check for options mentioned in the README + my $opts; + $opts = ask_opts $readme if get_opts $readme; print "\n". $readme unless $opts; # present the name as -compat32 if appropriate my $name = $compat32 ? "$sbo-compat32" : $sbo; @@ -197,7 +215,7 @@ sub readme_prompt ($$) { sub process_sbos ($) { exists $_[0] or script_error 'process_sbos requires an argument.'; my $todo = shift; - my @failures; + my %failures; FIRST: for my $sbo (@$todo) { my $opts = 0; $opts = readme_prompt $sbo, $locations{$sbo} unless $no_readme; @@ -211,7 +229,7 @@ sub process_sbos ($) { COMPAT32 => $compat32, ); }; if ($@) { - push @failures, $sbo; + $failures{$sbo} = $@; } else { unless ($distclean eq 'TRUE') { make_clean $sbo, $src, $version unless $noclean eq 'TRUE'; @@ -240,13 +258,16 @@ sub process_sbos ($) { } } } - return @failures; + return %failures; } -sub print_failures (;@) { +sub print_failures (;%) { if (exists $_[0]) { + my %failures = @_; say "Failures:"; - say " $_" for @_; + while (my ($key, $val) = each %failures) { + say " $key: $val"; + } exit 1; } } @@ -274,8 +295,8 @@ unless ($force) { push $todo_upgrade, $sbo if $sbo ~~ @$inst_names; } } -my @failures = process_sbos $todo_upgrade if exists $todo_upgrade[0]; -print_failures @failures; +my %failures = process_sbos $todo_upgrade if exists $todo_upgrade[0]; +print_failures %failures; INSTALL_NEW: exit 0 unless $install_new; @@ -302,7 +323,7 @@ FIRST: for my $sbo (@ARGV) { } push $todo_install, $sbo; } -@failures = process_sbos $todo_install if exists $todo_install[0]; -print_failures @failures; +%failures = process_sbos $todo_install if exists $todo_install[0]; +print_failures %failures; exit 0; diff --git a/t/SBO/Lib.pm~ b/t/SBO/Lib.pm~ deleted file mode 100644 index be29986..0000000 --- a/t/SBO/Lib.pm~ +++ /dev/null @@ -1,643 +0,0 @@ -#!/usr/bin/env perl -# -# vim: set ts=4:noet -# -# Lib.pm -# shared functions for the sbo_ scripts. -# -# author: Jacob Pipkin -# date: Setting Orange, the 37th day of Discord in the YOLD 3178 -# license: WTFPL - -use 5.16.0; -use warnings FATAL => 'all'; -use strict; - -package SBO::Lib 1.0; -my $version = "1.0"; - -require Exporter; -our @ISA = qw(Exporter); -our @EXPORT = qw(get_slack_version chk_slackbuilds_txt check_home rsync_sbo_tree get_sbo_from_loc get_sbo_version get_download_info get_arch get_sbo_downloads get_filename_from_link compute_md5sum compare_md5s check_distfile get_distfile get_symlink_from_filename check_x32 check_multilib rewrite_slackbuild revert_slackbuild create_symlinks grok_temp_file get_src_dir get_pkg_name perform_sbo - script_error - open_fh - open_read - show_version - slackbuilds_or_fetch - fetch_tree - update_tree - get_installed_sbos - get_available_updates - do_slackbuild - make_clean - make_distclean - do_upgradepkg - get_sbo_location - get_from_info -); - -#$< == 0 or die "This script requires root privileges.\n"; - -use Tie::File; -use Sort::Versions; -use Digest::MD5; -use File::Copy; -use File::Path qw(make_path remove_tree); -use Fcntl; -use File::Find; -use File::Temp qw(tempdir tempfile); -use Data::Dumper; - -our $tempdir = tempdir (CLEANUP => 1); - -# subroutine for throwing internal script errors -sub script_error (;$) { - exists $_[0] ? die "A fatal script error has occured:\n$_[0]\nExiting.\n" - : die "A fatal script error has occured. Exiting.\n"; -} - -# sub for opening files, second arg is like '<','>', etc -sub open_fh ($$) { - exists $_[1] or script_error 'open_fh requires two arguments'; - -f $_[0] or script_error 'open_fh first argument not a file'; - my ($file, $op) = @_; - open my $fh, $op, $file or die "Unable to open $file.\n"; - return $fh; -} - -sub open_read ($) { - return open_fh shift, '<'; -} - -# pull in configuration, set sane defaults, etc. -our $conf_dir = '/etc/sbotools'; -our $conf_file = "$conf_dir/sbotools.conf"; -our %config = ( - NOCLEAN => 'FALSE', - DISTCLEAN => 'FALSE', - JOBS => 'FALSE', - PKG_DIR => 'FALSE', - SBO_HOME => 'FALSE', -); - -# if the conf file exists, pull all the $key=$value pairs into a hash -my %conf_values; -if (-f $conf_file) { - my $fh = open_read $conf_file; - my $text = do {local $/; <$fh>}; - %conf_values = $text =~ /^(\w+)=(.*)$/mg; - close $fh; -} - -for my $key (keys %config) { - $config{$key} = $conf_values{$key} if exists $conf_values{$key}; -} -$config{JOBS} = 'FALSE' unless $config{JOBS} =~ /^\d+$/; -$config{SBO_HOME} = '/usr/sbo' if $config{SBO_HOME} eq 'FALSE'; - -# some stuff we'll need later. -my $distfiles = "$config{SBO_HOME}/distfiles"; -my $slackbuilds_txt = "$config{SBO_HOME}/SLACKBUILDS.TXT"; -my $name_regex = '\ASLACKBUILD\s+NAME:\s+'; - -sub show_version () { - print "sbotools version $version\n"; - print "licensed under the WTFPL\n"; - print "\n"; -} - -# %supported maps what's in /etc/slackware-version to what's at SBo -# which is now not needed since this version drops support < 14.0 -# but it's already future-proofed, so leave it. -sub get_slack_version () { - my %supported = ('14.0' => '14.0'); - my $fh = open_read '/etc/slackware-version'; - chomp (my $line = <$fh>); - close $fh; - my $version = ($line =~ /\s+(\d+[^\s]+)$/)[0]; - die "Unsupported Slackware version: $version\n" - unless $version ~~ %supported; - return $supported{$version}; -} - -# does the SLACKBUILDS.TXT file exist in the sbo tree? -sub chk_slackbuilds_txt () { - return -f $slackbuilds_txt ? 1 : 0; -} - -# check for the validity of new $config{SBO_HOME} -sub check_home () { - my $sbo_home = $config{SBO_HOME}; - if (-d $sbo_home) { - opendir (my $home_handle, $sbo_home); - FIRST: while (readdir $home_handle) { - next FIRST if /^\.[\.]{0,1}$/; - die "$sbo_home exists and is not empty. Exiting.\n"; - } - } else { - make_path ($sbo_home) or die "Unable to create $sbo_home.\n"; - } -} - -# rsync the sbo tree from slackbuilds.org to $config{SBO_HOME} -sub rsync_sbo_tree () { - my $slk_version = get_slack_version; - my @arg = ('rsync', '-a', '--exclude=*.tar.gz', '--exclude=*.tar.gz.asc'); - push @arg, "rsync://slackbuilds.org/slackbuilds/$slk_version/*"; - my $out = system @arg, $config{SBO_HOME}; - print "Finished.\n" and return $out; -} - -# wrappers for differing checks and output -sub fetch_tree () { - check_home; - print "Pulling SlackBuilds tree...\n"; - rsync_sbo_tree, return $?; -} - -sub update_tree () { - fetch_tree, return unless chk_slackbuilds_txt; - print "Updating SlackBuilds tree...\n"; - rsync_sbo_tree, return $?; -} - -# if the SLACKBUILDS.TXT is not in $config{SBO_HOME}, we assume the tree has -# not been populated there; prompt the user to automagickally pull the tree. -sub slackbuilds_or_fetch () { - unless (chk_slackbuilds_txt) { - print "It looks like you haven't run \"sbosnap fetch\" yet.\n"; - print "Would you like me to do this now? [y] "; - =~ /^[Yy\n]/ ? fetch_tree : - die "Please run \"sbosnap fetch\"\n"; - } - return 1; -} - -# pull an array of hashes, each hash containing the name and version of an sbo -# currently installed. -sub get_installed_sbos () { - my @installed; - # $1 == name, $2 == version - my $regex = qr#/([^/]+)-([^-]+)-[^-]+-[^-]+$#; - for my $path () { - my ($name, $version) = ($path =~ $regex)[0,1]; - push @installed, {name => $name, version => $version}; - } - return \@installed; -} - -# search the SLACKBUILDS.TXT for a given sbo's directory -sub get_sbo_location ($) { - exists $_[0] or script_error 'get_sbo_location requires an argument.'; - my $sbo = shift; - my $regex = qr#LOCATION:\s+\.(/[^/]+/$sbo)$#; - my $fh = open_read $slackbuilds_txt; - while (my $line = <$fh>) { - if (my $loc = ($line =~ $regex)[0]) { - return "$config{SBO_HOME}$loc"; - } - } - return; -} - -# pull the sbo name from a $location: $config{SBO_HOME}/system/wine, etc. -sub get_sbo_from_loc ($) { - exists $_[0] or script_error 'get_sbo_from_loc requires an argument.'; - return (shift =~ qr#/([^/]+)$#)[0]; -} - -# pull piece(s) of data, GET, from the $sbo.info file under LOCATION. -sub get_from_info { - warn " * * * * * * * * * * in get_from_info sub * * * * * * * * * *\n"; - my %args = ( - LOCATION => '', - GET => '', - @_ - ); - unless ($args{LOCATION} && $args{GET}) { - script_error 'get_from_info requires LOCATION and GET.'; - } - state $vars = {PKGNAM => ['']}; - my $sbo = get_sbo_from_loc $args{LOCATION}; - print Dumper ($vars); - return $$vars{$args{GET}} if $$vars{PKGNAM}[0] eq $sbo; - # if we haven't read in the .info file yet, do so now. - warn " * * * * * * * * * * parsing $sbo.info file * * * * * * * * * *\n"; - my $fh = open_read "$args{LOCATION}/$sbo.info"; - # suck it all in and join up the \ lines... - my $contents = do {local $/; <$fh>}; - $contents =~ s/("|\\\n)//g; - my %tmp = $contents =~ /^(\w+)=(.*)$/mg; - $vars = \%tmp; - # fill the hash with array refs - even for single values, - # since consistency here is a lot easier than sorting it out later - for my $key (keys %$vars) { - if ($$vars{$key} =~ /\s/) { - my @array = split ' ', $$vars{$key}; - $$vars{$key} = \@array; - } else { - $$vars{$key} = [$$vars{$key}]; - } - } - return $$vars{$args{GET}}; -} - -# find the version in the tree for a given sbo (provided a location) -sub get_sbo_version ($) { - exists $_[0] or script_error 'get_sbo_version requires an argument.'; - my $version = get_from_info (LOCATION => shift, GET => 'VERSION'); - return $$version[0] ? $$version[0] : 0; -} - -# for each installed sbo, find out whether or not the version in the tree is -# newer, and compile an array of hashes containing those which are -sub get_available_updates () { - my @updates; - my $pkg_list = get_installed_sbos; - FIRST: for my $key (keys @$pkg_list) { - my $location = get_sbo_location $$pkg_list[$key]{name}; - # if we can't find a location, assume invalid and skip - next FIRST unless defined $location; - my $version = get_sbo_version $location; - if (versioncmp ($version, $$pkg_list[$key]{version}) == 1) { - push @updates, { - name => $$pkg_list[$key]{name}, - installed => $$pkg_list[$key]{version}, - update => $version - }; - } - } - return \@updates; -} - -# get downloads and md5sums from an sbo's .info file, first -# checking for x86_64-specific info if we are told to -sub get_download_info { - my %args = ( - LOCATION => 0, - X64 => 1, - @_ - ); - $args{LOCATION} or script_error 'get_download_info requires LOCATION.'; - my ($get, $downs, $md5s, %return); - $get = ($args{X64} ? 'DOWNLOAD_x86_64' : 'DOWNLOAD'); - $downs = get_from_info (LOCATION => $args{LOCATION}, GET => $get); - # did we get nothing back, or UNSUPPORTED/UNTESTED? - if ($args{X64}) { - my $nothing; - if (! $$downs[0]) { - $nothing = 1; - } elsif ($$downs[0] =~ qr/^UN(SUPPOR|TES)TED$/) { - $nothing = 1; - } - if ($nothing) { - $args{X64} = 0; - $downs = get_from_info (LOCATION => $args{LOCATION}, - GET => 'DOWNLOAD'); - } - } - # if we still don't have any links, something is really wrong. - return unless $$downs[0]; - # grab the md5s and build a hash - $get = $args{X64} ? 'MD5SUM_x86_64' : 'MD5SUM'; - $md5s = get_from_info (LOCATION => $args{LOCATION}, GET => $get); - return unless $$md5s[0]; - $return{$$downs[$_]} = $$md5s[$_] for (keys @$downs); - return %return; -} - -sub get_arch () { - chomp (my $arch = `uname -m`); - return $arch; -} - -# TODO: should probably combine this with get_download_info -sub get_sbo_downloads { - my %args = ( - LOCATION => '', - 32 => 0, - @_ - ); - $args{LOCATION} or script_error 'get_sbo_downloads requires LOCATION.'; - my $location = $args{LOCATION}; - -d $location or script_error 'get_sbo_downloads given a non-directory.'; - my $arch = get_arch; - my %dl_info; - if ($arch eq 'x86_64') { - %dl_info = get_download_info (LOCATION => $location) unless $args{32}; - } - unless (keys %dl_info > 0) { - %dl_info = get_download_info (LOCATION => $location, X64 => 0); - } - return %dl_info; -} - -# given a link, grab the filename from the end of it -sub get_filename_from_link ($) { - exists $_[0] or script_error 'get_filename_from_link requires an argument'; - return "$distfiles/". (shift =~ qr#/([^/]+)$#)[0]; -} - -# for a given file, computer its md5sum -sub compute_md5sum ($) { - -f $_[0] or script_error 'compute_md5sum requires a file argument.'; - my $fh = open_read shift; - my $md5 = Digest::MD5->new; - $md5->addfile ($fh); - my $md5sum = $md5->hexdigest; - close $fh; - return $md5sum; -} - -sub compare_md5s ($$) { - exists $_[1] or script_error 'compare_md5s requires two arguments.'; - my ($first, $second) = @_; - return $first eq $second ? 1 : 0; -} - -# for a given distfile, see whether or not it exists, and if so, if its md5sum -# matches the sbo's .info file -sub check_distfile ($$) { - exists $_[1] or script_error 'check_distfile requires two arguments.'; - my ($link, $info_md5sum) = @_; - my $filename = get_filename_from_link $link; - return unless -d $distfiles; - return unless -f $filename; - my $md5sum = compute_md5sum $filename; - return compare_md5s $info_md5sum, $md5sum; -} - -# for a given distfile, attempt to retrieve it and, if successful, check its -# md5sum against that in the sbo's .info file -sub get_distfile ($$) { - exists $_[1] or script_error 'get_distfile requires an argument'; - my ($link, $exp_md5) = @_; - my $filename = get_filename_from_link $link; - mkdir $distfiles unless -d $distfiles; - chdir $distfiles; - system ("wget --no-check-certificate $link") == 0 or - die "Unable to wget $link\n"; - my $md5sum = compute_md5sum $filename; - # can't do anything if the link in the .info doesn't lead to a good d/l - compare_md5s $md5sum, $exp_md5 or die "md5sum failure for $filename.\n"; - return 1; -} - -# for a given distfile, figure out what the full path to its symlink will be -sub get_symlink_from_filename ($$) { - exists $_[1] or script_error - 'get_symlink_from_filename requires two arguments'; - -f $_[0] or script_error - 'get_symlink_from_filename first argument is not a file'; - my ($filename, $location) = @_; - return "$location/". ($filename =~ qr#/([^/]+)$#)[0]; -} - -# determine whether or not a given sbo is 32-bit only -sub check_x32 ($) { - exists $_[0] or script_error 'check_x32 requires an argument.'; - my $dl = get_from_info (LOCATION => shift, GET => 'DOWNLOAD_x86_64'); - return $$dl[0] =~ /UN(SUPPOR|TES)TED/ ? 1 : 0; -} - -# can't do 32-bit on x86_64 without this file, so we'll use it as the test to -# to determine whether or not an x86_64 system is setup for multilib -sub check_multilib () { - return 1 if -f '/etc/profile.d/32dev.sh'; - return; -} - -# make a backup of the existent SlackBuild, and rewrite the original as needed -sub rewrite_slackbuild ($$%) { - exists $_[1] or script_error 'rewrite_slackbuild requires two arguments.'; - my ($slackbuild, $tempfn, %changes) = @_; - copy ($slackbuild, "$slackbuild.orig") or - die "Unable to backup $slackbuild to $slackbuild.orig\n"; - my $tar_regex = qr/(un|)tar .*$/; - my $makepkg_regex = qr/makepkg/; - my $libdir_regex = qr/^\s*LIBDIRSUFFIX="64"\s*$/; - my $make_regex = qr/^\s*make(| \Q||\E exit 1)$/; - my $arch_regex = qr/\$VERSION-\$ARCH-\$BUILD/; - # tie the slackbuild, because this is the easiest way to handle this. - tie my @sb_file, 'Tie::File', $slackbuild; - for my $line (@sb_file) { - # get the output of the tar and makepkg commands. hope like hell that v - # is specified among tar's arguments - if ($line =~ $tar_regex || $line =~ $makepkg_regex) { - $line = "$line | tee -a $tempfn"; - } - # then check for and apply any other %changes - if (exists $changes{libdirsuffix}) { - $line =~ s/64/$changes{libdirsuffix}/ if $line =~ $libdir_regex; - } - if (exists $changes{make}) { - $line =~ s/make/make $changes{make}/ if $line =~ $make_regex; - } - if (exists $changes{arch_out}) { - $line =~ s/\$ARCH/$changes{arch_out}/ if $line =~ $arch_regex; - } - } - untie @sb_file; - return 1; -} - -# move a backed-up .SlackBuild file back into place -sub revert_slackbuild ($) { - exists $_[0] or script_error 'revert_slackbuild requires an argument'; - my $slackbuild = shift; - if (-f "$slackbuild.orig") { - unlink $slackbuild if -f $slackbuild; - rename ("$slackbuild.orig", $slackbuild); - } - return 1; -} - -# given a location and a list of download links, assemble a list of symlinks, -# and create them. -sub create_symlinks ($%) { - exists $_[1] or script_error 'create_symlinks requires two arguments.'; - my ($location, %downloads) = @_; - my @symlinks; - for my $link (keys %downloads) { - my $md5sum = $downloads{$link}; - unless (check_distfile $link, $md5sum) { - die unless get_distfile $link, $md5sum; - } - my $filename = get_filename_from_link $link; - my $symlink = get_symlink_from_filename $filename, $location; - push @symlinks, $symlink; - symlink $filename, $symlink; - } - return @symlinks; -} - -# pull the untarred source directory or created package name from the temp -# file (the one we tee'd to) -sub grok_temp_file { - my %args = ( - TEMPFN => '', - REGEX => '', - CAPTURE => 0, - @_ - ); - unless ($args{TEMPFN} && $args{REGEX}) { - script_error 'grok_temp_file requires two arguments'; - } - my $out; - my $fh = open_read $args{TEMPFN}; - FIRST: while (my $line = <$fh>) { - if ($line =~ $args{REGEX}) { - $out = ($line =~ $args{REGEX})[$args{CAPTURE}]; - last FIRST; - } - } - close $fh; - return $out; -} - -# wrappers around grok_temp_file -sub get_src_dir ($) { - exists $_[0] or script_error 'get_src_dir requires an argument'; - return grok_temp_file (TEMPFN => shift, REGEX => qr#^([^/]+)/#); -} - -sub get_pkg_name ($) { - exists $_[0] or script_error 'get_pkg_name requires an argument'; - return grok_temp_file (TEMPFN => shift, - REGEX => qr/^Slackware\s+package\s+([^\s]+)\s+created\.$/); -} - -# prep and run .SlackBuild -sub perform_sbo { - my %args = ( - OPTS => 0, - JOBS => 0, - LOCATION => '', - ARCH => '', - C32 => 0, - X32 => 0, - @_ - ); - unless ($args{LOCATION} && $args{ARCH}) { - script_error 'perform_sbo requires LOCATION and ARCH.'; - } - my $location = $args{LOCATION}; - my $sbo = get_sbo_from_loc $location; - my ($cmd, %changes); - $changes{make} = "-j $args{JOBS}" if $args{JOBS}; - if ($args{ARCH} eq 'x86_64' and ($args{C32} || $args{X32}) ) { - if ($args{C32}) { - $changes{libdirsuffix} = ''; - } elsif ($args{X32}) { - $changes{arch_out} = 'i486'; - } - $cmd = ". /etc/profile.d/32dev.sh &&"; - } - $cmd .= "/bin/sh $location/$sbo.SlackBuild"; - $cmd = "$args{OPTS} $cmd" if $args{OPTS}; - my ($tempfh, $tempfn) = tempfile (DIR => $tempdir); - close $tempfh; - rewrite_slackbuild "$location/$sbo.SlackBuild", $tempfn, %changes; - chdir $location, my $out = system $cmd; - revert_slackbuild "$location/$sbo.SlackBuild"; - die unless $out == 0; - my $src = get_src_dir $tempfn; - my $pkg = get_pkg_name $tempfn; - unlink $tempfn; - return $pkg, $src; -} - -# "public interface", sort of thing. -sub do_slackbuild { - my %args = ( - OPTS => 0, - JOBS => 0, - LOCATION => '', - COMPAT32 => 0, - @_ - ); - $args{LOCATION} or script_error 'do_slackbuild requires LOCATION.'; - my $location = $args{LOCATION}; - my $sbo = get_sbo_from_loc $location; - my $arch = get_arch; - my $multi = check_multilib; - my $version = get_sbo_version $location; - my $x32; - if ($args{COMPAT32}) { - die "compat32 only works on x86_64.\n" unless $arch eq 'x86_64'; - die "compat32 requires multilib.\n" unless $multi; - die "compat32 requires /usr/sbin/convertpkg-compat32.\n" - unless -f '/usr/sbin/convertpkg-compat32'; - } else { - if ($arch eq 'x86_64') { - $x32 = check_x32 $args{LOCATION}; - if ($x32 && ! $multi) { - die "$sbo is 32-bit which requires multilib on x86_64.\n"; - } - } - } - my %downloads = get_sbo_downloads ( - LOCATION => $location, - 32 => $args{COMPAT32} - ); - my @symlinks = create_symlinks $args{LOCATION}, %downloads; - my ($pkg, $src) = perform_sbo ( - OPTS => $args{OPTS}, - JOBS => $args{JOBS}, - LOCATION => $location, - ARCH => $arch, - C32 => $args{COMPAT32}, - X32 => $x32, - ); - if ($args{COMPAT32}) { - my ($tempfh, $tempfn) = tempfile (DIR => $tempdir); - close $tempfh; - my $cmd = "/usr/sbin/convertpkg-compat32 -i $pkg -d /tmp | tee $tempfn"; - system ($cmd) == 0 or die; - unlink $pkg; - $pkg = get_pkg_name $tempfn; - } - unlink $_ for @symlinks; - return $version, $pkg, $src; -} - -# remove work directories (source and packaging dirs under /tmp/SBo) -sub make_clean ($$$) { - exists $_[2] or script_error 'make_clean requires three arguments.'; - my ($sbo, $src, $version) = @_; - print "Cleaning for $sbo-$version...\n"; - my $tmpsbo = "/tmp/SBo"; - remove_tree ("$tmpsbo/$src") if -d "$tmpsbo/$src"; - remove_tree ("$tmpsbo/package-$sbo") if -d "$tmpsbo/package-$sbo"; - return 1; -} - -# remove distfiles -sub make_distclean { - my %args = ( - SRC => '', - VERSION => '', - LOCATION => '', - @_ - ); - unless ($args{SRC} && $args{VERSION} && $args{LOCATION}) { - script_error 'make_distclean requires four arguments.'; - } - my $sbo = get_sbo_from_loc $args{LOCATION}; - make_clean $sbo, $args{SRC}, $args{VERSION}; - print "Distcleaning for $sbo-$args{VERSION}...\n"; - # remove any distfiles for this particular SBo. - my %downloads = get_sbo_downloads (LOCATION => $args{LOCATION}); - for my $key (keys %downloads) { - my $filename = get_filename_from_link $key; - unlink $filename if -f $filename; - } - return 1; -} - -# run upgradepkg for a created package -sub do_upgradepkg ($) { - exists $_[0] or script_error 'do_upgradepkg requires an argument.'; - system ('/sbin/upgradepkg', '--reinstall', '--install-new', shift); - return 1; -} diff --git a/t/prep.pl b/t/prep.pl index 08efc61..c5591dc 100755 --- a/t/prep.pl +++ b/t/prep.pl @@ -1,5 +1,6 @@ #!/usr/bin/perl +use 5.16.0; use strict; use warnings FATAL => 'all'; use File::Copy; @@ -8,6 +9,49 @@ use Tie::File; chomp (my $pwd = `pwd`); mkdir "$pwd/SBO" unless -d "$pwd/SBO"; copy ('/home/d4wnr4z0r/projects/slack14/sbotools/SBO-Lib/lib/SBO/Lib.pm', "$pwd/SBO"); + +open my $write, '>>', "$pwd/SBO/Lib.pm"; + +print {$write} "my \$interactive = 1;\n"; +print {$write} "my \%locations;"; +print {$write} "my \$compat32 = 1;\n"; +print {$write} "my \$no_readme = 1;\n"; +print {$write} "my \$jobs = 1;\n"; +print {$write} "my \$distclean = 1;\n"; +print {$write} "my \$noclean = 1;\n"; +print {$write} "my \$no_install = 1;\n"; + +sub get_subs ($) { + my $read = shift; + my $begin_regex = qr/^sub\s+[a-z0-9_]+/; + my $usage_regex = qr/^sub\s+show_usage/; + my $end_regex = qr/^}$/; + my $begin = 0; + my $end = 0; + while (my $line = <$read>) { + if (! $begin) { + if ($line =~ $begin_regex) { + if ($line !~ $usage_regex) { + $end = 0, $begin++, print {$write} $line; + } + } + } elsif (! $end) { + if ($line =~ $end_regex) { + $begin = 0, $end++, print {$write} $line; + } else { + print {$write} $line; + } + } + } +} + +for my $file (qw(sbocheck sboclean sboconfig sbofind sboupgrade)) { + open my $read, '<', "../$file"; + get_subs $read; + close $read; +} +close $write; + my @subs; open my $file_h, '<', "$pwd/SBO/Lib.pm"; my $regex = qr/^sub\s+([^\s]+)\s+/; diff --git a/t/test.t b/t/test.t index aabb5fa..36306c4 100755 --- a/t/test.t +++ b/t/test.t @@ -4,7 +4,7 @@ use 5.16.0; use strict; use warnings FATAL => 'all'; use File::Temp qw(tempdir tempfile); -use Test::More tests => 61; +use Test::More tests => 87; use File::Copy; use Text::Diff; use SBO::Lib; @@ -210,5 +210,74 @@ is ($$info[0], 'http://www.libimobiledevice.org', 'get_from_info GET => HOMEPAGE $info = get_from_info (%params, GET => 'DOWNLOAD_x86_64'); is ($$info[0], "", 'get_from_info GET => DOWNLOAD_x86_64 is good'); +# 62-64, get_update_list tests +my $listing = get_update_list; +s/\s//g for @$listing; +for my $item (@$listing) { + is ($item, 'zdoom-2.5.0}; +close $fh; +my @cmds = get_user_group $readme; +is ($cmds[0], 'groupadd -g 213 nagios', 'get_user_group good for # groupadd'); +is ($cmds[1], 'useradd -u 213 -d /dev/null -s /bin/false -g nagios nagios', 'get_user_group for # useradd'); +$fh = open_read "$sbo_home/network/havp/README"; +$readme = do {local $/; <$fh>}; +close $fh; +@cmds = get_user_group $readme; +is ($cmds[0], 'groupadd -g 210 clamav', 'get_user_group good for groupadd'); +is ($cmds[1], 'useradd -u 256 -d /dev/null -s /bin/false -g clamav havp', 'get_user_group good for useradd'); -#is (do_convertpkg ($package), "$package-compat32", 'do_convertpkg good'); +# 86-87, get_opts test +$fh = open_read "$sbo_home/games/vbam/README"; +$readme = do {local $/; <$fh>}; +close $fh; +ok (get_opts $readme, 'get_opts good where README defines opts'); +$fh = open_read "$sbo_home/libraries/libmatchbox/README"; +$readme = do {local $/; <$fh>}; +close $fh; +ok (! (get_opts $readme), 'get_opts good where README does not define opts'); -- cgit v1.2.3 From e0bfabea2f76f45f8bb1450221d0d10cbcc9a516 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sat, 1 Sep 2012 00:09:16 -0500 Subject: make test.t use lib . instead of perl -I --- t/test.t | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/t/test.t b/t/test.t index 36306c4..0230830 100755 --- a/t/test.t +++ b/t/test.t @@ -1,4 +1,4 @@ -#!/usr/bin/perl -I/home/d4wnr4z0r/projects/slack14/sbotools/t +#!/usr/bin/env perl use 5.16.0; use strict; @@ -7,6 +7,7 @@ use File::Temp qw(tempdir tempfile); use Test::More tests => 87; use File::Copy; use Text::Diff; +use lib "."; use SBO::Lib; my $sbo_home = '/home/d4wnr4z0r/sbo.git/slackbuilds'; -- cgit v1.2.3 From 6be3ef603fefc5d04b506b17cbad140790698042 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sat, 1 Sep 2012 02:14:32 -0500 Subject: more cleanups and fixes and such --- SBO-Lib/lib/SBO/Lib.pm | 6 +++++- sbocheck | 8 ++------ sboclean | 6 +++--- sboconfig | 38 +++++++++++++++++++++----------------- sbofind | 6 +++--- sboinstall | 4 ++-- sbosnap | 6 +++--- sboupgrade | 6 +++--- 8 files changed, 42 insertions(+), 38 deletions(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 94ce3be..c5acbd3 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -36,6 +36,10 @@ our @EXPORT = qw( get_from_info get_tmp_extfn get_tmp_perlfn + $tempdir + $conf_dir + $conf_file + %config ); $< == 0 or die "This script requires root privileges.\n"; @@ -539,7 +543,7 @@ sub get_tmp_extfn ($) { sub get_tmp_perlfn ($) { exists $_[0] or script_error 'get_tmp_perlfn requires an argument.'; my $fh = clear_coe_bit shift; - return '+<=&'. fileno $fh; + return "+<=&". fileno $fh; } # prep and run .SlackBuild diff --git a/sbocheck b/sbocheck index d2e6f91..e85042a 100755 --- a/sbocheck +++ b/sbocheck @@ -10,15 +10,11 @@ # license: WTFPL use 5.16.0; +use strict; +use warnings FATAL => 'all'; use SBO::Lib; -use File::Basename; use Getopt::Std; use Text::Tabulate; -use warnings FATAL => 'all'; -use strict; - -my %config = %SBO::Lib::config; -my $self = basename ($0); my %options; getopts ('v',\%options); diff --git a/sboclean b/sboclean index 558272b..d85b7bc 100755 --- a/sboclean +++ b/sboclean @@ -10,14 +10,14 @@ # license: WTFPL use 5.16.0; +use strict; +use warnings FATAL => 'all'; use SBO::Lib; use File::Basename; use Getopt::Std; use File::Path qw(remove_tree); -use strict; -use warnings FATAL => 'all'; -my %config = %SBO::Lib::config; +#my %config = %SBO::Lib::config; my $self = basename ($0); sub show_usage () { diff --git a/sboconfig b/sboconfig index 2065a27..aca2ad1 100755 --- a/sboconfig +++ b/sboconfig @@ -19,7 +19,7 @@ use File::Copy; use File::Path qw(make_path); use File::Temp qw(tempfile);; -my %config = %SBO::Lib::config; +#my %config = %SBO::Lib::config; my $self = basename ($0); sub show_usage () { @@ -80,11 +80,11 @@ if (exists $changes{JOBS}) { ($changes{JOBS} =~ /^\d+$/ || $changes{JOBS} eq 'FALSE'); } -my $conf_dir = $SBO::Lib::conf_dir; -my $conf_file = $SBO::Lib::conf_file; +#my $conf_dir = $SBO::Lib::conf_dir; +#my $conf_file = $SBO::Lib::conf_file; -# safely modify our conf file; copy to a temp location, edit the temp file, -# move the edited file into place +# safely modify our conf file; write its contents to a temp file, modify the +# temp file, write the contents of the temp file back to the conf file sub config_write ($$) { exists $_[1] or script_error 'config_write requires two arguments.'; my ($key, $val) = @_; @@ -92,12 +92,14 @@ sub config_write ($$) { mkdir $conf_dir or die "Unable to create $conf_dir. Exiting.\n"; } if (-f $conf_file) { - my $tempfh = tempfile (DIR => $SBO::Lib::tempdir); - my $tempfn = get_tmp_perlfn $tempfh; - copy ($conf_file, $tempfn); +# my $tempfh = tempfile (DIR => $SBO::Lib::tempdir); + my $tempfh = tempfile (DIR => $tempdir); + my $conffh = open_read $conf_file; + my $conftents = do {local $/; <$conffh>}; + print {$tempfh} $conftents; # tie the file so that if $key is already there, we just change that # line and untie it - tie my @temp, 'Tie::File', $tempfn; + tie my @temp, 'Tie::File', $tempfh; my $has; my $regex = qr/\A\Q$key\E=/; FIRST: for my $tmpline (@temp) { @@ -105,16 +107,18 @@ sub config_write ($$) { } untie @temp; # otherwise, append our new $key=$value pair - unless ($has) { - my $fh = open_fh ($tempfn, '>>'); - print {$fh} "$key=$val\n"; - close $fh; - } - move ($tempfn, $conf_file) || return; + print {$tempfh} "$key=$val\n" unless $has; + seek $tempfh, 0, 0; + my $contents = do {local $/; <$tempfh>}; + close $conffh; + eval { $conffh = open_fh $conf_file, '>>' }; + warn "Cannot write configuration: $@\n", return if $@; + print {$conffh} $contents or return; + close $conffh, close $tempfh; } else { # no config file, easiest case of all. - my $fh = open_fh $conf_file, '>' || return; - say {$fh} "$key=$val"; + my $fh = open_fh $conf_file, '>' or return; + print {$fh} "$key=$val\n"; close $fh; } return 1; diff --git a/sbofind b/sbofind index 16ad1b1..63ef7e9 100755 --- a/sbofind +++ b/sbofind @@ -10,13 +10,13 @@ # license: WTFPL use 5.16.0; +use strict; +use warnings FATAL => 'all'; use SBO::Lib; use File::Basename; use Getopt::Std; -use strict; -use warnings FATAL => 'all'; -my %config = %SBO::Lib::config; +#my %config = %SBO::Lib::config; my $self = basename ($0); sub show_usage () { diff --git a/sboinstall b/sboinstall index 3637207..54459b9 100755 --- a/sboinstall +++ b/sboinstall @@ -10,11 +10,11 @@ # license: WTFPL use 5.16.0; +use strict; +use warnings FATAL => 'all'; use SBO::Lib; use Getopt::Std; use File::Basename; -use strict; -use warnings FATAL => 'all'; my $self = basename ($0); diff --git a/sbosnap b/sbosnap index 076cfb9..d17b8c7 100755 --- a/sbosnap +++ b/sbosnap @@ -13,13 +13,13 @@ # .01: initial creation. use 5.16.0; +use strict; +use warnings FATAL => 'all'; use SBO::Lib; use File::Basename; use Getopt::Std; -use warnings FATAL => 'all'; -use strict; -my %config = %SBO::Lib::config; +#my %config = %SBO::Lib::config; my $sbo_home = $config{SBO_HOME}; my $self = basename ($0); diff --git a/sboupgrade b/sboupgrade index 6633834..0403712 100755 --- a/sboupgrade +++ b/sboupgrade @@ -10,14 +10,14 @@ # license: WTFPL use 5.16.0; +use strict; +use warnings FATAL => 'all'; use SBO::Lib; use File::Basename; use Getopt::Std; use File::Copy; -use strict; -use warnings FATAL => 'all'; -my %config = %SBO::Lib::config; +#my %config = %SBO::Lib::config; my $self = basename ($0); sub show_usage () { -- cgit v1.2.3 From 90cd9a74b8b562bebd4a2eaeb01ccdb3d2a75c42 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sat, 1 Sep 2012 02:22:57 -0500 Subject: fix >> to > --- sboconfig | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/sboconfig b/sboconfig index aca2ad1..e993430 100755 --- a/sboconfig +++ b/sboconfig @@ -97,8 +97,8 @@ sub config_write ($$) { my $conffh = open_read $conf_file; my $conftents = do {local $/; <$conffh>}; print {$tempfh} $conftents; - # tie the file so that if $key is already there, we just change that - # line and untie it + # tie the temp file so that if $key is already there, we just change + # that line and untie it tie my @temp, 'Tie::File', $tempfh; my $has; my $regex = qr/\A\Q$key\E=/; @@ -108,11 +108,12 @@ sub config_write ($$) { untie @temp; # otherwise, append our new $key=$value pair print {$tempfh} "$key=$val\n" unless $has; + # then over the conf file with the contents of the temp file seek $tempfh, 0, 0; my $contents = do {local $/; <$tempfh>}; close $conffh; - eval { $conffh = open_fh $conf_file, '>>' }; - warn "Cannot write configuration: $@\n", return if $@; + eval { $conffh = open_fh $conf_file, '>' }; + warn "Cannot write configuration: $@\n" and return if $@; print {$conffh} $contents or return; close $conffh, close $tempfh; } else { -- cgit v1.2.3 From 22e595ded4d1bc5bf6b8987ffcdd0f522d1a1bd0 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sat, 1 Sep 2012 03:29:58 -0500 Subject: more cleanups --- SBO-Lib/lib/SBO/Lib.pm | 19 ++----------------- sboclean | 1 - sboconfig | 7 +------ sbofind | 1 - sbosnap | 3 --- sboupgrade | 1 - 6 files changed, 3 insertions(+), 29 deletions(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index c5acbd3..ff3c681 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -35,7 +35,6 @@ our @EXPORT = qw( get_sbo_location get_from_info get_tmp_extfn - get_tmp_perlfn $tempdir $conf_dir $conf_file @@ -524,28 +523,14 @@ sub get_pkg_name ($) { REGEX => qr/^Slackware\s+package\s+([^\s]+)\s+created\.$/); } -# clear the close-on-exec bit from a temp file handle -sub clear_coe_bit ($) { - exists $_[0] or script_error 'clear_coe_bit requires an argument'; - my $fh = shift; - fcntl ($fh, F_SETFD, 0) or die "no unset exec-close thingy\n"; - return $fh; -} - # return a filename from a temp fh for use externally sub get_tmp_extfn ($) { exists $_[0] or script_error 'get_tmp_extfn requires an argument.'; - my $fh = clear_coe_bit shift; + my $fh = shift; + fcntl ($fh, F_SETFD, 0) or die "Can't unset exec-on-close bit\n"; return '/dev/fd/'. fileno $fh; } -# return a filename from a temp fh for use internally -sub get_tmp_perlfn ($) { - exists $_[0] or script_error 'get_tmp_perlfn requires an argument.'; - my $fh = clear_coe_bit shift; - return "+<=&". fileno $fh; -} - # prep and run .SlackBuild sub perform_sbo (%) { my %args = ( diff --git a/sboclean b/sboclean index d85b7bc..b5588c7 100755 --- a/sboclean +++ b/sboclean @@ -17,7 +17,6 @@ use File::Basename; use Getopt::Std; use File::Path qw(remove_tree); -#my %config = %SBO::Lib::config; my $self = basename ($0); sub show_usage () { diff --git a/sboconfig b/sboconfig index e993430..c181b29 100755 --- a/sboconfig +++ b/sboconfig @@ -19,7 +19,6 @@ use File::Copy; use File::Path qw(make_path); use File::Temp qw(tempfile);; -#my %config = %SBO::Lib::config; my $self = basename ($0); sub show_usage () { @@ -80,9 +79,6 @@ if (exists $changes{JOBS}) { ($changes{JOBS} =~ /^\d+$/ || $changes{JOBS} eq 'FALSE'); } -#my $conf_dir = $SBO::Lib::conf_dir; -#my $conf_file = $SBO::Lib::conf_file; - # safely modify our conf file; write its contents to a temp file, modify the # temp file, write the contents of the temp file back to the conf file sub config_write ($$) { @@ -92,7 +88,6 @@ sub config_write ($$) { mkdir $conf_dir or die "Unable to create $conf_dir. Exiting.\n"; } if (-f $conf_file) { -# my $tempfh = tempfile (DIR => $SBO::Lib::tempdir); my $tempfh = tempfile (DIR => $tempdir); my $conffh = open_read $conf_file; my $conftents = do {local $/; <$conffh>}; @@ -108,7 +103,7 @@ sub config_write ($$) { untie @temp; # otherwise, append our new $key=$value pair print {$tempfh} "$key=$val\n" unless $has; - # then over the conf file with the contents of the temp file + # then over write the conf file with the contents of the temp file seek $tempfh, 0, 0; my $contents = do {local $/; <$tempfh>}; close $conffh; diff --git a/sbofind b/sbofind index 63ef7e9..180df7a 100755 --- a/sbofind +++ b/sbofind @@ -16,7 +16,6 @@ use SBO::Lib; use File::Basename; use Getopt::Std; -#my %config = %SBO::Lib::config; my $self = basename ($0); sub show_usage () { diff --git a/sbosnap b/sbosnap index d17b8c7..9072941 100755 --- a/sbosnap +++ b/sbosnap @@ -9,8 +9,6 @@ # author: Jacob Pipkin # date: Setting Orange, the 37th day of Discord in the YOLD 3178 # license: WTFPL -# changelog: -# .01: initial creation. use 5.16.0; use strict; @@ -19,7 +17,6 @@ use SBO::Lib; use File::Basename; use Getopt::Std; -#my %config = %SBO::Lib::config; my $sbo_home = $config{SBO_HOME}; my $self = basename ($0); diff --git a/sboupgrade b/sboupgrade index 0403712..842e833 100755 --- a/sboupgrade +++ b/sboupgrade @@ -17,7 +17,6 @@ use File::Basename; use Getopt::Std; use File::Copy; -#my %config = %SBO::Lib::config; my $self = basename ($0); sub show_usage () { -- cgit v1.2.3 From 8b08c603ae79c145bc3b344f6dca4f0a95ed6201 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sat, 1 Sep 2012 04:52:02 -0500 Subject: more and more cleanups and fixes --- SBO-Lib/lib/SBO/Lib.pm | 26 ++++++++++++------------ sbocheck | 2 +- sboconfig | 2 +- sbofind | 2 +- sboinstall | 1 - sboupgrade | 55 ++++++++++++++++++++++++++++---------------------- t/prep.pl | 19 +++++++++-------- t/test.t | 17 ++++++++-------- 8 files changed, 67 insertions(+), 57 deletions(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index ff3c681..2325153 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -10,8 +10,8 @@ # license: WTFPL use 5.16.0; -use warnings FATAL => 'all'; use strict; +use warnings FATAL => 'all'; package SBO::Lib 1.0; my $version = "1.0"; @@ -56,8 +56,8 @@ our $tempdir = tempdir (CLEANUP => 1); # subroutine for throwing internal script errors sub script_error (;$) { - exists $_[0] ? die "A fatal script error has occured:\n$_[0]\nExiting.\n" - : die "A fatal script error has occured. Exiting.\n"; + exists $_[0] ? die "A fatal script error has occurred:\n$_[0]\nExiting.\n" + : die "A fatal script error has occurred. Exiting.\n"; } # sub for opening files, second arg is like '<','>', etc @@ -131,7 +131,7 @@ sub get_slack_version () { # does the SLACKBUILDS.TXT file exist in the sbo tree? sub chk_slackbuilds_txt () { - return -f $slackbuilds_txt ? 1 : 0; + return -f $slackbuilds_txt ? 1 : undef; } # check for the validity of new $config{SBO_HOME} @@ -151,7 +151,7 @@ sub check_home () { # rsync the sbo tree from slackbuilds.org to $config{SBO_HOME} sub rsync_sbo_tree () { - my $slk_version = get_slack_version; + my $slk_version = get_slack_version; my @arg = ('rsync', '-a', '--exclude=*.tar.gz', '--exclude=*.tar.gz.asc'); push @arg, "rsync://slackbuilds.org/slackbuilds/$slk_version/*"; my $out = system @arg, $config{SBO_HOME}; @@ -160,13 +160,13 @@ sub rsync_sbo_tree () { # wrappers for differing checks and output sub fetch_tree () { - check_home; + check_home; say 'Pulling SlackBuilds tree...'; rsync_sbo_tree, return 1; } sub update_tree () { - fetch_tree, return unless chk_slackbuilds_txt; + fetch_tree, return unless chk_slackbuilds_txt; say 'Updating SlackBuilds tree...'; rsync_sbo_tree, return 1; } @@ -184,7 +184,7 @@ sub slackbuilds_or_fetch () { } # pull an array of hashes, each hash containing the name and version of an sbo -# currently installed. +# currently installed. sub get_installed_sbos () { my @installed; # $1 == name, $2 == version @@ -245,14 +245,14 @@ sub get_from_info (%) { $$vars{$key} = [$$vars{$key}]; } } - return exists $$vars{$args{GET}} ? $$vars{$args{GET}} : 0; + return exists $$vars{$args{GET}} ? $$vars{$args{GET}} : undef; } # find the version in the tree for a given sbo (provided a location) sub get_sbo_version ($) { exists $_[0] or script_error 'get_sbo_version requires an argument.'; my $version = get_from_info (LOCATION => shift, GET => 'VERSION'); - return $$version[0] ? $$version[0] : 0; + return $$version[0] ? $$version[0] : undef; } # for each installed sbo, find out whether or not the version in the tree is @@ -360,7 +360,7 @@ sub compute_md5sum ($) { sub compare_md5s ($$) { exists $_[1] or script_error 'compare_md5s requires two arguments.'; my ($first, $second) = @_; - return $first eq $second ? 1 : 0; + return $first eq $second ? 1 : undef; } # for a given distfile, see whether or not it exists, and if so, if its md5sum @@ -405,7 +405,7 @@ sub get_symlink_from_filename ($$) { sub check_x32 ($) { exists $_[0] or script_error 'check_x32 requires an argument.'; my $dl = get_from_info (LOCATION => shift, GET => 'DOWNLOAD_x86_64'); - return $$dl[0] =~ /UN(SUPPOR|TES)TED/ ? 1 : 0; + return $$dl[0] =~ /UN(SUPPOR|TES)TED/ ? 1 : undef; } # can't do 32-bit on x86_64 without this file, so we'll use it as the test to @@ -649,7 +649,7 @@ sub make_clean ($$$) { # remove distfiles sub make_distclean (%) { my %args = ( - SRC => '', + SRC => '', VERSION => '', LOCATION => '', @_ diff --git a/sbocheck b/sbocheck index e85042a..aa257c9 100755 --- a/sbocheck +++ b/sbocheck @@ -19,7 +19,7 @@ use Text::Tabulate; my %options; getopts ('v',\%options); -show_version && exit 0 if (exists $options{v}); +show_version && exit 0 if exists $options{v}; update_tree; diff --git a/sboconfig b/sboconfig index c181b29..27d3353 100755 --- a/sboconfig +++ b/sboconfig @@ -121,7 +121,7 @@ sub config_write ($$) { } while (my ($key, $value) = each %changes) { - print "Setting $key to $value...\n"; + say "Setting $key to $value..."; config_write $key, $value or warn "Unable to write to $conf_file\n"; } diff --git a/sbofind b/sbofind index 180df7a..368653c 100755 --- a/sbofind +++ b/sbofind @@ -94,7 +94,7 @@ if (exists $$findings[0]) { push @listing, "info: ". get_file_contents "$value/$key.info" if $show_info; push @listing, "README: ". get_file_contents "$value/README" - if $show_readme; + if $show_readme; push @listing, "\n"; } } diff --git a/sboinstall b/sboinstall index 54459b9..2aa76cb 100755 --- a/sboinstall +++ b/sboinstall @@ -59,4 +59,3 @@ for my $opt (@opts2) { system '/usr/sbin/sboupgrade', '-oN', @ARGV; exit 0; - diff --git a/sboupgrade b/sboupgrade index 842e833..2835a60 100755 --- a/sboupgrade +++ b/sboupgrade @@ -67,7 +67,7 @@ $jobs = 0 if $jobs eq 'FALSE'; show_usage and exit 1 unless exists $ARGV[0]; # if we can't find SLACKBUILDS.TXT in $config{HOME}, prompt to fetch the tree -slackbuilds_or_fetch; +slackbuilds_or_fetch; # build a hash of locations for each item provided on command line, at the same # time verifying each item is a valid slackbuild @@ -96,7 +96,8 @@ sub get_inst_names ($) { # pull list of requirements sub get_requires ($$) { - exists $_[1] or script_error 'get_requires requires an argument.'; + return if $no_reqs; + exists $_[1] or script_error 'get_requires requires two arguments.'; my ($sbo, $location) = @_; my $requires = get_from_info (LOCATION => $location, GET => 'REQUIRES'); return unless $$requires[0]; @@ -115,27 +116,33 @@ sub get_requires ($$) { sub ask_requires ($$$) { exists $_[2] or script_error 'ask_requires requires three arguments.'; my ($requires, $readme, $sbo) = shift; - for my $req (@$requires) { + FIRST: for my $req (@$requires) { + my $name = $compat32 ? "$req-compat32" : $req; my $inst = get_installed_sbos; - my $inst_names= get_inst_names $inst; - unless ($req ~~ @$inst_names) { - say $readme; - say "$sbo has $req listed as a requirement."; - print "Shall I attempt to install it first? [y] "; - if ( =~ /^[Yy\n]/) { - system ('/usr/sbin/sboupgrade', '-oN', $req) == 0 or - die "$req failed to install.\n"; + my $inst_names = get_inst_names $inst; + next FIRST if $name ~~ @$inst_names; + say $readme; + say "$sbo has $name listed as a requirement."; + print "Shall I attempt to install it first? [y] "; + if ( =~ /^[Yy\n]/) { + my @args = ('/usr/sbin/sboupgrade', '-oN'); + # populate args so that they carry over correctly + for my $arg (qw(c d p)) { + push @args, "-$arg" if exists $options{$arg}; } + push @args, "-j $options{j}" if exists $options{j}; + system (@args, $req) == 0 or die "$name failed to install.\n"; } } + return; } # look for any (user|group)add commands in the README sub get_user_group ($) { - exists $_[0] or script_error 'grok_user_group requires an argument'; + exists $_[0] or script_error 'get_user_group requires an argument'; my $readme = shift; my @cmds = $readme =~ /^\s*#*\s*(useradd.*|groupadd.*)/mg; - return @cmds; + return \@cmds; } # offer to run any user/group add commands @@ -156,7 +163,7 @@ sub ask_user_group ($$) { # see if the README mentions any options sub get_opts ($) { - exists $_[0] or script_error 'grok_options requires an argument'; + exists $_[0] or script_error 'get_opts requires an argument'; my $readme = shift; return $readme =~ /[A-Z]+=[^\s]/ ? 1 : undef; } @@ -278,23 +285,23 @@ goto INSTALL_NEW if $only_new; # doesn't matter what's updatable and what's not if force is specified my @updates unless $force; unless ($force) { - my $updates = get_available_updates; + my $updates = get_available_updates; push @updates, $$_{name} for @$updates; } my $todo_upgrade; # but without force, we only want to update what there are updates for unless ($force) { for my $sbo (@ARGV) { - push $$todo_upgrades, $sbo if $sbo ~~ @updates; + push @$todo_upgrade, $sbo if $sbo ~~ @updates; } } else { - my $inst = get_installed_sbos; - my $inst_names= get_inst_names $inst; + my $inst = get_installed_sbos; + my $inst_names = get_inst_names $inst; FIRST: for my $sbo (@ARGV) { - push $todo_upgrade, $sbo if $sbo ~~ @$inst_names; + push @$todo_upgrade, $sbo if $sbo ~~ @$inst_names; } } -my %failures = process_sbos $todo_upgrade if exists $todo_upgrade[0]; +my %failures = process_sbos $todo_upgrade if exists $$todo_upgrade[0]; print_failures %failures; INSTALL_NEW: @@ -302,12 +309,12 @@ exit 0 unless $install_new; my $todo_install; FIRST: for my $sbo (@ARGV) { my $name = $compat32 ? "$sbo-compat32" : $sbo; - my $inst = get_installed_sbos; + my $inst = get_installed_sbos; my $inst_names = get_inst_names $inst;; warn "$name already installed\n", next FIRST if $name ~~ @$inst_names; # if compat32 is TRUE, we need to see if the non-compat version exists. if ($compat32) { - my $inst = get_installed_sbos; + my $inst = get_installed_sbos; my $inst_names = get_inst_names $inst; unless ($sbo ~~ @$inst_names) { print "\nYou are attempting to install $name, however, $sbo is not"; @@ -320,9 +327,9 @@ FIRST: for my $sbo (@ARGV) { } } } - push $todo_install, $sbo; + push @$todo_install, $sbo; } -%failures = process_sbos $todo_install if exists $todo_install[0]; +%failures = process_sbos $todo_install if exists $$todo_install[0]; print_failures %failures; exit 0; diff --git a/t/prep.pl b/t/prep.pl index c5591dc..6b38a33 100755 --- a/t/prep.pl +++ b/t/prep.pl @@ -12,14 +12,17 @@ copy ('/home/d4wnr4z0r/projects/slack14/sbotools/SBO-Lib/lib/SBO/Lib.pm', "$pwd/ open my $write, '>>', "$pwd/SBO/Lib.pm"; -print {$write} "my \$interactive = 1;\n"; -print {$write} "my \%locations;"; -print {$write} "my \$compat32 = 1;\n"; -print {$write} "my \$no_readme = 1;\n"; -print {$write} "my \$jobs = 1;\n"; -print {$write} "my \$distclean = 1;\n"; -print {$write} "my \$noclean = 1;\n"; -print {$write} "my \$no_install = 1;\n"; +sub pr ($) { + my $thing = shift; + print {$write} "our \$$thing = 1;\n"; +} + +for my $thing (qw(interactive compat32 no_readme jobs distclean noclean no_install no_reqs)) { + pr $thing; +} + +print {$write} "my \%locations;\n"; +print {$write} "my \%options = (nothing => 'to see here');\n"; sub get_subs ($) { my $read = shift; diff --git a/t/test.t b/t/test.t index 0230830..cdc5701 100755 --- a/t/test.t +++ b/t/test.t @@ -34,7 +34,7 @@ is (get_slack_version, '14.0', 'get_slack_version is good'); # 10-11, chk_slackbuilds_txt tests is (chk_slackbuilds_txt, 1, 'chk_slackbuilds_txt is good'); move ("$sbo_home/SLACKBUILDS.TXT", "$sbo_home/SLACKBUILDS.TXT.moved"); -is (chk_slackbuilds_txt, 0, 'chk_slackbuilds_txt returns false with no SLACKBUILDS.TXT'); +is (chk_slackbuilds_txt, undef, 'chk_slackbuilds_txt returns false with no SLACKBUILDS.TXT'); move ("$sbo_home/SLACKBUILDS.TXT.moved", "$sbo_home/SLACKBUILDS.TXT"); #ok (rsync_sbo_tree == 1, 'rsync_sbo_tree is good'); @@ -148,7 +148,7 @@ ok (! get_sbo_from_loc 'omg_wtf_bbq', 'get_sbo_from_loc returns false with inval # 48-49, compare_md5s tests is (compare_md5s ('omgwtf123456789', 'omgwtf123456789'), 1, 'compare_md5s returns true for matching parameters'); -is (compare_md5s ('omgwtf123456788', 'somethingelsebbq'), 0, 'compare_md5s returns false for not-matching parameters'); +is (compare_md5s ('omgwtf123456788', 'somethingelsebbq'), undef, 'compare_md5s returns false for not-matching parameters'); # 50, get_distfile tests my $distfile = "$sbo_home/distfiles/Sort-Versions-1.5.tar.gz"; @@ -250,6 +250,7 @@ my $inst_names = get_inst_names $installed; ok ('zdoom' ~~ @$inst_names, 'get_inst_names is good'); # 76-81, get_reqs tests +$SBO::Lib::no_reqs = 0; ok (! (get_requires 'stops', "$sbo_home/audio/stops"), 'get_requires good for circular requirements'); ok (! (get_requires 'smc', "$sbo_home/games/smc"), 'get_requires good for REQUIRES="%README%"'); ok (! (get_requires 'krb5', "$sbo_home/network/krb5"), 'get_requires good for REQUIRES=""'); @@ -263,15 +264,15 @@ is ($$reqs[2], 'matchbox-common', $say); $fh = open_read "$sbo_home/network/nagios/README"; my $readme = do {local $/; <$fh>}; close $fh; -my @cmds = get_user_group $readme; -is ($cmds[0], 'groupadd -g 213 nagios', 'get_user_group good for # groupadd'); -is ($cmds[1], 'useradd -u 213 -d /dev/null -s /bin/false -g nagios nagios', 'get_user_group for # useradd'); +my $cmds = get_user_group $readme; +is ($$cmds[0], 'groupadd -g 213 nagios', 'get_user_group good for # groupadd'); +is ($$cmds[1], 'useradd -u 213 -d /dev/null -s /bin/false -g nagios nagios', 'get_user_group for # useradd'); $fh = open_read "$sbo_home/network/havp/README"; $readme = do {local $/; <$fh>}; close $fh; -@cmds = get_user_group $readme; -is ($cmds[0], 'groupadd -g 210 clamav', 'get_user_group good for groupadd'); -is ($cmds[1], 'useradd -u 256 -d /dev/null -s /bin/false -g clamav havp', 'get_user_group good for useradd'); +$cmds = get_user_group $readme; +is ($$cmds[0], 'groupadd -g 210 clamav', 'get_user_group good for groupadd'); +is ($$cmds[1], 'useradd -u 256 -d /dev/null -s /bin/false -g clamav havp', 'get_user_group good for useradd'); # 86-87, get_opts test $fh = open_read "$sbo_home/games/vbam/README"; -- cgit v1.2.3 From b182d3c89554828478d8d24fd31a87ba629e75fc Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sat, 1 Sep 2012 07:56:24 -0500 Subject: more of the same... --- SBO-Lib/lib/SBO/Lib.pm | 57 ++++++++++++++++++++++++++++++++++---------------- sboupgrade | 34 ++++++++++++++++++++---------- t/test.t | 6 +++--- 3 files changed, 65 insertions(+), 32 deletions(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 2325153..79a2946 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -416,9 +416,18 @@ sub check_multilib () { } # make a backup of the existent SlackBuild, and rewrite the original as needed -sub rewrite_slackbuild ($$%) { - exists $_[1] or script_error 'rewrite_slackbuild requires two arguments.'; - my ($slackbuild, $tempfn, %changes) = @_; +sub rewrite_slackbuild (%) { + my %args = ( + SLACKBUILD => '', + TEMPFN => '', + CHANGES => {}, + @_ + ); + unless ($args{SLACKBUILD} && $args{TEMPFN}) { + script_error 'rewrite_slackbuild requires SLACKBUILD and TEMPFN.'; + } + my $slackbuild = $args{SLACKBUILD}; + my $changes = $args{CHANGES}; copy ($slackbuild, "$slackbuild.orig") or die "Unable to backup $slackbuild to $slackbuild.orig\n"; my $tar_regex = qr/(un|)tar .*$/; @@ -432,17 +441,17 @@ sub rewrite_slackbuild ($$%) { # get the output of the tar and makepkg commands. hope like hell that v # is specified among tar's arguments if ($line =~ $tar_regex || $line =~ $makepkg_regex) { - $line = "$line | tee -a $tempfn"; + $line = "$line | tee -a $args{TEMPFN}"; } - # then check for and apply any other %changes - if (exists $changes{libdirsuffix}) { - $line =~ s/64/$changes{libdirsuffix}/ if $line =~ $libdir_regex; + # then check for and apply any other %$changes + if (exists $$changes{libdirsuffix}) { + $line =~ s/64/$$changes{libdirsuffix}/ if $line =~ $libdir_regex; } - if (exists $changes{make}) { - $line =~ s/make/make $changes{make}/ if $line =~ $make_regex; + if (exists $$changes{make}) { + $line =~ s/make/make $$changes{make}/ if $line =~ $make_regex; } - if (exists $changes{arch_out}) { - $line =~ s/\$ARCH/$changes{arch_out}/ if $line =~ $arch_regex; + if (exists $$changes{arch_out}) { + $line =~ s/\$ARCH/$$changes{arch_out}/ if $line =~ $arch_regex; } } untie @sb_file; @@ -562,7 +571,11 @@ sub perform_sbo (%) { $cmd = "$args{OPTS} $cmd" if $args{OPTS}; my $tempfh = tempfile (DIR => $tempdir); my $fn = get_tmp_extfn $tempfh; - rewrite_slackbuild "$location/$sbo.SlackBuild", $fn, %changes; + rewrite_slackbuild ( + SLACKBUILD => "$location/$sbo.SlackBuild", + TEMPFN => $fn, + CHANGES => \%changes, + ); chdir $location, my $out = system $cmd; revert_slackbuild "$location/$sbo.SlackBuild"; die "$sbo.SlackBuild returned non-zero ext status\n" unless $out == 0; @@ -636,13 +649,21 @@ sub do_slackbuild (%) { } # remove work directories (source and packaging dirs under /tmp/SBo) -sub make_clean ($$$) { - exists $_[2] or script_error 'make_clean requires three arguments.'; - my ($sbo, $src, $version) = @_; - say "Cleaning for $sbo-$version..."; +sub make_clean (%) { + my %args = ( + SBO => '', + SRC => '', + VERSION => '', + @_ + ); + unless ($args{SBO} && $args{SRC} && $args{VERSION}) { + script_error 'make_clean requires three arguments.'; + } + say "Cleaning for $args{SBO}-$args{VERSION}..."; my $tmpsbo = "/tmp/SBo"; - remove_tree ("$tmpsbo/$src") if -d "$tmpsbo/$src"; - remove_tree ("$tmpsbo/package-$sbo") if -d "$tmpsbo/package-$sbo"; + remove_tree ("$tmpsbo/$args{SRC}") if -d "$tmpsbo/$args{SRC}"; + remove_tree ("$tmpsbo/package-$args{SBO}") if + -d "$tmpsbo/package-$args{SBO}"; return 1; } diff --git a/sboupgrade b/sboupgrade index 2835a60..1ec26d7 100755 --- a/sboupgrade +++ b/sboupgrade @@ -113,25 +113,32 @@ sub get_requires ($$) { } # ask to install any requirements found -sub ask_requires ($$$) { - exists $_[2] or script_error 'ask_requires requires three arguments.'; - my ($requires, $readme, $sbo) = shift; - FIRST: for my $req (@$requires) { +sub ask_requires (%) { + my %args = ( + REQUIRES => '', + README => '', + SBO => '', + @_ + ); + unless ($args{REQUIRES} && $args{README} && $args{SBO}) { + script_error 'ask_requires requires three arguments.'; + } + FIRST: for my $req (@{$args{REQUIRES}}) { my $name = $compat32 ? "$req-compat32" : $req; my $inst = get_installed_sbos; my $inst_names = get_inst_names $inst; next FIRST if $name ~~ @$inst_names; - say $readme; - say "$sbo has $name listed as a requirement."; + say $args{README}; + say "$args{SBO} has $name listed as a requirement."; print "Shall I attempt to install it first? [y] "; if ( =~ /^[Yy\n]/) { - my @args = ('/usr/sbin/sboupgrade', '-oN'); + my @cmd_args = ('/usr/sbin/sboupgrade', '-oN'); # populate args so that they carry over correctly for my $arg (qw(c d p)) { - push @args, "-$arg" if exists $options{$arg}; + push @cmd_args, "-$arg" if exists $options{$arg}; } - push @args, "-j $options{j}" if exists $options{j}; - system (@args, $req) == 0 or die "$name failed to install.\n"; + push @cmd_args, "-j $options{j}" if exists $options{j}; + system (@cmd_args, $req) == 0 or die "$name failed to install.\n"; } } return; @@ -321,7 +328,12 @@ FIRST: for my $sbo (@ARGV) { print " yet installed. Shall I install it first? [y] "; if ( =~ /^[Yy\n]/) { my @args = ('/usr/sbin/sboupgrade', '-oN', $sbo); - system (@args) == 0 or exit 1; + # populate args so that they carry over correctly + for my $arg (qw(c d)) { + push @args, "-$arg" if exists $options{$arg}; + } + push @args, "-j $options{j}" if exists $options{j}; + system (@args) == 0 or die "$sbo failed to install.\n"; } else { warn "Please install $sbo\n" and exit 0; } diff --git a/t/test.t b/t/test.t index cdc5701..3a6e144 100755 --- a/t/test.t +++ b/t/test.t @@ -162,8 +162,8 @@ copy ("$sbo_home/system/ifuse/ifuse.SlackBuild", $rewrite_dir); my $slackbuild = "$rewrite_dir/ifuse.SlackBuild"; $tempfh = tempfile (DIR => $rewrite_dir); my $tempfn = get_tmp_extfn $tempfh; -my %changes; -is (rewrite_slackbuild ($slackbuild, $tempfn, %changes), 1, 'rewrite_slackbuild with no %changes good'); +my %changes = (); +is (rewrite_slackbuild (SLACKBUILD => $slackbuild, TEMPFN => $tempfn, CHANGES => \%changes), 1, 'rewrite_slackbuild with no %changes good'); ok (-f "$slackbuild.orig", 'rewrite_slackbuild backing up original is good.'); my $expected_out = "67c67 < tar xvf \$CWD/\$PRGNAM-\$VERSION.tar.bz2 @@ -179,7 +179,7 @@ is (revert_slackbuild $slackbuild, 1, 'revert_slackbuild is good'); $changes{libdirsuffix} = ''; $changes{make} = '-j 5'; $changes{arch_out} = 'i486'; -is (rewrite_slackbuild ($slackbuild, $tempfn, %changes), 1, 'rewrite_slackbuild with all %changes good'); +is (rewrite_slackbuild (SLACKBUILD => $slackbuild, TEMPFN => $tempfn, CHANGES => \%changes), 1, 'rewrite_slackbuild with all %changes good'); ok (-f "$slackbuild.orig", 'rewrite_slackbuild backing up original is good.'); $expected_out = "55c55 < LIBDIRSUFFIX=\"64\" -- cgit v1.2.3 From eb394521aabc27b9918c84a2fc6eb7571f577510 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sat, 1 Sep 2012 12:06:19 -0500 Subject: almost there. --- SBO-Lib/lib/SBO/Lib.pm | 2 +- sbofind | 8 +++++--- sboupgrade | 12 +++++++----- 3 files changed, 13 insertions(+), 9 deletions(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 79a2946..c3b86a0 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -680,7 +680,7 @@ sub make_distclean (%) { } my $sbo = get_sbo_from_loc $args{LOCATION}; make_clean $sbo, $args{SRC}, $args{VERSION}; - say "Distcleaning for $sbo-$args{VERSION}..."; + say "Distcleaning for $sbo-$args{VERSION}...\n"; # remove any distfiles for this particular SBo. my %downloads = get_sbo_downloads (LOCATION => $args{LOCATION}); for my $key (keys %downloads) { diff --git a/sbofind b/sbofind index 368653c..e61c76e 100755 --- a/sbofind +++ b/sbofind @@ -77,12 +77,14 @@ sub get_file_contents ($) { -f $_[0] or return "$_[0] doesn't exist.\n"; my $fh = open_read shift; my $contents = do {local $/; <$fh>}; - $contents =~ s/\n/\n /g; - $contents =~ s/ $//g; + for ($contents) { + s/\n/\n /g; + s/ $//g; + } return $contents; } -perform_search $search; +my $findings = perform_search $search; # pretty formatting if (exists $$findings[0]) { diff --git a/sboupgrade b/sboupgrade index 1ec26d7..403fed3 100755 --- a/sboupgrade +++ b/sboupgrade @@ -155,7 +155,7 @@ sub get_user_group ($) { # offer to run any user/group add commands sub ask_user_group ($$) { exists $_[1] or script_error 'ask_user_group requires two arguments'; - my ($cmds, $readme) = shift; + my ($cmds, $readme) = @_; say "\n". $readme; print "\nIt looks like this slackbuild requires the following"; say " command(s) to be run first:"; @@ -209,10 +209,11 @@ sub readme_prompt ($$) { close $fh; # check for requirements, offer to install any found my $requires = get_requires $sbo, $location; - ask_requires $requires, $readme, $sbo if ref $requires eq 'ARRAY'; + ask_requires (REQUIRES => $requires, README => $readme, SBO => $sbo) if + ref $requires eq 'ARRAY'; # check for user/group add commands, offer to run any found my $user_group = get_user_group $readme; - ask_user_group $user_group, $readme if ref $user_group eq 'ARRAY'; + ask_user_group $user_group, $readme if $$user_group[0]; # check for options mentioned in the README my $opts; $opts = ask_opts $readme if get_opts $readme; @@ -244,8 +245,10 @@ sub process_sbos ($) { if ($@) { $failures{$sbo} = $@; } else { + do_upgradepkg $pkg unless $no_install; unless ($distclean eq 'TRUE') { - make_clean $sbo, $src, $version unless $noclean eq 'TRUE'; + make_clean (SBO => $sbo, SRC => $src, VERSION => $version) + unless $noclean eq 'TRUE'; } else { make_distclean ( SBO => $sbo, @@ -254,7 +257,6 @@ sub process_sbos ($) { LOCATION => $locations{$sbo}, ); } - do_upgradepkg $pkg unless $no_install; # move package to $config{PKG_DIR} if defined unless ($config{PKG_DIR} eq 'FALSE') { my $dir = $config{PKG_DIR}; -- cgit v1.2.3 From ae4a6e80488279460453a387d28fc08219a0341a Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sun, 2 Sep 2012 00:05:39 -0500 Subject: sanity checks for sboconfig --- sboconfig | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/sboconfig b/sboconfig index 27d3353..85d4886 100755 --- a/sboconfig +++ b/sboconfig @@ -74,9 +74,23 @@ my %changes; while (my ($key, $value) = each %valid_confs) { $changes{$value} = $options{$key} if exists $options{$key}; } + +my $die = "You have provided an invalid parameter for"; + +if (exists $changes{NOCLEAN}) { + die "$die -c\n" unless $changes{NOCLEAN} =~ /^(TRUE|FALSE)$/; +} +if (exists $changes{DISTCLEAN}) { + die "$die -d\n" unless $changes{DISTCLEAN} =~ /^(TRUE|FALSE)$/; +} if (exists $changes{JOBS}) { - die "You have provided an invalid parameter for -j\n" unless - ($changes{JOBS} =~ /^\d+$/ || $changes{JOBS} eq 'FALSE'); + die "$die -j\n" unless $changes{JOBS} =~ /^(\d+|FALSE)$/; +} +if (exists $changes{PKG_DIR}) { + die "$die -p\n" unless $changes{PKG_DIR} =~ qr#^(/|FALSE$)#; +} +if (exists $changes{SBO_HOME}) { + die "$die -s\n" unless $changes{SBO_HOME} =~ qr#^/#; } # safely modify our conf file; write its contents to a temp file, modify the -- cgit v1.2.3 From 34e2c5af5a0b8e8cf2247cdc5283aef85e37fb65 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sun, 2 Sep 2012 03:38:43 -0500 Subject: recursive chown root after rsync --- SBO-Lib/lib/SBO/Lib.pm | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index c3b86a0..0c562dc 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -48,8 +48,8 @@ use Sort::Versions; use Digest::MD5; use File::Copy; use File::Path qw(make_path remove_tree); -use Fcntl; use File::Temp qw(tempdir tempfile); +use File::Find; use Fcntl qw(F_SETFD F_GETFD); our $tempdir = tempdir (CLEANUP => 1); @@ -155,6 +155,11 @@ sub rsync_sbo_tree () { my @arg = ('rsync', '-a', '--exclude=*.tar.gz', '--exclude=*.tar.gz.asc'); push @arg, "rsync://slackbuilds.org/slackbuilds/$slk_version/*"; my $out = system @arg, $config{SBO_HOME}; + my $wanted = sub { + $File::Find::name ? chown 0, 0, $File::Find::name + : chown 0, 0, $File::Find::dir; + ); + find ($wanted, $config{SBO_HOME}); say 'Finished.' and return $out; } -- cgit v1.2.3 From 99a7325b924a1e037657a84f0dee96bb8a6c065d Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 21 Sep 2012 06:58:54 -0500 Subject: add get_arch to export list, fix bug where ) should be }, make get_sbo_location find for sbos with special characters in their names, check_distfile -> verify_distfile, typo ext -> exit, remove now excess check for x86_64 for compat32, call make_clean with parameter format --- SBO-Lib/lib/SBO/Lib.pm | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 0c562dc..38e754c 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -35,6 +35,7 @@ our @EXPORT = qw( get_sbo_location get_from_info get_tmp_extfn + get_arch $tempdir $conf_dir $conf_file @@ -158,7 +159,7 @@ sub rsync_sbo_tree () { my $wanted = sub { $File::Find::name ? chown 0, 0, $File::Find::name : chown 0, 0, $File::Find::dir; - ); + }; find ($wanted, $config{SBO_HOME}); say 'Finished.' and return $out; } @@ -205,7 +206,7 @@ sub get_installed_sbos () { sub get_sbo_location ($) { exists $_[0] or script_error 'get_sbo_location requires an argument.'; my $sbo = shift; - my $regex = qr#LOCATION:\s+\.(/[^/]+/$sbo)$#; + my $regex = qr#LOCATION:\s+\.(/[^/]+/\Q$sbo\E)$#; my $fh = open_read $slackbuilds_txt; while (my $line = <$fh>) { if (my $loc = ($line =~ $regex)[0]) { @@ -371,7 +372,7 @@ sub compare_md5s ($$) { # for a given distfile, see whether or not it exists, and if so, if its md5sum # matches the sbo's .info file sub verify_distfile ($$) { - exists $_[1] or script_error 'check_distfile requires two arguments.'; + exists $_[1] or script_error 'verify_distfile requires two arguments.'; my ($link, $info_md5sum) = @_; my $filename = get_filename_from_link $link; return unless -d $distfiles; @@ -583,7 +584,7 @@ sub perform_sbo (%) { ); chdir $location, my $out = system $cmd; revert_slackbuild "$location/$sbo.SlackBuild"; - die "$sbo.SlackBuild returned non-zero ext status\n" unless $out == 0; + die "$sbo.SlackBuild returned non-zero exit status\n" unless $out == 0; my $pkg = get_pkg_name $tempfh; my $src = get_src_dir $tempfh; return $pkg, $src; @@ -620,7 +621,6 @@ sub do_slackbuild (%) { my $x32; # ensure x32 stuff is set correctly, or that we're setup for it if ($args{COMPAT32}) { - die "compat32 only works on x86_64.\n" unless $arch eq 'x86_64'; die "compat32 requires multilib.\n" unless $multi; die "compat32 requires /usr/sbin/convertpkg-compat32.\n" unless -f '/usr/sbin/convertpkg-compat32'; @@ -684,8 +684,8 @@ sub make_distclean (%) { script_error 'make_distclean requires four arguments.'; } my $sbo = get_sbo_from_loc $args{LOCATION}; - make_clean $sbo, $args{SRC}, $args{VERSION}; - say "Distcleaning for $sbo-$args{VERSION}...\n"; + make_clean (SBO => $sbo, SRC => $args{SRC}, VERSION => $args{VERSION}); + say "Distcleaning for $sbo-$args{VERSION}..."; # remove any distfiles for this particular SBo. my %downloads = get_sbo_downloads (LOCATION => $args{LOCATION}); for my $key (keys %downloads) { -- cgit v1.2.3 From 494771b27db5e36e9d34513ef3cd52e33257de58 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 21 Sep 2012 06:59:39 -0500 Subject: updated dates in man pages and fixed some bugs --- man1/sbocheck.1 | 2 +- man1/sboclean.1 | 2 +- man1/sboconfig.1 | 2 +- man1/sbofind.1 | 2 +- man1/sboinstall.1 | 8 ++++---- man1/sbosnap.1 | 2 +- man1/sboupgrade.1 | 16 +++++++++++----- man5/sbotools.conf.5 | 2 +- 8 files changed, 21 insertions(+), 15 deletions(-) diff --git a/man1/sbocheck.1 b/man1/sbocheck.1 index 0cfc1e5..7a66264 100644 --- a/man1/sbocheck.1 +++ b/man1/sbocheck.1 @@ -1,4 +1,4 @@ -.TH sbocheck 1 "Setting Orange, the 34th day of Confusion in the YOLD 3178" "sbotools 0.7 fnord" dawnrazor.net +.TH sbocheck 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net .SH NAME .P sbocheck - update a local slackbuilds.org tree and check for updates. diff --git a/man1/sboclean.1 b/man1/sboclean.1 index b11dbc5..4cc8299 100644 --- a/man1/sboclean.1 +++ b/man1/sboclean.1 @@ -1,4 +1,4 @@ -.TH sboclean 1 "Setting Orange, the 34th day of Confusion in the YOLD 3178" "sbotools 0.7 fnord" dawnrazor.net +.TH sboclean 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net .SH NAME .P sboclean - clean files left around by sbotools. diff --git a/man1/sboconfig.1 b/man1/sboconfig.1 index fc7613b..2089b49 100644 --- a/man1/sboconfig.1 +++ b/man1/sboconfig.1 @@ -1,4 +1,4 @@ -.TH sboconfig 1 "Setting Orange, the 34th day of Confusion in the YOLD 3178" "sbotools 0.7 fnord" dawnrazor.net +.TH sboconfig 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net .SH NAME .P sboconfig - set sbotools configuration options. diff --git a/man1/sbofind.1 b/man1/sbofind.1 index e2bbd83..d217924 100644 --- a/man1/sbofind.1 +++ b/man1/sbofind.1 @@ -1,4 +1,4 @@ -.TH sbofind 1 "Setting Orange, the 34th day of Confusion in the YOLD 3178" "sbotools 0.7 fnord" dawnrazor.net +.TH sbofind 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net .SH NAME .P sbofind - search slackbuilds.org tree for a given name diff --git a/man1/sboinstall.1 b/man1/sboinstall.1 index 6ab6880..38dd531 100644 --- a/man1/sboinstall.1 +++ b/man1/sboinstall.1 @@ -1,4 +1,4 @@ -.TH sboinstall 1 "Setting Orange, the 34th day of Confusion in the YOLD 3178" "sbotools 0.7 fnord" dawnrazor.net +.TH sboinstall 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net .SH NAME .P sboinstall - install slackbuilds @@ -7,7 +7,7 @@ sboinstall - install slackbuilds sboinstall [-h] [-v] [-d TRUE|FALSE] [-j #|FALSE] [-c TRUE|FALSE] [-N] [-r] [-R] [-i] [-p] sbo_name (sbo_name) .SH DESCRIPTION .P -sboinstall is equivalent to sboupgrade -N, but is faster, so is preferred if only installing one or more new packages. If the -r flag is NOT specified, sboinstall will attempt to grok a list of requirements in the README for a given slackbuild. If such a list exists, sboinstall will look to see whether or not those requirements are already installed, and if not, it will ask whether or not it should attempt to install them first. Note that this method is FAR from foolproof, which is why this does not happen if the README is bypassed. sboinstall will also note groupadd and useradd commands in README files and offer to run those first. If the README documents options of the KEY=value form, sboinstall will offer the opportunity to set options. +sboinstall is equivalent to sboupgrade -N, but is faster since it only installs new slackbuidls, so is preferred for installs. If the -i flag is NOT specified, sboinstall will pull the list of requirements from the .info file for any specified SlackBuild. If such a list exists, sboinstall will look to see whether or not those requirements are already installed, and if not, it will ask whether or not it should attempt to install them first. sboinstall will also note groupadd and useradd commands in README files and offer to run those first. If the README documents options of the KEY=value form, sboinstall will offer the opportunity to set options. .SH OPTIONS .P -h @@ -45,13 +45,13 @@ If numeric (2,5,10, etc), then that number will be fed to the "-j" argument to m Create a -compat32 package instead of a normal x86_64 package on multilib x86_64 systems. This requires /usr/sbin/convertpkg-compat32; this can at least be obtained from AlienBob's compat32-tools package - see http://alien.slackbook.org/blog/. Note that this may or may not be foolproof, and is not supported by anyone; not me, not AlienBob, not Slackware, etc. I recommend using this with the -i option so that the created package can be inspected prior to installation. If you find that a particular slackbuild needs additional help to be created as -compat32 package, contact me at j@dawnrazor.net. .RE .P --r +-i .RS Skip viewing of the README and the yes or no question which accompanies it. Anytime sboupgrade or sboinstall is run, the first thing the command will attempt to do is show you the README for a given slackbuild and ask whether or not you wish to proceed; this option skips the README and bypasses the question. If multiple slackbuilds are specified, this option bypasses them all. .RE -R .RS -This option causes sboupgrade to skip requirement parsing, but still show the README and prompt the user to proceed. +This option causes sboupgrade to ignore the requirement list. .RE .SH BUGS .P diff --git a/man1/sbosnap.1 b/man1/sbosnap.1 index b021b89..1637788 100644 --- a/man1/sbosnap.1 +++ b/man1/sbosnap.1 @@ -1,4 +1,4 @@ -.TH sbosnap 1 "Setting Orange, the 34th day of Confusion in the YOLD 3178" "sbotools 0.7 fnord" dawnrazor.net +.TH sbosnap 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net .SH NAME .P sbosnap - slackbuilds.org tree fetch and update command. diff --git a/man1/sboupgrade.1 b/man1/sboupgrade.1 index c7ff348..37db705 100644 --- a/man1/sboupgrade.1 +++ b/man1/sboupgrade.1 @@ -1,4 +1,4 @@ -.TH sboupgrade 1 "Setting Orange, the 34th day of Confusion in the YOLD 3178" "sbotools 0.7 fnord" dawnrazor.net +.TH sboupgrade 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net .SH NAME .P sboupgrade - install or upgrade slackbuilds @@ -7,7 +7,7 @@ sboupgrade - install or upgrade slackbuilds sboupgrade [-h] [-v] [-d TRUE|FALSE] [-j #|FALSE] [-c TRUE|FALSE] [-f] [-N] [-r] [-R] [-i] sbo_name (sbo_name) .SH DESCRIPTION .P -sboupgrade is used to upgrade packages installed from slackbuilds. If the -r flag is NOT specified, sboupgrade will attempt to grok a list of requirements in the README for a given slackbuild. If such a list exists, sboupgrade, will look to see whether or not those requirements are already installed, and if not, it will ask whether or not it should attempt to install them first. Note that this method is FAR from foolproof, which is why this does not happen if the README is bypassed. sboupgrade will also note groupadd and useradd commands in README files and offer to run those first. If the README documents options of the KEY=value form, sboupgrade will offer the opportunity to set options. +sboupgrade is used to upgrade packages installed from slackbuilds. If the -i flag is NOT specified, sboupgrade will pull a list of requirements for any specified SlackBuild. If such a list exists, sboupgrade will look to see whether or not those requirements are already installed, and if not, it will ask whether or not it should attempt to install them first. sboupgrade will also note groupadd and useradd commands in README files and offer to run those first. If the README documents options of the KEY=value form, sboupgrade will offer the opportunity to set options. .SH OPTIONS .P @@ -36,10 +36,11 @@ If TRUE, then DO remove the source code after building the slackbuild. By defaul Force an upgrade, even if the installed version is equal to or less than the slackbuilds.org version. .RE .P --i +-n .RS Do not actually install the package created at the end of the build process. So, the slackbuild will be run, and the package will be left in /tmp, or in $PKG_DIR if so defined (see sboconfig(1) and sbotools.conf(5)). .RE +.P -j (#|FALSE) .RS If numeric (2,5,10, etc), then that number will be fed to the "-j" argument to make when a slackbuild which invokes "make" is run. This only makes sense on multicore systems, where one might set the JOBS to the number of available cores, or half that number, etc. @@ -50,7 +51,7 @@ If numeric (2,5,10, etc), then that number will be fed to the "-j" argument to m Install any new slackbuilds specified. So, if you want to upgrade some things and install new things with the same command, then you would use the -N flag. Note that upgrades are handled prior to new installs. .RE .P --r +-i .RS Skip viewing of the README and the yes or no question which accompanies it. Anytime sboupgrade is run, the first thing the command will attempt to do is show you the README for a given slackbuild and ask whether or not you wish to proceed; this option skips the README and bypasses the question. If multiple slackbuilds are specified, this option bypasses them all. .RE @@ -59,9 +60,14 @@ Skip viewing of the README and the yes or no question which accompanies it. Anyt .RS This option causes sboupgrade to skip requirement parsing, but still show the README and prompt the user to proceed. .RE +.P +-r +.RS +When used in combination with the -f option, to force a slackbuild even if it would not constitute an update, this will cause sboupgrade to also rebuild all of that slackbuild's requirements that it can grok. Normally with -f, only the slackbuild(s) specified, and any requirements not already installed, will be rebuilt. +.RE .SH BUGS .P -Requirement parsing is not foolproof; there are very likely corner cases where it does not function as expected. If any such cases are found, please report this to j@dawnrazor.net; patches are always welcome as well. +None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. .SH SEE ALSO .P sbocheck(1), sboclean(1), sboconfig(1), sbofind(1), sbosnap(1), sbotools.conf(5) diff --git a/man5/sbotools.conf.5 b/man5/sbotools.conf.5 index 81ccb7c..ea03f64 100644 --- a/man5/sbotools.conf.5 +++ b/man5/sbotools.conf.5 @@ -1,4 +1,4 @@ -.TH sbotools.conf 5 "Setting Orange, the 34th day of Confusion in the YOLD 3178" "sbotools 0.7 fnord" dawnrazor.net +.TH sbotools.conf 5 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net .SH NAME .P sbotools.conf - configuration file for sbotools commands. -- cgit v1.2.3 From 698a4c30a34eafda3f4a325cd3cef1f7672bcdec Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 21 Sep 2012 07:00:32 -0500 Subject: sbocheck converted to long options and fixes added from 0.8 --- sbocheck | 28 +++++++++++++++++++++++----- 1 file changed, 23 insertions(+), 5 deletions(-) diff --git a/sbocheck b/sbocheck index aa257c9..ccbbe24 100755 --- a/sbocheck +++ b/sbocheck @@ -13,15 +13,33 @@ use 5.16.0; use strict; use warnings FATAL => 'all'; use SBO::Lib; -use Getopt::Std; +use Getopt::Long; use Text::Tabulate; +use File::Basename; -my %options; -getopts ('v',\%options); +my $self = basename ($0); -show_version && exit 0 if exists $options{v}; +sub show_usage () { + print < \$help, 'version|v' => \$vers); + +show_usage && exit 0 if $help; +show_version && exit 0 if $vers; + +update_tree; # retrieve and format list of available updates sub get_update_list () { -- cgit v1.2.3 From 7ea05b95efb546b3540b807fb6979d7599b907ff Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 21 Sep 2012 07:00:41 -0500 Subject: sboclean converted to long options and fixes added from 0.8 --- sboclean | 37 +++++++++++++++++++++++-------------- 1 file changed, 23 insertions(+), 14 deletions(-) diff --git a/sboclean b/sboclean index b5588c7..3244412 100755 --- a/sboclean +++ b/sboclean @@ -14,7 +14,7 @@ use strict; use warnings FATAL => 'all'; use SBO::Lib; use File::Basename; -use Getopt::Std; +use Getopt::Long qw(:config bundling); use File::Path qw(remove_tree); my $self = basename ($0); @@ -24,23 +24,32 @@ sub show_usage () { Usage: $self (options) [package] Options: - -h: this screen. - -v: version information. - -d: clean distfiles. - -w: clean working directories. - -i: be interactive. + -h|--help: + this screen. + -v|--version: + version information. + -d|--clean-dist: + clean distfiles. + -w|--clean-work: + clean working directories. + -i|--interactive: + be interactive. EOF } -my %options; -getopts ('hvdwi', \%options); +my ($help, $vers, $clean_dist, $clean_work, $interactive); -show_usage && exit 0 if exists $options{h}; -show_version && exit 0 if exists $options{v}; -my $clean_dist = exists $options{d} ? 1 : 0; -my $clean_work = exists $options{w} ? 1 : 0; -my $interactive = exists $options{i} ? 1 : 0; +GetOptions ( + 'help|h' => \$help, + 'version|v' => \$vers, + 'clean-dist|d' => \$clean_dist, + 'clean-work|w' => \$clean_work, + 'interactive|i' => \$interactive, +); + +show_usage && exit 0 if $help; +show_version && exit 0 if $vers; unless ($clean_dist || $clean_work) { show_usage, die "You must specify at least one of -d or -w.\n"; @@ -48,7 +57,7 @@ unless ($clean_dist || $clean_work) { sub remove_stuff ($) { exists $_[0] or script_error 'remove_stuff requires an argument'; - -d $_[0] or say "Nothing to do." and return 1; + -d $_[0] or say 'Nothing to do.' and return 1; my $dir = shift; opendir (my $dh, $dir); FIRST: while (my $ls = readdir $dh) { -- cgit v1.2.3 From 027d01c433b17b1914ba58fae90d6b422d4a45e7 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 21 Sep 2012 07:00:56 -0500 Subject: sboconfig converted to long options and fixes added from 0.8 --- sboconfig | 44 ++++++++++++++++++++++++++------------------ 1 file changed, 26 insertions(+), 18 deletions(-) diff --git a/sboconfig b/sboconfig index 85d4886..f07b589 100755 --- a/sboconfig +++ b/sboconfig @@ -14,7 +14,7 @@ use strict; use warnings FATAL => 'all'; use SBO::Lib; use File::Basename; -use Getopt::Std; +use Getopt::Long; use File::Copy; use File::Path qw(make_path); use File::Temp qw(tempfile);; @@ -31,45 +31,53 @@ Options: -l: show current options. Config options (defaults shown): - -c FALSE: + -c|--clean FALSE: NOCLEAN: if TRUE, do NOT clean up after building by default. - -d FALSE: + -d|--distclean FALSE: DISTCLEAN: if TRUE, DO clean distfiles by default after building. - -j FALSE: + -j|--jobs FALSE: JOBS: numeric -j setting to feed to make for multicore systems. - -p FALSE: + -p|--pkg-dir FALSE: PKG_DIR: set a directory to store packages in. - -s /usr/sbo: + -s|--sbo-home /usr/sbo: SBO_HOME: set the SBo directory. EOF } my %options; -getopts ('hvlc:d:p:s:j:', \%options); -show_usage and exit 0 if exists $options{h}; -show_version and exit 0 if exists $options{v}; +GetOptions (\%options, 'help|h', 'version|v', 'list|l', 'noclean|c=s', + 'distclean|d=s', 'jobs|j=s', 'pkg-dir|p=s', 'sbo-home|s=s'); + +show_usage and exit 0 if exists $options{help}; +show_version and exit 0 if exists $options{version}; my %valid_confs = ( - c => 'NOCLEAN', - d => 'DISTCLEAN', - j => 'JOBS', - p => 'PKG_DIR', - s => 'SBO_HOME', + noclean => 'NOCLEAN', + distclean => 'DISTCLEAN', + jobs => 'JOBS', + 'pkg-dir' => 'PKG_DIR', + 'sbo-home' => 'SBO_HOME', ); -my %params = reverse %valid_confs; +my %params = ( + NOCLEAN => 'c|--noclean', + DISTCLEAN => 'd|--distclean', + JOBS => 'j|--jobs', + PKG_DIR => 'p|--pkg-dir', + SBO_HOME => 's|--sbo-home', +); -if (exists $options{l}) { +if (exists $options{list}) { my @keys = sort {$a cmp $b} keys %config; say "sboconfig -$params{$_}:\n $_=$config{$_}" for @keys; exit 0; } -show_usage and exit 0 unless %options; +show_usage and exit 0 unless keys %options > 0; -# setup what's being changed. +# setup what's being changed, sanity check. my %changes; while (my ($key, $value) = each %valid_confs) { $changes{$value} = $options{$key} if exists $options{$key}; -- cgit v1.2.3 From 26b9790353908f811dbbc565ff35eec2f8b0f11f Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 21 Sep 2012 07:01:05 -0500 Subject: sbofind converted to long options and fixes added from 0.8 --- sbofind | 31 +++++++++++++++++++------------ 1 file changed, 19 insertions(+), 12 deletions(-) diff --git a/sbofind b/sbofind index e61c76e..a2f731d 100755 --- a/sbofind +++ b/sbofind @@ -14,7 +14,7 @@ use strict; use warnings FATAL => 'all'; use SBO::Lib; use File::Basename; -use Getopt::Std; +use Getopt::Long qw(:config bundling); my $self = basename ($0); @@ -23,10 +23,14 @@ sub show_usage () { Usage: $self (search_term) Options: - -h: this screen. - -v: version information. - -i: show the .info for each found item. - -r: show the README for each found item. + -h|--help: + this screen. + -v|--verison: + version information. + -i|--info: + show the .info for each found item. + -r|--readme: + show the README for each found item. Example: $self libsexy @@ -34,20 +38,23 @@ Example: EOF } -my %options; -getopts ('hvir', \%options); +my ($help, $vers, $show_info, $show_readme); -show_usage and exit 0 if exists $options{h}; -show_version and exit 0 if exists $options{v}; +GetOptions ( + 'help|h' => \$help, + 'version|v' => \$vers, + 'info|i' => \$show_info, + 'readme|r' => \$show_readme, +); -my $show_readme = exists $options{r} ? 1 : 0; -my $show_info = exists $options{i} ? 1 : 0; +show_usage and exit 0 if $help; +show_version and exit 0 if $vers; show_usage and exit 1 unless exists $ARGV[0]; my $search = $ARGV[0]; # if we can't find SLACKBUILDS.TXT in $config{HOME}, prompt to fetch the tree -slackbuilds_or_fetch; +slackbuilds_or_fetch; # find anything with $search in its name sub perform_search ($) { -- cgit v1.2.3 From 32d62c3cfd5e43ab6c5a90382b1dabedd09921c3 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 21 Sep 2012 07:01:16 -0500 Subject: sboinstall converted to long options and fixes added from 0.8 --- sboinstall | 72 ++++++++++++++++++++++++++++++++++++++++---------------------- 1 file changed, 47 insertions(+), 25 deletions(-) diff --git a/sboinstall b/sboinstall index 2aa76cb..3e251ca 100755 --- a/sboinstall +++ b/sboinstall @@ -13,7 +13,7 @@ use 5.16.0; use strict; use warnings FATAL => 'all'; use SBO::Lib; -use Getopt::Std; +use Getopt::Long qw(:config bundling); use File::Basename; my $self = basename ($0); @@ -22,39 +22,61 @@ sub show_usage () { print < \$help, + 'version|v' => \$vers, + 'noclean|c=s' => \$noclean, + 'distclean|d=s' => \$distclean, + 'noinstall|i' => \$no_install, + 'jobs|j=s' => \$jobs, + 'compat32|p' => \$compat32, + 'nointeractive|r' => \$non_int, + 'norequirements|R' => \$no_reqs, +); +show_usage and exit 0 if $help; +show_version and exit 0 if $vers; show_usage and exit 0 unless exists $ARGV[0]; -# setup any options which do not require arguments -my @opts1 = ('c', 'd', 'r', 'i', 'p', 'R'); -for my $opt (@opts1) { - unshift @ARGV, "-$opt" if exists $options{$opt}; -} +$noclean = $noclean eq 'TRUE' ? 1 : 0; +$distclean = $distclean eq 'TRUE' ? 1 : 0; -# setup any options which do require arguments -my @opts2 = ('j'); -for my $opt (@opts2) { - unshift @ARGV, "-$opt $options{$opt}" if exists $options{$opt}; -} +# setup any options +unshift @ARGV, $noclean ? '-cTRUE' : '-cFALSE'; +unshift @ARGV, $distclean ? '-dTRUE' : '-dFALSE'; +unshift @ARGV, '-i' if $no_install; +unshift @ARGV, '-p' if $compat32; +unshift @ARGV, '-r' if $non_int; +unshift @ARGV, '-R' if $no_reqs; +unshift @ARGV, "-j$jobs" if $jobs; system '/usr/sbin/sboupgrade', '-oN', @ARGV; -- cgit v1.2.3 From d79f3ffe2ebaaa33f2c2324c3a2dba8aedc0efcc Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 21 Sep 2012 07:01:29 -0500 Subject: sbosnap converted to long options and fixes added from 0.8 --- sbosnap | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) diff --git a/sbosnap b/sbosnap index 9072941..2562356 100755 --- a/sbosnap +++ b/sbosnap @@ -15,7 +15,7 @@ use strict; use warnings FATAL => 'all'; use SBO::Lib; use File::Basename; -use Getopt::Std; +use Getopt::Long; my $sbo_home = $config{SBO_HOME}; my $self = basename ($0); @@ -25,8 +25,10 @@ sub show_usage () { Usage: $self [options|command] Options: - -h: this screen. - -v: version information. + -h|--help: + this screen. + -v|--version: + version information. Commands: fetch: initialize a local copy of the slackbuilds.org tree. @@ -38,11 +40,12 @@ EOF show_usage and exit 1 unless exists $ARGV[0]; -my %options; -getopts ('hv', \%options); +my ($help, $vers); -show_usage and exit 0 if exists $options{h}; -show_version and exit 0 if exists $options{v}; +GetOptions ('help|h' => \$help, 'version|v' => \$vers); + +show_usage and exit 0 if $help; +show_version and exit 0 if $vers; # check for a command and, if found, execute it my $command; -- cgit v1.2.3 From 1a0e9da0d21f2682be30fc58d6fc694b7b927c74 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 21 Sep 2012 07:01:43 -0500 Subject: sboupgrade converted to long options and fixes added from 0.8 --- sboupgrade | 173 +++++++++++++++++++++++++++++++++++++++++-------------------- 1 file changed, 116 insertions(+), 57 deletions(-) diff --git a/sboupgrade b/sboupgrade index 403fed3..fa0c570 100755 --- a/sboupgrade +++ b/sboupgrade @@ -14,7 +14,7 @@ use strict; use warnings FATAL => 'all'; use SBO::Lib; use File::Basename; -use Getopt::Std; +use Getopt::Long qw(:config bundling); use File::Copy; my $self = basename ($0); @@ -23,48 +23,74 @@ sub show_usage () { print < \$help, + 'version|v' => \$vers, + 'noclean|c=s' => \$noclean, + 'distclean|d=s' => \$distclean, + 'force|f' => \$force, + 'noinstall|i' => \$no_install, + 'jobs|j=s' => \$jobs, + 'installnew|N' => \$install_new, + 'nointeractive|r' => \$non_int, + 'norequirements|R' => \$no_reqs, + 'force-reqs|z' => \$force_reqs, + 'only-new|o' => \$only_new, + 'compat32|p' => \$compat32, +); -if (exists $options{j}) { +show_usage && exit 0 if $help; +show_version && exit 0 if $vers; + +$noclean = $noclean eq 'TRUE' ? 1 : 0; +$distclean = $distclean eq 'TRUE' ? 1 : 0; + +if ($jobs) { die "You have provided an invalid parameter for -j\n" unless - ($options{j} =~ /^\d+$/ || $options{j} eq 'FALSE'); + ($jobs =~ /^\d+$/ || $jobs eq 'FALSE'); } -my $jobs = exists $options{j} ? $options{j} : $config{JOBS}; $jobs = 0 if $jobs eq 'FALSE'; show_usage and exit 1 unless exists $ARGV[0]; +if ($compat32) { + die "compat32 only works on x86_64.\n" unless get_arch eq 'x86_64'; +} # if we can't find SLACKBUILDS.TXT in $config{HOME}, prompt to fetch the tree slackbuilds_or_fetch; @@ -112,6 +138,20 @@ sub get_requires ($$) { return $requires; } +# remove any installed requirements from req list +sub clean_reqs ($) { + exists $_[0] or script_error 'clean_reqs requires an argument.'; + my $reqs = shift; + my $inst = get_installed_sbos; + my $inst_names = get_inst_names $inst; + my @new_reqs; + for my $req (@$reqs) { + $req = $compat32 ? "$req-compat32" : $req; + push @new_reqs, $req unless $req ~~ @$inst_names; + } + return \@new_reqs; +} + # ask to install any requirements found sub ask_requires (%) { my %args = ( @@ -123,21 +163,23 @@ sub ask_requires (%) { unless ($args{REQUIRES} && $args{README} && $args{SBO}) { script_error 'ask_requires requires three arguments.'; } - FIRST: for my $req (@{$args{REQUIRES}}) { + my $reqs = $args{REQUIRES}; + $reqs = clean_reqs $reqs unless ($force && $force_reqs); + FIRST: for my $req (@$reqs) { my $name = $compat32 ? "$req-compat32" : $req; - my $inst = get_installed_sbos; - my $inst_names = get_inst_names $inst; - next FIRST if $name ~~ @$inst_names; say $args{README}; say "$args{SBO} has $name listed as a requirement."; - print "Shall I attempt to install it first? [y] "; + print 'Shall I attempt to install it first? [y] '; if ( =~ /^[Yy\n]/) { - my @cmd_args = ('/usr/sbin/sboupgrade', '-oN'); + my @cmd_args = ('/usr/sbin/sboupgrade'); + push @cmd_args, $force_reqs ? '-N' : '-oN'; # populate args so that they carry over correctly - for my $arg (qw(c d p)) { - push @cmd_args, "-$arg" if exists $options{$arg}; - } - push @cmd_args, "-j $options{j}" if exists $options{j}; + push @cmd_args, $noclean ? '-cTRUE' : '-cFALSE'; + push @cmd_args, $distclean ? '-dTRUE' : '-dFALSE'; + push @cmd_args, '-p' if $compat32; + push @cmd_args, '-f' if $force; + push @cmd_args, '-r' if $force_reqs; + push @cmd_args, "-j$jobs" if $jobs; system (@cmd_args, $req) == 0 or die "$name failed to install.\n"; } } @@ -172,7 +214,7 @@ sub ask_user_group ($$) { sub get_opts ($) { exists $_[0] or script_error 'get_opts requires an argument'; my $readme = shift; - return $readme =~ /[A-Z]+=[^\s]/ ? 1 : undef; + return $readme =~ /[A-Z0-9]+=[^\s]/ ? 1 : undef; } # provide an opportunity to set options @@ -186,11 +228,12 @@ sub ask_opts ($) { my $ask = sub () { print "\nPlease supply any options here, or enter to skip: "; chomp (my $opts = ); - return if $opts =~ /^$/; + return if $opts =~ /^\n/; return $opts; }; - my $kv_regex = qr/[A-Z]+=[^\s]+(|\s([A-Z]+=[^\s]+){0,})/; + my $kv_regex = qr/[A-Z0-9]+=[^\s]+(|\s([A-Z]+=[^\s]+){0,})/; my $opts = &$ask; + return unless $opts; FIRST: while ($opts !~ $kv_regex) { warn "Invalid input received.\n"; $opts = &$ask; @@ -232,7 +275,7 @@ sub process_sbos ($) { my %failures; FIRST: for my $sbo (@$todo) { my $opts = 0; - $opts = readme_prompt $sbo, $locations{$sbo} unless $no_readme; + $opts = readme_prompt $sbo, $locations{$sbo} unless $non_int; # switch compat32 on if upgrading a -compat32 $compat32 = 1 if $sbo =~ /-compat32$/; my ($version, $pkg, $src); @@ -246,9 +289,9 @@ sub process_sbos ($) { $failures{$sbo} = $@; } else { do_upgradepkg $pkg unless $no_install; - unless ($distclean eq 'TRUE') { + unless ($distclean) { make_clean (SBO => $sbo, SRC => $src, VERSION => $version) - unless $noclean eq 'TRUE'; + unless $noclean; } else { make_distclean ( SBO => $sbo, @@ -268,7 +311,7 @@ sub process_sbos ($) { } else { warn "$pkg left in /tmp\n"; } - } elsif ($distclean eq 'TRUE') { + } elsif ($distclean) { unlink $pkg; } } @@ -299,15 +342,32 @@ unless ($force) { } my $todo_upgrade; # but without force, we only want to update what there are updates for +my @remove; unless ($force) { - for my $sbo (@ARGV) { - push @$todo_upgrade, $sbo if $sbo ~~ @updates; + for my $key (keys @ARGV) { + if ($ARGV[$key] ~~ @updates) { + push @$todo_upgrade, $ARGV[$key]; + push @remove, $key; + } + } + # don't pass upgradable stuff to the install code + for my $rem (@remove) { + splice @ARGV, $rem, 1; + $_-- for @remove; } } else { my $inst = get_installed_sbos; my $inst_names = get_inst_names $inst; - FIRST: for my $sbo (@ARGV) { - push @$todo_upgrade, $sbo if $sbo ~~ @$inst_names; + for my $key (keys @ARGV) { + if ($ARGV[$key] ~~ @$inst_names) { + push @$todo_upgrade, $ARGV[$key]; + push @remove, $key; + } + } + # don't pass upgradable stuff to the install code + for my $rem (@remove) { + splice @ARGV, $rem, 1; + $_-- for @remove; } } my %failures = process_sbos $todo_upgrade if exists $$todo_upgrade[0]; @@ -319,8 +379,8 @@ my $todo_install; FIRST: for my $sbo (@ARGV) { my $name = $compat32 ? "$sbo-compat32" : $sbo; my $inst = get_installed_sbos; - my $inst_names = get_inst_names $inst;; - warn "$name already installed\n", next FIRST if $name ~~ @$inst_names; + my $inst_names = get_inst_names $inst; + warn "$name already installed.\n" and next FIRST if $name ~~ @$inst_names; # if compat32 is TRUE, we need to see if the non-compat version exists. if ($compat32) { my $inst = get_installed_sbos; @@ -331,11 +391,10 @@ FIRST: for my $sbo (@ARGV) { if ( =~ /^[Yy\n]/) { my @args = ('/usr/sbin/sboupgrade', '-oN', $sbo); # populate args so that they carry over correctly - for my $arg (qw(c d)) { - push @args, "-$arg" if exists $options{$arg}; - } - push @args, "-j $options{j}" if exists $options{j}; - system (@args) == 0 or die "$sbo failed to install.\n"; + push @args, $noclean ? '-cTRUE' : '-cFALSE'; + push @args, $distclean ? '-dTRUE' : '-dFALSE'; + push @args, "-j$jobs" if $jobs; + system (@args, $sbo) == 0 or die "$sbo failed to install.\n"; } else { warn "Please install $sbo\n" and exit 0; } -- cgit v1.2.3 From a4cf58095097080537001f9ff25518584b7286ca Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Fri, 21 Sep 2012 07:02:25 -0500 Subject: prep.pl and test.t updated to test correctly --- t/prep.pl | 3 +- t/test.t | 172 +++++++++++++++++++++++++++++++++++++++++++------------------- 2 files changed, 122 insertions(+), 53 deletions(-) diff --git a/t/prep.pl b/t/prep.pl index 6b38a33..ebffd40 100755 --- a/t/prep.pl +++ b/t/prep.pl @@ -17,7 +17,8 @@ sub pr ($) { print {$write} "our \$$thing = 1;\n"; } -for my $thing (qw(interactive compat32 no_readme jobs distclean noclean no_install no_reqs)) { +for my $thing (qw(interactive compat32 no_readme jobs distclean noclean + no_install no_reqs force force_reqs clean non_int)) { pr $thing; } diff --git a/t/test.t b/t/test.t index 3a6e144..97b15cc 100755 --- a/t/test.t +++ b/t/test.t @@ -4,7 +4,7 @@ use 5.16.0; use strict; use warnings FATAL => 'all'; use File::Temp qw(tempdir tempfile); -use Test::More tests => 87; +use Test::More tests => 90; use File::Copy; use Text::Diff; use lib "."; @@ -34,7 +34,8 @@ is (get_slack_version, '14.0', 'get_slack_version is good'); # 10-11, chk_slackbuilds_txt tests is (chk_slackbuilds_txt, 1, 'chk_slackbuilds_txt is good'); move ("$sbo_home/SLACKBUILDS.TXT", "$sbo_home/SLACKBUILDS.TXT.moved"); -is (chk_slackbuilds_txt, undef, 'chk_slackbuilds_txt returns false with no SLACKBUILDS.TXT'); +is (chk_slackbuilds_txt, undef, + 'chk_slackbuilds_txt returns false with no SLACKBUILDS.TXT'); move ("$sbo_home/SLACKBUILDS.TXT.moved", "$sbo_home/SLACKBUILDS.TXT"); #ok (rsync_sbo_tree == 1, 'rsync_sbo_tree is good'); @@ -47,24 +48,36 @@ is (slackbuilds_or_fetch, 1, 'slackbuilds_or_fetch is good'); print "pseudo-random sampling of get_installed_sbos output...\n"; my $installed = get_installed_sbos; for my $key (keys @$installed) { - is ($$installed[$key]{version}, '1.13') if $$installed[$key]{name} eq 'OpenAL'; - is ($$installed[$key]{version}, '9.5.1_enu') if $$installed[$key]{name} eq 'adobe-reader'; - is ($$installed[$key]{version}, '4.1.3') if $$installed[$key]{name} eq 'libdvdnav'; - is ($$installed[$key]{version}, '0.8.8.4') if $$installed[$key]{name} eq 'libmodplug'; - is ($$installed[$key]{version}, '3.12.4') if $$installed[$key]{name} eq 'mozilla-nss'; - is ($$installed[$key]{version}, '2.5.0') if $$installed[$key]{name} eq 'zdoom'; + is ($$installed[$key]{version}, '1.13') if $$installed[$key]{name} eq + 'OpenAL'; + is ($$installed[$key]{version}, '9.5.1_enu') if $$installed[$key]{name} eq + 'adobe-reader'; + is ($$installed[$key]{version}, '4.1.3') if $$installed[$key]{name} eq + 'libdvdnav'; + is ($$installed[$key]{version}, '0.8.8.4') if $$installed[$key]{name} eq + 'libmodplug'; + is ($$installed[$key]{version}, '3.12.4') if $$installed[$key]{name} eq + 'mozilla-nss'; + is ($$installed[$key]{version}, '2.5.0') if $$installed[$key]{name} eq + 'zdoom'; } print "completed pseudo-random testing of get_installed_sbos \n"; # 19-20, get_sbo_location tests -is (get_sbo_location 'nginx', "$sbo_home/network/nginx", 'get_sbo_location is good'); -is (get_sbo_location 'omgwtfbbq', undef, 'get_sbo_location returns false with not-an-sbo input'); +is (get_sbo_location 'nginx', "$sbo_home/network/nginx", + 'get_sbo_location is good'); +is (get_sbo_location 'omgwtfbbq', undef, + 'get_sbo_location returns false with not-an-sbo input'); # 21-22, get_available_updates tests my $updates = get_available_updates; for my $key (keys @$updates) { - is ($$updates[$key]{installed}, '1.15', '$$updates[$key]{installed} good for mutagen') if $$updates[$key]{name} eq 'mutagen'; - is ($$updates[$key]{update}, '1.20', '$$updates[$key]{update} good for mutagen') if $$updates[$key]{name} eq 'mutagen'; + is ($$updates[$key]{installed}, '1.15', + '$$updates[$key]{installed} good for mutagen') if $$updates[$key]{name} + eq 'mutagen'; + is ($$updates[$key]{update}, '1.20', + '$$updates[$key]{update} good for mutagen') if $$updates[$key]{name} eq + 'mutagen'; } # 23, get_arch test @@ -73,39 +86,54 @@ is (get_arch, 'x86_64', 'get_arch is good'); # 24-25, get_download_info tests my %dl_info = get_download_info (LOCATION => "$sbo_home/system/wine", X64 => 0); my $link = 'http://downloads.sf.net/wine/source/1.4/wine-1.4.1.tar.bz2'; -is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', 'get_download_info test 01 good.'); +is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', + 'get_download_info test 01 good.'); $link = 'http://www.unrealize.co.uk/source/dibeng-max-2010-11-12.zip'; -is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', 'get_download_info test 02 good.'); +is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', + 'get_download_info test 02 good.'); # 26-28, get_sbo_downloads tests %dl_info = get_sbo_downloads (LOCATION => "$sbo_home/system/wine"); $link = 'http://downloads.sf.net/wine/source/1.4/wine-1.4.1.tar.bz2'; -is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', 'get_sbo_downloads test 01 good.'); +is ($dl_info{$link}, '0c28702ed478df7a1c097f3a9c4cabd6', + 'get_sbo_downloads test 01 good.'); $link = 'http://www.unrealize.co.uk/source/dibeng-max-2010-11-12.zip'; -is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', 'get_sbo_downloads test 02 good.'); +is ($dl_info{$link}, '97159d77631da13952fe87e846cf1f3b', + 'get_sbo_downloads test 02 good.'); my %downloads = get_sbo_downloads (LOCATION => "$sbo_home/system/ifuse"); $link = 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2'; -is ($downloads{$link}, '8d528a79de024b91f12f8ac67965c37c', 'get_sbo_downloads test 03 good.'); +is ($downloads{$link}, '8d528a79de024b91f12f8ac67965c37c', + 'get_sbo_downloads test 03 good.'); # 29, get_filename_from_link test -is (get_filename_from_link 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2', "$sbo_home/distfiles/ifuse-1.1.1.tar.bz2", 'get_file_from_link good'); -is (get_filename_from_link 'adf;lkajsdfaksjdfalsdjfalsdkfjdsfj', undef, 'get_filename_from_link good with invalid input'); +is (get_filename_from_link + 'http://www.libimobiledevice.org/downloads/ifuse-1.1.1.tar.bz2', + "$sbo_home/distfiles/ifuse-1.1.1.tar.bz2", 'get_file_from_link good'); +is (get_filename_from_link 'adf;lkajsdfaksjdfalsdjfalsdkfjdsfj', undef, + 'get_filename_from_link good with invalid input'); # 31, compute_md5sum test -is (compute_md5sum "$sbo_home/distfiles/laptop-mode-tools_1.61.tar.gz", '6685af5dbb34c3d51ca27933b58f484e', 'compute_md5sum good'); +is (compute_md5sum "$sbo_home/distfiles/laptop-mode-tools_1.61.tar.gz", + '6685af5dbb34c3d51ca27933b58f484e', 'compute_md5sum good'); # 32, verify_distfile test -is ((verify_distfile "$sbo_home/distfiles/laptop-mode-tools_1.61.tar.gz", '6685af5dbb34c3d51ca27933b58f484e'), 1, 'verify_distfile good'); +is ((verify_distfile "$sbo_home/distfiles/laptop-mode-tools_1.61.tar.gz", + '6685af5dbb34c3d51ca27933b58f484e'), 1, 'verify_distfile good'); # 33, get_sbo_version test is (get_sbo_version "$sbo_home/system/wine", '1.4.1', 'get_sbo_version good'); # 34, get_symlink_from_filename test -is ((get_symlink_from_filename "$sbo_home/distfiles/laptop-mode-tools_1.61.tar.gz", "$sbo_home/system/laptop-mode-tools"), "$sbo_home/system/laptop-mode-tools/laptop-mode-tools_1.61.tar.gz", 'get_symlink_from_filename good'); +is ((get_symlink_from_filename + "$sbo_home/distfiles/laptop-mode-tools_1.61.tar.gz", + "$sbo_home/system/laptop-mode-tools"), + "$sbo_home/system/laptop-mode-tools/laptop-mode-tools_1.61.tar.gz", + 'get_symlink_from_filename good'); # 35-36, check_x32 tests ok (check_x32 "$sbo_home/system/wine", 'check_x32 true for 32-bit only wine'); -ok (!(check_x32 "$sbo_home/system/ifuse"), 'check_x32 false for not-32-bit-only ifuse'); +ok (!(check_x32 "$sbo_home/system/ifuse"), + 'check_x32 false for not-32-bit-only ifuse'); # 37, check_multilib tests ok (check_multilib, 'check_multilib good'); @@ -113,8 +141,10 @@ ok (check_multilib, 'check_multilib good'); # 38-39, create_symlinks tests %downloads = get_sbo_downloads (LOCATION => "$sbo_home/system/wine", 32 => 1); my @symlinks = create_symlinks "$sbo_home/system/wine", %downloads; -is ($symlinks[0], "$sbo_home/system/wine/wine-1.4.1.tar.bz2", '$symlinks[0] good for create_symlinks'); -is ($symlinks[1], "$sbo_home/system/wine/dibeng-max-2010-11-12.zip", '$symlinks[1] good for create_symlinks'); +is ($symlinks[0], "$sbo_home/system/wine/wine-1.4.1.tar.bz2", + '$symlinks[0] good for create_symlinks'); +is ($symlinks[1], "$sbo_home/system/wine/dibeng-max-2010-11-12.zip", + '$symlinks[1] good for create_symlinks'); # 40-41, grok_temp_file, get_src_dir/get_pkg_name tests my $tempdir = tempdir (CLEANUP => 1); @@ -133,27 +163,35 @@ close $tempfh; is ((check_distfiles %downloads), 1, 'check_distfiles good'); # 43-45, check_home tests -system ('sudo /usr/sbin/sboconfig -s /home/d4wnr4z0r/opt_sbo') == 0 or die "unable to set sboconfig -s\n"; +system ('sudo /usr/sbin/sboconfig -s /home/d4wnr4z0r/opt_sbo') == 0 or die + "unable to set sboconfig -s\n"; read_config; ok (check_home, 'check_home returns true with new non-existent directory'); ok (-d '/home/d4wnr4z0r/opt_sbo', 'check_home creates $config{SBO_HOME}'); ok (check_home, 'check_home returns true with new existent empty directory'); -system ("sudo /usr/sbin/sboconfig -s $sbo_home") == 0 or die "unable to reset sboconfig -s\n"; +system ("sudo /usr/sbin/sboconfig -s $sbo_home") == 0 or die + "unable to reset sboconfig -s\n"; read_config; rmdir "/home/d4wnr4z0r/opt_sbo"; # 46-47 get_sbo_from_loc tests -is (get_sbo_from_loc '/home/d4wnr4z0r/sbo.git/system/ifuse', 'ifuse', 'get_sbo_from_loc returns correctly with valid input'); -ok (! get_sbo_from_loc 'omg_wtf_bbq', 'get_sbo_from_loc returns false with invalid input'); +is (get_sbo_from_loc '/home/d4wnr4z0r/sbo.git/system/ifuse', 'ifuse', + 'get_sbo_from_loc returns correctly with valid input'); +ok (! get_sbo_from_loc 'omg_wtf_bbq', + 'get_sbo_from_loc returns false with invalid input'); # 48-49, compare_md5s tests -is (compare_md5s ('omgwtf123456789', 'omgwtf123456789'), 1, 'compare_md5s returns true for matching parameters'); -is (compare_md5s ('omgwtf123456788', 'somethingelsebbq'), undef, 'compare_md5s returns false for not-matching parameters'); +is (compare_md5s ('omgwtf123456789', 'omgwtf123456789'), 1, + 'compare_md5s returns true for matching parameters'); +is (compare_md5s ('omgwtf123456788', 'somethingelsebbq'), undef, + 'compare_md5s returns false for not-matching parameters'); # 50, get_distfile tests my $distfile = "$sbo_home/distfiles/Sort-Versions-1.5.tar.gz"; unlink $distfile if -f $distfile; -is (get_distfile ('http://search.cpan.org/CPAN/authors/id/E/ED/EDAVIS/Sort-Versions-1.5.tar.gz', '5434f948fdea6406851c77bebbd0ed19'), 1, 'get_distfile is good'); +is (get_distfile + ('http://search.cpan.org/CPAN/authors/id/E/ED/EDAVIS/Sort-Versions-1.5.tar.gz', + '5434f948fdea6406851c77bebbd0ed19'), 1, 'get_distfile is good'); unlink $distfile; # 51-58, rewrite_slackbuilds/revert_slackbuild tests @@ -163,7 +201,8 @@ my $slackbuild = "$rewrite_dir/ifuse.SlackBuild"; $tempfh = tempfile (DIR => $rewrite_dir); my $tempfn = get_tmp_extfn $tempfh; my %changes = (); -is (rewrite_slackbuild (SLACKBUILD => $slackbuild, TEMPFN => $tempfn, CHANGES => \%changes), 1, 'rewrite_slackbuild with no %changes good'); +is (rewrite_slackbuild (SLACKBUILD => $slackbuild, TEMPFN => $tempfn, + CHANGES => \%changes), 1, 'rewrite_slackbuild with no %changes good'); ok (-f "$slackbuild.orig", 'rewrite_slackbuild backing up original is good.'); my $expected_out = "67c67 < tar xvf \$CWD/\$PRGNAM-\$VERSION.tar.bz2 @@ -174,12 +213,14 @@ my $expected_out = "67c67 --- > /sbin/makepkg -l y -c n \$OUTPUT/\$PRGNAM-\$VERSION-\$ARCH-\$BUILD\$TAG.\${PKGTYPE:-tgz} | tee -a $tempfn "; -is (diff ("$slackbuild.orig", $slackbuild, {STYLE => 'OldStyle'}), $expected_out, 'tar line rewritten correctly'); +is (diff ("$slackbuild.orig", $slackbuild, {STYLE => 'OldStyle'}), + $expected_out, 'tar line rewritten correctly'); is (revert_slackbuild $slackbuild, 1, 'revert_slackbuild is good'); $changes{libdirsuffix} = ''; $changes{make} = '-j 5'; $changes{arch_out} = 'i486'; -is (rewrite_slackbuild (SLACKBUILD => $slackbuild, TEMPFN => $tempfn, CHANGES => \%changes), 1, 'rewrite_slackbuild with all %changes good'); +is (rewrite_slackbuild (SLACKBUILD => $slackbuild, TEMPFN => $tempfn, + CHANGES => \%changes), 1, 'rewrite_slackbuild with all %changes good'); ok (-f "$slackbuild.orig", 'rewrite_slackbuild backing up original is good.'); $expected_out = "55c55 < LIBDIRSUFFIX=\"64\" @@ -198,7 +239,8 @@ $expected_out = "55c55 --- > /sbin/makepkg -l y -c n \$OUTPUT/\$PRGNAM-\$VERSION-i486-\$BUILD\$TAG.\${PKGTYPE:-tgz} | tee -a $tempfn "; -is (diff ("$slackbuild.orig", $slackbuild, {STYLE => 'OldStyle'}), $expected_out, 'all changed lines rewritten correctly'); +is (diff ("$slackbuild.orig", $slackbuild, {STYLE => 'OldStyle'}), + $expected_out, 'all changed lines rewritten correctly'); is (revert_slackbuild $slackbuild, 1, 'revert_slackbuild is good again'); # 59-61, get_from_info tests @@ -207,7 +249,8 @@ my %params = (LOCATION => $test_loc); my $info = get_from_info (%params, GET => 'VERSION'); is ($$info[0], '1.1.1', 'get_from_info GET => VERSION is good'); $info = get_from_info (%params, GET => 'HOMEPAGE'); -is ($$info[0], 'http://www.libimobiledevice.org', 'get_from_info GET => HOMEPAGE is good'); +is ($$info[0], 'http://www.libimobiledevice.org', + 'get_from_info GET => HOMEPAGE is good'); $info = get_from_info (%params, GET => 'DOWNLOAD_x86_64'); is ($$info[0], "", 'get_from_info GET => DOWNLOAD_x86_64 is good'); @@ -215,16 +258,20 @@ is ($$info[0], "", 'get_from_info GET => DOWNLOAD_x86_64 is good'); my $listing = get_update_list; s/\s//g for @$listing; for my $item (@$listing) { - is ($item, 'zdoom-2.5.0}; close $fh; my $cmds = get_user_group $readme; is ($$cmds[0], 'groupadd -g 213 nagios', 'get_user_group good for # groupadd'); -is ($$cmds[1], 'useradd -u 213 -d /dev/null -s /bin/false -g nagios nagios', 'get_user_group for # useradd'); +is ($$cmds[1], 'useradd -u 213 -d /dev/null -s /bin/false -g nagios nagios', + 'get_user_group for # useradd'); $fh = open_read "$sbo_home/network/havp/README"; $readme = do {local $/; <$fh>}; close $fh; $cmds = get_user_group $readme; is ($$cmds[0], 'groupadd -g 210 clamav', 'get_user_group good for groupadd'); -is ($$cmds[1], 'useradd -u 256 -d /dev/null -s /bin/false -g clamav havp', 'get_user_group good for useradd'); +is ($$cmds[1], 'useradd -u 256 -d /dev/null -s /bin/false -g clamav havp', + 'get_user_group good for useradd'); # 86-87, get_opts test $fh = open_read "$sbo_home/games/vbam/README"; $readme = do {local $/; <$fh>}; close $fh; ok (get_opts $readme, 'get_opts good where README defines opts'); -$fh = open_read "$sbo_home/libraries/libmatchbox/README"; +$fh = open_read "$sbo_home/audio/gmpc/README"; $readme = do {local $/; <$fh>}; close $fh; ok (! (get_opts $readme), 'get_opts good where README does not define opts'); + +# 88-90, clean_reqs tests +#$reqs = get_requires "wine", "$sbo_home/system/wine"; +#$reqs = clean_reqs $reqs; +#print $_,"\n" for @$reqs; +#ok (! $$reqs[0], 'clean_reqs good for already installed reqs'); +$SBO::Lib::compat32 = 0; +$reqs = get_requires 'gmpc', "$sbo_home/audio/gmpc"; +$reqs = clean_reqs $reqs; +ok ($$reqs[0] eq 'gob2', 'clean_reqs good for un/installed reqs.'); +ok ($$reqs[1] eq 'libmpd', 'clean_reqs good for un/installed reqs.'); + -- cgit v1.2.3 From 3b691ad54986277326cbd133f19a75bc21694c72 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sat, 22 Sep 2012 03:22:01 -0500 Subject: fix bug where compat32 packages wouldn't get installed after building --- SBO-Lib/lib/SBO/Lib.pm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 38e754c..9f35fd8 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -648,7 +648,7 @@ sub do_slackbuild (%) { C32 => $args{COMPAT32}, X32 => $x32, ); - do_convertpkg $pkg if $args{COMPAT32}; + $pkg = do_convertpkg $pkg if $args{COMPAT32}; unlink $_ for @symlinks; return $version, $pkg, $src; } -- cgit v1.2.3 From 1354c09e1b93567ef309ffe0f966cd0de00cf95f Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sat, 22 Sep 2012 03:22:46 -0500 Subject: fix bug where installing a compat32 where its 64-bit version is already installed results in the 64-bit version building and installing twice --- sboupgrade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sboupgrade b/sboupgrade index fa0c570..544ae92 100755 --- a/sboupgrade +++ b/sboupgrade @@ -389,7 +389,7 @@ FIRST: for my $sbo (@ARGV) { print "\nYou are attempting to install $name, however, $sbo is not"; print " yet installed. Shall I install it first? [y] "; if ( =~ /^[Yy\n]/) { - my @args = ('/usr/sbin/sboupgrade', '-oN', $sbo); + my @args = ('/usr/sbin/sboupgrade', '-oN'); # populate args so that they carry over correctly push @args, $noclean ? '-cTRUE' : '-cFALSE'; push @args, $distclean ? '-dTRUE' : '-dFALSE'; -- cgit v1.2.3 From 0af02e57b6fbfd559a48ba0061245e6148d12814 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Wed, 3 Oct 2012 03:55:38 -0500 Subject: when circular reqs are found, advise the user of the situation and ask whether or not proceed, default no --- sboupgrade | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/sboupgrade b/sboupgrade index 544ae92..406ac4a 100755 --- a/sboupgrade +++ b/sboupgrade @@ -133,7 +133,12 @@ sub get_requires ($$) { FIRST: for my $req (@$requires) { my $req_req = get_from_info (LOCATION => get_sbo_location $req, GET => 'REQUIRES'); - return if $sbo ~~ @$req_req; + if ($sbo ~~ @$req_req) { + say "I am seeing circular requirements between $sbo and $req."; + say "Therefore, I am not going to handle requirements for $sbo."; + print 'Do you still wish to proceed? [n] '; + ~ /^[Yy\n]/ ? return : exit 0; + } } return $requires; } -- cgit v1.2.3 From fbf71b740fbd3e249a5fd780543f018dd1c77c7b Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Wed, 3 Oct 2012 04:13:05 -0500 Subject: ... --- sboupgrade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sboupgrade b/sboupgrade index 406ac4a..ae6ad74 100755 --- a/sboupgrade +++ b/sboupgrade @@ -237,7 +237,7 @@ sub ask_opts ($) { return $opts; }; my $kv_regex = qr/[A-Z0-9]+=[^\s]+(|\s([A-Z]+=[^\s]+){0,})/; - my $opts = &$ask; + my $opts = &$ask; return unless $opts; FIRST: while ($opts !~ $kv_regex) { warn "Invalid input received.\n"; -- cgit v1.2.3 From cfa0795650606f5e629a65b3e243e8c2ccc000ef Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Wed, 3 Oct 2012 06:10:18 -0500 Subject: bug fix to previous change --- sboupgrade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sboupgrade b/sboupgrade index ae6ad74..0ef528a 100755 --- a/sboupgrade +++ b/sboupgrade @@ -137,7 +137,7 @@ sub get_requires ($$) { say "I am seeing circular requirements between $sbo and $req."; say "Therefore, I am not going to handle requirements for $sbo."; print 'Do you still wish to proceed? [n] '; - ~ /^[Yy\n]/ ? return : exit 0; + =~ /^[Yy\n]/ ? return : exit 0; } } return $requires; -- cgit v1.2.3 From 8afc555e23623c6ab4d36aeff48269baf2c8eea4 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Wed, 3 Oct 2012 12:13:14 -0500 Subject: fix bug where sboupgrade -fz passed -r flag on recursion instead of -z --- sboupgrade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sboupgrade b/sboupgrade index 0ef528a..64650d7 100755 --- a/sboupgrade +++ b/sboupgrade @@ -183,7 +183,7 @@ sub ask_requires (%) { push @cmd_args, $distclean ? '-dTRUE' : '-dFALSE'; push @cmd_args, '-p' if $compat32; push @cmd_args, '-f' if $force; - push @cmd_args, '-r' if $force_reqs; + push @cmd_args, '-z' if $force_reqs; push @cmd_args, "-j$jobs" if $jobs; system (@cmd_args, $req) == 0 or die "$name failed to install.\n"; } -- cgit v1.2.3 From 3b8140f9b9231ddc3fdf15bc809fa2896c5c82e9 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 4 Oct 2012 04:31:20 -0500 Subject: many fixes, cleanups, and consistency corrections in the man pages --- man1/sbocheck.1 | 13 +++++++++---- man1/sboclean.1 | 18 +++++++++--------- man1/sboconfig.1 | 36 ++++++++++++++++++------------------ man1/sbofind.1 | 16 ++++++++-------- man1/sboinstall.1 | 33 +++++++++++++++++---------------- man1/sbosnap.1 | 21 +++++++++++++-------- man1/sboupgrade.1 | 33 ++++++++++++++++----------------- 7 files changed, 90 insertions(+), 80 deletions(-) diff --git a/man1/sbocheck.1 b/man1/sbocheck.1 index 7a66264..1467096 100644 --- a/man1/sbocheck.1 +++ b/man1/sbocheck.1 @@ -4,19 +4,24 @@ sbocheck - update a local slackbuilds.org tree and check for updates. .SH SYNAPSES .P -sbocheck [-v] +sbocheck [-h|-v] .SH DESCRIPTION .P sbocheck first updates a previously fetched copy of the slackbuilds.org tree (see sbosnap(1)) and then checks to see if any packages installed from slackbuilds.org have updates, and reports what it finds. .SH OPTIONS .P --v +-h|--help .RS -Show sbotools version information. +Show help information. +.RE +.P +-v|--version +.RS +Show version information. .RE .SH BUGS .P -None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. In the future sbotools may exist in a public git repository and this section may change to reflect that. +None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. .SH SEE ALSO .P sboclean(1), sboconfig(1), sbofind(1), sboinstall(1), sboupgrade(1), sbosnap(1), sbotools.conf(5) diff --git a/man1/sboclean.1 b/man1/sboclean.1 index 4cc8299..bcbdc9c 100644 --- a/man1/sboclean.1 +++ b/man1/sboclean.1 @@ -4,38 +4,38 @@ sboclean - clean files left around by sbotools. .SH SYNAPSES .P -sboclean [-hvdwi] +sboclean [-h|-v] [-dwi] .SH DESCRIPTION .P sboclean is used to clean files left around by sbotools, such as downloaded source files ("distfiles"), or work directories under /tmp/SBo. Note that if not run with the -i flag, sboclean will remove anything in the distfiles or /tmp/SBo folders with extreme prejudice. One of either -d or -w must be specified for this script to do anything. .SH OPTIONS .P --h +-h|--help .RS Show help information. .RE .P --v +-v|--version .RS -Show sbotools version information. +Show version information. .RE .P --d +-d|--clean-dist .RS Clean distfiles, by default located at /usr/sbo/distfiles. .RE .P --w +-w|--clean-work .RS Clean working directories, located under /tmp/SBo. .RE .P --i +-i|--interactive .RS -Be interactive; sboclean will ask for confirmation for each item which it think should be removed. +Be interactive; sboclean will ask for confirmation for each item which it thinks should be removed. .SH BUGS .P -None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. In the future sbotools may exist in a public git repository and this section may change to reflect that. +None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. .SH SEE ALSO .P sbocheck(1), sboconfig(1), sbofind(1), sboinstall(1), sboupgrade(1), sbosnap(1), sbotools.conf(5) diff --git a/man1/sboconfig.1 b/man1/sboconfig.1 index 2089b49..6dc032a 100644 --- a/man1/sboconfig.1 +++ b/man1/sboconfig.1 @@ -4,54 +4,54 @@ sboconfig - set sbotools configuration options. .SH SYNAPSES .P -sboconfig [-h] [-l] [-d TRUE|FALSE] [-j #|FALSE] [-c TRUE|FALSE] [-p /path|FALSE] [-s /path|/usr/sbo] [-v] +sboconfig [-h|-v] [-l] [-c TRUE|FALSE] [-d TRUE|FALSE] [-j #|FALSE] [-p /path|FALSE] [-s /path|/usr/sbo] .SH DESCRIPTION .P -sboconfig is a front-end for managing sbotools configuration options. The sbotools.conf(5) file can also be manually edited; any fields not relevant to sbotools configuration will be ignored. Note that more options may be added in the future, so you should not add garbage to the sbotools.conf(5) file. +sboconfig is a front-end for managing sbotools configuration options. The sbotools.conf(5) file can also be manually edited; any fields not relevant to sbotools configuration will be ignored. .SH OPTIONS .P --h +-h|--help .RS Show help information. .RE .P --l +-v|--version .RS -List out current configuration options, including unmodified default configuration options (meaning that if a given option is not set in the sbotools.conf(5) file, the default will be shown for that option). +Show version information. .RE .P --d (TRUE|FALSE) +-l|--list .RS -DISTCLEAN: If TRUE, then DO remove the source code after building the slackbuild. By default, the source code is not removed, and lives under $SBO_HOME/distfiles, which, by default, is /usr/sbo/distfiles. Setting this option to TRUE causes the source code to be removed by default. This can be overridden when running sboupgrade(1)/sboinstall(1). +List out current configuration options, including unmodified default configuration options (meaning that if a given option is not set in the sbotools.conf(5) file, the default will be shown for that option). Also shows the flag to sboconfig used to set each option. .RE .P --j (#|FALSE) +-c|--noclean (FALSE|TRUE) .RS -JOBS: If numeric (2,5,10, etc), then that number will be fed to the "-j" argument to make when a slackbuild which invokes "make" is run. This only makes sense on multicore systems, where one might set the JOBS to the number of available cores, or half that number, etc. +NOCLEAN: If TRUE, then DO NOT clean working directories after building the slackbuild. These are the directories where the source is unpacked and compiled, and where the package is put together in, which are under /tmp/SBo. By default, these directories are removed after building an slackbuild. Setting this option to TRUE causes the working directories to not be cleaned by default. This can be overridden when running sboupgrade(1)/sboinstall(1). .RE .P --c (TRUE|FALSE) +-d|--distclean (FALSE|TRUE) .RS -NOCLEAN: If TRUE, then DO NOT clean working directories after building the slackbuild. These are the directories where the source is unpacked and compiled, and where the package is put together in, which are under /tmp/SBo. By default, these directories are removed after building an slackbuild. Setting this option to TRUE causes the working directories to not be cleaned by default. This can be overridden when running sboupgrade(1)/sboinstall(1). +DISTCLEAN: If TRUE, then DO remove the source code after building the slackbuild. By default, the source code is not removed, and lives under $SBO_HOME/distfiles, which, by default, is /usr/sbo/distfiles. Setting this option to TRUE causes the source code to be removed by default. This can be overridden when running sboupgrade(1)/sboinstall(1). .RE .P --p (/path|FALSE) +-j|--jobs (FALSE|#) .RS -PKG_DIR: If set to a path, packages will be stored at the given location after building and installing. By default, packages are left where they are deposited by slackbuilds, which is typically (probably always) /tmp. If PKG_DIR is FALSE and DISTCLEAN is TRUE (either in sbotools.conf(5) or at sboupgrade/sboinstall runtime), the package will be deleted. If this option is set to a path in the filesystem, the package will be stored in that directory, regardless of any DISTCLEAN option. +JOBS: If numeric (2,5,10, etc), then that number will be fed to the "-j" argument to make when a slackbuild which invokes "make" is run. This only makes sense on multicore systems, where one might set the JOBS to the number of available cores, or half that number, etc. .RE .P --s (/path|/usr/sbo) +-p|--pkg-dir (FALSE|/path) .RS -SBO_HOME: If set to a path, this is where the slackbuilds.org tree will live; by default, /usr/sbo will be used. If the tree should live elsewhere, this option can be set to the path where the tree should live. Note that if you set this option after fetching the tree to a different location (such as the default), you will need to fetch the tree again. +PKG_DIR: If set to a path, packages will be stored at the given location after building and installing. By default, packages are left where they are deposited by slackbuilds, which is typically (probably always) /tmp. If PKG_DIR is FALSE and DISTCLEAN is TRUE (either in sbotools.conf(5) or at sboupgrade/sboinstall runtime), the package will be deleted. If this option is set to a path in the filesystem, the package will be stored in that directory, regardless of any DISTCLEAN option. .RE .P --v +-s|--sbo-home (/usr/sbo|/path) .RS -Show sbotools version information. +SBO_HOME: If set to a path, this is where the slackbuilds.org tree will live; by default, /usr/sbo will be used. If the tree should live elsewhere, this option can be set to the path where the tree should live. Note that if you set this option after fetching the tree to a different location (such as the default), you will need to fetch the tree again. .RE .SH BUGS .P -None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. In the future sbotools may exist in a public git repository and this section may change to reflect that. +None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. .SH SEE ALSO .P sbocheck(1), sboclean(1), sbofind(1), sboinstall(1), sboupgrade(1), sbosnap(1), sbotools.conf(5) diff --git a/man1/sbofind.1 b/man1/sbofind.1 index d217924..56f26b9 100644 --- a/man1/sbofind.1 +++ b/man1/sbofind.1 @@ -4,34 +4,34 @@ sbofind - search slackbuilds.org tree for a given name .SH SYNAPSES .P -sbofind [-hvir] search_term +sbofind [-h|-v] [-ir] search_term .SH DESCRIPTION .P sbofind searches the names of all slackbuilds for a given term. It reports back any slackbuilds found along with the path for each. This is equivalent to running "cd /usr/ports; make search name=$search_term display=name,path" on a FreeBSD system. For a more general search, the slackbuilds.org site should be consulted, where tags also exist and are included in the searched fields. .SH OPTIONS .P --h +-h|--help .RS Show help information. .RE .P --v +-v|--version .RS -Show sbotools version information. +Show version information. .RE .P --i +-i|--info .RS -Show the contents of a the .info file for each slackbuild found. +Show the contents of the .info file for each slackbuild found. .RE .P --r +-r|--readme .RS Show the contents of the README file for each slackbuild found. .RE .SH BUGS .P -None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. In the future sbotools may exist in a public git repository and this section may change to reflect that. +None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. .SH SEE ALSO .P sbocheck(1), sboclean(1), sboconfig(1), sboinstall(1), sboupgrade(1), sbosnap(1), sbotools.conf(5) diff --git a/man1/sboinstall.1 b/man1/sboinstall.1 index 38dd531..2bb057b 100644 --- a/man1/sboinstall.1 +++ b/man1/sboinstall.1 @@ -4,61 +4,62 @@ sboinstall - install slackbuilds .SH SYNAPSES .P -sboinstall [-h] [-v] [-d TRUE|FALSE] [-j #|FALSE] [-c TRUE|FALSE] [-N] [-r] [-R] [-i] [-p] sbo_name (sbo_name) +sboinstall [-h|-v] [-d TRUE|FALSE] [-j #|FALSE] [-c TRUE|FALSE] [-NrRip] sbo_name (sbo_name) .SH DESCRIPTION .P -sboinstall is equivalent to sboupgrade -N, but is faster since it only installs new slackbuidls, so is preferred for installs. If the -i flag is NOT specified, sboinstall will pull the list of requirements from the .info file for any specified SlackBuild. If such a list exists, sboinstall will look to see whether or not those requirements are already installed, and if not, it will ask whether or not it should attempt to install them first. sboinstall will also note groupadd and useradd commands in README files and offer to run those first. If the README documents options of the KEY=value form, sboinstall will offer the opportunity to set options. +sboinstall is equivalent to sboupgrade -N, but is faster since it only installs new slackbuidls, so is preferred for installs. If the -r flag is NOT specified, sboinstall will pull the list of requirements from the .info file for any specified slackbuild. If such a list exists, sboinstall will look to see whether or not those requirements are already installed, and if not, it will ask whether or not it should attempt to install them first. This is recursive, so that ordering happens correctly. sboinstall will refuse to handle circular requirements. sboinstall will also note groupadd and useradd commands in README files and offer to run those first. If the README documents options of the KEY=value form, sboinstall will offer the opportunity to set options. .SH OPTIONS .P --h +-h|--help .RS Show help information. .RE .P --v +-v|--version .RS -Show sbotools version information. +Show version information. .RE .P --c (TRUE|FALSE) +-c|--noclean (TRUE|FALSE) .RS If TRUE, then DO NOT clean working directories after building the slackbuild. These are the directories where the source is unpacked and compiled, and where the package is put together in, which are under /tmp/SBo. By default, these directories are removed after building an slackbuild. This option leaves those directories in place. This can be set as default via the sboconfig(1) command. Also see sbotools.conf(5). This option overrides the default. .RE .P --d (TRUE|FALSE) +-d|--distclean (TRUE|FALSE) .RS If TRUE, then DO remove the source code after building the slackbuild. By default, the source code is not removed, and lives under $SBO_HOME/distfiles, which, by default, is /usr/sbo/distfiles; this option can be set as default via the sboconfig(1) command. See also sbotools.conf(5). This option overrides the default. .RE .P --i +-i|--noinstall .RS Do not actually install the package created at the end of the build process. So, the slackbuild will be run, and the package will be left in /tmp, or in $PKG_DIR if so defined (see sboconfig(1) and sbotools.conf(5)). .RE .P --j (#|FALSE) +-j|--jobs (FALSE|#) .RS If numeric (2,5,10, etc), then that number will be fed to the "-j" argument to make when a slackbuild which invokes "make" is run. This only makes sense on multicore systems, where one might set the JOBS to the number of available cores, or half that number, etc. .RE .P --p +-p|--compat32 .RS Create a -compat32 package instead of a normal x86_64 package on multilib x86_64 systems. This requires /usr/sbin/convertpkg-compat32; this can at least be obtained from AlienBob's compat32-tools package - see http://alien.slackbook.org/blog/. Note that this may or may not be foolproof, and is not supported by anyone; not me, not AlienBob, not Slackware, etc. I recommend using this with the -i option so that the created package can be inspected prior to installation. If you find that a particular slackbuild needs additional help to be created as -compat32 package, contact me at j@dawnrazor.net. .RE .P --i +-r|--nointeractive .RS -Skip viewing of the README and the yes or no question which accompanies it. Anytime sboupgrade or sboinstall is run, the first thing the command will attempt to do is show you the README for a given slackbuild and ask whether or not you wish to proceed; this option skips the README and bypasses the question. If multiple slackbuilds are specified, this option bypasses them all. +Skip viewing of the README and the yes or no question which accompanies it. Anytime sboinstall is run, the first thing the command will attempt to do is show you the README for a given slackbuild and ask whether or not you wish to proceed; this option skips the README and bypasses the question. If multiple slackbuilds are specified, this option bypasses them all. .RE --R +.P +-R|--norequirements .RS -This option causes sboupgrade to ignore the requirement list. +This option causes sboinstall to skip requirement handling, but still show the README and prompt the user to proceed. .RE .SH BUGS .P -Requirement parsing is not foolproof; there are very likely corner cases where it does not function as expected. If any such cases are found, please report this to j@dawnrazor.net; patches are always welcome as well. +None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. .SH SEE ALSO .P -sbocheck(1), sboclean(1), sboconfig(1), sbofind(1), sbosnap(1), sbotools.conf(5) +sbocheck(1), sboclean(1), sboconfig(1), sbofind(1), sbosnap(1), sboupgrade(1), sbotools.conf(5) .SH AUTHOR .P Jacob Pipkin diff --git a/man1/sbosnap.1 b/man1/sbosnap.1 index 1637788..de8b84c 100644 --- a/man1/sbosnap.1 +++ b/man1/sbosnap.1 @@ -4,12 +4,23 @@ sbosnap - slackbuilds.org tree fetch and update command. .SH SYNAPSES .P -sbosnap [-v] (fetch|update) +sbosnap [-h|-v] (fetch|update) .SH DESCRIPTION .P sbosnap is used to download and update a local copy of the slackbuilds.org tree, minus the .tar.gz{,.asc} files. Note that sbocheck(1) will also update the tree, and will then also check for updated slackbuilds. rsync is used for both operations. .SH OPTIONS .P +-h|--help +.RS +Show help information. +.RE +.P +-v|--version +.RS +Show version information. +.RE +.SH COMMANDS +.P fetch .RS Download a local copy of the slackbuilds.org tree. The copy will be downloaded to the SBO_HOME setting (see sboconfig(1) and sbotools.conf(5)), which, by default, is /usr/sbo @@ -19,15 +30,9 @@ update .RS Update an previously fetch'd copy of the slackbuilds.org tree. .RE -.P --v -.RS -Show sbotools version information. -.RE - .SH BUGS .P -None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. In the future sbotools may exist in a public git repository and this section may change to reflect that. +None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. .SH SEE ALSO .P sbocheck(1), sboclean(1), sboconfig(1), sbofind(1), sboinstall(1), sboupgrade(1), sbotools.conf(5) diff --git a/man1/sboupgrade.1 b/man1/sboupgrade.1 index 37db705..580b527 100644 --- a/man1/sboupgrade.1 +++ b/man1/sboupgrade.1 @@ -4,73 +4,72 @@ sboupgrade - install or upgrade slackbuilds .SH SYNAPSES .P -sboupgrade [-h] [-v] [-d TRUE|FALSE] [-j #|FALSE] [-c TRUE|FALSE] [-f] [-N] [-r] [-R] [-i] sbo_name (sbo_name) +sboupgrade [-h|-v] [-d TRUE|FALSE] [-j #|FALSE] [-c TRUE|FALSE] [-fNrRiz] sbo_name (sbo_name) .SH DESCRIPTION .P -sboupgrade is used to upgrade packages installed from slackbuilds. If the -i flag is NOT specified, sboupgrade will pull a list of requirements for any specified SlackBuild. If such a list exists, sboupgrade will look to see whether or not those requirements are already installed, and if not, it will ask whether or not it should attempt to install them first. sboupgrade will also note groupadd and useradd commands in README files and offer to run those first. If the README documents options of the KEY=value form, sboupgrade will offer the opportunity to set options. - +sboupgrade is used to upgrade packages installed from slackbuilds. If the -r flag is NOT specified, sboupgrade will pull the list of requirements from the .info file for any specified slackbuild. If such a list exists, sboupgrade will look to see whether or not those requirements are already installed, and if not, it will ask whether or not it should attempt to install them first. This is recursive, so that ordering happens correctly. sboupgrade will refuse to handle circular requirements. sboupgrade will also note groupadd and useradd commands in README files and offer to run those first. If the README documents options of the KEY=value form, sboupgrade will offer the opportunity to set options. .SH OPTIONS .P --h +-h|--help .RS Show help information. .RE .P --v +-v|--version .RS Show sbotools version information. .RE .P --c (TRUE|FALSE) +-c|--noclean (FALSE|TRUE) .RS If TRUE, then DO NOT clean working directories after building the slackbuild. These are the directories where the source is unpacked and compiled, and where the package is put together in, which are under /tmp/SBo. By default, these directories are removed after building an slackbuild. This option leaves those directories in place. This can be set as default via the sboconfig(1) command. Also see sbotools.conf(5). This option overrides the default. .RE .P --d (TRUE|FALSE) +-d|--distclean (FALSE|TRUE) .RS If TRUE, then DO remove the source code after building the slackbuild. By default, the source code is not removed, and lives under $SBO_HOME/distfiles, which, by default, is /usr/sbo/distfiles; this option can be set as default via the sboconfig(1) command. See also sbotools.conf(5). This option overrides the default. .RE .P --f +-f|--force .RS Force an upgrade, even if the installed version is equal to or less than the slackbuilds.org version. .RE .P --n +-i|--noinstall .RS Do not actually install the package created at the end of the build process. So, the slackbuild will be run, and the package will be left in /tmp, or in $PKG_DIR if so defined (see sboconfig(1) and sbotools.conf(5)). .RE .P --j (#|FALSE) +-j|--jobs (FALSE|#) .RS If numeric (2,5,10, etc), then that number will be fed to the "-j" argument to make when a slackbuild which invokes "make" is run. This only makes sense on multicore systems, where one might set the JOBS to the number of available cores, or half that number, etc. .RE .P --N +-N|--installnew .RS Install any new slackbuilds specified. So, if you want to upgrade some things and install new things with the same command, then you would use the -N flag. Note that upgrades are handled prior to new installs. .RE .P --i +-r|--nointeractive .RS Skip viewing of the README and the yes or no question which accompanies it. Anytime sboupgrade is run, the first thing the command will attempt to do is show you the README for a given slackbuild and ask whether or not you wish to proceed; this option skips the README and bypasses the question. If multiple slackbuilds are specified, this option bypasses them all. .RE .P --R +-R|--norequirements .RS -This option causes sboupgrade to skip requirement parsing, but still show the README and prompt the user to proceed. +This option causes sboupgrade to skip requirement handling, but still show the README and prompt the user to proceed. .RE .P --r +-z|--force-reqs .RS -When used in combination with the -f option, to force a slackbuild even if it would not constitute an update, this will cause sboupgrade to also rebuild all of that slackbuild's requirements that it can grok. Normally with -f, only the slackbuild(s) specified, and any requirements not already installed, will be rebuilt. +When used in combination with the -f option, to force an update even if it would not constitute an update, this will cause sboupgrade to also rebuild all of that slackbuild's requirements. Normally with -f, only the slackbuild(s) specified, and any requirements not already installed, will be rebuilt. This allows for recursive upgrades, among other things. .RE .SH BUGS .P None known, but there may be some. Please report any found to j@dawnrazor.net; patches are always welcome. .SH SEE ALSO .P -sbocheck(1), sboclean(1), sboconfig(1), sbofind(1), sbosnap(1), sbotools.conf(5) +sbocheck(1), sboclean(1), sboconfig(1), sbofind(1), sboinstall(1), sbosnap(1), sbotools.conf(5) .SH AUTHOR .P Jacob Pipkin -- cgit v1.2.3 From 861743630dd171ca7be845c0f8373fff92b55320 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 4 Oct 2012 04:32:44 -0500 Subject: sbotools.conf.5 ordering of options for flags reversed to show defaults first --- man5/sbotools.conf.5 | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/man5/sbotools.conf.5 b/man5/sbotools.conf.5 index ea03f64..ff50a91 100644 --- a/man5/sbotools.conf.5 +++ b/man5/sbotools.conf.5 @@ -1,4 +1,4 @@ -.TH sbotools.conf 5 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net +.TH sbotools.conf 5 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net .SH NAME .P sbotools.conf - configuration file for sbotools commands. @@ -8,28 +8,27 @@ This file, location at /etc/sbotools/sbotools.conf, contains KEY=VALUE configura .P The current configuration keys are as follows: .P -DISTCLEAN=(TRUE|FALSE) +DISTCLEAN=(FALSE|TRUE) .RS If TRUE, then DO remove the source code after building the slackbuild. By default, the source code is not removed, and lives under $SBO_HOME/distfiles, which, by default, is /usr/sbo/distfiles. Setting this option to TRUE causes the source code to be removed by default. This can be overridden when running sboupgrade(1)/sboinstall(1). .RE .P -JOBS=(#|FALSE) +JOBS=(FALSE|#) .RS If numeric (2,5,10, etc), then that number will be fed to the "-j" argument to make when a SlackBuild which invokes "make" is run. This only makes sense on multicore systems, where one might set the JOBS to the number of available cores, or half that number, etc. .RE .P -NOCLEAN=(TRUE|FALSE) +NOCLEAN=(FALSE|TRUE) .RS If TRUE, then DO NOT clean working directories after building the slackbuild. These are the directories where the source is unpacked and compiled, and where the package is put together in, which are under /tmp/SBo. By default, these directories are removed after building a slackbuild. Setting this option to TRUE causes the working directories to not be cleaned by default. This can be overridden when running sboupgrade(1)/sboinstall(1). .RE - .P -PKG_DIR=(/path|FALSE) +PKG_DIR=(FALSE|/path) .RS If set to a path, packages will be stored at the given location after building and installing. By default, packages are left where they are deposited by SlackBuilds, which is typically (probably always) /tmp. If PKG_DIR is FALSE and DISTCLEAN is TRUE (either in sbotools.conf(5) or at sboupgrade/sboinstall runtime), the package will be deleted. If this option is set to a path in the filesystem, the package will be stored in that directory, regardless of any DISTCLEAN option. .RE .P -SBO_HOME=(/path|/usr/sbo) +SBO_HOME=(/usr/sbo|/path) .RS If set to a path, this is where the slackbuilds.org tree will live; by default, /usr/sbo will be used. If the tree should live elsewhere, this option can be set to the path where the tree should live. Note that if you set this option after fetching the tree to a different location (such as the default), you will need to fetch the tree again. .RE -- cgit v1.2.3 From 9b1554dd0a3788f0f1082df1428d5b0068340de8 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 4 Oct 2012 04:32:59 -0500 Subject: man pages updated with new ddate and version 1.0 --- man1/sbocheck.1 | 2 +- man1/sboclean.1 | 2 +- man1/sboconfig.1 | 2 +- man1/sbofind.1 | 2 +- man1/sboinstall.1 | 2 +- man1/sbosnap.1 | 2 +- man1/sboupgrade.1 | 2 +- 7 files changed, 7 insertions(+), 7 deletions(-) diff --git a/man1/sbocheck.1 b/man1/sbocheck.1 index 1467096..72dcb63 100644 --- a/man1/sbocheck.1 +++ b/man1/sbocheck.1 @@ -1,4 +1,4 @@ -.TH sbocheck 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net +.TH sbocheck 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net .SH NAME .P sbocheck - update a local slackbuilds.org tree and check for updates. diff --git a/man1/sboclean.1 b/man1/sboclean.1 index bcbdc9c..4fc6695 100644 --- a/man1/sboclean.1 +++ b/man1/sboclean.1 @@ -1,4 +1,4 @@ -.TH sboclean 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net +.TH sboclean 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net .SH NAME .P sboclean - clean files left around by sbotools. diff --git a/man1/sboconfig.1 b/man1/sboconfig.1 index 6dc032a..3d13179 100644 --- a/man1/sboconfig.1 +++ b/man1/sboconfig.1 @@ -1,4 +1,4 @@ -.TH sboconfig 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net +.TH sboconfig 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net .SH NAME .P sboconfig - set sbotools configuration options. diff --git a/man1/sbofind.1 b/man1/sbofind.1 index 56f26b9..5347c31 100644 --- a/man1/sbofind.1 +++ b/man1/sbofind.1 @@ -1,4 +1,4 @@ -.TH sbofind 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net +.TH sbofind 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net .SH NAME .P sbofind - search slackbuilds.org tree for a given name diff --git a/man1/sboinstall.1 b/man1/sboinstall.1 index 2bb057b..6b1c2c9 100644 --- a/man1/sboinstall.1 +++ b/man1/sboinstall.1 @@ -1,4 +1,4 @@ -.TH sboinstall 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net +.TH sboinstall 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net .SH NAME .P sboinstall - install slackbuilds diff --git a/man1/sbosnap.1 b/man1/sbosnap.1 index de8b84c..8ca4c56 100644 --- a/man1/sbosnap.1 +++ b/man1/sbosnap.1 @@ -1,4 +1,4 @@ -.TH sbosnap 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net +.TH sbosnap 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net .SH NAME .P sbosnap - slackbuilds.org tree fetch and update command. diff --git a/man1/sboupgrade.1 b/man1/sboupgrade.1 index 580b527..ee09103 100644 --- a/man1/sboupgrade.1 +++ b/man1/sboupgrade.1 @@ -1,4 +1,4 @@ -.TH sboupgrade 1 "Pungenday, Bureaucracy 29, 3178 YOLD" "sbotools 0.7 fnord" dawnrazor.net +.TH sboupgrade 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net .SH NAME .P sboupgrade - install or upgrade slackbuilds -- cgit v1.2.3 From bf6b66358659cf0e49d207ea4286b4153a1e6610 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 4 Oct 2012 05:05:18 -0500 Subject: quoting consistency cleanups --- SBO-Lib/lib/SBO/Lib.pm | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 9f35fd8..1d47cd4 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -14,7 +14,7 @@ use strict; use warnings FATAL => 'all'; package SBO::Lib 1.0; -my $version = "1.0"; +my $version = '1.0'; require Exporter; our @ISA = qw(Exporter); @@ -571,7 +571,7 @@ sub perform_sbo (%) { } elsif ($args{X32}) { $changes{arch_out} = 'i486'; } - $cmd = ". /etc/profile.d/32dev.sh &&"; + $cmd = '. /etc/profile.d/32dev.sh &&'; } $cmd .= "/bin/sh $location/$sbo.SlackBuild"; $cmd = "$args{OPTS} $cmd" if $args{OPTS}; @@ -665,7 +665,7 @@ sub make_clean (%) { script_error 'make_clean requires three arguments.'; } say "Cleaning for $args{SBO}-$args{VERSION}..."; - my $tmpsbo = "/tmp/SBo"; + my $tmpsbo = '/tmp/SBo'; remove_tree ("$tmpsbo/$args{SRC}") if -d "$tmpsbo/$args{SRC}"; remove_tree ("$tmpsbo/package-$args{SBO}") if -d "$tmpsbo/package-$args{SBO}"; -- cgit v1.2.3 From 62405748ab1470aac11811167c001ce7cbeb040a Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 4 Oct 2012 05:05:52 -0500 Subject: removed 'date:' line from comments, cleanups for quote consistency, etc --- sbocheck | 5 ++--- sboclean | 10 ++++------ sboconfig | 8 +++++--- sbofind | 18 +++++++----------- sboinstall | 1 - sbosnap | 4 +--- sboupgrade | 18 +++++++----------- 7 files changed, 26 insertions(+), 38 deletions(-) diff --git a/sbocheck b/sbocheck index ccbbe24..091164a 100755 --- a/sbocheck +++ b/sbocheck @@ -6,7 +6,6 @@ # script to update the local sbo tree and check for updates # # author: Jacob Pipkin -# date: Sweetmorn, the 38th day of Discord in the YOLD 3178 # license: WTFPL use 5.16.0; @@ -36,8 +35,8 @@ my ($help, $vers); GetOptions ('help|h' => \$help, 'version|v' => \$vers); -show_usage && exit 0 if $help; -show_version && exit 0 if $vers; +show_usage and exit 0 if $help; +show_version and exit 0 if $vers; update_tree; diff --git a/sboclean b/sboclean index 3244412..e9aedd8 100755 --- a/sboclean +++ b/sboclean @@ -6,7 +6,6 @@ # script to clean stuff left around from sbotools. # # author: Jacob Pipkin -# date: Boomtime, the 6th day of Confusion in the YOLD 3178 # license: WTFPL use 5.16.0; @@ -48,12 +47,11 @@ GetOptions ( 'interactive|i' => \$interactive, ); -show_usage && exit 0 if $help; -show_version && exit 0 if $vers; +show_usage and exit 0 if $help; +show_version and exit 0 if $vers; -unless ($clean_dist || $clean_work) { - show_usage, die "You must specify at least one of -d or -w.\n"; -} +show_usage, die "You must specify at least one of -d or -w.\n" unless + ($clean_dist || $clean_work); sub remove_stuff ($) { exists $_[0] or script_error 'remove_stuff requires an argument'; diff --git a/sboconfig b/sboconfig index f07b589..892279c 100755 --- a/sboconfig +++ b/sboconfig @@ -6,7 +6,6 @@ # script to handle sbotools configuration # # author: Jacob Pipkin -# date: Pungenday, the 40th day of Discord in the YOLD 3178 # license: WTFPL use 5.16.0; @@ -83,7 +82,7 @@ while (my ($key, $value) = each %valid_confs) { $changes{$value} = $options{$key} if exists $options{$key}; } -my $die = "You have provided an invalid parameter for"; +my $die = 'You have provided an invalid parameter for'; if (exists $changes{NOCLEAN}) { die "$die -c\n" unless $changes{NOCLEAN} =~ /^(TRUE|FALSE)$/; @@ -103,6 +102,9 @@ if (exists $changes{SBO_HOME}) { # safely modify our conf file; write its contents to a temp file, modify the # temp file, write the contents of the temp file back to the conf file +# TODO: if multiple options are provided to this script, this sub should write +# them all at once, instead of only a single one and having to call it once for +# each option specified to the script. sub config_write ($$) { exists $_[1] or script_error 'config_write requires two arguments.'; my ($key, $val) = @_; @@ -125,7 +127,7 @@ sub config_write ($$) { untie @temp; # otherwise, append our new $key=$value pair print {$tempfh} "$key=$val\n" unless $has; - # then over write the conf file with the contents of the temp file + # then overwrite the conf file with the contents of the temp file seek $tempfh, 0, 0; my $contents = do {local $/; <$tempfh>}; close $conffh; diff --git a/sbofind b/sbofind index a2f731d..61fbd48 100755 --- a/sbofind +++ b/sbofind @@ -6,7 +6,6 @@ # script to locate something in a local SlackBuilds tree. # # author: Jacob Pipkin -# date: Boomtime, the 39th day of Discord in the YOLD 3178 # license: WTFPL use 5.16.0; @@ -86,7 +85,7 @@ sub get_file_contents ($) { my $contents = do {local $/; <$fh>}; for ($contents) { s/\n/\n /g; - s/ $//g; + s/\n $//g; } return $contents; } @@ -97,17 +96,14 @@ my $findings = perform_search $search; if (exists $$findings[0]) { my @listing = ("\n"); for my $hash (@$findings) { - while (my ($key, $value) = each %$hash) { - push @listing, "SBo: $key\n"; - push @listing, "Path: $value\n"; - push @listing, "info: ". get_file_contents "$value/$key.info" - if $show_info; - push @listing, "README: ". get_file_contents "$value/README" - if $show_readme; - push @listing, "\n"; + while (my ($key, $val) = each %$hash) { + say "SBo: $key"; + say "Path: $val"; + say "info: ". get_file_contents "$val/$key.info" if $show_info; + say "README: ". get_file_contents "$val/README" if $show_readme; + say ''; } } - print $_ for @listing; } else { say "Nothing found for search term: $search"; } diff --git a/sboinstall b/sboinstall index 3e251ca..624d188 100755 --- a/sboinstall +++ b/sboinstall @@ -6,7 +6,6 @@ # script to install a SlackBuild by name # # author: Jacob Pipkin -# date: Pungenday, the 40th day of Discord in the YOLD 3178 # license: WTFPL use 5.16.0; diff --git a/sbosnap b/sbosnap index 2562356..6e61e14 100755 --- a/sbosnap +++ b/sbosnap @@ -3,11 +3,9 @@ # vim: set ts=4:noet # # sbosnap -# script to pull down / update a local copy of the -# slackbuilds.org tree. +# script to pull down / update a local copy of the slackbuilds.org tree. # # author: Jacob Pipkin -# date: Setting Orange, the 37th day of Discord in the YOLD 3178 # license: WTFPL use 5.16.0; diff --git a/sboupgrade b/sboupgrade index 64650d7..04d9732 100755 --- a/sboupgrade +++ b/sboupgrade @@ -6,7 +6,6 @@ # script to update an installed SlackBuild. # # author: Jacob Pipkin -# date: Boomtime, the 39th day of Discord in the YOLD 3178 # license: WTFPL use 5.16.0; @@ -47,9 +46,6 @@ Options (defaults shown first where applicable): -z|--force-reqs: when used with -f, will force rebuilding an SBo's requirements as well. -Example: - $self -d libsexy - EOF } @@ -75,8 +71,8 @@ GetOptions ( 'compat32|p' => \$compat32, ); -show_usage && exit 0 if $help; -show_version && exit 0 if $vers; +show_usage and exit 0 if $help; +show_version and exit 0 if $vers; $noclean = $noclean eq 'TRUE' ? 1 : 0; $distclean = $distclean eq 'TRUE' ? 1 : 0; @@ -205,9 +201,9 @@ sub ask_user_group ($$) { my ($cmds, $readme) = @_; say "\n". $readme; print "\nIt looks like this slackbuild requires the following"; - say " command(s) to be run first:"; + say ' command(s) to be run first:'; say " # $_" for @$cmds; - print "Shall I run it/them now? [y] "; + print 'Shall I run it/them now? [y] '; if ( =~ /^[Yy\n]/) { for my $cmd (@$cmds) { system ($cmd) == 0 or warn "\"$cmd\" exited non-zero\n"; @@ -228,7 +224,7 @@ sub ask_opts ($) { my $readme = shift; say "\n". $readme; print "\nIt looks this slackbuilds has options; would you like to set any"; - print " when the slackbuild is run? [n] "; + print ' when the slackbuild is run? [n] '; if ( =~ /^[Yy]/) { my $ask = sub () { print "\nPlease supply any options here, or enter to skip: "; @@ -327,7 +323,7 @@ sub process_sbos ($) { sub print_failures (;%) { if (exists $_[0]) { my %failures = @_; - say "Failures:"; + say 'Failures:'; while (my ($key, $val) = each %failures) { say " $key: $val"; } @@ -392,7 +388,7 @@ FIRST: for my $sbo (@ARGV) { my $inst_names = get_inst_names $inst; unless ($sbo ~~ @$inst_names) { print "\nYou are attempting to install $name, however, $sbo is not"; - print " yet installed. Shall I install it first? [y] "; + print ' yet installed. Shall I install it first? [y] '; if ( =~ /^[Yy\n]/) { my @args = ('/usr/sbin/sboupgrade', '-oN'); # populate args so that they carry over correctly -- cgit v1.2.3 From 2beda783d846ae15763bdee06aa8ddeeecff9fae Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 4 Oct 2012 16:17:50 -0500 Subject: fix bug where links with %2B would not work because the result filenames had the %2Bs converted to + signs --- SBO-Lib/lib/SBO/Lib.pm | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 1d47cd4..e801fbb 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -349,7 +349,8 @@ sub get_filename_from_link ($) { exists $_[0] or script_error 'get_filename_from_link requires an argument'; my $fn = shift; my $regex = qr#/([^/]+)$#; - return $fn =~ $regex ? $distfiles .'/'. ($fn =~ $regex)[0] : undef; + my $filename = $fn =~ $regex ? $distfiles .'/'. ($fn =~ $regex)[0] : undef; + return $filename; } # for a given file, computer its md5sum -- cgit v1.2.3 From 710557681d72594e24effa0b32878fb4b358c5ce Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 4 Oct 2012 21:21:05 -0500 Subject: minor cleanups, updated version --- man1/sbocheck.1 | 2 +- man1/sboclean.1 | 2 +- man1/sboconfig.1 | 2 +- man1/sbofind.1 | 2 +- man1/sboinstall.1 | 8 ++++---- man1/sbosnap.1 | 4 ++-- man1/sboupgrade.1 | 6 +++--- man5/sbotools.conf.5 | 2 +- 8 files changed, 14 insertions(+), 14 deletions(-) diff --git a/man1/sbocheck.1 b/man1/sbocheck.1 index 72dcb63..59c2560 100644 --- a/man1/sbocheck.1 +++ b/man1/sbocheck.1 @@ -1,4 +1,4 @@ -.TH sbocheck 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net +.TH sbocheck 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.1 fnord" dawnrazor.net .SH NAME .P sbocheck - update a local slackbuilds.org tree and check for updates. diff --git a/man1/sboclean.1 b/man1/sboclean.1 index 4fc6695..1bed44b 100644 --- a/man1/sboclean.1 +++ b/man1/sboclean.1 @@ -1,4 +1,4 @@ -.TH sboclean 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net +.TH sboclean 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.1 fnord" dawnrazor.net .SH NAME .P sboclean - clean files left around by sbotools. diff --git a/man1/sboconfig.1 b/man1/sboconfig.1 index 3d13179..b4f47da 100644 --- a/man1/sboconfig.1 +++ b/man1/sboconfig.1 @@ -1,4 +1,4 @@ -.TH sboconfig 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net +.TH sboconfig 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.1 fnord" dawnrazor.net .SH NAME .P sboconfig - set sbotools configuration options. diff --git a/man1/sbofind.1 b/man1/sbofind.1 index 5347c31..f9973e4 100644 --- a/man1/sbofind.1 +++ b/man1/sbofind.1 @@ -1,4 +1,4 @@ -.TH sbofind 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net +.TH sbofind 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.1 fnord" dawnrazor.net .SH NAME .P sbofind - search slackbuilds.org tree for a given name diff --git a/man1/sboinstall.1 b/man1/sboinstall.1 index 6b1c2c9..3f8fa91 100644 --- a/man1/sboinstall.1 +++ b/man1/sboinstall.1 @@ -1,4 +1,4 @@ -.TH sboinstall 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net +.TH sboinstall 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.1 fnord" dawnrazor.net .SH NAME .P sboinstall - install slackbuilds @@ -7,7 +7,7 @@ sboinstall - install slackbuilds sboinstall [-h|-v] [-d TRUE|FALSE] [-j #|FALSE] [-c TRUE|FALSE] [-NrRip] sbo_name (sbo_name) .SH DESCRIPTION .P -sboinstall is equivalent to sboupgrade -N, but is faster since it only installs new slackbuidls, so is preferred for installs. If the -r flag is NOT specified, sboinstall will pull the list of requirements from the .info file for any specified slackbuild. If such a list exists, sboinstall will look to see whether or not those requirements are already installed, and if not, it will ask whether or not it should attempt to install them first. This is recursive, so that ordering happens correctly. sboinstall will refuse to handle circular requirements. sboinstall will also note groupadd and useradd commands in README files and offer to run those first. If the README documents options of the KEY=value form, sboinstall will offer the opportunity to set options. +sboinstall is equivalent to sboupgrade -N, but is faster since it only installs new slackbuilds, so is preferred for installs. If the -r flag is NOT specified, sboinstall will pull the list of requirements from the .info file for any specified slackbuild. If such a list exists, sboinstall will look to see whether or not those requirements are already installed, and if not, it will ask whether or not it should attempt to install them first. This is recursive, so that ordering happens correctly. sboinstall will refuse to handle circular requirements. sboinstall will also note groupadd and useradd commands in README files and offer to run those first. If the README documents options of the KEY=value form, sboinstall will offer the opportunity to set options. .SH OPTIONS .P -h|--help @@ -20,12 +20,12 @@ Show help information. Show version information. .RE .P --c|--noclean (TRUE|FALSE) +-c|--noclean (FALSE|TRUE) .RS If TRUE, then DO NOT clean working directories after building the slackbuild. These are the directories where the source is unpacked and compiled, and where the package is put together in, which are under /tmp/SBo. By default, these directories are removed after building an slackbuild. This option leaves those directories in place. This can be set as default via the sboconfig(1) command. Also see sbotools.conf(5). This option overrides the default. .RE .P --d|--distclean (TRUE|FALSE) +-d|--distclean (FALSE|TRUE) .RS If TRUE, then DO remove the source code after building the slackbuild. By default, the source code is not removed, and lives under $SBO_HOME/distfiles, which, by default, is /usr/sbo/distfiles; this option can be set as default via the sboconfig(1) command. See also sbotools.conf(5). This option overrides the default. .RE diff --git a/man1/sbosnap.1 b/man1/sbosnap.1 index 8ca4c56..dba3d0c 100644 --- a/man1/sbosnap.1 +++ b/man1/sbosnap.1 @@ -1,4 +1,4 @@ -.TH sbosnap 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net +.TH sbosnap 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.1 fnord" dawnrazor.net .SH NAME .P sbosnap - slackbuilds.org tree fetch and update command. @@ -28,7 +28,7 @@ Download a local copy of the slackbuilds.org tree. The copy will be downloaded t .P update .RS -Update an previously fetch'd copy of the slackbuilds.org tree. +Update a previously fetch'd copy of the slackbuilds.org tree. .RE .SH BUGS .P diff --git a/man1/sboupgrade.1 b/man1/sboupgrade.1 index ee09103..fba3f58 100644 --- a/man1/sboupgrade.1 +++ b/man1/sboupgrade.1 @@ -1,10 +1,10 @@ -.TH sboupgrade 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net +.TH sboupgrade 1 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.1 fnord" dawnrazor.net .SH NAME .P sboupgrade - install or upgrade slackbuilds .SH SYNAPSES .P -sboupgrade [-h|-v] [-d TRUE|FALSE] [-j #|FALSE] [-c TRUE|FALSE] [-fNrRiz] sbo_name (sbo_name) +sboupgrade [-h|-v] [-c TRUE|FALSE] [-d TRUE|FALSE] [-j #|FALSE] [-fNrRiz] sbo_name (sbo_name) .SH DESCRIPTION .P sboupgrade is used to upgrade packages installed from slackbuilds. If the -r flag is NOT specified, sboupgrade will pull the list of requirements from the .info file for any specified slackbuild. If such a list exists, sboupgrade will look to see whether or not those requirements are already installed, and if not, it will ask whether or not it should attempt to install them first. This is recursive, so that ordering happens correctly. sboupgrade will refuse to handle circular requirements. sboupgrade will also note groupadd and useradd commands in README files and offer to run those first. If the README documents options of the KEY=value form, sboupgrade will offer the opportunity to set options. @@ -17,7 +17,7 @@ Show help information. .P -v|--version .RS -Show sbotools version information. +Show version information. .RE .P -c|--noclean (FALSE|TRUE) diff --git a/man5/sbotools.conf.5 b/man5/sbotools.conf.5 index ff50a91..ff5786b 100644 --- a/man5/sbotools.conf.5 +++ b/man5/sbotools.conf.5 @@ -1,4 +1,4 @@ -.TH sbotools.conf 5 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.0 fnord" dawnrazor.net +.TH sbotools.conf 5 "Boomtime, Bureaucracy 58, 3178 YOLD" "sbotools 1.1 fnord" dawnrazor.net .SH NAME .P sbotools.conf - configuration file for sbotools commands. -- cgit v1.2.3 From a593f85e54bef80e33944cc3926a2c9cef13fbf8 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 4 Oct 2012 21:21:48 -0500 Subject: version 1.0 -> 1.1 --- SBO-Lib/lib/SBO/Lib.pm | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index e801fbb..7a2cf97 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -13,8 +13,8 @@ use 5.16.0; use strict; use warnings FATAL => 'all'; -package SBO::Lib 1.0; -my $version = '1.0'; +package SBO::Lib 1.1; +my $version = '1.1'; require Exporter; our @ISA = qw(Exporter); -- cgit v1.2.3 From ae4a62999a4c4c26ad4bae13867721dc0f6ad694 Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Thu, 4 Oct 2012 22:19:41 -0500 Subject: fix the %2B thing for real this time :-/ --- SBO-Lib/lib/SBO/Lib.pm | 1 + 1 file changed, 1 insertion(+) diff --git a/SBO-Lib/lib/SBO/Lib.pm b/SBO-Lib/lib/SBO/Lib.pm index 7a2cf97..92f22b5 100644 --- a/SBO-Lib/lib/SBO/Lib.pm +++ b/SBO-Lib/lib/SBO/Lib.pm @@ -350,6 +350,7 @@ sub get_filename_from_link ($) { my $fn = shift; my $regex = qr#/([^/]+)$#; my $filename = $fn =~ $regex ? $distfiles .'/'. ($fn =~ $regex)[0] : undef; + $filename =~ s/%2B/+/g; return $filename; } -- cgit v1.2.3 From b9036db1e5e965dc395d978397e8151ca9ab59fd Mon Sep 17 00:00:00 2001 From: Jacob Pipkin Date: Sat, 6 Oct 2012 08:42:41 -0500 Subject: fix bug where, when circular requirements are found, the default chocie is claimed to be no, but is actually yes --- sboupgrade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sboupgrade b/sboupgrade index 04d9732..c4c8e2f 100755 --- a/sboupgrade +++ b/sboupgrade @@ -133,7 +133,7 @@ sub get_requires ($$) { say "I am seeing circular requirements between $sbo and $req."; say "Therefore, I am not going to handle requirements for $sbo."; print 'Do you still wish to proceed? [n] '; - =~ /^[Yy\n]/ ? return : exit 0; + =~ /^[Yy]/ ? return : exit 0; } } return $requires; -- cgit v1.2.3