Make test drill, next steps, call for help with Winetest

Francois Gouget fgouget at free.fr
Thu Nov 1 11:29:09 CDT 2007


On Sat, 27 Oct 2007, Francois Gouget wrote:
[...]
> There are other options to specify which version of winetest.exe to 
> grab, to set the timeout on the tests execution, etc.
> 
> Things still on the todo list:
>  * the script also grabs the winetest.exe signature and attempts to 
> verify it. But I don't know where to find the corresponding public key 
> (651FD487) so I don't know if this really works.

Hmm, as pointed out by Detlef, there a link on Paul's home page pointing 
to his public key and the required key is in there. Then it's just a 
matter of telling gpg to use it which I have now done and the signature 
checking code seems to work as intended.


>  * the script gets the 'latest' winetest.exe version by default, but 
> when there are compilation problems I guess this may stay stuck at the 
> same revision for some time. So it would be nice if the script could 
> know which version it's getting so it could skip the tests if that 
> version is too old, or has already been tested.

The script can now use a local cache containing the already downloaded 
files, and can be told to skip the tests if it finds that a file has not 
changed since the last time it has been used in a given vm+snapshot 
combination.

In fact I've been able to verify that it works in real life since 
winetest has not been updated since last monday :-(
Compilation problems?

I've attached the latest version of the script.


-- 
Francois Gouget <fgouget at free.fr>              http://fgouget.free.fr/
                  Hiroshima '45 - Czernobyl '86 - Windows '95
-------------- next part --------------
#!/bin/sh
# Copyright (C) 2007 Francois Gouget
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public
# License as published by the Free Software Foundation; either
# version 2.1 of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
# General Public License for more details.
#
# You should have received a copy of the GNU General Public
# License along with this library; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
name0=`basename "$0"`

verbose=""
base_url="http://www.astro.gla.ac.uk/users/paulm/WRT/CrossBuilt"
vmware="/usr/local/opt/vmware/bin"
if [ -z "$DISPLAY" ]
then
    DISPLAY=":0.0"
    export DISPLAY
fi


verbose()
{
    if [ -n "$verbose" ]
    then
        echo "$@"
    fi
}

vm_is_busy()
{
    vm="$1"
    test -f "$vm.WRITELOCK"
    return $?
}

vm_is_running()
{
    # For VM matching purposes, only keep the last two elements of the path
    # to avoid trouble with symbolic links
    vm_match=`dirname "$opt_vm"`
    vm_match=`basename "$vm_match"`/`basename "$opt_vm"`
    vm_match=`echo "$vm_match" | sed -e 's/\([^a-zA-Z0-9_ /]\)/[\1]/g'`
    "$vmware/vmrun" list | egrep "$vm_match" >/dev/null
    return $?
}

cached_wget()
{
    url="$1"
    dst="$2"
    cache="$3"

    if [ -n "$cache" ]
    then
    filename=`basename "$url"`
    (
        cd "$cache" &&
        wget -N "$url" &&
        cp -pr "$filename" "$dst"
    )
    else
        wget -O "$dst" "$url"
    fi
}


### Main

opt_vm=""
opt_tag_prefix=""
opt_tag=""
opt_cache=""
opt_version=""
opt_check_sig=""
opt_submit=""
opt_timeout=""
opt_autorun=""
opt_snapshot=""
opt_cddevice=""
opt_usage=""
while [ $# -gt 0 ]
do
    arg="$1"
    shift
    case "$arg" in
    --tag-prefix)
        if [ -n "$opt_tag_prefix" ]
        then
            echo "$name0:error: --tag-prefix can only be used once" >&2
            opt_usage="2"
            break
        elif [ $# -eq 0 ]
        then
            echo "$name0:error: missing argument for the --tag-prefix option" >&2
            opt_usage="2"
            break
        else
            opt_tag_prefix="$1"
            shift
        fi
        ;;
    --tag)
        if [ -n "$opt_tag" ]
        then
            echo "$name0:error: --tag can only be used once" >&2
            opt_usage="2"
            break
        elif [ $# -eq 0 ]
        then
            echo "$name0:error: missing argument for the --tag option" >&2
            opt_usage="2"
            break
        else
            opt_tag="$1"
            shift
        fi
        ;;
    --cache)
        if [ -n "$opt_cache" ]
        then
            echo "$name0:error: --cache can only be used once" >&2
            opt_usage="2"
            break
        elif [ $# -eq 0 ]
        then
            echo "$name0:error: missing argument for the --cache option" >&2
            opt_usage="2"
            break
        else
            opt_cache="$1"
            shift
        fi
        ;;
    --skip-old)
        opt_skip_old="1"
        ;;
    --no-skip-old)
        opt_skip_old="0"
        ;;
    --version)
        if [ -n "$opt_version" ]
        then
            echo "$name0:error: --version can only be used once" >&2
            opt_usage="2"
            break
        elif [ $# -eq 0 ]
        then
            echo "$name0:error: missing argument for the --version option" >&2
            opt_usage="2"
            break
        else
            opt_version="$1"
            shift
        fi
        ;;
    --check-sig)
        opt_check_sig="1"
        ;;
    --no-check-sig)
        opt_check_sig="0"
        ;;
    --submit)
        opt_submit="1"
        ;;
    --no-submit)
        opt_submit="0"
        ;;
    --timeout)
        if [ -n "$opt_timeout" ]
        then
            echo "$name0:error: --timeout can only be used once" >&2
            opt_usage="2"
            break
        elif [ $# -eq 0 ]
        then
            echo "$name0:error: missing argument for the --timeout option" >&2
            opt_usage="2"
            break
        elif echo "$1" | egrep '^[0-9][0-9]*$' >/dev/null
        then
            opt_timeout="$1"
            shift
        else
            echo "$name0:error: the timeout value must be a decimal number" >&2
            opt_usage="2"
            break
        fi
        ;;
    --autorun)
        opt_autorun="1"
        ;;
    --no-autorun)
        opt_autorun="0"
        ;;
    --snapshot)
        if [ -n "$opt_snapshot" ]
        then
            echo "$name0:error: --snapshot can only be used once" >&2
            opt_usage="2"
            break
        elif [ $# -eq 0 ]
        then
            echo "$name0:error: missing argument for the --snapshot option" >&2
            opt_usage="2"
            break
        else
            opt_snapshot="$1"
            shift
        fi
        ;;
    --cddevice)
        if [ -n "$opt_cddevice" ]
        then
            echo "$name0:error: --cddevice can only be used once" >&2
            opt_usage="2"
            break
        elif [ $# -eq 0 ]
        then
            echo "$name0:error: missing argument for the --cddevice option" >&2
            opt_usage="2"
            break
        else
            opt_cddevice="$1"
            shift
        fi
        ;;
    --verbose)
        verbose="1"
        ;;
    --help|-help|-h|-?)
        opt_usage="0"
        break
        ;;
    *)
        if [ -z "$opt_vm" ]
        then
            opt_vm="$arg"
        else
            echo "$name0:error: unknown option '$arg'" >&2
            opt_usage="2"
            break
        fi
    esac
