Home | History | Annotate | Download | only in test
      1 #!/bin/sh
      2 ##
      3 ##  Copyright (c) 2014 The WebM project authors. All Rights Reserved.
      4 ##
      5 ##  Use of this source code is governed by a BSD-style license
      6 ##  that can be found in the LICENSE file in the root of the source
      7 ##  tree. An additional intellectual property rights grant can be found
      8 ##  in the file PATENTS.  All contributing project authors may
      9 ##  be found in the AUTHORS file in the root of the source tree.
     10 ##
     11 ##  This file contains shell code shared by test scripts for libvpx tools.
     12 
     13 # Use $VPX_TEST_TOOLS_COMMON_SH as a pseudo include guard.
     14 if [ -z "${VPX_TEST_TOOLS_COMMON_SH}" ]; then
     15 VPX_TEST_TOOLS_COMMON_SH=included
     16 
     17 set -e
     18 devnull='> /dev/null 2>&1'
     19 VPX_TEST_PREFIX=""
     20 
     21 elog() {
     22   echo "$@" 1>&2
     23 }
     24 
     25 vlog() {
     26   if [ "${VPX_TEST_VERBOSE_OUTPUT}" = "yes" ]; then
     27     echo "$@"
     28   fi
     29 }
     30 
     31 # Sets $VPX_TOOL_TEST to the name specified by positional parameter one.
     32 test_begin() {
     33   VPX_TOOL_TEST="${1}"
     34 }
     35 
     36 # Clears the VPX_TOOL_TEST variable after confirming that $VPX_TOOL_TEST matches
     37 # positional parameter one.
     38 test_end() {
     39   if [ "$1" != "${VPX_TOOL_TEST}" ]; then
     40     echo "FAIL completed test mismatch!."
     41     echo "  completed test: ${1}"
     42     echo "  active test: ${VPX_TOOL_TEST}."
     43     return 1
     44   fi
     45   VPX_TOOL_TEST='<unset>'
     46 }
     47 
     48 # Echoes the target configuration being tested.
     49 test_configuration_target() {
     50   vpx_config_mk="${LIBVPX_CONFIG_PATH}/config.mk"
     51   # Find the TOOLCHAIN line, split it using ':=' as the field separator, and
     52   # print the last field to get the value. Then pipe the value to tr to consume
     53   # any leading/trailing spaces while allowing tr to echo the output to stdout.
     54   awk -F ':=' '/TOOLCHAIN/ { print $NF }' "${vpx_config_mk}" | tr -d ' '
     55 }
     56 
     57 # Trap function used for failure reports and tool output directory removal.
     58 # When the contents of $VPX_TOOL_TEST do not match the string '<unset>', reports
     59 # failure of test stored in $VPX_TOOL_TEST.
     60 cleanup() {
     61   if [ -n "${VPX_TOOL_TEST}" ] && [ "${VPX_TOOL_TEST}" != '<unset>' ]; then
     62     echo "FAIL: $VPX_TOOL_TEST"
     63   fi
     64   if [ -n "${VPX_TEST_OUTPUT_DIR}" ] && [ -d "${VPX_TEST_OUTPUT_DIR}" ]; then
     65     rm -rf "${VPX_TEST_OUTPUT_DIR}"
     66   fi
     67 }
     68 
     69 # Echoes the git hash portion of the VERSION_STRING variable defined in
     70 # $LIBVPX_CONFIG_PATH/config.mk to stdout, or the version number string when
     71 # no git hash is contained in VERSION_STRING.
     72 config_hash() {
     73   vpx_config_mk="${LIBVPX_CONFIG_PATH}/config.mk"
     74   # Find VERSION_STRING line, split it with "-g" and print the last field to
     75   # output the git hash to stdout.
     76   vpx_version=$(awk -F -g '/VERSION_STRING/ {print $NF}' "${vpx_config_mk}")
     77   # Handle two situations here:
     78   # 1. The default case: $vpx_version is a git hash, so echo it unchanged.
     79   # 2. When being run a non-dev tree, the -g portion is not present in the
     80   #    version string: It's only the version number.
     81   #    In this case $vpx_version is something like 'VERSION_STRING=v1.3.0', so
     82   #    we echo only what is after the '='.
     83   echo "${vpx_version##*=}"
     84 }
     85 
     86 # Echoes the short form of the current git hash.
     87 current_hash() {
     88   if git --version > /dev/null 2>&1; then
     89     (cd "$(dirname "${0}")"
     90     git rev-parse --short HEAD)
     91   else
     92     # Return the config hash if git is unavailable: Fail silently, git hashes
     93     # are used only for warnings.
     94     config_hash
     95   fi
     96 }
     97 
     98 # Echoes warnings to stdout when git hash in vpx_config.h does not match the
     99 # current git hash.
    100 check_git_hashes() {
    101   hash_at_configure_time=$(config_hash)
    102   hash_now=$(current_hash)
    103 
    104   if [ "${hash_at_configure_time}" != "${hash_now}" ]; then
    105     echo "Warning: git hash has changed since last configure."
    106   fi
    107 }
    108 
    109 # $1 is the name of an environment variable containing a directory name to
    110 # test.
    111 test_env_var_dir() {
    112   local dir=$(eval echo "\${$1}")
    113   if [ ! -d "${dir}" ]; then
    114     elog "'${dir}': No such directory"
    115     elog "The $1 environment variable must be set to a valid directory."
    116     return 1
    117   fi
    118 }
    119 
    120 # This script requires that the LIBVPX_BIN_PATH, LIBVPX_CONFIG_PATH, and
    121 # LIBVPX_TEST_DATA_PATH variables are in the environment: Confirm that
    122 # the variables are set and that they all evaluate to directory paths.
    123 verify_vpx_test_environment() {
    124   test_env_var_dir "LIBVPX_BIN_PATH" \
    125     && test_env_var_dir "LIBVPX_CONFIG_PATH" \
    126     && test_env_var_dir "LIBVPX_TEST_DATA_PATH"
    127 }
    128 
    129 # Greps vpx_config.h in LIBVPX_CONFIG_PATH for positional parameter one, which
    130 # should be a LIBVPX preprocessor flag. Echoes yes to stdout when the feature
    131 # is available.
    132 vpx_config_option_enabled() {
    133   vpx_config_option="${1}"
    134   vpx_config_file="${LIBVPX_CONFIG_PATH}/vpx_config.h"
    135   config_line=$(grep "${vpx_config_option}" "${vpx_config_file}")
    136   if echo "${config_line}" | egrep -q '1$'; then
    137     echo yes
    138   fi
    139 }
    140 
    141 # Echoes yes when output of test_configuration_target() contains win32 or win64.
    142 is_windows_target() {
    143   if test_configuration_target \
    144      | grep -q -e win32 -e win64 > /dev/null 2>&1; then
    145     echo yes
    146   fi
    147 }
    148 
    149 # Echoes path to $1 when it's executable and exists in ${LIBVPX_BIN_PATH}, or an
    150 # empty string. Caller is responsible for testing the string once the function
    151 # returns.
    152 vpx_tool_path() {
    153   local tool_name="$1"
    154   local tool_path="${LIBVPX_BIN_PATH}/${tool_name}${VPX_TEST_EXE_SUFFIX}"
    155   if [ ! -x "${tool_path}" ]; then
    156     # Try one directory up: when running via examples.sh the tool could be in
    157     # the parent directory of $LIBVPX_BIN_PATH.
    158     tool_path="${LIBVPX_BIN_PATH}/../${tool_name}${VPX_TEST_EXE_SUFFIX}"
    159   fi
    160 
    161   if [ ! -x "${tool_path}" ]; then
    162     tool_path=""
    163   fi
    164   echo "${tool_path}"
    165 }
    166 
    167 # Echoes yes to stdout when the file named by positional parameter one exists
    168 # in LIBVPX_BIN_PATH, and is executable.
    169 vpx_tool_available() {
    170   local tool_name="$1"
    171   local tool="${LIBVPX_BIN_PATH}/${tool_name}${VPX_TEST_EXE_SUFFIX}"
    172   [ -x "${tool}" ] && echo yes
    173 }
    174 
    175 # Echoes yes to stdout when vpx_config_option_enabled() reports yes for
    176 # CONFIG_VP8_DECODER.
    177 vp8_decode_available() {
    178   [ "$(vpx_config_option_enabled CONFIG_VP8_DECODER)" = "yes" ] && echo yes
    179 }
    180 
    181 # Echoes yes to stdout when vpx_config_option_enabled() reports yes for
    182 # CONFIG_VP8_ENCODER.
    183 vp8_encode_available() {
    184   [ "$(vpx_config_option_enabled CONFIG_VP8_ENCODER)" = "yes" ] && echo yes
    185 }
    186 
    187 # Echoes yes to stdout when vpx_config_option_enabled() reports yes for
    188 # CONFIG_VP9_DECODER.
    189 vp9_decode_available() {
    190   [ "$(vpx_config_option_enabled CONFIG_VP9_DECODER)" = "yes" ] && echo yes
    191 }
    192 
    193 # Echoes yes to stdout when vpx_config_option_enabled() reports yes for
    194 # CONFIG_VP9_ENCODER.
    195 vp9_encode_available() {
    196   [ "$(vpx_config_option_enabled CONFIG_VP9_ENCODER)" = "yes" ] && echo yes
    197 }
    198 
    199 # Echoes yes to stdout when vpx_config_option_enabled() reports yes for
    200 # CONFIG_WEBM_IO.
    201 webm_io_available() {
    202   [ "$(vpx_config_option_enabled CONFIG_WEBM_IO)" = "yes" ] && echo yes
    203 }
    204 
    205 # Filters strings from $1 using the filter specified by $2. Filter behavior
    206 # depends on the presence of $3. When $3 is present, strings that match the
    207 # filter are excluded. When $3 is omitted, strings matching the filter are
    208 # included.
    209 # The filtered result is echoed to stdout.
    210 filter_strings() {
    211   strings=${1}
    212   filter=${2}
    213   exclude=${3}
    214 
    215   if [ -n "${exclude}" ]; then
    216     # When positional parameter three exists the caller wants to remove strings.
    217     # Tell grep to invert matches using the -v argument.
    218     exclude='-v'
    219   else
    220     unset exclude
    221   fi
    222 
    223   if [ -n "${filter}" ]; then
    224     for s in ${strings}; do
    225       if echo "${s}" | egrep -q ${exclude} "${filter}" > /dev/null 2>&1; then
    226         filtered_strings="${filtered_strings} ${s}"
    227       fi
    228     done
    229   else
    230     filtered_strings="${strings}"
    231   fi
    232   echo "${filtered_strings}"
    233 }
    234 
    235 # Runs user test functions passed via positional parameters one and two.
    236 # Functions in positional parameter one are treated as environment verification
    237 # functions and are run unconditionally. Functions in positional parameter two
    238 # are run according to the rules specified in vpx_test_usage().
    239 run_tests() {
    240   local env_tests="verify_vpx_test_environment $1"
    241   local tests_to_filter="$2"
    242   local test_name="${VPX_TEST_NAME}"
    243 
    244   if [ -z "${test_name}" ]; then
    245     test_name="$(basename "${0%.*}")"
    246   fi
    247 
    248   if [ "${VPX_TEST_RUN_DISABLED_TESTS}" != "yes" ]; then
    249     # Filter out DISABLED tests.
    250     tests_to_filter=$(filter_strings "${tests_to_filter}" ^DISABLED exclude)
    251   fi
    252 
    253   if [ -n "${VPX_TEST_FILTER}" ]; then
    254     # Remove tests not matching the user's filter.
    255     tests_to_filter=$(filter_strings "${tests_to_filter}" ${VPX_TEST_FILTER})
    256   fi
    257 
    258   # User requested test listing: Dump test names and return.
    259   if [ "${VPX_TEST_LIST_TESTS}" = "yes" ]; then
    260     for test_name in $tests_to_filter; do
    261       echo ${test_name}
    262     done
    263     return
    264   fi
    265 
    266   # Don't bother with the environment tests if everything else was disabled.
    267   [ -z "${tests_to_filter}" ] && return
    268 
    269   # Combine environment and actual tests.
    270   local tests_to_run="${env_tests} ${tests_to_filter}"
    271 
    272   check_git_hashes
    273 
    274   # Run tests.
    275   for test in ${tests_to_run}; do
    276     test_begin "${test}"
    277     vlog "  RUN  ${test}"
    278     "${test}"
    279     vlog "  PASS ${test}"
    280     test_end "${test}"
    281   done
    282 
    283   local tested_config="$(test_configuration_target) @ $(current_hash)"
    284   echo "${test_name}: Done, all tests pass for ${tested_config}."
    285 }
    286 
    287 vpx_test_usage() {
    288 cat << EOF
    289   Usage: ${0##*/} [arguments]
    290     --bin-path <path to libvpx binaries directory>
    291     --config-path <path to libvpx config directory>
    292     --filter <filter>: User test filter. Only tests matching filter are run.
    293     --run-disabled-tests: Run disabled tests.
    294     --help: Display this message and exit.
    295     --test-data-path <path to libvpx test data directory>
    296     --show-program-output: Shows output from all programs being tested.
    297     --prefix: Allows for a user specified prefix to be inserted before all test
    298               programs. Grants the ability, for example, to run test programs
    299               within valgrind.
    300     --list-tests: List all test names and exit without actually running tests.
    301     --verbose: Verbose output.
    302 
    303     When the --bin-path option is not specified the script attempts to use
    304     \$LIBVPX_BIN_PATH and then the current directory.
    305 
    306     When the --config-path option is not specified the script attempts to use
    307     \$LIBVPX_CONFIG_PATH and then the current directory.
    308 
    309     When the -test-data-path option is not specified the script attempts to use
    310     \$LIBVPX_TEST_DATA_PATH and then the current directory.
    311 EOF
    312 }
    313 
    314 # Returns non-zero (failure) when required environment variables are empty
    315 # strings.
    316 vpx_test_check_environment() {
    317   if [ -z "${LIBVPX_BIN_PATH}" ] || \
    318      [ -z "${LIBVPX_CONFIG_PATH}" ] || \
    319      [ -z "${LIBVPX_TEST_DATA_PATH}" ]; then
    320     return 1
    321   fi
    322 }
    323 
    324 # Parse the command line.
    325 while [ -n "$1" ]; do
    326   case "$1" in
    327     --bin-path)
    328       LIBVPX_BIN_PATH="$2"
    329       shift
    330       ;;
    331     --config-path)
    332       LIBVPX_CONFIG_PATH="$2"
    333       shift
    334       ;;
    335     --filter)
    336       VPX_TEST_FILTER="$2"
    337       shift
    338       ;;
    339     --run-disabled-tests)
    340       VPX_TEST_RUN_DISABLED_TESTS=yes
    341       ;;
    342     --help)
    343       vpx_test_usage
    344       exit
    345       ;;
    346     --test-data-path)
    347       LIBVPX_TEST_DATA_PATH="$2"
    348       shift
    349       ;;
    350     --prefix)
    351       VPX_TEST_PREFIX="$2"
    352       shift
    353       ;;
    354     --verbose)
    355       VPX_TEST_VERBOSE_OUTPUT=yes
    356       ;;
    357     --show-program-output)
    358       devnull=
    359       ;;
    360     --list-tests)
    361       VPX_TEST_LIST_TESTS=yes
    362       ;;
    363     *)
    364       vpx_test_usage
    365       exit 1
    366       ;;
    367   esac
    368   shift
    369 done
    370 
    371 # Handle running the tests from a build directory without arguments when running
    372 # the tests on *nix/macosx.
    373 LIBVPX_BIN_PATH="${LIBVPX_BIN_PATH:-.}"
    374 LIBVPX_CONFIG_PATH="${LIBVPX_CONFIG_PATH:-.}"
    375 LIBVPX_TEST_DATA_PATH="${LIBVPX_TEST_DATA_PATH:-.}"
    376 
    377 # Create a temporary directory for output files, and a trap to clean it up.
    378 if [ -n "${TMPDIR}" ]; then
    379   VPX_TEST_TEMP_ROOT="${TMPDIR}"
    380 elif [ -n "${TEMPDIR}" ]; then
    381   VPX_TEST_TEMP_ROOT="${TEMPDIR}"
    382 else
    383   VPX_TEST_TEMP_ROOT=/tmp
    384 fi
    385 
    386 VPX_TEST_OUTPUT_DIR="${VPX_TEST_TEMP_ROOT}/vpx_test_$$"
    387 
    388 if ! mkdir -p "${VPX_TEST_OUTPUT_DIR}" || \
    389    [ ! -d "${VPX_TEST_OUTPUT_DIR}" ]; then
    390   echo "${0##*/}: Cannot create output directory, giving up."
    391   echo "${0##*/}:   VPX_TEST_OUTPUT_DIR=${VPX_TEST_OUTPUT_DIR}"
    392   exit 1
    393 fi
    394 
    395 if [ "$(is_windows_target)" = "yes" ]; then
    396   VPX_TEST_EXE_SUFFIX=".exe"
    397 fi
    398 
    399 # Variables shared by tests.
    400 VP8_IVF_FILE="${LIBVPX_TEST_DATA_PATH}/vp80-00-comprehensive-001.ivf"
    401 VP9_IVF_FILE="${LIBVPX_TEST_DATA_PATH}/vp90-2-09-subpixel-00.ivf"
    402 
    403 VP9_WEBM_FILE="${LIBVPX_TEST_DATA_PATH}/vp90-2-00-quantizer-00.webm"
    404 VP9_FPM_WEBM_FILE="${LIBVPX_TEST_DATA_PATH}/vp90-2-07-frame_parallel-1.webm"
    405 VP9_LT_50_FRAMES_WEBM_FILE="${LIBVPX_TEST_DATA_PATH}/vp90-2-02-size-32x08.webm"
    406 
    407 VP9_RAW_FILE="${LIBVPX_TEST_DATA_PATH}/crbug-1539.rawfile"
    408 
    409 YUV_RAW_INPUT="${LIBVPX_TEST_DATA_PATH}/hantro_collage_w352h288.yuv"
    410 YUV_RAW_INPUT_WIDTH=352
    411 YUV_RAW_INPUT_HEIGHT=288
    412 
    413 Y4M_NOSQ_PAR_INPUT="${LIBVPX_TEST_DATA_PATH}/park_joy_90p_8_420_a10-1.y4m"
    414 Y4M_720P_INPUT="${LIBVPX_TEST_DATA_PATH}/niklas_1280_720_30.y4m"
    415 
    416 # Setup a trap function to clean up after tests complete.
    417 trap cleanup EXIT
    418 
    419 vlog "$(basename "${0%.*}") test configuration:
    420   LIBVPX_BIN_PATH=${LIBVPX_BIN_PATH}
    421   LIBVPX_CONFIG_PATH=${LIBVPX_CONFIG_PATH}
    422   LIBVPX_TEST_DATA_PATH=${LIBVPX_TEST_DATA_PATH}
    423   VP8_IVF_FILE=${VP8_IVF_FILE}
    424   VP9_IVF_FILE=${VP9_IVF_FILE}
    425   VP9_WEBM_FILE=${VP9_WEBM_FILE}
    426   VPX_TEST_EXE_SUFFIX=${VPX_TEST_EXE_SUFFIX}
    427   VPX_TEST_FILTER=${VPX_TEST_FILTER}
    428   VPX_TEST_LIST_TESTS=${VPX_TEST_LIST_TESTS}
    429   VPX_TEST_OUTPUT_DIR=${VPX_TEST_OUTPUT_DIR}
    430   VPX_TEST_PREFIX=${VPX_TEST_PREFIX}
    431   VPX_TEST_RUN_DISABLED_TESTS=${VPX_TEST_RUN_DISABLED_TESTS}
    432   VPX_TEST_SHOW_PROGRAM_OUTPUT=${VPX_TEST_SHOW_PROGRAM_OUTPUT}
    433   VPX_TEST_TEMP_ROOT=${VPX_TEST_TEMP_ROOT}
    434   VPX_TEST_VERBOSE_OUTPUT=${VPX_TEST_VERBOSE_OUTPUT}
    435   YUV_RAW_INPUT=${YUV_RAW_INPUT}
    436   YUV_RAW_INPUT_WIDTH=${YUV_RAW_INPUT_WIDTH}
    437   YUV_RAW_INPUT_HEIGHT=${YUV_RAW_INPUT_HEIGHT}
    438   Y4M_NOSQ_PAR_INPUT=${Y4M_NOSQ_PAR_INPUT}"
    439 
    440 fi  # End $VPX_TEST_TOOLS_COMMON_SH pseudo include guard.
    441