diff --git a/.gitignore b/.gitignore index 8cc2c0c3fb..583fbd5fa3 100644 --- a/.gitignore +++ b/.gitignore @@ -1,185 +1,187 @@ # Common \#* .\#* GPATH GRTAGS GTAGS TAGS Makefile Makefile.in .deps .libs *.pc *.pyc *.bz2 *.tar.gz *.rpm *.la *.lo *.o *~ *.gcda *.gcno # Autobuild aclocal.m4 autoconf autoheader autom4te.cache/ automake build.counter compile config.guess config.log config.status config.sub configure depcomp install-sh include/stamp-* libtool libtool.m4 ltdl.m4 libltdl ltmain.sh missing py-compile /m4/argz.m4 /m4/ltargz.m4 /m4/ltoptions.m4 /m4/ltsugar.m4 /m4/ltversion.m4 /m4/lt~obsolete.m4 test-driver ylwrap # Configure targets Doxyfile cts/CTSlab.py cts/CTSvars.py cts/LSBDummy cts/OCFIPraTest.py cts/benchmark/clubench cts/cts-coverage cts/cts-lrmd cts/cts-pengine cts/cts-stonithd cts/fence_dummy cts/lxc_autogen.sh extra/logrotate/pacemaker include/config.h include/config.h.in include/crm_config.h lrmd/pacemaker_remote lrmd/pacemaker_remoted lrmd/pacemaker_remote.service mcp/pacemaker mcp/pacemaker.combined.upstart mcp/pacemaker.service mcp/pacemaker.upstart publican.cfg tools/cibsecret tools/crm_error tools/crm_mon.service tools/crm_mon.upstart tools/crm_report tools/report.common # Build targets *.7 *.7.xml *.7.html *.8 *.8.xml *.8.html attrd/attrd doc/*/en-US/images/*.png doc/*/tmp/** doc/*/publish cib/cib cib/cibmon cib/cibpipe crmd/atest crmd/crmd doc/api/* doc/Clusters_from_Scratch.txt doc/Pacemaker_Explained.txt doc/acls.html doc/crm_fencing.html doc/publican-catalog* fencing/stonith-test fencing/stonith_admin fencing/stonithd fencing/stonithd.xml lrmd/lrmd lrmd/lrmd_internal_ctl lrmd/lrmd_test mcp/pacemakerd pengine/pengine pengine/pengine.xml pengine/ptest scratch tools/attrd_updater tools/cibadmin tools/crm_attribute tools/crm_diff tools/crm_mon tools/crm_node tools/crm_resource tools/crm_shadow tools/crm_simulate tools/crm_verify tools/crmadmin tools/iso8601 tools/crm_ticket tools/report.collector.1 xml/crm.dtd xml/pacemaker*.rng xml/versions.rng doc/shared/en-US/*.xml doc/Clusters_from_Scratch.build doc/Clusters_from_Scratch/en-US/Ap-*.xml doc/Clusters_from_Scratch/en-US/Ch-*.xml doc/Pacemaker_Administration.build doc/Pacemaker_Administration/en-US/Ch-*.xml doc/Pacemaker_Development.build doc/Pacemaker_Development/en-US/Ch-*.xml doc/Pacemaker_Explained.build doc/Pacemaker_Explained/en-US/Ch-*.xml doc/Pacemaker_Explained/en-US/Ap-*.xml doc/Pacemaker_Remote.build doc/Pacemaker_Remote/en-US/Ch-*.xml lib/gnu/libgnu.a lib/gnu/stdalign.h *.coverity # Test detritus cts/.regression.failed.diff cts/pengine/shadow.* +/xml/test-2/*.up +/xml/test-2/*.up.err # Formerly built files (helps when jumping back and forth in checkout) /coverage.sh /fencing/regression.py /lrmd/regression.py /pengine/.regression.failed.diff /pengine/regression.core.sh /pengine/test10/shadow.* #Other mock HTML pacemaker*.spec coverity-* compat_reports .ABI-build abi_dumps logs *.patch *.diff *.sed *.orig *.rej *.swp diff --git a/xml/regression.core.sh b/xml/regression.core.sh deleted file mode 100755 index b8389bf75b..0000000000 --- a/xml/regression.core.sh +++ /dev/null @@ -1,104 +0,0 @@ -#!/bin/bash - - # Copyright (C) 2004 Andrew Beekhof - # - # 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 of the License, or (at your option) any later version. - # - # This software 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 - # - -verbose=$1 -io_dir=../pengine/test06 -diff_opts="--ignore-all-space -u -N" -failed=.regression.failed.diff -# zero out the error log -> $failed - -num_failed=0 -function do_test { - - base=$1; shift - name=$1; shift - input=$io_dir/${base}.xml - output=$io_dir/${base}.upgrade.xml - expected=$io_dir/${base}.expected.xml - - if [ ! -f $input ]; then - echo "Test $name ($base)... Error (PE : input)"; - num_failed=`expr $num_failed + 1` - return; - fi - - echo "Test $base : $name"; - if [ "$create_mode" != "true" -a ! -f $expected ]; then - echo " Error (PE : expected)"; - return; - fi - - xsltproc --novalid upgrade06.xsl $input > $output - if [ $? != 0 ]; then - echo " * Failed (xml : xsltproc)"; - num_failed=`expr $num_failed + 1` - fi - - if [ ! -s $output ]; then - echo " Error (xml : no conversion)"; - num_failed=`expr $num_failed + 1` - rm $output - return; - fi - - xmllint --relaxng pacemaker.rng $output > /dev/null 2>&1 - - if [ $? != 0 ]; then - echo " * Failed (xml : xmllint)"; - num_failed=`expr $num_failed + 1` - xmllint --relaxng pacemaker.rng $output > /dev/null - cat -n $output - fi - - # Now convert again, this time stripping the auto-id's so that the diffs are useful - xsltproc --novalid upgrade06.xsl $input | sed s/\\.id[0-9]*//g | sed s/nvpair.meta.auto-[0-9]*/nvpair/g > $output - if [ "$create_mode" = "true" ]; then - cp $output $expected - fi - - diff $diff_opts $expected $output >/dev/null - rc2=$? - if [ $rc2 != 0 ]; then - echo " * Failed"; - diff $diff_opts $expected $output 2>/dev/null >> $failed - echo "" >> $failed - num_failed=`expr $num_failed + 1` - else - rm $output - fi -} - -function test_results { - if [ $num_failed != 0 ]; then - if [ -s $failed ]; then - if [ "$verbose" = "-v" ]; then - echo "Results of $num_failed failed tests...." - less $failed - else - echo "Results of $num_failed failed tests are in $failed...." - echo "Use $0 -v to display them automatically." - fi - else - echo "$num_failed tests failed (no diff results)" - rm $failed - fi - fi -} - diff --git a/xml/regression.sh b/xml/regression.sh index cc435ef703..cf9c55992f 100755 --- a/xml/regression.sh +++ b/xml/regression.sh @@ -1,288 +1,303 @@ -#!/bin/bash - - # Copyright (C) 2004 Andrew Beekhof - # - # 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 of the License, or (at your option) any later version. - # - # This software 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 - # - -. regression.core.sh -create_mode="true" -echo Generating test outputs for these tests... -# do_test -echo Done. -echo "" - -echo Performing the following tests... -create_mode="false" - -echo "" -do_test simple1 "Offline " -do_test simple2 "Start " -do_test simple3 "Start 2 " -do_test simple4 "Start Failed" -do_test simple6 "Stop Start " -do_test simple7 "Shutdown " -#do_test simple8 "Stonith " -#do_test simple9 "Lower version" -#do_test simple10 "Higher version" -do_test simple11 "Priority (ne)" -do_test simple12 "Priority (eq)" -do_test simple8 "Stickiness" - -echo "" -do_test params-0 "Params: No change" -do_test params-1 "Params: Changed" -do_test params-2 "Params: Resource definition" -do_test params-4 "Params: Reload" -do_test novell-251689 "Resource definition change + target_role=stopped" - -echo "" -do_test orphan-0 "Orphan ignore" -do_test orphan-1 "Orphan stop" - -echo "" -do_test target-0 "Target Role : baseline" -do_test target-1 "Target Role : test" - -echo "" -do_test date-1 "Dates" -d "2005-020" -do_test date-2 "Date Spec - Pass" -d "2005-020T12:30" -do_test date-3 "Date Spec - Fail" -d "2005-020T11:30" -do_test probe-0 "Probe (anon clone)" -do_test probe-1 "Pending Probe" -do_test standby "Standby" -do_test comments "Comments" - -echo "" -do_test rsc_dep1 "Must not " -do_test rsc_dep3 "Must " -do_test rsc_dep5 "Must not 3 " -do_test rsc_dep7 "Must 3 " -do_test rsc_dep10 "Must (but cant)" -do_test rsc_dep2 "Must (running) " -do_test rsc_dep8 "Must (running : alt) " -do_test rsc_dep4 "Must (running + move)" -do_test asymmetric "Asymmetric - require explicit location constraints" - -echo "" -do_test order1 "Order start 1 " -do_test order2 "Order start 2 " -do_test order3 "Order stop " -do_test order4 "Order (multiple) " -do_test order5 "Order (move) " -do_test order6 "Order (move w/ restart) " -do_test order7 "Order (mandatory) " -do_test order-optional "Order (score=0) " -do_test order-required "Order (score=INFINITY) " - -echo "" -do_test coloc-loop "Colocation - loop" -do_test coloc-many-one "Colocation - many-to-one" -do_test coloc-list "Colocation - many-to-one with list" -do_test coloc-group "Colocation - groups" -do_test coloc-slave-anti "Anti-colocation with slave shouldn't prevent master colocation" - -#echo "" -#do_test agent1 "version: lt (empty)" -#do_test agent2 "version: eq " -#do_test agent3 "version: gt " - -echo "" -do_test attrs1 "string: eq (and) " -do_test attrs2 "string: lt / gt (and)" -do_test attrs3 "string: ne (or) " -do_test attrs4 "string: exists " -do_test attrs5 "string: not_exists " -do_test attrs6 "is_dc: true " -do_test attrs7 "is_dc: false " -do_test attrs8 "score_attribute " - -echo "" -do_test mon-rsc-1 "Schedule Monitor - start" -do_test mon-rsc-2 "Schedule Monitor - move " -do_test mon-rsc-3 "Schedule Monitor - pending start " -do_test mon-rsc-4 "Schedule Monitor - move/pending start" - -echo "" -do_test rec-rsc-0 "Resource Recover - no start " -do_test rec-rsc-1 "Resource Recover - start " -do_test rec-rsc-2 "Resource Recover - monitor " -do_test rec-rsc-3 "Resource Recover - stop - ignore" -do_test rec-rsc-4 "Resource Recover - stop - block " -do_test rec-rsc-5 "Resource Recover - stop - fence " -do_test rec-rsc-6 "Resource Recover - multiple - restart" -do_test rec-rsc-7 "Resource Recover - multiple - stop " -do_test rec-rsc-8 "Resource Recover - multiple - block " -do_test rec-rsc-9 "Resource Recover - group/group" - -echo "" -do_test quorum-1 "No quorum - ignore" -do_test quorum-2 "No quorum - freeze" -do_test quorum-3 "No quorum - stop " -do_test quorum-4 "No quorum - start anyway" -do_test quorum-5 "No quorum - start anyway (group)" -do_test quorum-6 "No quorum - start anyway (clone)" - -echo "" -do_test rec-node-1 "Node Recover - Startup - no fence" -do_test rec-node-2 "Node Recover - Startup - fence " -do_test rec-node-3 "Node Recover - HA down - no fence" -do_test rec-node-4 "Node Recover - HA down - fence " -do_test rec-node-5 "Node Recover - CRM down - no fence" -do_test rec-node-6 "Node Recover - CRM down - fence " -do_test rec-node-7 "Node Recover - no quorum - ignore " -do_test rec-node-8 "Node Recover - no quorum - freeze " -do_test rec-node-9 "Node Recover - no quorum - stop " -do_test rec-node-10 "Node Recover - no quorum - stop w/fence" -do_test rec-node-11 "Node Recover - CRM down w/ group - fence " -do_test rec-node-12 "Node Recover - nothing active - fence " -do_test rec-node-13 "Node Recover - failed resource + shutdown - fence " -do_test rec-node-15 "Node Recover - unknown lrm section" -do_test rec-node-14 "Serialize all stonith's" - -echo "" -do_test multi1 "Multiple Active (stop/start)" - -echo "" -do_test migrate-1 "Migrate (migrate)" -do_test migrate-2 "Migrate (stable)" -do_test migrate-3 "Migrate (failed migrate_to)" -do_test migrate-4 "Migrate (failed migrate_from)" -do_test novell-252693 "Migration in a stopping stack" -do_test novell-252693-2 "Migration in a starting stack" -do_test novell-252693-3 "Non-Migration in a starting and stopping stack" -do_test bug-1820 "Migration in a group" -do_test bug-1820-1 "Non-migration in a group" - -#echo "" -#do_test complex1 "Complex " - -echo "" -do_test group1 "Group " -do_test group2 "Group + Native " -do_test group3 "Group + Group " -do_test group4 "Group + Native (nothing)" -do_test group5 "Group + Native (move) " -do_test group6 "Group + Group (move) " -do_test group7 "Group colocation" -do_test group13 "Group colocation (cant run)" -do_test group8 "Group anti-colocation" -do_test group9 "Group recovery" -do_test group10 "Group partial recovery" -do_test group11 "Group target_role" -do_test group14 "Group stop (graph terminated)" -do_test group15 "-ve group colocation" -do_test bug-1573 "Partial stop of a group with two children" -do_test bug-1718 "Mandatory group ordering - Stop group_FUN" - -echo "" -do_test clone-anon-probe-1 "Probe the correct (anonymous) clone instance for each node" -do_test clone-anon-probe-2 "Avoid needless re-probing of anonymous clones" -do_test inc0 "Incarnation start" -do_test inc1 "Incarnation start order" -do_test inc2 "Incarnation silent restart, stop, move" -do_test inc3 "Inter-incarnation ordering, silent restart, stop, move" -do_test inc4 "Inter-incarnation ordering, silent restart, stop, move (ordered)" -do_test inc5 "Inter-incarnation ordering, silent restart, stop, move (restart 1)" -do_test inc6 "Inter-incarnation ordering, silent restart, stop, move (restart 2)" -do_test inc7 "Clone colocation" -do_test inc8 "Clone anti-colocation" -do_test inc9 "Non-unique clone" -do_test inc10 "Non-unique clone (stop)" -do_test inc11 "Primitive colocation with clones" -do_test inc12 "Clone shutdown" -do_test cloned-group "Make sure only the correct number of cloned groups are started" -do_test clone-no-shuffle "Don't prioritize allocation of instances that must be moved" - -echo "" -do_test master-0 "Stopped -> Slave" -do_test master-1 "Stopped -> Promote" -do_test master-2 "Stopped -> Promote : notify" -do_test master-3 "Stopped -> Promote : master location" -do_test master-4 "Started -> Promote : master location" -do_test master-5 "Promoted -> Promoted" -do_test master-6 "Promoted -> Promoted (2)" -do_test master-7 "Promoted -> Fenced" -do_test master-8 "Promoted -> Fenced -> Moved" -do_test master-9 "Stopped + Promotable + No quorum" -do_test master-10 "Stopped -> Promotable : notify with monitor" -do_test master-11 "Stopped -> Promote : colocation" -do_test novell-239082 "Demote/Promote ordering" -do_test novell-239087 "Stable master placement" -do_test master-12 "Promotion based solely on rsc_location constraints" -do_test master-13 "Include preferences of colocated resources when placing master" -do_test master-demote "Ordering when actions depends on demoting a slave resource" -do_test master-ordering "Prevent resources from starting that need a master" -do_test bug-1765 "Master-Master Colocation (dont stop the slaves)" -do_test master-group "Promotion of cloned groups" -do_test bug-lf-1852 "Don't shuffle master/slave instances unnecessarily" -do_test master-failed-demote "Don't retry failed demote actions" -do_test master-failed-demote-2 "Don't retry failed demote actions (notify=false)" -do_test master-depend "Ensure resources that depend on the master don't get allocated until the master does" - -echo "" -do_test managed-0 "Managed (reference)" -do_test managed-1 "Not managed - down " -do_test managed-2 "Not managed - up " - -echo "" -do_test interleave-0 "Interleave (reference)" -do_test interleave-1 "coloc - not interleaved" -do_test interleave-2 "coloc - interleaved " -do_test interleave-3 "coloc - interleaved (2)" -do_test interleave-pseudo-stop "Interleaved clone during stonith" -do_test interleave-stop "Interleaved clone during stop" -do_test interleave-restart "Interleaved clone during dependency restart" - -echo "" -do_test notify-0 "Notify reference" -do_test notify-1 "Notify simple" -do_test notify-2 "Notify simple, confirm" -do_test notify-3 "Notify move, confirm" -do_test novell-239079 "Notification priority" -#do_test notify-2 "Notify - 764" - -echo "" -do_test 594 "OSDL #594" -do_test 662 "OSDL #662" -do_test 696 "OSDL #696" -do_test 726 "OSDL #726" -do_test 735 "OSDL #735" -do_test 764 "OSDL #764" -do_test 797 "OSDL #797" -do_test 829 "OSDL #829" -do_test 994 "OSDL #994" -do_test 994-2 "OSDL #994 - with a dependent resource" -do_test 1360 "OSDL #1360 - Clone stickiness" -do_test 1484 "OSDL #1484 - on_fail=stop" -do_test 1494 "OSDL #1494 - Clone stability" -do_test unrunnable-1 "Unrunnable" -do_test stonith-0 "Stonith loop - 1" -do_test stonith-1 "Stonith loop - 2" -do_test stonith-2 "Stonith loop - 3" -do_test bug-1572-1 "Recovery of groups depending on master/slave" -do_test bug-1572-2 "Recovery of groups depending on master/slave when the master is never re-promoted" -do_test bug-1685 "Depends-on-master ordering" -do_test bug-1822 "Don't promote partially active groups" -do_test bug-pm-11 "New resource added to a m/s group" -do_test bug-pm-12 "Recover only the failed portion of a cloned group" -do_test bug-n-387749 "Don't shuffle clone instances" -do_test bug-n-385265 "Don't ignore the failure stickiness of group children - resource_idvscommon should stay stopped" -do_test bug-n-385265-2 "Ensure groups are migrated instead of remaining partially active on the current node" -do_test bug-lf-1920 "Correctly handle probes that find active resources" - -echo "" - -test_results +#!/bin/sh +# Copyright 2018 Red Hat, Inc. +# Author: Jan Pokorny +# Part of pacemaker project +# SPDX-License-Identifier: GPL-2.0-or-later + +set -eu +DIFF=${DIFF:-diff} +DIFFOPTS=${DIFFOPTS:--u} +DIFFPAGER=${DIFFPAGER:-less -LRX} +tests= + +# +# commons +# + +emit_result() { + _er_howmany=${1:?} # how many errors (0/anything else incl. strings) + _er_subject=${2:?} + _er_prefix=${3-} + + test -z "${_er_prefix}" || _er_prefix="${_er_prefix}: " + + if test "${_er_howmany}" = 0; then + printf "%s%s finished OK\n" "${_er_prefix}" "${_er_subject}" + else + printf "%s%s encountered ${_er_howmany} errors\n" \ + "${_er_prefix}" "${_er_subject}" + fi +} + +emit_error() { + _ee_msg=${1:?} + printf "%s\n" "${_ee_msg}" >&2 +} + +# returns 1 + floor of base 2 logaritm for _lo0r_i in 1...255, +# or 0 for _lo0r_i = 0 +log2_or_0_return() { + _lo0r_i=${1:?} + return $(((!(_lo0r_i >> 1) && _lo0r_i) * 1 \ + + (!(_lo0r_i >> 2) && _lo0r_i & (1 << 1)) * 2 \ + + (!(_lo0r_i >> 3) && _lo0r_i & (1 << 2)) * 3 \ + + (!(_lo0r_i >> 4) && _lo0r_i & (1 << 3)) * 4 \ + + (!(_lo0r_i >> 5) && _lo0r_i & (1 << 4)) * 5 \ + + (!(_lo0r_i >> 6) && _lo0r_i & (1 << 5)) * 6 \ + + (!(_lo0r_i >> 7) && _lo0r_i & (1 << 6)) * 7 \ + + !!(_lo0r_i >> 7) * 7 )) +} + +# rough addition of two base 2 logarithms +log2_or_0_add() { + _lo0a_op1=${1:?} + _lo0a_op2=${2:?} + + if test ${_lo0a_op1} -gt ${_lo0a_op2}; then + return ${_lo0a_op1} + elif test ${_lo0a_op2} -gt ${_lo0a_op1}; then + return ${_lo0a_op2} + elif test ${_lo0a_op1} -gt 0; then + return $((_lo0a_op1 + 1)) + else + return ${_lo0a_op1} + fi +} + +# +# test phases +# + +# stdin: input file per line +test_cleaner() { + while read _tc_origin; do + rm -f ${_tc_origin%.*}.up ${_tc_origin%.*}.up.err + done +} + +test_selfcheck() { + _tsc_template= + + while test $# -gt 0; do + case "$1" in + -o=*) _tsc_template="upgrade-${1#-o=}.xsl";; + esac + shift + done + + xmllint --noout --relaxng 'http://www.thaiopensource.com/relaxng/xslt.rng' \ + "${_tsc_template:?}" +} + +# stdout: filename of the transformed file +test_runner_upgrade() { + _tru_template=${1:?} + _tru_source=${2:?} # filename + _tru_mode=${3:?} # extra modes wrt. "referential" outcome, see below + + _tru_ref="${_tru_source%.*}.ref" + { test "${_tru_mode}" -ne 0 || test -f "${_tru_ref}.err"; } \ + && _tru_ref_err="${_tru_ref}.err" \ + || _tru_ref_err=/dev/null + _tru_target="${_tru_source%.*}.up" + _tru_target_err="${_tru_target}.err" + + xsltproc "${_tru_template}" "${_tru_source}" \ + > "${_tru_target}" 2> "${_tru_target_err}" \ + || { _tru_ref=$?; echo "${_tru_target_err}"; return ${_tru_ref}; } + + if test "${_tru_mode}" -ne 0; then + if test $((_tru_mode & (1 << 0))) -ne 0; then + cp -a "${_tru_target}" "${_tru_ref}" + cp -a "${_tru_target_err}" "${_tru_ref_err}" + fi + if test $((_tru_mode & (1 << 1))) -ne 0; then + "${DIFF}" ${DIFFOPTS} "${_tru_source}" "${_tru_ref}" \ + | ${DIFFPAGER} >&2 + if test $? -ne 0; then + printf "\npager failure\n" >&2 + return 1 + fi + printf '\nIs comparison OK? ' >&2 + read _tru_answer &2; return 1;; + esac + fi + elif test -f "${_tru_ref}" && test -f "${_tru_ref_err}"; then + "${DIFF}" ${DIFFOPTS} "${_tru_ref}" "${_tru_target}" >&2 \ + && "${DIFF}" ${DIFFOPTS} "${_tru_ref_err}" "${_tru_target_err}" >&2 + if test $? -ne 0; then + emit_error "Outputs differ from referential ones" + echo "/dev/null" + return 1 + fi + else + emit_error "Referential file(s) missing: ${_tru_ref}" + echo "/dev/null" + return 1 + fi + + echo "${_tru_target}" +} + +test_runner_validate() { + _trv_schema=${1:?} + _trv_target=${2:?} # filename + + if ! xmllint --noout --relaxng "${_trv_schema}" "${_trv_target}" \ + 2>/dev/null; then + xmllint --noout --relaxng "${_trv_schema}" "${_trv_target}" + fi +} + +# -g ... request generating "referential" outcomes +# -o= ... which conventional version to deem as the transform origin +# -t= ... which conventional version to deem as the transform target +# -D +# -G ... see usage +# stdin: input file per line +test_runner() { + _tr_mode=0 + _tr_ret=0 + _tr_schema_o= + _tr_schema_t= + _tr_target= + _tr_template= + + while test $# -gt 0; do + case "$1" in + -o=*) _tr_template="upgrade-${1#-o=}.xsl" + _tr_schema_o="pacemaker-${1#-o=}.rng";; + -t=*) _tr_schema_t="pacemaker-${1#-t=}.rng";; + -G) _tr_mode=$((_tr_mode | (1 << 0)));; + -D) _tr_mode=$((_tr_mode | (1 << 1)));; + esac + shift + done + + if ! test -f "${_tr_schema_o:?}" || ! test -f "${_tr_schema_t:?}"; then + emit_error "Origin and/or target schema missing, rerun make" + return 1 + fi + + while read _tr_origin; do + printf '%-60s' "${_tr_origin}... " + + # pre-validate + if ! test_runner_validate "${_tr_schema_o}" "${_tr_origin}"; then + _tr_ret=$((_tr_ret + 1)); echo "E:pre-validate"; continue + fi + + # upgrade + if ! _tr_target=$(test_runner_upgrade "${_tr_template}" \ + "${_tr_origin}" "${_tr_mode}"); then + _tr_ret=$((_tr_ret + 1)); + test -n "${_tr_target}" || break + echo "E:upgrade" + test -s "${_tr_target}" \ + && { echo ---; cat "${_tr_target}" || :; echo ---; } + continue + fi + + # post-validate + if ! test_runner_validate "${_tr_schema_t}" "${_tr_target}"; then + _tr_ret=$((_tr_ret + 1)); echo "E:post-validate"; continue + fi + + echo "OK" + done + + log2_or_0_return ${_tr_ret} +} + +# +# particular test variations +# + +test_2to3() { + find test-2 -name '*.xml' -print | env LC_ALL=C sort \ + | { case " $* " in + *\ -C\ *) test_cleaner;; + *\ -S\ *) test_selfcheck -o=2.10;; + *) test_runner -o=2.10 -t=3.0 "$@" || return $?;; + esac; } +} +tests="${tests} test_2to3" + +# +# "framework" +# + +# option-likes ... options to be passed down +# argument-likes ... drives a test selection +test_suite() { + _ts_pass= + _ts_global_ret=0 + _ts_ret=0 + _ts_select=@ + + while test $# -gt 0; do + case "$1" in + -*) _ts_pass="${_ts_pass} $1";; + *) _ts_select="${_ts_select}@$1";; + esac + shift + done + _ts_select="${_ts_select}@" + + for _ts_test in ${tests}; do + if test "${_ts_select}" != @@; then + case "${_ts_test}" in + *@${_ts_select}@*) ;; # jump through + *) break;; + esac + fi + "${_ts_test}" ${_ts_pass} || _ts_ret=$? + test ${_ts_ret} = 0 \ + && emit_result ${_ts_ret} "${_ts_test}" \ + || emit_result "at least 2^$((_ts_ret - 1))" "${_ts_test}" + log2_or_0_add ${_ts_global_ret} ${_ts_ret} + _ts_global_ret=$? + done + + return ${_ts_global_ret} +} + +# NOTE: big letters are dedicated for per-test-set behaviour, +# small ones for generic/global behaviour +usage() { + printf '%s\n %s\n %s\n %s\n %s\n' \ + "usage: $0 [-{C,G,S}]* [{${tests## }}*]" \ + "- use '-C' to only cleanup ephemeral byproducts" \ + "- use '-D' to review originals vs. \"referential\" outcomes" \ + "- use '-G' to generate \"referential\" outcomes" \ + "- use '-S' for template self-check (requires net access)" +} + +main() { + _main_pass= + _main_bailout=0 + _main_ret=0 + + while test $# -gt 0; do + case "$1" in + -h) usage; exit;; + -C) _main_pass="${_main_pass} $1"; _main_bailout=1;; + -S) _main_pass="${_main_pass} $1"; _main_bailout=1;; + *) _main_pass="${_main_pass} $1";; + esac + shift + done + + test_suite ${_main_pass} || _main_ret=$? + test ${_main_bailout} -eq 1 && return ${_main_ret} \ + || test_suite -C ${_main_pass} >/dev/null + test ${_main_ret} = 0 && emit_result ${_main_ret} "Overall suite" \ + || emit_result "at least 2^$((_main_ret - 1))" "Overall suite" + + return ${_main_ret} +} + +main "$@"