done

if [ -z "$opt_usage" ]
then
    if [ -n "$opt_tag_prefix" -a -n "$opt_tag" ]
    then
        echo "$name0:error: --tag-prefix and --tag are incompatible" >&2
        opt_usage="2"
    elif [ -z "$opt_tag_prefix" ]
    then
        opt_tag_prefix="vmware"
    fi
    if [ -z "$opt_vm" ]
    then
        echo "$name0:error: you must specify a VM path" >&2
        opt_usage="2"
    elif [ -z "$opt_tag" ]
    then
        opt_tag="$opt_tag_prefix-"`basename "$opt_vm" | sed -e 's/\.[cv][fm][gx]$//' -e 's/ //g'`
    fi
    [ -n "$opt_skip_old" ] || opt_skip_old="0"
    if [ -n "$opt_cache" -a ! -d "$opt_cache" ]
    then
        echo "$name0:error: --cache must point to a directory" >&2
        opt_usage="2"
    elif [ -z "$opt_cache" -a "$opt_skip_old" != "0" ]
    then
        echo "$name0:error: --skip-old can only be used with --cache" >&2
        opt_usage="2"
    fi
    [ -n "$opt_version" ] || opt_version="latest"
    if [ -z "$opt_snapshot" ]
    then
        opt_snapshot="winetest"
    fi
    [ -n "$opt_autorun" ] || opt_autorun="1"
    if [ "$opt_autorun" = "0" -a -n "$opt_submit" ]
    then
        echo "$name0:error: --(no-)submit can only be used with the --autorun option" >&2
        opt_usage="2"
    fi
    [ -n "$opt_submit" ] || opt_submit="1"
    if [ "$opt_submit" = "0" -a -z "$opt_timeout" ]
    then
        opt_timeout="0"
    fi
    if [ "$opt_submit" = "0" -a "$opt_skip_old" != "0" ]
    then
        echo "$name0:error: --no-submit and --skip-old are incompatible" >&2
        opt_usage="2"
    fi
    [ -n "$opt_timeout" ] || opt_timeout="30"
    [ -n "$opt_cddevice" ] || opt_cddevice="ide1:0"
fi

