2 # SPDX-License-Identifier: GPL-2.0-or-later
3 # Copyright (c) 2016 Microsemi. All Rights Reserved.
5 # Author: Logan Gunthorpe <logang@deltatee.com>
10 DEBUGFS=${DEBUGFS-/sys/kernel/debug}
20 echo "Usage: $0 [OPTIONS] LOCAL_DEV REMOTE_DEV"
21 echo "Run tests on a pair of NTB endpoints."
23 echo "If the NTB device loops back to the same host then,"
24 echo "just specifying the two PCI ids on the command line is"
25 echo "sufficient. Otherwise, if the NTB link spans two hosts"
26 echo "use the -r option to specify the hostname for the remote"
27 echo "device. SSH will then be used to test the remote side."
28 echo "An SSH key between the root users of the host would then"
29 echo "be highly recommended."
32 echo " -C don't cleanup ntb modules on exit"
33 echo " -h show this help message"
34 echo " -l list available local and remote PCI ids"
35 echo " -r REMOTE_HOST specify the remote's hostname to connect"
36 echo " to for the test (using ssh)"
37 echo " -m MW_SIZE memory window size for ntb_tool"
38 echo " (default: $MW_SIZE)"
39 echo " -d run dma tests for ntb_perf"
40 echo " -p ORDER total data order for ntb_perf"
41 echo " (default: $PERF_RUN_ORDER)"
42 echo " -w MAX_MW_SIZE maxmium memory window size for ntb_perf"
49 while getopts "b:Cdhlm:r:p:w:" opt; do
53 h) show_help; exit 0 ;;
55 m) MW_SIZE=${OPTARG} ;;
56 r) REMOTE_HOST=${OPTARG} ;;
57 p) PERF_RUN_ORDER=${OPTARG} ;;
58 w) MAX_MW_SIZE=${OPTARG} ;;
60 echo "Invalid option: -$OPTARG" >&2
83 if [[ "$REMOTE_HOST" != "" ]]; then
84 ssh "$REMOTE_HOST" modprobe "$@"
88 function split_remote()
93 if [[ "$VPATH" == *":/"* ]]; then
102 if [[ "$REMOTE" != "" ]]; then
103 ssh "$REMOTE" cat "$VPATH"
109 function write_file()
114 if [[ "$REMOTE" != "" ]]; then
115 ssh "$REMOTE" "echo \"$VALUE\" > \"$VPATH\""
117 echo "$VALUE" > "$VPATH"
121 function check_file()
125 if [[ "$REMOTE" != "" ]]; then
126 ssh "$REMOTE" "[[ -e ${VPATH} ]]"
132 function subdirname()
134 echo $(basename $(dirname $1)) 2> /dev/null
142 for ((i = 0; i < 64; i++)); do
143 PEER_DIR="$PPATH/peer$i"
145 check_file ${PEER_DIR} || break
147 PEER_PORT=$(read_file "${PEER_DIR}/port")
148 if [[ ${PORT} -eq $PEER_PORT ]]; then
162 echo "Running port tests on: $(basename $LOC) / $(basename $REM)"
164 LOCAL_PORT=$(read_file "$LOC/port")
165 REMOTE_PORT=$(read_file "$REM/port")
167 LOCAL_PIDX=$(find_pidx ${REMOTE_PORT} "$LOC")
168 REMOTE_PIDX=$(find_pidx ${LOCAL_PORT} "$REM")
170 echo "Local port ${LOCAL_PORT} with index ${REMOTE_PIDX} on remote host"
171 echo "Peer port ${REMOTE_PORT} with index ${LOCAL_PIDX} on local host"
182 echo "Running link tests on: $(subdirname $LOC) / $(subdirname $REM)"
184 if ! write_file "N" "$LOC/../link" 2> /dev/null; then
189 write_file "N" "$LOC/link_event"
191 if [[ $(read_file "$REM/link") != "N" ]]; then
192 echo "Expected link to be down in $REM/link" >&2
196 write_file "Y" "$LOC/../link"
201 function doorbell_test()
207 echo "Running db tests on: $(basename $LOC) / $(basename $REM)"
209 DB_VALID_MASK=$(read_file "$LOC/db_valid_mask")
211 write_file "c $DB_VALID_MASK" "$REM/db"
213 for ((i = 0; i < 64; i++)); do
214 DB=$(read_file "$REM/db")
215 if [[ "$DB" -ne "$EXP" ]]; then
216 echo "Doorbell doesn't match expected value $EXP " \
221 let "MASK = (1 << $i) & $DB_VALID_MASK" || true
222 let "EXP = $EXP | $MASK" || true
224 write_file "s $MASK" "$LOC/peer_db"
227 write_file "c $DB_VALID_MASK" "$REM/db_mask"
228 write_file $DB_VALID_MASK "$REM/db_event"
229 write_file "s $DB_VALID_MASK" "$REM/db_mask"
231 write_file "c $DB_VALID_MASK" "$REM/db"
236 function get_files_count()
243 if [[ "$REMOTE" == "" ]]; then
244 echo $(ls -1 "$LOC"/${NAME}* 2>/dev/null | wc -l)
246 echo $(ssh "$REMOTE" "ls -1 \"$VPATH\"/${NAME}* | \
251 function scratchpad_test()
256 echo "Running spad tests on: $(subdirname $LOC) / $(subdirname $REM)"
258 CNT=$(get_files_count "spad" "$LOC")
260 if [[ $CNT -eq 0 ]]; then
265 for ((i = 0; i < $CNT; i++)); do
267 write_file "$VAL" "$LOC/spad$i"
268 RVAL=$(read_file "$REM/../spad$i")
270 if [[ "$VAL" -ne "$RVAL" ]]; then
271 echo "Scratchpad $i value $RVAL doesn't match $VAL" >&2
279 function message_test()
284 echo "Running msg tests on: $(subdirname $LOC) / $(subdirname $REM)"
286 CNT=$(get_files_count "msg" "$LOC")
288 if [[ $CNT -eq 0 ]]; then
293 MSG_OUTBITS_MASK=$(read_file "$LOC/../msg_inbits")
294 MSG_INBITS_MASK=$(read_file "$REM/../msg_inbits")
296 write_file "c $MSG_OUTBITS_MASK" "$LOC/../msg_sts"
297 write_file "c $MSG_INBITS_MASK" "$REM/../msg_sts"
299 for ((i = 0; i < $CNT; i++)); do
301 write_file "$VAL" "$LOC/msg$i"
302 RVAL=$(read_file "$REM/../msg$i")
304 if [[ "$VAL" -ne "${RVAL%%<-*}" ]]; then
305 echo "Message $i value $RVAL doesn't match $VAL" >&2
313 function get_number()
317 sed -n "s/^\(${KEY}\)[ \t]*\(0x[0-9a-fA-F]*\)\(\[p\]\)\?$/\2/p"
326 write_file $MW_SIZE "$LOC/mw_trans$IDX"
328 INB_MW=$(read_file "$LOC/mw_trans$IDX")
329 MW_ALIGNED_SIZE=$(echo "$INB_MW" | get_number "Window Size")
330 MW_DMA_ADDR=$(echo "$INB_MW" | get_number "DMA Address")
332 write_file "$MW_DMA_ADDR:$(($MW_ALIGNED_SIZE))" "$REM/peer_mw_trans$IDX"
334 if [[ $MW_SIZE -ne $MW_ALIGNED_SIZE ]]; then
335 echo "MW $IDX size aligned to $MW_ALIGNED_SIZE"
343 if [[ "$REMOTE" != "" ]]; then
345 dd if=/dev/urandom "of=$VPATH" 2> /dev/null || true
347 dd if=/dev/urandom "of=$VPATH" 2> /dev/null || true
357 write_mw "$LOC/mw$IDX"
359 split_remote "$LOC/mw$IDX"
360 if [[ "$REMOTE" == "" ]]; then
364 ssh "$REMOTE" cat "$VPATH" > "$A"
367 split_remote "$REM/peer_mw$IDX"
368 if [[ "$REMOTE" == "" ]]; then
372 ssh "$REMOTE" cat "$VPATH" > "$B"
375 cmp -n $MW_ALIGNED_SIZE "$A" "$B"
376 if [[ $? != 0 ]]; then
377 echo "Memory window $MW did not match!" >&2
380 if [[ "$A" == "/tmp/*" ]]; then
384 if [[ "$B" == "/tmp/*" ]]; then
395 write_file "$MW_DMA_ADDR:0" "$REM/peer_mw_trans$IDX"
397 write_file 0 "$LOC/mw_trans$IDX"
405 CNT=$(get_files_count "mw_trans" "$LOC")
407 for ((i = 0; i < $CNT; i++)); do
408 echo "Running mw$i tests on: $(subdirname $LOC) / " \
411 mw_alloc $i $LOC $REM
413 mw_check $i $LOC $REM
422 function pingpong_test()
427 echo "Running ping pong tests on: $(basename $LOC) / $(basename $REM)"
429 LOC_START=$(read_file "$LOC/count")
430 REM_START=$(read_file "$REM/count")
434 LOC_END=$(read_file "$LOC/count")
435 REM_END=$(read_file "$REM/count")
437 if [[ $LOC_START == $LOC_END ]] || [[ $REM_START == $REM_END ]]; then
438 echo "Ping pong counter not incrementing!" >&2
449 if [[ $USE_DMA == "1" ]]; then
455 _modprobe ntb_perf total_order=$PERF_RUN_ORDER \
456 max_mw_size=$MAX_MW_SIZE use_dma=$USE_DMA
458 echo "Running local perf test $WITH DMA"
459 write_file "$LOCAL_PIDX" "$LOCAL_PERF/run"
461 read_file "$LOCAL_PERF/run"
464 echo "Running remote perf test $WITH DMA"
465 write_file "$REMOTE_PIDX" "$REMOTE_PERF/run"
467 read_file "$REMOTE_PERF/run"
470 _modprobe -r ntb_perf
473 function ntb_tool_tests()
475 LOCAL_TOOL="$DEBUGFS/ntb_tool/$LOCAL_DEV"
476 REMOTE_TOOL="$REMOTE_HOST:$DEBUGFS/ntb_tool/$REMOTE_DEV"
478 echo "Starting ntb_tool tests..."
482 port_test "$LOCAL_TOOL" "$REMOTE_TOOL"
484 LOCAL_PEER_TOOL="$LOCAL_TOOL/peer$LOCAL_PIDX"
485 REMOTE_PEER_TOOL="$REMOTE_TOOL/peer$REMOTE_PIDX"
487 link_test "$LOCAL_PEER_TOOL" "$REMOTE_PEER_TOOL"
488 link_test "$REMOTE_PEER_TOOL" "$LOCAL_PEER_TOOL"
490 #Ensure the link is up on both sides before continuing
491 write_file "Y" "$LOCAL_PEER_TOOL/link_event"
492 write_file "Y" "$REMOTE_PEER_TOOL/link_event"
494 doorbell_test "$LOCAL_TOOL" "$REMOTE_TOOL"
495 doorbell_test "$REMOTE_TOOL" "$LOCAL_TOOL"
497 scratchpad_test "$LOCAL_PEER_TOOL" "$REMOTE_PEER_TOOL"
498 scratchpad_test "$REMOTE_PEER_TOOL" "$LOCAL_PEER_TOOL"
500 message_test "$LOCAL_PEER_TOOL" "$REMOTE_PEER_TOOL"
501 message_test "$REMOTE_PEER_TOOL" "$LOCAL_PEER_TOOL"
503 mw_test "$LOCAL_PEER_TOOL" "$REMOTE_PEER_TOOL"
504 mw_test "$REMOTE_PEER_TOOL" "$LOCAL_PEER_TOOL"
506 _modprobe -r ntb_tool
509 function ntb_pingpong_tests()
511 LOCAL_PP="$DEBUGFS/ntb_pingpong/$LOCAL_DEV"
512 REMOTE_PP="$REMOTE_HOST:$DEBUGFS/ntb_pingpong/$REMOTE_DEV"
514 echo "Starting ntb_pingpong tests..."
516 _modprobe ntb_pingpong
518 pingpong_test $LOCAL_PP $REMOTE_PP
520 _modprobe -r ntb_pingpong
523 function ntb_perf_tests()
525 LOCAL_PERF="$DEBUGFS/ntb_perf/$LOCAL_DEV"
526 REMOTE_PERF="$REMOTE_HOST:$DEBUGFS/ntb_perf/$REMOTE_DEV"
528 echo "Starting ntb_perf tests..."
532 if [[ $RUN_DMA_TESTS ]]; then
540 _modprobe -r ntb_tool 2> /dev/null
541 _modprobe -r ntb_perf 2> /dev/null
542 _modprobe -r ntb_pingpong 2> /dev/null
543 _modprobe -r ntb_transport 2> /dev/null
549 if ! [[ $$DONT_CLEANUP ]]; then
553 if [ "$(id -u)" != "0" ]; then
554 echo "This script must be run as root" 1>&2
558 if [[ "$LIST_DEVS" == TRUE ]]; then
559 echo "Local Devices:"
560 ls -1 /sys/bus/ntb/devices
563 if [[ "$REMOTE_HOST" != "" ]]; then
564 echo "Remote Devices:"
565 ssh $REMOTE_HOST ls -1 /sys/bus/ntb/devices
571 if [[ "$LOCAL_DEV" == $"" ]] || [[ "$REMOTE_DEV" == $"" ]]; then