diff options
author | Vagrant Cascadian <vagrant@debian.org> | 2017-08-02 17:03:03 -0400 |
---|---|---|
committer | Holger Levsen <holger@layer-acht.org> | 2017-08-03 16:22:39 -0400 |
commit | 4c5ea6af7385064575531b1572c9bebf999b005d (patch) | |
tree | c8528a53c4157d3e5b945149e887f5eaf117a247 /hosts/jtx1b-armhf-rb/usr/local/bin | |
parent | 34c1dd358e6879664f12703ccdcd1e88f11854b1 (diff) | |
download | jenkins.debian.net-4c5ea6af7385064575531b1572c9bebf999b005d.tar.xz |
reproducible: Add two new armhf builders (jtk1b, jtx1b).
Temporarily disable two armhf build nodes (jtk1a down, ff64a too
slow).
Add an additional build job, as the new machines have more capacity
than the old.
Signed-off-by: Holger Levsen <holger@layer-acht.org>
Diffstat (limited to 'hosts/jtx1b-armhf-rb/usr/local/bin')
-rwxr-xr-x | hosts/jtx1b-armhf-rb/usr/local/bin/dsa-check-packages | 362 | ||||
-rwxr-xr-x | hosts/jtx1b-armhf-rb/usr/local/bin/dsa-check-running-kernel | 254 |
2 files changed, 616 insertions, 0 deletions
diff --git a/hosts/jtx1b-armhf-rb/usr/local/bin/dsa-check-packages b/hosts/jtx1b-armhf-rb/usr/local/bin/dsa-check-packages new file mode 100755 index 00000000..28844e5a --- /dev/null +++ b/hosts/jtx1b-armhf-rb/usr/local/bin/dsa-check-packages @@ -0,0 +1,362 @@ +#!/usr/bin/perl + +# dsa-check-packages + +# checks for obsolete/local and upgradeable packages. +# +# packages for the obsolete/local check can be ignored, by +# listing their full name in /etc/nagios/obsolete-packages-ignore +# or by having a regex (starting a line with "/") that matches +# the packagename in said file. +# +# Takes one optional argument, the location of the ignore file. + + +# Copyright (C) 2008, 2009 Peter Palfrader <peter@palfrader.org> +# +# Permission is hereby granted, free of charge, to any person obtaining +# a copy of this software and associated documentation files (the +# "Software"), to deal in the Software without restriction, including +# without limitation the rights to use, copy, modify, merge, publish, +# distribute, sublicense, and/or sell copies of the Software, and to +# permit persons to whom the Software is furnished to do so, subject to +# the following conditions: +# +# The above copyright notice and this permission notice shall be +# included in all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE +# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION +# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION +# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +use strict; +use warnings; +use English; + +my $IGNORE = "/etc/nagios/obsolete-packages-ignore"; +my $IGNORED = "/etc/nagios/obsolete-packages-ignore.d"; + +my %CODE = ( + 'OK' => 0, + 'WARNING' => 1, + 'CRITICAL' => 2, + 'UNKNOWN' => 3 +); +my $EXITCODE = 'OK'; +sub record($) { + my ($newexit) = @_; + die "code $newexit not defined\n" unless defined $CODE{$newexit}; + + if ($CODE{$newexit} > $CODE{$EXITCODE}) { + $EXITCODE = $newexit; + }; +} + + + +sub get_packages { + $ENV{'COLUMNS'} = 1000; + $ENV{'LC_ALL'} = 'C'; + open(F, "dpkg -l|") or die ("Cannot run dpkg: $!\n"); + my @lines = <F>; + close(F); + chomp(@lines); + + my $line; + my $has_arch = 0; + while (defined($line = shift @lines) && ($line !~ /\+\+\+/)) { + if ($line =~ /Architecture/) { $has_arch = 1; } + } + + my %pkgs; + for $line (@lines) { + my ($state, $pkg, $version, $arch, undef) = split(/ */, $line); + $arch = '' unless $has_arch; + $pkgs{$state}{$pkg} = { 'installed' => $version, arch => $arch } + } + + my $installed = $pkgs{'ii'}; + delete $pkgs{'ii'}; + + my @installed_packages = keys(%$installed); + my @cmd = ("apt-cache", "policy", @installed_packages); + + open my $olderr, ">&STDERR" or die "Can't dup STDERR: $!"; + open STDERR, ">/dev/null" or die "Can't dup STDOUT: $!"; + open (F, "-|", @cmd) or die ("Cannot run apt-cache policy: $!\n"); + @lines = <F>; + close(F); + open STDERR, ">&", $olderr or die "Can't dup OLDERR: $!"; + chomp(@lines); + + my $pkgname = undef; + my $candidate_found = 0; + while (defined($line = shift @lines)) { + if ($line =~ /^([^ ]*):$/) { + # when we have multi-arch capable fu, we require that + # apt-cache policy output is in the same order as its + # arguments. + # + # We needs thi, because the output block in apt-cache + # policy does not show the arch: + # + # | weasel@stanley:~$ apt-cache policy libedit2:amd64 + # | libedit2: + # | Installed: 2.11-20080614-5 + # | Candidate: 2.11-20080614-5 + # + # We replace the package name in the output with the + # one we asked for ($pkg:$arch) - but to match this up + # sanely we need the order to be correct. + # + # For squeeze systems (no m-a), apt-cache policy output + # is all different. + $pkgname = $1; + $candidate_found = 0; + if ($has_arch) { + my $from_list = shift @installed_packages; + next if ($pkgname eq $from_list); # no :$arch in pkgname we asked for + + my $ma_fix_pkgname = $pkgname.':'.$installed->{$from_list}->{'arch'}; + my $ma_fix_from_list = $from_list.':'.$installed->{$from_list}->{'arch'}; + + if ($pkgname eq $ma_fix_from_list || # e.g. ia32-libs-i386. dpkg -l: ia32-libs-i386, apt-cache policy: ia32-libs-i386:i386 + $ma_fix_pkgname eq $from_list) { + $pkgname = $from_list; + } else { + die "Unexpected order mismatch in apt-cache policy output (apt-cache policy name: $pkgname - dpkg -l name: $from_list)\n"; + } + } + } elsif ($line =~ /^ +Installed: (.*)$/) { + # etch dpkg -l does not print epochs, so use this info, it's better + $installed->{$pkgname}{'installed'} = $1; + # initialize security-update + $installed->{$pkgname}{'security-update'} = 0; + } elsif ($line =~ /^ +Candidate: (.*)$/) { + $installed->{$pkgname}{'candidate'} = $1; + } elsif ($line =~ / ([^ ]+) [0-9]+/) { + # check if the next lines show the sources of our candidate + if ($1 eq $installed->{$pkgname}{'candidate'}) { + $candidate_found = 1; + } + } elsif (($line =~ / +[0-9]+ [^ ]+\/(security\.([^ ]+\.)?debian\.org|debian-security).*\/updates\//) && $candidate_found ) { + $installed->{$pkgname}{'security-update'} = 1; + } elsif ($line =~ /^ +\*\*\*/) { + $line = shift @lines; + my @l = split(/ +/, $line); + $installed->{$pkgname}{'origin'} = $l[2]; + $candidate_found = 0; + } + } + + my (%current, %obsolete, %outofdate, %security_outofdate); + for my $pkgname (keys %$installed) { + my $pkg = $installed->{$pkgname}; + + unless (defined($pkg->{'candidate'}) && defined($pkg->{'origin'})) { + $obsolete{$pkgname} = $pkg; + next; + } + + if ($pkg->{'candidate'} ne $pkg->{'installed'}) { + if ($pkg->{'security-update'}) { + $security_outofdate{$pkgname} = $pkg; + } else { + $outofdate{$pkgname} = $pkg; + } + next; + }; + if ($pkg->{'origin'} eq '/var/lib/dpkg/status') { + $obsolete{$pkgname} = $pkg; + next; + } + $current{$pkgname} = $pkg; + } + + $pkgs{'current'} = \%current; + $pkgs{'outofdate'} = \%outofdate; + $pkgs{'security_outofdate'} = \%security_outofdate; + $pkgs{'obsolete'} = \%obsolete; + return \%pkgs; +} + +sub load_ignores { + my ($ignorefiles, $require_file) = @_; + + my @ignores; + + for my $ignoreitem (@$ignorefiles) { + next if (!$require_file and ! -e $ignoreitem); + + my @filestoopen; + if (-d $ignoreitem) { + opendir(DIR, $ignoreitem) or die ("Cannot open dir $ignoreitem: $!\n"); + @filestoopen = readdir(DIR); + closedir(DIR); + + @filestoopen = grep { -f ($ignoreitem.'/'.$_) } @filestoopen; + @filestoopen = grep { /^([a-z0-9_.-]+)+[a-z0-9]+$/i } @filestoopen; + @filestoopen = grep { !/dpkg-(old|dist|new|tmp)$/ } @filestoopen; + @filestoopen = map { ($ignoreitem.'/'.$_) } @filestoopen; + } else { + push @filestoopen, $ignoreitem; + } + + for my $f (@filestoopen) { + open (F, "< $f") or die ("Cannot open $f: $!\n"); + push @ignores, <F>; + close F; + } + } + chomp(@ignores); + return \@ignores; +} + +sub check_ignore { + my ($pkg, $ignores) = @_; + + my $ignore_this = 0; + for my $ignore (@$ignores) { + my $ig = $ignore; + return 1 if ($ig eq $pkg); + if (substr($ig,0,1) eq '/') { + substr($ig, 0, 1, ''); + $ig =~ s,/$,,; + return 1 if ($pkg =~ /$ig/); + } + } + return 0 +} + +sub filter_ignored { + my ($packages, $ignores) = @_; + + my $obs = $packages->{'obsolete'}; + + my (%ignored, %bad); + for my $pkg (keys %$obs) { + if (check_ignore($pkg, $ignores)) { + $ignored{$pkg} = $obs->{$pkg}; + } else { + $bad{$pkg} = $obs->{$pkg}; + }; + } + delete $packages->{'obsolete'}; + $packages->{'obsolete'} = \%bad; + $packages->{'obsolete-ignored'} = \%ignored; +}; + +sub usage { + my ($fd, $exit) = @_; + print $fd "Usage: $PROGRAM_NAME [<ignorefile|dir> [<ignorefile|dir> ...]]\n"; + exit $exit; +} + +my $ignorefiles = [$IGNORE, $IGNORED]; +my $ignorefile_userset = 0; +if (@ARGV >= 1) { + usage(\*STDOUT, 0) if ($ARGV[0] eq "-h"); + usage(\*STDOUT, 0) if ($ARGV[0] eq "--help"); + $ignorefile_userset = 1; + $ignorefiles = \@ARGV; +}; + +my $ignores = load_ignores($ignorefiles, $ignorefile_userset); +my $packages = get_packages(); + +filter_ignored($packages, $ignores); + + + +my @reportform = ( + { 'key' => 'obsolete', + 'listpackages' => 1, + 'long' => "%d local or obsolete packages: %s", + 'short' => "%d obs/loc", + 'perf' => "obs_loc=%d;1;5;0", + 'status' => 'WARNING' }, + { 'key' => 'outofdate', + 'listpackages' => 1, + 'long' => "%d out of date packages: %s", + 'short' => "%d updates", + 'perf' => "outdated=%d;1;5;0", + 'status' => 'WARNING' }, + { 'key' => 'current', + 'listpackages' => 0, + 'long' => "%d packages current.", + 'short' => "%d ok", + 'perf' => "current=%d;;;0", + 'status' => 'OK' }, + { 'key' => 'obsolete-ignored', + 'listpackages' => 1, + 'long' => "%d whitelisted local or obsolete packages: %s", + 'short' => "%d obs/loc(ignored)", + 'perf' => "obs_ign=%d;;;0", + 'status' => 'OK' }, + { 'key' => 'rc', + 'listpackages' => 1, + 'long' => "%d packages removed but not purged: %s", + 'short' => "%d rc", + 'perf' => "rm_unprg=%d;;;0", + 'status' => 'OK' }, + { 'key' => 'hi', + 'listpackages' => 1, + 'long' => "%d packages on hold: %s", + 'short' => "%d hi", + 'perf' => "hold=%d;;;0", + 'status' => 'OK' }, + { 'key' => 'pc', + 'listpackages' => 1, + 'long' => "%d packages requested to be purged but conffiles still installed: %s", + 'short' => "%d pc", + 'perf' => "prg_conf=%d;1;;0", + 'status' => 'WARNING' }, + { 'key' => 'security_outofdate', + 'listpackages' => 1, + 'long' => "%d packages with outstanding security updates: %s", + 'short' => "%d security-updates", + 'perf' => "security_outdated=%d;;1;0", + 'status' => 'CRITICAL' }, + ); + +my @longout; +my @perfout; +my @shortout; +for my $form (@reportform) { + my $pkgs = $packages->{$form->{'key'}}; + delete $packages->{$form->{'key'}}; + my $num = scalar keys %$pkgs; + push @perfout, sprintf($form->{'perf'}, $num); + next unless ($num > 0); + if ($form->{'listpackages'}) { + my $list = join(", ", keys %$pkgs); + push @longout, sprintf($form->{'long'}, $num, $list); + } else { + push @longout, sprintf($form->{'long'}, $num); + }; + push @shortout, sprintf($form->{'short'}, $num); + record($form->{'status'}); +}; +if (scalar keys %$packages) { + record('WARNING'); + unshift @shortout, "unk: ".join(", ", keys %$packages); + for my $status (sort {$b cmp $a} keys %$packages) { + my $pkgs = $packages->{$status}; + my $list = join(", ", keys %$pkgs); + unshift @longout, "Unknown package status $status: $list"; + }; +} + +my $shortout = $EXITCODE.": ".join(", ", @shortout); +my $longout = join("\n", @longout); +my $perfout = "|".join(" ", @perfout); + +print $shortout,"\n"; +print $longout,"\n"; +print $perfout,"\n"; + +exit $CODE{$EXITCODE}; diff --git a/hosts/jtx1b-armhf-rb/usr/local/bin/dsa-check-running-kernel b/hosts/jtx1b-armhf-rb/usr/local/bin/dsa-check-running-kernel new file mode 100755 index 00000000..aa6e35bd --- /dev/null +++ b/hosts/jtx1b-armhf-rb/usr/local/bin/dsa-check-running-kernel @@ -0,0 +1,254 @@ +#!/bin/bash + +# Check if the running kernel has the same version string as the on-disk +# kernel image. + +# Copyright 2008,2009,2011,2012,2013,2014 Peter Palfrader +# Copyright 2009 Stephen Gran +# Copyright 2010,2012,2013 Uli Martens +# Copyright 2011 Alexander Reichle-Schmehl +# +# Permission is hereby granted, free of charge, to any person obtaining +# a copy of this software and associated documentation files (the +# "Software"), to deal in the Software without restriction, including +# without limitation the rights to use, copy, modify, merge, publish, +# distribute, sublicense, and/or sell copies of the Software, and to +# permit persons to whom the Software is furnished to do so, subject to +# the following conditions: +# +# The above copyright notice and this permission notice shall be +# included in all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE +# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION +# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION +# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +OK=0; +WARNING=1; +CRITICAL=2; +UNKNOWN=3; + +get_offset() { + local file needle + + file="$1" + needle="$2" + + perl -e ' + undef $/; + $i = 0; $k=<>; + while (($i = index($k, "'"$needle"'", $i)) >= 0) { + print $i++,"\n"; + }; ' < "$file" +} + +get_avail() { + # This is wrong, but leaves room for when we have to care for machines running + # myfirstunix-image-0.1-dsa-arm + local prefix="$1"; shift + + local kervers=$(uname -r) + + local metavers='' + + # DSA uses kernel versions of the form 2.6.29.3-dsa-dl380-oldxeon, where + # Debian uses versions of the form 2.6.29-2-amd64 + if [ "${kervers#2}" != "$kervers" ]; then + if [ "${kervers//dsa}" != "$kervers" ]; then + metavers=$(echo $kervers | sed -r -e 's/^2\.(4|6)\.[0-9]+([\.0-9]+?)-(.*)/2.\1-\3/') + else + metavers=$(echo $kervers | sed -r -e 's/^2\.(4|6)\.[0-9]+-[A-Za-z0-9\.]+-(.*)/2.\1-\2/') + fi + else + metavers=$(echo $kervers | sed -r -e 's/^[0-9]+\.[0-9]+(\.[0-9])?+-[A-Za-z0-9\.]+-(.*)/\2/') + fi + + # Attempt to track back to a metapackage failed. bail + if [ "$metavers" = "$kervers" ]; then + return 2 + fi + + # We're just going to give up if we can't find a matching metapackage + # I tried being strict once, and it just caused a lot of headaches. We'll see how + # being lax does for us + + local output=$(apt-cache policy ${prefix}-image-${metavers} 2>/dev/null) + local metaavailvers=$(echo "$output" | grep '^ Candidate:' | awk '{print $2}') + local metainstavers=$(echo "$output" | grep '^ Installed:' | awk '{print $2}') + + if [ -z "$metaavailvers" ] || [ "$metaavailvers" = '(none)' ]; then + return 2 + fi + if [ -z "$metainstavers" ] || [ "$metainstavers" = '(none)' ]; then + return 2 + fi + + if [ "$metaavailvers" != "$metainstavers" ] ; then + echo "${prefix}-image-${metavers} $metaavailvers available but $metainstavers installed" + return 1 + fi + + local imagename=0 + # --no-all-versions show shows only the candidate + for vers in $(apt-cache --no-all-versions show ${prefix}-image-${metavers} | sed -n 's/^Depends: //p' | tr ',' '\n' | tr -d ' ' | grep ${prefix}-image | awk '{print $1}' | sort -u); do + if dpkg --compare-versions "1.$vers" gt "1.$imagename"; then + imagename=$vers + fi + done + + if [ -z "$imagename" ] || [ "$imagename" = 0 ]; then + return 2 + fi + + if [ "$imagename" != "${prefix}-image-${kervers}" ]; then + if dpkg --compare-versions 1."$imagename" lt 1."${prefix}-image-${kervers}"; then + return 2 + fi + echo "$imagename" != "${prefix}-image-${kervers}" + return 1 + fi + + local availvrs=$(apt-cache policy ${imagename} 2>/dev/null | grep '^ Candidate' | awk '{print $2}') + local kernelversion=$(apt-cache policy ${prefix}-image-${kervers} 2>/dev/null | grep '^ Installed:' | awk '{print $2}') + + if [ "$availvrs" = "$kernelversion" ]; then + return 0 + fi + + echo "$kernelversion != $availvrs" + return 1 +} + +cat_vmlinux() { + local image header filter hdroff + + image="$1" + header="$2" + filter="$3" + hdroff="$4" + + get_offset "$image" $header | head -n 5 | while read off; do + (if [ "$off" != 0 ]; then + dd ibs="$((off+hdroff))" skip=1 count=0 + fi && + dd bs=512k) < "$image" 2>/dev/null | $filter 2>/dev/null + done +} + +get_image_linux() { + local image + + image="$1" + + # gzip compressed image + cat_vmlinux "$image" "\x1f\x8b\x08\x00" "zcat" 0 + cat_vmlinux "$image" "\x1f\x8b\x08\x08" "zcat" 0 + # lzma compressed image + cat_vmlinux "$image" "\x00\x00\x00\x02\xff" "xzcat" -1 + cat_vmlinux "$image" "\x00\x00\x00\x04\xff" "xzcat" -1 + # xz compressed image + cat_vmlinux "$image" "\xfd\x37\x7a\x58\x5a " "xzcat" 0 + + echo "ERROR: Unable to extract kernel image." 2>&1 + exit 1 +} + + +freebsd_check_running_version() { + local imagefile="$1"; shift + + local r="$(uname -r)" + local v="$(uname -v| sed -e 's/^#[0-9]*/&:/')" + + local q='@(#)FreeBSD '"$r $v" + + if zcat "$imagefile" | $STRINGS | grep -F -q "$q"; then + echo "OK" + else + echo "not OK" + fi +} + +STRINGS=""; +if [ -x "$(which strings)" ]; then + STRINGS="$(which strings)" +elif [ -x "$(which busybox)" -a "$( echo foobar | $(which busybox) strings 2>/dev/null)" = "foobar" ]; then + STRINGS="$(which busybox) strings" +fi + +searched="" +for on_disk in \ + "/boot/vmlinuz-`uname -r`"\ + "/boot/vmlinux-`uname -r`"\ + "/boot/kfreebsd-`uname -r`.gz"; do + + if [ -e "$on_disk" ]; then + if [ -z "$STRINGS" ]; then + echo "UNKNOWN: 'strings' command missing, perhaps install binutils or busybox?" + exit $UNKNOWN + fi + if [ "${on_disk/vmlinu}" != "$on_disk" ]; then + on_disk_version="`get_image_linux "$on_disk" | $STRINGS | grep 'Linux version' | head -n1`" + if [ -x /usr/bin/lsb_release ] ; then + vendor=$(lsb_release -i -s) + if [ -n "$vendor" ] && [ "xDebian" != "x$vendor" ] ; then + on_disk_version=$( echo $on_disk_version|sed -e "s/ ($vendor [[:alnum:]\.-]\+ [[:alnum:]\.]\+)//") + fi + fi + [ -z "$on_disk_version" ] || break + on_disk_version="`cat "$on_disk" | $STRINGS | grep 'Linux version' | head -n1`" + [ -z "$on_disk_version" ] || break + + echo "UNKNOWN: Failed to get a version string from image $on_disk" + exit $UNKNOWN + else + on_disk_version="$(zcat $on_disk | $STRINGS | grep Debian | head -n 1 | sed -e 's/Debian [[:alnum:]]\+ (\(.*\))/\1/')" + fi + fi + searched="$searched $on_disk" +done + +if ! [ -e "$on_disk" ]; then + echo "WARNING: Did not find a kernel image (checked$searched) - I have no idea which kernel I am running" + exit $WARNING +fi + +if [ "$(uname -s)" = "Linux" ]; then + running_version="`cat /proc/version`" + if [ -z "$running_version" ] ; then + echo "UNKNOWN: Failed to get a version string from running system" + exit $UNKNOWN + fi + + if [ "$running_version" != "$on_disk_version" ]; then + echo "WARNING: Running kernel does not match on-disk kernel image: [$running_version != $on_disk_version]" + exit $WARNING + fi + + ret="$(get_avail linux)" + if [ $? = 1 ]; then + echo "WARNING: Kernel needs upgrade [$ret]" + exit $WARNING + fi +else + image_current=$(freebsd_check_running_version $on_disk) + running_version="`uname -s` `uname -r` `uname -v`" + if [ "$image_current" != "OK" ]; then + approx_time="$(date -d "@`stat -c '%Y' "$on_disk"`" +"%Y-%m-%d %H:%M:%S")" + echo "WARNING: Currently running kernel ($running_version) does not match on disk image (~ $approx_time)" + exit $WARNING; + fi + + ret="$(get_avail linux)" + if [ $? = 1 ]; then + echo "WARNING: Kernel needs upgrade [$ret]" + exit $WARNING + fi +fi + +echo "OK: Running kernel matches on disk image: [$running_version]" +exit $OK |