if [ -n "$opt_usage" ]
then
    if [ "$opt_usage" != "0" ]
    then
        echo "$name0:error: try '$name0 --help' for more information" >&2
        exit $opt_usage
    fi
    echo "Usage: $name0 [--version VERSION] [--cache DIR [--skip-old]] [--check-sig]"
    echo "                [--tag-prefix PREFIX] [--tag TAG] [--submit|--no-submit]"
    echo "                [--autorun|--no-autorun] [--cddevice DEVICE]"
    echo "                [--timeout TIMEOUT] [--snapshot SNAPSHOT] /path/to/vm.vmx"
    echo "                [--verbose] [--help]"
    echo
    echo "Downloads the latest winetest.exe, and runs it in a VMware virtual machine by"
    echo "putting it on a virtual CD. The state of the virtual machine is left"
    echo "undisturbed."
    echo
    echo "Options:"
    echo "   --version VERSION   Specifies which version of winetest.exe to download."
    echo "                       By default this is 'latest'."
    echo "   --cache DIR         Specifies where to cache the downloaded binaries. This"
    echo "                       is useful when running a test multiple times in"
    echo "                       different virtual machines."
    echo "   --skip-old          Exit without running the test if the test has not"
    echo "                       changed and has already been run in this virtual"
    echo "                       machine+snapshot combination."
    echo "   --check-sig         Specifies that winetest.exe should not be run if its"
    echo "                       signature cannot be checked. By default, the tests are"
    echo "                       only aborted if winetest.exe does not match its"
    echo "                       signature. If --no-check-sig is used, then the"
    echo "                       signature is not checked at all'."
    echo "   --tag-prefix PREFIX Specifies what to prefix to the virtual machine name"
    echo "                       with when building the default tag. By default this is"
    echo "                       'vmware'."
    echo "   --tag TAG           The tag to use when submitting the results. By default"
    echo "                       this is the tag prefix, followed by a dash and the"
    echo "                       basename of the virtual machine file."
    echo "   --timeout TIMEOUT   Specifies how long, in minutes, to give to winetest.exe"
    echo "                       to run. By default this is 30 minutes."
    echo "   --submit            Submit the test results to http://test.winehq.org/data/"
    echo "                       This is the default. Use --no-submit to not submit the"
    echo "                       results, and remove the 30 minutes timeout."
    echo "   --autorun           Generate an autorun.inf file so the tests are started"
    echo "                       automatically. This is the default. If you use"
    echo "                       --no-autorun, then you will need to make your own"
    echo "                       arrangements to start the tests from the CD."
    echo "   --cddevice DEVICE   The name of the virtual machine's device for the cdrom"
    echo "                       drive. By default this is 'ide1:0'."
    echo "   --snapshot SNAPSHOT The snapshot to use to run the tests. By default this"
    echo "                       is 'winetest'. Make sure that, in this snapshot, the"
    echo "                       cdrom device is connected. If you use the --autorun"
    echo "                       option, then autorun should also be enabled."
    echo "   /path/to/vm.vmx     This is the path to the virtual machine's vmx or cfg"
    echo "                       file."
    echo "   --verbose           Print some extra informational messages."
    echo "   --help              Show this help message."
    exit 0
fi


### Check that the VM is usable
verbose "Checking the VM..."

if vm_is_busy "$opt_vm"
then
    echo "$name0:error: '$opt_vm' is already opened or running." >&2
    if [ $opt_timeout -eq 0 ]
    then
        echo "$name0:error: Aborting." >&2
        exit 1
    fi
    count=`expr $opt_timeout + 2`
    while vm_is_busy "$opt_vm"
    do
        if [ $count -eq 0 ]
        then
            echo "$name0:error: '$opt_vm' is still in use. Giving up." >&2
            exit 1
        fi
        count=`expr $count - 1`
        sleep 60
    done
fi

"$vmware/vmrun" listSnapshots "$opt_vm" | egrep "^$opt_snapshot\$" >/dev/null
if [ $? -ne 0 ]
then
    echo "$name0:error: the '$opt_snapshot' snapshot does not exist. Aborting" >&2
    exit 1
fi


### Grab winetest and prepare the ISO
verbose "Downloading winetest.exe..."

[ -n "$TMPDIR" ] || TMPDIR="/tmp"
tmpdir="$TMPDIR/$name0-$$"
if ! mkdir -p "$tmpdir/master"
then
    echo "$name0:error: unable to create the '$tmpdir/master' directory" >&2
    exit 1
fi
logfile="$tmpdir/$name0.log"

cached_wget "$base_url/winetest-$opt_version.exe" "$tmpdir/master/winetest.exe" "$opt_cache" >"$logfile" 2>&1
if [ $? -ne 0 ]
then
    echo "$name0:error: unable to download winetest.exe" >&2
    echo
    cat "$logfile"
    exit 1
