Whamcloud - gitweb
EX-6170 tests: make sanity-lipe-scan3.sh support remote MDS
authorJian Yu <yujian@whamcloud.com>
Thu, 5 Jan 2023 07:51:38 +0000 (23:51 -0800)
committerAndreas Dilger <adilger@whamcloud.com>
Thu, 12 Jan 2023 01:07:46 +0000 (01:07 +0000)
The sanity-lipe-scan3.sh script was written to only run on a local
client+MDS configuration. This patch fixes it to support running
the lipe_scan3 command on remote MDS.

Test-Parameters: trivial testlist=sanity-lipe-scan3
Test-Parameters: trivial mdscount=2 mdtcount=4 \
testlist=sanity-lipe-scan3

Signed-off-by: Jian Yu <yujian@whamcloud.com>
Change-Id: I0ede3420c6f529cdfb9e97a5664945a5c2f0ff09
Reviewed-on: https://review.whamcloud.com/c/ex/lustre-release/+/49559
Tested-by: jenkins <devops@whamcloud.com>
Tested-by: Maloo <maloo@whamcloud.com>
Reviewed-by: Andreas Dilger <adilger@whamcloud.com>
lustre/tests/sanity-lipe-scan3.sh

index 8ac5764..5bc83f1 100644 (file)
@@ -1,9 +1,10 @@
 #!/bin/bash
 #
-# Tests for lipe_find and lipe_scan.
+# Tests for lipe_scan3.
 #
-# lipe_find - search for files on Lustre devices or directories
-# lipe_scan - fast scan tool based on LiPE (Lustre integrated Policy Engine)
+# lipe_scan3 is a Lustre device scanner which provides
+# the scanning core to the user facing lipe_find3 utility
+# and to the Unified Policy Engine.
 
 ONLY=${ONLY:-"$*"}
 
@@ -12,14 +13,13 @@ LUSTRE=${LUSTRE:-$(dirname $0)/..}
 init_test_env $@
 . ${CONFIG:=$LUSTRE/tests/cfg/$NAME.sh}
 init_logging
-FAIL_ON_ERROR=false
-
-declare -r ROOT_FID="[0x200000007:0x1:0x0]"
 
-# bug number for skipped test:           DCO-8906
-ALWAYS_EXCEPT="$SANITY_LIPE_SCAN3_EXCEPT 130"
+# bug number for skipped test:
+ALWAYS_EXCEPT="$SANITY_LIPE_SCAN3_EXCEPT"
 # UPDATE THE COMMENT ABOVE WITH BUG NUMBERS WHEN CHANGING ALWAYS_EXCEPT!
 
+check_versions || skip_env "no need to test lipe_scan3 under interop mode"
+
 (( OSTCOUNT >= 2 )) || skip_env "need at least 2 OSTs"
 
 [[ $(facet_fstype mds1) = ldiskfs ]] || skip_env "need ldiskfs on MDS"
@@ -28,30 +28,26 @@ ALWAYS_EXCEPT="$SANITY_LIPE_SCAN3_EXCEPT 130"
 ! remote_ost_nodsh || skip_env "remote OSS with nodsh"
 
 # check if lipe_scan3 is installed on MDS(s)
-for t in lipe_scan3; do
-       do_nodes $(comma_list $(all_mdts_nodes)) "which $t" &>/dev/null ||
-       skip_env "$t is not installed on MDS"
-done
+do_nodes $(comma_list $(all_mdts_nodes)) "which lipe_scan3" &>/dev/null ||
+       skip_env "lipe_scan3 is not installed on MDS"
 
 which jq || skip_env "jq is not installed"
 which yq || skip_env "yq is not installed"
 jq --version
 yq --version
 
+SAVED_FAIL_ON_ERROR=$FAIL_ON_ERROR
+FAIL_ON_ERROR=false
+
+declare -r ROOT_FID="[0x200000007:0x1:0x0]"
+
 build_test_filter
 check_and_setup_lustre
 