fi
if [ -n "$opt_cache" ]
then
    run="$vm $opt_snapshot"
    runfile="$opt_cache/winetest-$opt_version.exe.runs"

    egrep "^Server file no newer than local file" "$logfile" >/dev/null
    if [ $? -ne 0 ]
    then
        rm -f "$runfile"
    fi

    if [ "$opt_skip_old" = "1" ] && egrep "^$run\$" "$runfile" >/dev/null 2>&1
    then
        verbose "The test has already been run in $run."
        exit 0
    fi
fi

cached_wget "$base_url/winetest-$opt_version.exe.sig" "$tmpdir/master/winetest.exe.sig" "$opt_cache" >"$logfile" 2>&1
if [ $? -ne 0 -a "$opt_check_sig" != "0" ]
then
    echo "$name0:error: unable to download winetest.exe.sig" >&2
    echo
    cat "$logfile"
    exit 1
fi


### Check the winetest.exe signature
if [ "$opt_check_sig" != "0" ]
then
    verbose "Checking the winetest.exe signature..."

    type gpg >/dev/null 2>&1
    if [ $? -eq 0 ]
    then
        gpg --verify "$tmpdir/master/winetest.exe.sig"
        rc=$?
        if [ $rc -eq 0 ]
        then
            echo "Signature checked."
        elif [ $rc -eq 1 ]
        then
            echo "$name0:error: it looks like winetest.exe has been tampered with. Aborting" >&2
            exit 1
        elif [ "$opt_check_sig" = "1" ]
        then
            echo "$name0:warning: your system does not seem to be set up to check the signature. Aborting." >&2
            exit 1
        else
            echo "$name0:warning: your system does not seem to be set up to check the signature. Continuing anyway..." >&2
        fi
    elif [ "$opt_check_sig" = "1" ]
    then
        echo "$name0:error: gpg is not installed. Aborting." >&2
        exit 1
    else
        echo "$name0:warning: unable to check the winetest.exe signature because gpg is not installed. Continuing anyway..." >&2
    fi
fi


### Create the CD image
verbose "Creating the CD image..."
if [ "$opt_autorun" = "1" ]
then
    options=""
    if [ "$opt_submit" = "0" ]
    then
        options="-o c:\\winetest.log"
    fi
    cat >"$tmpdir/master/autorun.inf" <<_EOF_
[autorun]
open=winetest.exe -q -t $opt_tag $options
_EOF_
fi

mkisofs -o "$tmpdir/winetest.iso" "$tmpdir/master" >"$logfile" 2>&1
if [ $? -ne 0 ]
then
    echo "$name0:error: unable to create the CD image" >&2
    echo
    cat "$logfile"
    exit 1
fi


### Prepare the VM

tmp_snapshot="$name0-`date +%Y%m%d`"
"$vmware/vmrun" listSnapshots "$opt_vm" | egrep "^$tmp_snapshot\$" >/dev/null
if [ $? -eq 0 ]
then
    # This is not our snapshot so don't delete it after we're done
    delete_snapshot=0
else
    "$vmware/vmrun" snapshot "$opt_vm" "$tmp_snapshot"
    if [ $? -ne 0 ]
    then
        echo "$name0:error: an error occurred while saving the VM's current state" >&2
        exit 1
    fi
    delete_snapshot=1
fi

"$vmware/vmrun" revertToSnapshot "$opt_vm" "$opt_snapshot"
if [ $? -ne 0 ]
then
    echo "$name0:error: an error occurred while switching to the '$opt_snapshot' snapshot" >&2
    exit 1
fi


### Run the test
verbose "Running the tests..."
"$vmware/vmware" -s "$opt_cddevice.fileName=$tmpdir/winetest.iso" \
                 -s "$opt_cddevice.deviceType=cdrom-image" \
                 -x -q "$opt_vm" &
count=0
while [ $opt_timeout -eq 0 -o $count -lt $opt_timeout ]
do
    sleep 60
    if vm_is_running "$opt_vm"
    then
        count=`expr $count + 1`
    else
        break
    fi
done
if [ $opt_timeout -ne 0 -a $count -gt $opt_timeout ]
then
    "$vmware/vmrun" stop "$opt_vm"
fi
if [ "$opt_skip_old" = "1" ]
then
    echo "$run" >>"$runfile"
fi


### Restore the VM and cleanup
verbose "Cleaning up..."

"$vmware/vmrun" revertToSnapshot "$opt_vm" "$tmp_snapshot"
if [ $? -ne 0 ]
then
    echo "$name0:error: an error occurred while restoring the VM's to its initial state ($tmp_snapshot)" >&2
    exit 1
fi
if [ $delete_snapshot -ne 0 ]
then
    "$vmware/vmrun" deleteSnapshot "$opt_vm" "$tmp_snapshot"
fi

rm -rf "$tmpdir"

exit 0


More information about the wine-devel mailing list