-# mount Lustre clients on MDS node(s)
-mount_client_on_mds() {
-       local mds_nodes
-
-       mds_nodes=$(exclude_items_from_list $(comma_list $(all_mdts_nodes)) \
-               $HOSTNAME)
-       if [[ -n $mds_nodes ]]; then
-               zconf_mount_clients $mds_nodes $MOUNT ||
-               error "failed to mount client on MDS node $mds_nodes"
-               stack_trap "zconf_umount_clients $mds_nodes $MOUNT"
-       fi
+# choose a random MDS and return its facet
+lipe_get_random_mds() {
+       (( MDSCOUNT != 1 )) || { echo -n mds1; return; }
+       echo -n $(get_random_entry $(get_facets MDS))
 }
 
 # if the test suite was run on an MDS, then return the MDS facet
@@ -68,24 +64,47 @@ lipe_get_local_mds() {
        done
 }
 
+function mount_client_on_facet() {
+       local facet="$1"
+       local nodes=$(facets_nodes "$facet")
+       local node
+
+       for node in $nodes; do
+               if local_node $node; then
+                       continue
+               fi
+
+               zconf_mount_clients $node $MOUNT ||
+                       error "cannot mount client on '$node' for '$facet'"
+
+               stack_trap "zconf_umount_clients $node $MOUNT"
+       done
+}
+
 function lipe_scan3_body() {
-       local device="$1"
+       local facet="$1"
+       local device="$(facet_device "$facet")"
        local body="$2"
        shift 2
 
-       sync
-       printf '(lipe-scan "%q" (lipe-getopt-client-mount-path) (lambda () %s) (lipe-getopt-required-attrs) (lipe-getopt-thread-count))' "${device}" "${body}" |
-       lipe_scan3 --script=/dev/stdin "$@"
+       VERBOSE=false do_facet $facet "sync; \
+               printf '(lipe-scan \\\"%q\\\" (lipe-getopt-client-mount-path) \
+               (lambda () %s) (lipe-getopt-required-attrs) \
+               (lipe-getopt-thread-count))' $device '$body' |
+               lipe_scan3 --script=/dev/stdin $@"
 }
 
 function lipe_scan3_format() {
-       local device="$1"
+       local facet="$1"
+       local device="$(facet_device "$facet")"
        local expr="$2"
        shift 2
 
-       sync
-       printf '(lipe-scan "%q" (lipe-getopt-client-mount-path) (lambda () (format #t "~a\n" %s)) (lipe-getopt-required-attrs) (lipe-getopt-thread-count))' "${device}" "${expr}" |
-       lipe_scan3 --script=/dev/stdin "$@"
+       VERBOSE=false do_facet $facet "sync; \
+               printf '(lipe-scan \\\"%q\\\" (lipe-getopt-client-mount-path) \
+               (lambda () (format #t \\\"~a\n\\\" %s)) \
+               (lipe-getopt-required-attrs) (lipe-getopt-thread-count))' \
+               $device '$expr' | lipe_scan3 --script=/dev/stdin $@"
 }
 
 function init_lipe_scan3_env() {
@@ -94,10 +113,14 @@ function init_lipe_scan3_env() {
        local file
        local index
 
-       [[ "$fid" == "$ROOT_FID" ]] || error "'$MOUNT' is not a lustre client mount"
+       [[ "$fid" == "$ROOT_FID" ]] ||
+               error "'$MOUNT' is not a lustre client mount"
 
        find "$MOUNT" -mindepth 1 -delete || error "cannot clean '$MOUNT'"
-       find "$MOUNT" -mindepth 1 | grep . && error "find -delete did not delete all files from '$MOUNT'"
+       find "$MOUNT" -mindepth 1 | grep . &&
+               error "find -delete did not delete all files from '$MOUNT'"
+
+       mount_client_on_facet mds1
        for file in "$@"; do
                mcreate $file || error "cannot create $file"
                index=$($LFS getstripe --mdt-index $file)
@@ -108,6 +131,23 @@ function init_lipe_scan3_env() {
        sync
 }
 
+function lipe_scan3_on() {
+       local facet="$1"
+       shift 1
+
+       sync
+       do_facet_vp "$facet" sync
+       do_facet_vp "$facet" lipe_scan3 "$@"
+}
+
+function lipe_scan3_facet() {
+       local facet="$1"
+       local device="$(facet_device "$facet")"
+       shift 1
+
+       lipe_scan3_on "$facet" "$device" "$@"
+}
+
 function expect_stdout() {
        "$@" | grep --quiet . || error "command '$*' should write to stdout"
 }
@@ -118,11 +158,13 @@ function expect_no_stdout() {
 }
 
 function expect_stderr() {
-       "$@" 2>&1 > /dev/null | grep --quiet . || error "command '$*' should write to stderr"
+       "$@" 2>&1 > /dev/null | grep --quiet . ||
+               error "command '$*' should write to stderr"
 }
 
 function expect_no_stderr() {
-       "$@" 2>&1 > /dev/null | grep . && error "command '$*' should not write to stderr"
+       "$@" 2>&1 > /dev/null | grep . &&
+               error "command '$*' should not write to stderr"
        true
 }
 
@@ -154,27 +196,33 @@ function expect_error() {
 }
 
 function expect_expr() {
-       local device="$1"
+       local facet="$1"
        local expr="$2"
        local a0="$3"
        local a1
        shift 3
 
-       a1=$(lipe_scan3_format "$device" "$expr" "$@")
+       a1=$(lipe_scan3_format "$facet" "$expr" "$@")
        [[ "$a0" == "$a1" ]] || error "$expr expect '$a0', got '$a1'"
 }
 
 function expect_attr() {
-       local device="$1"
+       local facet="$1"
        local proc="$2"
        local a0="$3"
        local a1
        shift 3
 
-       a1=$(lipe_scan3_format "$device" "($proc)" "$@")
+       a1=$(lipe_scan3_format "$facet" "($proc)" "$@")
        [[ "$a0" == "$a1" ]] || error "$proc expect '$a0', got '$a1'"
 }
 
+LIPE_MDS_FACET=""
+(( MDSCOUNT == 1 )) && LIPE_MDS_FACET=mds1 ||
+       LIPE_MDS_FACET=$(lipe_get_local_mds)
+[[ -n $LIPE_MDS_FACET ]] ||
+       echo "No local MDS. Each test will be run on a random MDS."
+
 test_0() {
        expect_success true
        expect_failure false
@@ -189,89 +237,104 @@ test_0() {
 run_test 0 "expect functions meet our expectations"
 
 test_10() {
-       expect_print lipe_scan3 -h
-       expect_print lipe_scan3 --help
+       local facet=${LIPE_MDS_FACET:-$(lipe_get_random_mds)}
 
-       expect_print lipe_scan3 -v
-       expect_print lipe_scan3 --version
+       expect_print lipe_scan3_on $facet -h
+       expect_print lipe_scan3_on $facet --help
 
-       expect_error lipe_scan3
-       expect_error lipe_scan3 --barf
+       expect_print lipe_scan3_on $facet -v
+       expect_print lipe_scan3_on $facet --version
 
-       expect_print lipe_scan3 --interactive < /dev/null
-       expect_print lipe_scan3 -i < /dev/null
+       expect_error lipe_scan3_on $facet
+       expect_error lipe_scan3_on $facet --barf
 
-       expect_print lipe_scan3 --list-attrs
-       expect_print lipe_scan3 --list-json-attrs
+       # expect_print lipe_scan3_on $facet "--interactive < /dev/null"
+       # expect_print lipe_scan3_on $facet -i < /dev/null
 
-       expect_error lipe_scan3 -s /dev/null --thread-count=zzz
-       expect_error lipe_scan3 -s /dev/null --thread-count=42q
-       expect_error lipe_scan3 -s /dev/null --thread-count=''
+       expect_print lipe_scan3_on $facet --list-attrs
+       expect_print lipe_scan3_on $facet --list-json-attrs
+
+       expect_error lipe_scan3_on $facet -s /dev/null --thread-count=zzz
+       expect_error lipe_scan3_on $facet -s /dev/null --thread-count=42q
+       expect_error lipe_scan3_on $facet -s /dev/null --thread-count=''
 }
 run_test 10 "lipe_scan3 option handling"
 
 test_11() {
-       expect_error lipe_scan3 --print-self-fid /dev/null
-       expect_error lipe_scan3 --print-self-fid /dev/zero
-       expect_error lipe_scan3 --print-self-fid /dev/zapper/mds1_flakey
-       expect_error lipe_scan3 --print-self-fid /dev/
-       expect_error lipe_scan3 --print-self-fid ''
-       expect_error lipe_scan3 --print-self-fid
+       local facet=${LIPE_MDS_FACET:-$(lipe_get_random_mds)}
+
+       expect_error lipe_scan3_on $facet --print-self-fid /dev/null
+       expect_error lipe_scan3_on $facet --print-self-fid /dev/zero
+       expect_error lipe_scan3_on $facet --print-self-fid /dev/
+       expect_error lipe_scan3_on $facet --print-self-fid ''
+       expect_error lipe_scan3_on $facet --print-self-fid
+       expect_error lipe_scan3_on $facet --print-self-fid \
+               /dev/zapper/mds1_flakey
 }
 run_test 11 "lipe_scan3 bad device handling"
 
 test_12() {
        local facet=mds1
-       local device="$(facet_device $facet)"
+       local device="$(facet_device "$facet")"
        local file=$MOUNT/$tfile
        local tmp=$(mktemp -d)
        local fid
+       local cmd
+       local expect_error_cmd="expect_error lipe_scan3_facet $facet"
+       local expect_stderr_cmd="expect_stderr lipe_scan3_facet $facet"
 
        init_lipe_scan3_env "$file"
        fid=$($LFS path2fid "$file")
        touch $tmp/$tfile
 
-       expect_error lipe_scan3  "$device" --print-absolute-path --client-mount=''
-       expect_error lipe_scan3  "$device" --print-absolute-path --client-mount=/dev/null
-       expect_error lipe_scan3  "$device" --print-absolute-path --client-mount=$tmp
-       expect_error lipe_scan3  "$device" --print-absolute-path --client-mount=$tmp/noent
-       expect_error lipe_scan3  "$device" --print-absolute-path --client-mount=$tmp/$tfile
+       $expect_error_cmd --print-absolute-path --client-mount=''
+       $expect_error_cmd --print-absolute-path --client-mount=/dev/null
+       $expect_error_cmd --print-absolute-path --client-mount=$tmp
+       $expect_error_cmd --print-absolute-path --client-mount=$tmp/noent
+       $expect_error_cmd --print-absolute-path --client-mount=$tmp/$tfile
 
        # We print a warning for non canonicalized client mounts.
-       expect_stderr lipe_scan3  "$device" --print-absolute-path --client-mount=$MOUNT/
-       expect_stderr lipe_scan3  "$device" --print-absolute-path --client-mount=$MOUNT//
-       expect_stderr lipe_scan3  "$device" --print-absolute-path --client-mount=$MOUNT/.
-       expect_stderr lipe_scan3  "$device" --print-absolute-path --client-mount=$MOUNT/./.
-       (cd $MOUNT && expect_stderr lipe_scan3  "$device" --print-absolute-path --client-mount=.)
+       $expect_stderr_cmd --print-absolute-path --client-mount=$MOUNT/
+       $expect_stderr_cmd --print-absolute-path --client-mount=$MOUNT//
+       $expect_stderr_cmd --print-absolute-path --client-mount=$MOUNT/.
+       $expect_stderr_cmd --print-absolute-path --client-mount=$MOUNT/./.
+
+       cmd="lipe_scan3 $device --print-absolute-path --client-mount=."
+       do_facet_vp "$facet" "cd $MOUNT; $cmd" 2>&1 > /dev/null |
+               grep --quiet . || error "command '$cmd' should write to stderr"
 
-       expect_attr "$device" self-fid "$fid" --client-mount=$MOUNT/
-       expect_attr "$device" self-fid "$fid" --no-client-mount
-       expect_attr "$device" absolute-paths "($file)" --client-mount=$MOUNT/
+       expect_attr "$facet" self-fid "$fid" --client-mount=$MOUNT/
+       expect_attr "$facet" self-fid "$fid" --no-client-mount
+       expect_attr "$facet" absolute-paths "($file)" --client-mount=$MOUNT/
 
        # FIXME
-       # expect_error lipe_scan3  "$device" --print-absolute-path --no-client-mount
-       # expect_error lipe_scan3  "$device" --print-relative-path --no-client-mount
+       # $expect_error_cmd --print-absolute-path --no-client-mount
+       # $expect_error_cmd --print-relative-path --no-client-mount
 
        umount_client $MOUNT
-       expect_attr "$device" self-fid "$fid"
-       mount_client $MOUNT
+       stack_trap "mount_client $MOUNT"
+       expect_attr "$facet" self-fid "$fid"
 }
 run_test 12 "--client-mount is handled correctly"
 
 test_13() {
-       expect_success lipe_scan3 -s /dev/null --required-attrs=#x0
-       expect_success lipe_scan3 -s /dev/null --required-attrs=all
-       expect_success lipe_scan3 -s /dev/null --required-attrs=ino
-       expect_success lipe_scan3 -s /dev/null --required-attrs=mode
-
-       lipe_scan3 --list-attrs | while read attr; do
-               expect_success lipe_scan3 -s /dev/null --required-attrs=$attr
-               expect_success lipe_scan3 -s /dev/null --required-attrs=ino,$attr
+       local facet=${LIPE_MDS_FACET:-$(lipe_get_random_mds)}
+       local expect_success_cmd="expect_success lipe_scan3_facet $facet"
+       local expect_error_cmd="expect_error lipe_scan3_facet $facet"
+
+       $expect_success_cmd -s /dev/null --required-attrs=#x0
+       $expect_success_cmd -s /dev/null --required-attrs=all
+       $expect_success_cmd -s /dev/null --required-attrs=ino
+       $expect_success_cmd -s /dev/null --required-attrs=mode
+
+       do_facet $facet "lipe_scan3 --list-attrs" | while read attr; do
+               $expect_success_cmd -s /dev/null --required-attrs=$attr
+               $expect_success_cmd -s /dev/null --required-attrs=ino,$attr
        done
 
-       expect_error lipe_scan3 -s /dev/null --required-attrs=barf
-       expect_error lipe_scan3 -s /dev/null --required-attrs=ino,barf
-       expect_error lipe_scan3 -s /dev/null --required-attrs=barf,ino
+       $expect_error_cmd -s /dev/null --required-attrs=barf
+       $expect_error_cmd -s /dev/null --required-attrs=ino,barf
+       $expect_error_cmd -s /dev/null --required-attrs=barf,ino
 }
 run_test 13 "--required-attrs is handled correctly"
 
@@ -280,7 +343,7 @@ run_test 13 "--required-attrs is handled correctly"
 
 test_90() {
        local facet=mds1
-       local device="$(facet_device $facet)"
+       local expect_empty_cmd="expect_empty lipe_scan3_facet $facet"
 
        init_lipe_scan3_env
 
@@ -296,33 +359,34 @@ test_90() {
        # Now delete those files.
        init_lipe_scan3_env
 
-       expect_empty lipe_scan3 "$device" --print-file-fid
-       expect_empty lipe_scan3 "$device" --print-self-fid
-       expect_empty lipe_scan3 "$device" --print-json
-       expect_empty lipe_scan3 "$device" --print-absolute-path
-       expect_empty lipe_scan3 "$device" --print-relative-path
-       expect_empty lipe_scan3_format "$device" '(ino)'
+       $expect_empty_cmd --print-file-fid
+       $expect_empty_cmd --print-self-fid
+       $expect_empty_cmd --print-json
+       $expect_empty_cmd --print-absolute-path
+       $expect_empty_cmd --print-relative-path
+       expect_empty lipe_scan3_format $facet '(ino)'
 }
 run_test 90 "lipe_scan3 on an empty FS"
 
 test_100() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local proc
 
        init_lipe_scan3_env "$file"
 
-       lipe_scan3 "$device" --print-self-fid
-       lipe_scan3_format "$device" '(self-fid)'
-       lipe_scan3_format "$device" '(ino)'
+       lipe_scan3_facet $facet --print-self-fid
+       lipe_scan3_format $facet '(self-fid)'
+       lipe_scan3_format $facet '(ino)'
 
-       for proc in ino atime blocks crtime ctime self-fid file-fid flags gid mode mtime nlink projid size uid; do
-               expect_print lipe_scan3_format "$device" "($proc)"
+       for proc in ino atime blocks crtime ctime self-fid file-fid flags gid \
+               mode mtime nlink projid size uid; do
+               expect_print lipe_scan3_format $facet "($proc)"
        done
 
-       for proc in absolute-paths relative-paths links lov-mirror-count lov-ost-indexes lov-pools lov-stripe-count xattrs; do
-               expect_print lipe_scan3_format "$device" "($proc)"
+       for proc in absolute-paths relative-paths links lov-mirror-count \
+               lov-ost-indexes lov-pools lov-stripe-count xattrs; do
+               expect_print lipe_scan3_format $facet "($proc)"
        done
 }
 run_test 100 "lipe_scan3 attrs and scan functions do something"
@@ -332,18 +396,18 @@ declare -a MODES=(0 1 0111 0222 0444 0555 0666 0777)
 
 test_101() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local mode
 
        init_lipe_scan3_env "$file"
 
        mode=0$(stat --format=%a $file) # octal access rights
-       expect_attr "$device" mode $((S_IFREG | mode)) # $((...)) converts to decimal
+       # $((...)) converts to decimal
+       expect_attr "$facet" mode $((S_IFREG | mode))
 
        for mode in "${MODES[@]}"; do
                chmod "$mode" $file || error "cannot set mode to '$mode'"
-               expect_attr "$device" mode $((S_IFREG | mode))
+               expect_attr $facet mode $((S_IFREG | mode))
        done
 
        # dir ...
@@ -366,26 +430,25 @@ declare -a IDS=(
 
 test_102() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local id
 
        init_lipe_scan3_env "$file"
 
        id=$(stat --format=%u $file) # uid
-       expect_attr "$device" uid "$id"
+       expect_attr "$facet" uid "$id"
 
        for id in "${IDS[@]}"; do
                chown $id $file || error "cannot set UID to '$id'"
-               expect_attr "$device" uid "$id"
+               expect_attr "$facet" uid "$id"
        done
 
        id=$(stat --format=%g $file) # gid
-       expect_attr "$device" gid "$id"
+       expect_attr "$facet" gid "$id"
 
        for id in "${IDS[@]}"; do
                chown :$id $file || error "cannot set GID to '$id'"
-               expect_attr "$device" gid "$id"
+               expect_attr "$facet" gid "$id"
        done
 }
 run_test 102 "lipe_scan3 uid/gid do the right thing"
@@ -413,32 +476,33 @@ declare -a TIMES=(
 
 test_103() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local time
 
        init_lipe_scan3_env "$file"
 
-       expect_expr "$device" '(positive? (crtime))' '#t'
+       expect_expr "$facet" '(positive? (crtime))' '#t'
 
        time=$(stat --format=%X $file) # atime
-       expect_attr "$device" atime "$time"
+       expect_attr "$facet" atime "$time"
 
        for time in "${TIMES[@]}"; do
-               touch --date=@$time -a $file || error "cannot set atime to '$time'"
-               expect_attr "$device" atime "$time"
+               touch --date=@$time -a $file ||
+                       error "cannot set atime to '$time'"
+               expect_attr "$facet" atime "$time"
        done
 
        time=$(stat --format=%Y $file) # mtime
-       expect_attr "$device" mtime "$time"
+       expect_attr "$facet" mtime "$time"
 
        for time in "${TIMES[@]}"; do
-               touch --date=@$time -m $file || error "cannot set mtime to '$time'"
-               expect_attr "$device" mtime "$time"
+               touch --date=@$time -m $file ||
+                       error "cannot set mtime to '$time'"
+               expect_attr "$facet" mtime "$time"
        done
 
        time=$(stat --format=%Z $file) # ctime
-       expect_attr "$device" ctime "$time"
+       expect_attr "$facet" ctime "$time"
 
        # We could use LL_IOC_FUTIMES_3 here.
 }
@@ -463,7 +527,6 @@ declare -a SIZES=(
 
 test_104() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local size
        local som_size
@@ -474,15 +537,15 @@ test_104() {
 
        init_lipe_scan3_env "$file"
 
-       expect_attr "$device" size 0
+       expect_attr "$facet" size 0
 
        # For a file without striping, the MDT inode has the szie.
        for size in "${SIZES[@]}"; do
                $TRUNCATE $file "$size"
-               expect_attr "$device" size "$size"
+               expect_attr "$facet" size "$size"
        done
 
-       expect_attr "$device" blocks 0
+       expect_attr "$facet" blocks 0
 
        params=$($LCTL get_param 'llite.*.xattr_cache')
        $LCTL set_param 'llite.*.xattr_cache=0'
@@ -499,44 +562,43 @@ test_104() {
        som_blocks=$($LFS getsom -b "$file")
        som_flags=$($LFS getsom -f "$file")
        ((som_flags == 4)) || error "expected som flags 4, got '$som_flags'"
-       expect_attr "$device" size "$som_size"
-       expect_attr "$device" blocks "$som_blocks"
+       expect_attr "$facet" size "$som_size"
+       expect_attr "$facet" blocks "$som_blocks"
        rm "$file"
 
        $LFS mkdir -i0 -c1 "$file"
        stat_size=$(stat --format=%s "$file")
        stat_blocks=$(stat --format=%b "$file")
-       expect_attr "$device" size "$stat_size"
-       expect_attr "$device" blocks "$stat_blocks"
+       expect_attr "$facet" size "$stat_size"
+       expect_attr "$facet" blocks "$stat_blocks"
        rmdir "$file"
 
        ln -s /dev/null "$file"
        stat_size=$(stat --format=%s "$file")
        stat_blocks=$(stat --format=%b "$file")
-       expect_attr "$device" size "$stat_size"
-       expect_attr "$device" blocks "$stat_blocks"
+       expect_attr "$facet" size "$stat_size"
+       expect_attr "$facet" blocks "$stat_blocks"
        rm "$file"
 
        mkfifo "$file"
        stat_size=$(stat --format=%s "$file")
        stat_blocks=$(stat --format=%b "$file")
-       expect_attr "$device" size "$stat_size"
-       expect_attr "$device" blocks "$stat_blocks"
+       expect_attr "$facet" size "$stat_size"
+       expect_attr "$facet" blocks "$stat_blocks"
        rm "$file"
 }
 run_test 104 "lipe_scan3 size/blocks do the right thing"
 
 test_105() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
 
        init_lipe_scan3_env "$file"
 
-       expect_attr "$device" nlink 1
+       expect_attr "$facet" nlink 1
        ln $file $file-2
        ln $file $file-3
-       expect_attr "$device" nlink 3
+       expect_attr "$facet" nlink 3
 
        # If we hold $file open and remove all three links then
        # lipe_scan3 will still return a link count of 1 because of
@@ -546,38 +608,36 @@ run_test 105 "lipe_scan3 nlink does the right thing"
 
 test_106() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local id
 
        init_lipe_scan3_env "$file"
 
        id=$($LFS project "$file" | awk '{ print $1 }')
-       expect_attr "$device" projid "$id"
+       expect_attr "$facet" projid "$id"
 
        for id in "${IDS[@]}"; do
-               $LFS project -p "$id" "$file" || error "cannot set projid to '$id'"
-               expect_attr "$device" projid "$id"
+               $LFS project -p "$id" "$file" ||
+                       error "cannot set projid to '$id'"
+               expect_attr "$facet" projid "$id"
        done
 }
 run_test 106 "lipe_scan3 projid does the right thing"
 
 test_107() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local fid
 
        init_lipe_scan3_env "$file"
        fid=$($LFS path2fid $file)
-       expect_attr "$device" file-fid "$fid"
-       expect_attr "$device" self-fid "$fid"
+       expect_attr "$facet" file-fid "$fid"
+       expect_attr "$facet" self-fid "$fid"
 }
 run_test 107 "lipe_scan3 file-fid and self-fid do the right thing"
 
 test_108() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local fd
        local link_count=200
@@ -588,52 +648,50 @@ test_108() {
        # (links) returns a list of parent-fid, name pairs
        # (([0x200000007:0x1:0x0] . "f0") ...)
 
-       expect_expr "$device" '(caar (links))' "$ROOT_FID"
-       expect_expr "$device" '(cdar (links))' "$tfile"
+       expect_expr "$facet" '(caar (links))' "$ROOT_FID"
+       expect_expr "$facet" '(cdar (links))' "$tfile"
 
        ln $file $file-2
-       expect_expr "$device" '(length (links))' 2
+       expect_expr "$facet" '(length (links))' 2
 
        ln $file $file-3
-       expect_expr "$device" '(length (links))' 3
+       expect_expr "$facet" '(length (links))' 3
 
        for ((i = 4; i < link_count; i++)); do
                ln $file $file-$i
        done
 
-       expect_expr "$device" '(caar (links))' "$ROOT_FID"
-       expect_expr "$device" '(cdar (links))' "$tfile"
+       expect_expr "$facet" '(caar (links))' "$ROOT_FID"
+       expect_expr "$facet" '(cdar (links))' "$tfile"
 
        # FIXME link xattr is not updated when removing last link.
        # exec {fd}>$file
        # rm -- "$file" "$file-2" "$file-3"
-       # expect_expr "$device" '(length (links))' 0
+       # expect_expr "$facet" '(length (links))' 0
        # exec {fd}>&-
 }
 run_test 108 "lipe_scan3 links does the right thing"
 
 test_109() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
 
        init_lipe_scan3_env "$file"
-       expect_expr "$device" '(absolute-paths)' "($file)"
-       expect_expr "$device" '(relative-paths)' "($tfile)"
+       expect_expr "$facet" '(absolute-paths)' "($file)"
+       expect_expr "$facet" '(relative-paths)' "($tfile)"
 
        ln $file $file-2
-       expect_expr "$device" '(absolute-paths)' "($file $file-2)"
-       expect_expr "$device" '(relative-paths)' "($tfile $tfile-2)"
+       expect_expr "$facet" '(absolute-paths)' "($file $file-2)"
+       expect_expr "$facet" '(relative-paths)' "($tfile $tfile-2)"
 
        ln $file $file-3
-       expect_expr "$device" '(absolute-paths)' "($file $file-2 $file-3)"
-       expect_expr "$device" '(relative-paths)' "($tfile $tfile-2 $tfile-3)"
+       expect_expr "$facet" '(absolute-paths)' "($file $file-2 $file-3)"
+       expect_expr "$facet" '(relative-paths)' "($tfile $tfile-2 $tfile-3)"
 }
 run_test 109 "lipe_scan3 paths thunks do the right thing"
 
 test_110() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local params
        local fd
@@ -656,19 +714,19 @@ test_110() {
 
        sync
        $LFS getsom "$file"
-       lipe_scan3 "$device" --print-json=som
+       lipe_scan3_facet "$facet" --print-json=som
 
        # file: /mnt/lustre/f110.sanity-lipe-scan3 size: 4 blocks: 8 flags: 4
        a1=$($LFS getsom "$file" | awk '{ print $4 }')
-       a2=$(lipe_scan3 "$device" --print-json=som | jq .som.size)
+       a2=$(lipe_scan3_facet "$facet" --print-json=som | jq .som.size)
        ((a1 == a2)) || error "som.size expected '$a1', got '$a2'"
 
        a1=$($LFS getsom "$file" | awk '{ print $6 }')
-       a2=$(lipe_scan3 "$device" --print-json=som | jq .som.blocks)
+       a2=$(lipe_scan3_facet "$facet" --print-json=som | jq .som.blocks)
        ((a1 == a2)) || error "som.blocks expected '$a1', got '$a2'"
 
        a1=$($LFS getsom "$file" | awk '{ print $8 }')
-       a2=$(lipe_scan3 "$device" --print-json=som | jq .som._flags)
+       a2=$(lipe_scan3_facet "$facet" --print-json=som | jq .som._flags)
        ((a1 == a2)) || error "som.flags expected '$a1', got '$a2'"
 
        # .som.flags should be ["lazy"] here
@@ -677,7 +735,6 @@ run_test 110 "lipe_scan3 som attr works"
 
 test_111() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local fid
        local fid2
@@ -695,14 +752,15 @@ test_111() {
        #  }
        # }
 
-       fid2=$(lipe_scan3 "$device" --print-json=lma | jq --raw-output .lma.self_fid)
-       [[ "$fid" == "$fid2" ]] || error "lma.self_fid expected '$fid', got '$fid2'"
+       fid2=$(lipe_scan3_facet "$facet" --print-json=lma |
+              jq --raw-output .lma.self_fid)
+       [[ "$fid" == "$fid2" ]] ||
+               error "lma.self_fid expected '$fid', got '$fid2'"
 }
 run_test 111 "lipe_scan3 lma attr does the right thing"
 
 test_112() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local hsm
 
@@ -710,14 +768,13 @@ test_112() {
 
        # FIXME Make a better test.
 
-       hsm=$(lipe_scan3 "$device" --print-json='[hsm]')
+       hsm=$(lipe_scan3_facet "$facet" --print-json='[hsm]')
        [[ "$hsm" == "{}" ]] || error "hsm expected '{}', got '$hsm'"
 }
 run_test 112 "lipe_scan3 hsm attr does the right thing"
 
 test_113() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local a2
 
@@ -727,66 +784,64 @@ test_113() {
        # filter_fid. This just checks that ls3 understands the
        # filter_fid attr.
 
-       a2=$(lipe_scan3 "$device" --print-json='[filter_fid]')
+       a2=$(lipe_scan3_facet "$facet" --print-json='[filter_fid]')
        [[ "$a2" == "{}" ]] || error "filter_fid expected '', got '$a2'"
 }
 run_test 113 "lipe_scan3 filter_fid does the right thing"
 
 test_120() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
 
        init_lipe_scan3_env "$file"
        echo XXX > "$file"
 
-       expect_expr "$device" '(car (assoc "trusted.lov" (xattrs)))' trusted.lov
-       expect_print lipe_scan3_format "$device" '(xattr-ref "trusted.lov")'
+       expect_expr $facet '(car (assoc \"trusted.lov\" (xattrs)))' trusted.lov
+       expect_print lipe_scan3_format "$facet" '(xattr-ref \"trusted.lov\")'
 
        setfattr -n user.NAME -v VALUE "$file"
-       expect_expr "$device" '(car (assoc "user.NAME" (xattrs)))' user.NAME
-       expect_print lipe_scan3_format "$device" '(xattr-ref "user.NAME")'
+       expect_expr $facet '(car (assoc \"user.NAME\" (xattrs)))' user.NAME
+       expect_print lipe_scan3_format "$facet" '(xattr-ref \"user.NAME\")'
 
-       # expect_expr "$device" '(xattr-ref-string "user.NAME")' VALUE
+       # expect_expr "$facet" '(xattr-ref-string "user.NAME")' VALUE
 }
 run_test 120 "lipe_scan3 xattrs does the right thing"
 
 test_130() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local -a ost_indexes
 
        init_lipe_scan3_env "$file"
        $LFS setstripe -c -1 "$file"
-       ost_indexes=($($LFS getstripe --yaml "$file" | yq '.lmm_objects[] | .l_ost_idx'))
+       ost_indexes=($($LFS getstripe --yaml "$file" | yq '.lmm_objects[] |
+                       .l_ost_idx'))
 
-       expect_expr "$device" '(lov-pools)' '()'
-       expect_expr "$device" '(lov-ost-indexes)' "(${ost_indexes[*]})"
+       expect_expr "$facet" '(lov-pools)' '()'
+       expect_expr "$facet" '(lov-ost-indexes)' "(${ost_indexes[*]})"
 }
 run_test 130 "lipe_scan3 lov-pools and lov-ost-indexes do the right thing"
 
 test_131() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
 
        init_lipe_scan3_env "$file"
-       expect_expr "$device" '(lov-mirror-count)' 0
-       expect_expr "$device" '(lov-stripe-count)' 0
+       expect_expr "$facet" '(lov-mirror-count)' 0
+       expect_expr "$facet" '(lov-stripe-count)' 0
 
        $LFS setstripe -c 2 "$file"
        sync
 
-       expect_expr "$device" '(lov-mirror-count)' 1
-       expect_expr "$device" '(lov-stripe-count)' 2
+       expect_expr "$facet" '(lov-mirror-count)' 1
+       expect_expr "$facet" '(lov-stripe-count)' 2
 
        echo XXX > "$file"
-       $LFS mirror extend -N -c 4 "$file"
+       $LFS mirror extend -N -c $OSTCOUNT "$file"
        sync
 
-       expect_expr "$device" '(lov-mirror-count)' 2
-       expect_expr "$device" '(lov-stripe-count)' 4
+       expect_expr "$facet" '(lov-mirror-count)' 2
+       expect_expr "$facet" '(lov-stripe-count)' $OSTCOUNT
 }
 run_test 131 "lipe_scan3 lov-mirror-count and lov-stripe-count do the right thing"
 
@@ -798,14 +853,14 @@ test_200() {
 
        init_lipe_scan3_env "$file"
 
-       lipe_scan3_format "$device" '(lipe-scan-device-name)'
-       expect_attr "$device" lipe-scan-fsname "$FSNAME"
-       expect_attr "$device" lipe-scan-client-mount-path "$MOUNT"
-       expect_attr "$device" lipe-scan-device-name "$FSNAME-MDT0000"
-       expect_attr "$device" lipe-scan-device-path "$device"
-       expect_attr "$device" lipe-scan-thread-count 1 --thread-count=1
-       expect_attr "$device" lipe-scan-thread-count 2 --thread-count=2
-       expect_attr "$device" lipe-scan-thread-index 0 --thread-count=1
+       lipe_scan3_format "$facet" '(lipe-scan-device-name)'
+       expect_attr "$facet" lipe-scan-fsname "$FSNAME"
+       expect_attr "$facet" lipe-scan-client-mount-path "$MOUNT"
+       expect_attr "$facet" lipe-scan-device-name "$FSNAME-MDT0000"
+       expect_attr "$facet" lipe-scan-device-path "$device"
+       expect_attr "$facet" lipe-scan-thread-count 1 --thread-count=1
+       expect_attr "$facet" lipe-scan-thread-count 2 --thread-count=2
+       expect_attr "$facet" lipe-scan-thread-index 0 --thread-count=1
 
        for proc in \
                lipe-debug-enable \
@@ -813,20 +868,19 @@ test_200() {
                lipe-scan-client-mount-fd \
                lipe-scan-current-attrs \
                lipe-scan-thread-index; do
-               expect_print lipe_scan3_format "$device" "($proc)"
+               expect_print lipe_scan3_format "$facet" "($proc)"
        done
 }
 run_test 200 "lipe-scan-* procedures do the right thing"
 
 test_201() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local rc
 
        init_lipe_scan3_env "$file"
 
-       lipe_scan3_body "$device" '(lipe-scan-break 7)'
+       lipe_scan3_body "$facet" '(lipe-scan-break 7)'
        rc=$?
        ((rc == 7)) || error "(lipe-scan-break 7) should return 7"
 }
@@ -836,7 +890,6 @@ run_test 201 "lipe-scan-break works"
 
 test_300() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local fid
        local out
@@ -844,19 +897,18 @@ test_300() {
        init_lipe_scan3_env "$file"
        fid=$($LFS path2fid "$file")
 
-       lipe_scan3 "$device" --print-file-fid
+       lipe_scan3_facet "$facet" --print-file-fid
 
-       out=$(lipe_scan3 "$device" --print-file-fid)
+       out=$(lipe_scan3_facet "$facet" --print-file-fid)
        [[ "$out" == "$fid" ]] || error "--print-file-fid should print '$fid'"
 
-       out=$(lipe_scan3 "$device" --print-self-fid)
+       out=$(lipe_scan3_facet "$facet" --print-self-fid)
        [[ "$out" == "$fid" ]] || error "--print-self-fid should print '$fid'"
 }
 run_test 300 "--print-*-fid options work"
 
 test_301() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local fid
        local fd
@@ -873,27 +925,33 @@ test_301() {
 
        fid=$($LFS path2fid "$file")
 
-       lipe_scan3 "$device" --print-json | jq . || error "--print-json should print JSON"
-       lipe_scan3 "$device" --print-json=#x0 | jq . || error "--print-json should print JSON"
-       lipe_scan3 "$device" --print-json=#xffffffff | jq . || error "--print-json should print JSON"
-       lipe_scan3 "$device" --print-json=all | jq . || error "--print-json should print JSON"
-       lipe_scan3 "$device" --print-json=ino | jq . || error "--print-json should print JSON"
+       lipe_scan3_facet "$facet" --print-json | jq . ||
+               error "--print-json should print JSON"
+       lipe_scan3_facet "$facet" --print-json=#x0 | jq . ||
+               error "--print-json should print JSON"
+       lipe_scan3_facet "$facet" --print-json=#xffffffff | jq . ||
+               error "--print-json should print JSON"
+       lipe_scan3_facet "$facet" --print-json=all | jq . ||
+               error "--print-json should print JSON"
+       lipe_scan3_facet "$facet" --print-json=ino | jq . ||
+               error "--print-json should print JSON"
 }
 run_test 301 "--print-json options work"
 
 test_302() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local out
 
        init_lipe_scan3_env "$file"
 
-       out=$(lipe_scan3 "$device" --print-absolute-path)
-       [[ "$out" == "$file" ]] || error "--print-absolute-path should print absolute path"
+       out=$(lipe_scan3_facet "$facet" --print-absolute-path)
+       [[ "$out" == "$file" ]] ||
+               error "--print-absolute-path should print absolute path"
 
-       out=$(lipe_scan3 "$device" --print-relative-path)
-       [[ "$out" == "$tfile" ]] || error "--print-relative-path should print relative path"
+       out=$(lipe_scan3_facet "$facet" --print-relative-path)
+       [[ "$out" == "$tfile" ]] ||
+               error "--print-relative-path should print relative path"
 
        # TODO --null
        # TODO --delim
@@ -902,7 +960,6 @@ run_test 302 "--print-*-path options work"
 
 test_303() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local tmp1=$(mktemp)
        local tmp2=$(mktemp)
 
@@ -915,15 +972,16 @@ test_303() {
        sync
 
        # XXX lipe_scan3 does not return the ROOT
-       (echo "$MOUNT"; lipe_scan3 "${device}" --print-absolute-path) | sort > $tmp1
+       (echo "$MOUNT"; lipe_scan3_facet "$facet" --print-absolute-path) |
+               sort > $tmp1
        lfs find "$MOUNT" --mdt-index 0 | sort > $tmp2
-       diff $tmp1 $tmp2 || error "--print-absolute-path should print the right paths"
+       diff $tmp1 $tmp2 ||
+               error "--print-absolute-path should print the right paths"
 }
 run_test 303 "--print-absolute-paths prints the right paths"
 
 test_304() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file=$MOUNT/$tfile
        local out
        local expect
@@ -934,26 +992,31 @@ test_304() {
        ln "$file" "$file-2"
        sync
 
-       out=$(lipe_scan3 "${device}" --print-absolute-path)
-       [[ "$out" == "$file" ]] || error "print-absolute-path got '$out', expected '$file"
+       out=$(lipe_scan3_facet "$facet" --print-absolute-path)
+       [[ "$out" == "$file" ]] ||
+               error "print-absolute-path got '$out', expected '$file"
 
-       out=$(lipe_scan3 "${device}" --print-absolute-path --all-paths | sort)
+       out=$(lipe_scan3_facet "$facet" --print-absolute-path --all-paths |
+             sort)
        expect=$(ls "$file"*)
 
-       [[ "$out" == "$expect" ]] || error "print-absolute-path got '$out', expected '$expect'"
+       [[ "$out" == "$expect" ]] ||
+               error "print-absolute-path got '$out', expected '$expect'"
 
-       out=$(lipe_scan3 "${device}" --print-relative-path)
-       [[ "$out" == "$tfile" ]] || error "print-absolute-path got '$out', expected '$tfile"
+       out=$(lipe_scan3_facet "$facet" --print-relative-path)
+       [[ "$out" == "$tfile" ]] ||
+               error "print-absolute-path got '$out', expected '$tfile"
 
-       out=$(lipe_scan3 "${device}" --print-relative-path --all-paths | sort)
+       out=$(lipe_scan3_facet "$facet" --print-relative-path --all-paths |
+             sort)
        expect=$(ls "$MOUNT")
-       [[ "$out" == "$expect" ]] || error "print-relative-path got '$out', expected '$expect'"
+       [[ "$out" == "$expect" ]] ||
+               error "print-relative-path got '$out', expected '$expect'"
 }
 run_test 304 "print-*-paths with multiple links"
 
 test_305() {
        local facet=mds1
-       local device="$(facet_device $facet)"
        local file
        local fid
        local mdt_index
@@ -971,62 +1034,73 @@ test_305() {
        ((mdt_index == 0)) || error "expected MDT index 0, got '$mdt_index'"
        sync
 
-       out=$(lipe_scan3 "${device}" --print-json=file_fid,paths |
-       jq --raw-output --arg FID "$fid" 'select(.file_fid == $FID) | .paths[]')
-       [[ "$out" == "$tdir/d0/d0/f0" ]] || error "JSON got '$out', expected '$tdir/d0/d0/f0'"
+       out=$(lipe_scan3_facet "$facet" --print-json=file_fid,paths |
+             jq --raw-output --arg FID "$fid" 'select(.file_fid == $FID) |
+             .paths[]')
+       [[ "$out" == "$tdir/d0/d0/f0" ]] ||
+               error "JSON got '$out', expected '$tdir/d0/d0/f0'"
 
        ln "$file" "$file"-1
        ln "$file" "$file"-2
        sync
 
-       out=$(lipe_scan3 "${device}" --print-json=file_fid,paths |
-       jq --raw-output --arg FID "$fid" 'select(.file_fid == $FID) | .paths[0]')
-       [[ "$out" == "$tdir/d0/d0/f0" ]] || error "JSON got '$out', expected '$tdir/d0/d0/f0'"
-
-       out=$(lipe_scan3 "${device}" --print-json=file_fid,paths |
-       jq --raw-output --arg FID "$fid" 'select(.file_fid == $FID) | .paths[1]')
-       [[ "$out" == "$tdir/d0/d0/f0-1" ]] || error "JSON got '$out', expected '$tdir/d0/d0/f0-1'"
-
-       out=$(lipe_scan3 "${device}" --print-json=file_fid,paths |
-       jq --raw-output --arg FID "$fid" 'select(.file_fid == $FID) | .paths[2]')
-       [[ "$out" == "$tdir/d0/d0/f0-2" ]] || error "JSON got '$out', expected '$tdir/d0/d0/f0-2'"
+       out=$(lipe_scan3_facet "$facet" --print-json=file_fid,paths |
+             jq --raw-output --arg FID "$fid" 'select(.file_fid == $FID) |
+             .paths[0]')
+       [[ "$out" == "$tdir/d0/d0/f0" ]] ||
+               error "JSON got '$out', expected '$tdir/d0/d0/f0'"
+
+       out=$(lipe_scan3_facet "$facet" --print-json=file_fid,paths |
+             jq --raw-output --arg FID "$fid" 'select(.file_fid == $FID) |
+             .paths[1]')
+       [[ "$out" == "$tdir/d0/d0/f0-1" ]] ||
+               error "JSON got '$out', expected '$tdir/d0/d0/f0-1'"
+
+       out=$(lipe_scan3_facet "$facet" --print-json=file_fid,paths |
+             jq --raw-output --arg FID "$fid" 'select(.file_fid == $FID) |
+             .paths[2]')
+       [[ "$out" == "$tdir/d0/d0/f0-2" ]] ||
+               error "JSON got '$out', expected '$tdir/d0/d0/f0-2'"
 }
 run_test 305 "print-json prints the right paths"
 
 # loading and scripts
 
 test_400() {
-       expect_empty lipe_scan3 --script=/dev/null
-       expect_empty lipe_scan3 -s /dev/null
-       expect_empty lipe_scan3 --load=/dev/null --script=/dev/null
-       expect_empty lipe_scan3 -l /dev/null -s /dev/null
+       local facet=${LIPE_MDS_FACET:-$(lipe_get_random_mds)}
+
+       expect_empty lipe_scan3_on $facet --script=/dev/null
+       expect_empty lipe_scan3_on $facet -s /dev/null
+       expect_empty lipe_scan3_on $facet --load=/dev/null --script=/dev/null
+       expect_empty lipe_scan3_on $facet -l /dev/null -s /dev/null
 }
 run_test 400 "empty scripts and loaded files"
 
 test_401() {
+       local facet=${LIPE_MDS_FACET:-$(lipe_get_random_mds)}
        local rc
 
-       echo '#t' | lipe_scan3 --script=/dev/stdin
+       do_facet $facet "echo '#t' | lipe_scan3 --script=/dev/stdin"
        rc=$?
        ((rc == 0)) || error "rc expect 0, got '$rc'"
 
-       echo '#f' | lipe_scan3 --script=/dev/stdin
+       do_facet $facet "echo '#f' | lipe_scan3 --script=/dev/stdin"
        rc=$?
        ((rc == 1)) || error "rc expect 1, got '$rc'"
 
-       echo '0' | lipe_scan3 --script=/dev/stdin
+       do_facet $facet "echo '0' | lipe_scan3 --script=/dev/stdin"
        rc=$?
        ((rc == 0)) || error "rc expect 0, got '$rc'"
 
-       echo '7' | lipe_scan3 --script=/dev/stdin
+       do_facet $facet "echo '7' | lipe_scan3 --script=/dev/stdin"
        rc=$?
        ((rc == 7)) || error "rc expect 7, got '$rc'"
 
-       echo 'cons' | lipe_scan3 --script=/dev/stdin
+       do_facet $facet "echo 'cons' | lipe_scan3 --script=/dev/stdin"
        rc=$?
        ((rc == 0)) || error "rc expect 0, got '$rc'"
 
-       echo "'()" | lipe_scan3 --script=/dev/stdin
+       do_facet $facet "echo \\\"'()\\\" | lipe_scan3 --script=/dev/stdin"
        rc=$?
        ((rc == 0)) || error "rc expect 0, got '$rc'"
 }
@@ -1039,6 +1113,8 @@ run_test 401 "lipe_scan3 script exit statuses work"
 # --print-json on OST
 # Automagic required attrs work on OST
 
+FAIL_ON_ERROR=$SAVED_FAIL_ON_ERROR
+
 complete $SECONDS
 check_and_cleanup_lustre
 exit_status