* [PATCH v2 0/8] selftests: ublk: add user copy test cases
@ 2025-12-12 5:16 Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 1/8] selftests: ublk: correct last_rw map type in seq_io.bt Caleb Sander Mateos
` (7 more replies)
0 siblings, 8 replies; 16+ messages in thread
From: Caleb Sander Mateos @ 2025-12-12 5:16 UTC (permalink / raw)
To: Ming Lei, Shuah Khan
Cc: linux-block, linux-kselftest, linux-kernel, Caleb Sander Mateos
Fix some existing issues in the ublk selftest suite and add coverage
for user copy, which is currently untested.
v2:
- Allow --zero_copy and --auto_zc to coexist for --auto_zc_fallback
- Don't add test cases to test_stress_05.sh as it's close to the timeout
- Add Reviewed-By tags
Caleb Sander Mateos (8):
selftests: ublk: correct last_rw map type in seq_io.bt
selftests: ublk: remove unused ios map in seq_io.bt
selftests: ublk: fix fio arguments in run_io_and_recover()
selftests: ublk: use auto_zc for PER_IO_DAEMON tests in stress_04
selftests: ublk: don't share backing files between ublk servers
selftests: ublk: forbid multiple data copy modes
selftests: ublk: add support for user copy to kublk
selftests: ublk: add user copy test cases
tools/testing/selftests/ublk/Makefile | 8 +++
tools/testing/selftests/ublk/file_backed.c | 7 +-
tools/testing/selftests/ublk/kublk.c | 64 +++++++++++++++++--
tools/testing/selftests/ublk/kublk.h | 11 ++++
tools/testing/selftests/ublk/stripe.c | 2 +-
tools/testing/selftests/ublk/test_common.sh | 5 +-
.../testing/selftests/ublk/test_generic_04.sh | 2 +-
.../testing/selftests/ublk/test_generic_05.sh | 2 +-
.../testing/selftests/ublk/test_generic_11.sh | 2 +-
.../testing/selftests/ublk/test_generic_14.sh | 40 ++++++++++++
tools/testing/selftests/ublk/test_loop_06.sh | 25 ++++++++
tools/testing/selftests/ublk/test_loop_07.sh | 21 ++++++
tools/testing/selftests/ublk/test_null_03.sh | 24 +++++++
.../testing/selftests/ublk/test_stress_04.sh | 12 ++--
.../testing/selftests/ublk/test_stress_05.sh | 10 +--
.../testing/selftests/ublk/test_stress_06.sh | 39 +++++++++++
.../testing/selftests/ublk/test_stress_07.sh | 39 +++++++++++
.../testing/selftests/ublk/test_stripe_05.sh | 26 ++++++++
.../testing/selftests/ublk/test_stripe_06.sh | 21 ++++++
tools/testing/selftests/ublk/trace/seq_io.bt | 3 +-
20 files changed, 336 insertions(+), 27 deletions(-)
create mode 100755 tools/testing/selftests/ublk/test_generic_14.sh
create mode 100755 tools/testing/selftests/ublk/test_loop_06.sh
create mode 100755 tools/testing/selftests/ublk/test_loop_07.sh
create mode 100755 tools/testing/selftests/ublk/test_null_03.sh
create mode 100755 tools/testing/selftests/ublk/test_stress_06.sh
create mode 100755 tools/testing/selftests/ublk/test_stress_07.sh
create mode 100755 tools/testing/selftests/ublk/test_stripe_05.sh
create mode 100755 tools/testing/selftests/ublk/test_stripe_06.sh
--
2.45.2
^ permalink raw reply [flat|nested] 16+ messages in thread
* [PATCH v2 1/8] selftests: ublk: correct last_rw map type in seq_io.bt
2025-12-12 5:16 [PATCH v2 0/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
@ 2025-12-12 5:16 ` Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 2/8] selftests: ublk: remove unused ios map " Caleb Sander Mateos
` (6 subsequent siblings)
7 siblings, 0 replies; 16+ messages in thread
From: Caleb Sander Mateos @ 2025-12-12 5:16 UTC (permalink / raw)
To: Ming Lei, Shuah Khan
Cc: linux-block, linux-kselftest, linux-kernel, Caleb Sander Mateos
The last_rw map is initialized with a value of 0 but later assigned the
value args.sector + args.nr_sector, which has type sector_t = u64.
bpftrace complains about the type mismatch between int64 and uint64:
trace/seq_io.bt:18:3-59: ERROR: Type mismatch for @last_rw: trying to assign value of type 'uint64' when map already contains a value of type 'int64'
@last_rw[$dev, str($2)] = (args.sector + args.nr_sector);
Cast the initial value to uint64 so bpftrace will load the program.
Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
Reviewed-by: Ming Lei <ming.lei@redhat.com>
---
tools/testing/selftests/ublk/trace/seq_io.bt | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/tools/testing/selftests/ublk/trace/seq_io.bt b/tools/testing/selftests/ublk/trace/seq_io.bt
index 272ac54c9d5f..507a3ca05abf 100644
--- a/tools/testing/selftests/ublk/trace/seq_io.bt
+++ b/tools/testing/selftests/ublk/trace/seq_io.bt
@@ -2,11 +2,11 @@
$1: dev_t
$2: RWBS
$3: strlen($2)
*/
BEGIN {
- @last_rw[$1, str($2)] = 0;
+ @last_rw[$1, str($2)] = (uint64)0;
}
tracepoint:block:block_rq_complete
{
$dev = $1;
if ((int64)args.dev == $1 && !strncmp(args.rwbs, str($2), $3)) {
--
2.45.2
^ permalink raw reply related [flat|nested] 16+ messages in thread
* [PATCH v2 2/8] selftests: ublk: remove unused ios map in seq_io.bt
2025-12-12 5:16 [PATCH v2 0/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 1/8] selftests: ublk: correct last_rw map type in seq_io.bt Caleb Sander Mateos
@ 2025-12-12 5:16 ` Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 3/8] selftests: ublk: fix fio arguments in run_io_and_recover() Caleb Sander Mateos
` (5 subsequent siblings)
7 siblings, 0 replies; 16+ messages in thread
From: Caleb Sander Mateos @ 2025-12-12 5:16 UTC (permalink / raw)
To: Ming Lei, Shuah Khan
Cc: linux-block, linux-kselftest, linux-kernel, Caleb Sander Mateos
The ios map populated by seq_io.bt is never read, so remove it.
Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
Reviewed-by: Ming Lei <ming.lei@redhat.com>
---
tools/testing/selftests/ublk/trace/seq_io.bt | 1 -
1 file changed, 1 deletion(-)
diff --git a/tools/testing/selftests/ublk/trace/seq_io.bt b/tools/testing/selftests/ublk/trace/seq_io.bt
index 507a3ca05abf..b2f60a92b118 100644
--- a/tools/testing/selftests/ublk/trace/seq_io.bt
+++ b/tools/testing/selftests/ublk/trace/seq_io.bt
@@ -15,11 +15,10 @@ tracepoint:block:block_rq_complete
printf("io_out_of_order: exp %llu actual %llu\n",
args.sector, $last);
}
@last_rw[$dev, str($2)] = (args.sector + args.nr_sector);
}
- @ios = count();
}
END {
clear(@last_rw);
}
--
2.45.2
^ permalink raw reply related [flat|nested] 16+ messages in thread
* [PATCH v2 3/8] selftests: ublk: fix fio arguments in run_io_and_recover()
2025-12-12 5:16 [PATCH v2 0/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 1/8] selftests: ublk: correct last_rw map type in seq_io.bt Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 2/8] selftests: ublk: remove unused ios map " Caleb Sander Mateos
@ 2025-12-12 5:16 ` Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 4/8] selftests: ublk: use auto_zc for PER_IO_DAEMON tests in stress_04 Caleb Sander Mateos
` (4 subsequent siblings)
7 siblings, 0 replies; 16+ messages in thread
From: Caleb Sander Mateos @ 2025-12-12 5:16 UTC (permalink / raw)
To: Ming Lei, Shuah Khan
Cc: linux-block, linux-kselftest, linux-kernel, Caleb Sander Mateos
run_io_and_recover() invokes fio with --size="${size}", but the variable
size doesn't exist. Thus, the argument expands to --size=, which causes
fio to exit immediately with an error without issuing any I/O. Pass the
value for size as the first argument to the function.
Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
Reviewed-by: Ming Lei <ming.lei@redhat.com>
---
tools/testing/selftests/ublk/test_common.sh | 5 +++--
tools/testing/selftests/ublk/test_generic_04.sh | 2 +-
tools/testing/selftests/ublk/test_generic_05.sh | 2 +-
tools/testing/selftests/ublk/test_generic_11.sh | 2 +-
4 files changed, 6 insertions(+), 5 deletions(-)
diff --git a/tools/testing/selftests/ublk/test_common.sh b/tools/testing/selftests/ublk/test_common.sh
index 8a4dbd09feb0..6f1c042de40e 100755
--- a/tools/testing/selftests/ublk/test_common.sh
+++ b/tools/testing/selftests/ublk/test_common.sh
@@ -331,15 +331,16 @@ run_io_and_kill_daemon()
fi
}
run_io_and_recover()
{
- local action=$1
+ local size=$1
+ local action=$2
local state
local dev_id
- shift 1
+ shift 2
dev_id=$(_add_ublk_dev "$@")
_check_add_dev "$TID" $?
fio --name=job1 --filename=/dev/ublkb"${dev_id}" --ioengine=libaio \
--rw=randread --iodepth=256 --size="${size}" --numjobs=4 \
diff --git a/tools/testing/selftests/ublk/test_generic_04.sh b/tools/testing/selftests/ublk/test_generic_04.sh
index 8b533217d4a1..baf5b156193d 100755
--- a/tools/testing/selftests/ublk/test_generic_04.sh
+++ b/tools/testing/selftests/ublk/test_generic_04.sh
@@ -6,11 +6,11 @@
TID="generic_04"
ERR_CODE=0
ublk_run_recover_test()
{
- run_io_and_recover "kill_daemon" "$@"
+ run_io_and_recover 256M "kill_daemon" "$@"
ERR_CODE=$?
if [ ${ERR_CODE} -ne 0 ]; then
echo "$TID failure: $*"
_show_result $TID $ERR_CODE
fi
diff --git a/tools/testing/selftests/ublk/test_generic_05.sh b/tools/testing/selftests/ublk/test_generic_05.sh
index 398e9e2b58e1..7b5083afc02a 100755
--- a/tools/testing/selftests/ublk/test_generic_05.sh
+++ b/tools/testing/selftests/ublk/test_generic_05.sh
@@ -6,11 +6,11 @@
TID="generic_05"
ERR_CODE=0
ublk_run_recover_test()
{
- run_io_and_recover "kill_daemon" "$@"
+ run_io_and_recover 256M "kill_daemon" "$@"
ERR_CODE=$?
if [ ${ERR_CODE} -ne 0 ]; then
echo "$TID failure: $*"
_show_result $TID $ERR_CODE
fi
diff --git a/tools/testing/selftests/ublk/test_generic_11.sh b/tools/testing/selftests/ublk/test_generic_11.sh
index a00357a5ec6b..d1f973c8c645 100755
--- a/tools/testing/selftests/ublk/test_generic_11.sh
+++ b/tools/testing/selftests/ublk/test_generic_11.sh
@@ -6,11 +6,11 @@
TID="generic_11"
ERR_CODE=0
ublk_run_quiesce_recover()
{
- run_io_and_recover "quiesce_dev" "$@"
+ run_io_and_recover 256M "quiesce_dev" "$@"
ERR_CODE=$?
if [ ${ERR_CODE} -ne 0 ]; then
echo "$TID failure: $*"
_show_result $TID $ERR_CODE
fi
--
2.45.2
^ permalink raw reply related [flat|nested] 16+ messages in thread
* [PATCH v2 4/8] selftests: ublk: use auto_zc for PER_IO_DAEMON tests in stress_04
2025-12-12 5:16 [PATCH v2 0/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
` (2 preceding siblings ...)
2025-12-12 5:16 ` [PATCH v2 3/8] selftests: ublk: fix fio arguments in run_io_and_recover() Caleb Sander Mateos
@ 2025-12-12 5:16 ` Caleb Sander Mateos
2025-12-12 10:21 ` Ming Lei
2025-12-12 10:56 ` Ming Lei
2025-12-12 5:16 ` [PATCH v2 5/8] selftests: ublk: don't share backing files between ublk servers Caleb Sander Mateos
` (3 subsequent siblings)
7 siblings, 2 replies; 16+ messages in thread
From: Caleb Sander Mateos @ 2025-12-12 5:16 UTC (permalink / raw)
To: Ming Lei, Shuah Khan
Cc: linux-block, linux-kselftest, linux-kernel, Caleb Sander Mateos
stress_04 is described as "run IO and kill ublk server(zero copy)" but
the --per_io_tasks tests cases don't use zero copy. Plus, one of the
test cases is duplicated. Add --auto_zc to these test cases and
--auto_zc_fallback to one of the duplicated ones. This matches the test
cases in stress_03.
Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
---
tools/testing/selftests/ublk/test_stress_04.sh | 8 ++++----
1 file changed, 4 insertions(+), 4 deletions(-)
diff --git a/tools/testing/selftests/ublk/test_stress_04.sh b/tools/testing/selftests/ublk/test_stress_04.sh
index 3f901db4d09d..965befcee830 100755
--- a/tools/testing/selftests/ublk/test_stress_04.sh
+++ b/tools/testing/selftests/ublk/test_stress_04.sh
@@ -38,14 +38,14 @@ if _have_feature "AUTO_BUF_REG"; then
ublk_io_and_kill_daemon 256M -t stripe -q 4 --auto_zc --no_ublk_fixed_fd "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
ublk_io_and_kill_daemon 8G -t null -q 4 -z --auto_zc --auto_zc_fallback &
fi
if _have_feature "PER_IO_DAEMON"; then
- ublk_io_and_kill_daemon 8G -t null -q 4 --nthreads 8 --per_io_tasks &
- ublk_io_and_kill_daemon 256M -t loop -q 4 --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[0]}" &
- ublk_io_and_kill_daemon 256M -t stripe -q 4 --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
- ublk_io_and_kill_daemon 8G -t null -q 4 --nthreads 8 --per_io_tasks &
+ ublk_io_and_kill_daemon 8G -t null -q 4 --auto_zc --nthreads 8 --per_io_tasks &
+ ublk_io_and_kill_daemon 256M -t loop -q 4 --auto_zc --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[0]}" &
+ ublk_io_and_kill_daemon 256M -t stripe -q 4 --auto_zc --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
+ ublk_io_and_kill_daemon 8G -t null -q 4 --auto_zc --auto_zc_fallback --nthreads 8 --per_io_tasks &
fi
wait
_cleanup_test "stress"
_show_result $TID $ERR_CODE
--
2.45.2
^ permalink raw reply related [flat|nested] 16+ messages in thread
* [PATCH v2 5/8] selftests: ublk: don't share backing files between ublk servers
2025-12-12 5:16 [PATCH v2 0/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
` (3 preceding siblings ...)
2025-12-12 5:16 ` [PATCH v2 4/8] selftests: ublk: use auto_zc for PER_IO_DAEMON tests in stress_04 Caleb Sander Mateos
@ 2025-12-12 5:16 ` Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 6/8] selftests: ublk: forbid multiple data copy modes Caleb Sander Mateos
` (2 subsequent siblings)
7 siblings, 0 replies; 16+ messages in thread
From: Caleb Sander Mateos @ 2025-12-12 5:16 UTC (permalink / raw)
To: Ming Lei, Shuah Khan
Cc: linux-block, linux-kselftest, linux-kernel, Caleb Sander Mateos
stress_04 is missing a wait between blocks of tests, meaning multiple
ublk servers will be running in parallel using the same backing files.
Add a wait after each section to ensure each backing file is in use by a
single ublk server at a time.
Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
Reviewed-by: Ming Lei <ming.lei@redhat.com>
---
tools/testing/selftests/ublk/test_stress_04.sh | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/tools/testing/selftests/ublk/test_stress_04.sh b/tools/testing/selftests/ublk/test_stress_04.sh
index 965befcee830..c7220723b537 100755
--- a/tools/testing/selftests/ublk/test_stress_04.sh
+++ b/tools/testing/selftests/ublk/test_stress_04.sh
@@ -29,23 +29,25 @@ _create_backfile 1 128M
_create_backfile 2 128M
ublk_io_and_kill_daemon 8G -t null -q 4 -z --no_ublk_fixed_fd &
ublk_io_and_kill_daemon 256M -t loop -q 4 -z --no_ublk_fixed_fd "${UBLK_BACKFILES[0]}" &
ublk_io_and_kill_daemon 256M -t stripe -q 4 -z "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
+wait
if _have_feature "AUTO_BUF_REG"; then
ublk_io_and_kill_daemon 8G -t null -q 4 --auto_zc &
ublk_io_and_kill_daemon 256M -t loop -q 4 --auto_zc "${UBLK_BACKFILES[0]}" &
ublk_io_and_kill_daemon 256M -t stripe -q 4 --auto_zc --no_ublk_fixed_fd "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
ublk_io_and_kill_daemon 8G -t null -q 4 -z --auto_zc --auto_zc_fallback &
+ wait
fi
if _have_feature "PER_IO_DAEMON"; then
ublk_io_and_kill_daemon 8G -t null -q 4 --auto_zc --nthreads 8 --per_io_tasks &
ublk_io_and_kill_daemon 256M -t loop -q 4 --auto_zc --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[0]}" &
ublk_io_and_kill_daemon 256M -t stripe -q 4 --auto_zc --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
ublk_io_and_kill_daemon 8G -t null -q 4 --auto_zc --auto_zc_fallback --nthreads 8 --per_io_tasks &
+ wait
fi
-wait
_cleanup_test "stress"
_show_result $TID $ERR_CODE
--
2.45.2
^ permalink raw reply related [flat|nested] 16+ messages in thread
* [PATCH v2 6/8] selftests: ublk: forbid multiple data copy modes
2025-12-12 5:16 [PATCH v2 0/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
` (4 preceding siblings ...)
2025-12-12 5:16 ` [PATCH v2 5/8] selftests: ublk: don't share backing files between ublk servers Caleb Sander Mateos
@ 2025-12-12 5:16 ` Caleb Sander Mateos
2025-12-12 11:09 ` Ming Lei
2025-12-12 11:13 ` Ming Lei
2025-12-12 5:16 ` [PATCH v2 7/8] selftests: ublk: add support for user copy to kublk Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 8/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
7 siblings, 2 replies; 16+ messages in thread
From: Caleb Sander Mateos @ 2025-12-12 5:16 UTC (permalink / raw)
To: Ming Lei, Shuah Khan
Cc: linux-block, linux-kselftest, linux-kernel, Caleb Sander Mateos
The kublk mock ublk server allows multiple data copy mode arguments to
be passed on the command line (--zero_copy, --get_data, and --auto_zc).
The ublk device will be created with all the requested feature flags,
however kublk will only use one of the modes to interact with request
data (arbitrarily preferring auto_zc over zero_copy over get_data). To
clarify the intent of the test, don't allow multiple data copy modes to
be specified. --zero_copy and --auto_zc are allowed together for
--auto_zc_fallback, which uses both copy modes.
Don't set UBLK_F_USER_COPY for zero_copy, as it's a separate feature.
Fix the test cases in test_stress_05 passing --get_data along with
--zero_copy or --auto_zc.
Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
---
tools/testing/selftests/ublk/kublk.c | 11 ++++++++++-
tools/testing/selftests/ublk/test_stress_05.sh | 10 +++++-----
2 files changed, 15 insertions(+), 6 deletions(-)
diff --git a/tools/testing/selftests/ublk/kublk.c b/tools/testing/selftests/ublk/kublk.c
index f8fa102a627f..4dd02cb083ba 100644
--- a/tools/testing/selftests/ublk/kublk.c
+++ b/tools/testing/selftests/ublk/kublk.c
@@ -1611,11 +1611,11 @@ int main(int argc, char *argv[])
break;
case 'd':
ctx.queue_depth = strtol(optarg, NULL, 10);
break;
case 'z':
- ctx.flags |= UBLK_F_SUPPORT_ZERO_COPY | UBLK_F_USER_COPY;
+ ctx.flags |= UBLK_F_SUPPORT_ZERO_COPY;
break;
case 'r':
value = strtol(optarg, NULL, 10);
if (value)
ctx.flags |= UBLK_F_USER_RECOVERY;
@@ -1684,10 +1684,19 @@ int main(int argc, char *argv[])
"F_AUTO_BUF_REG nor F_SUPPORT_ZERO_COPY is enabled\n",
__func__);
return -EINVAL;
}
+ if (!!(ctx.flags & UBLK_F_NEED_GET_DATA) +
+ !!(ctx.flags & UBLK_F_USER_COPY) +
+ (ctx.flags & UBLK_F_SUPPORT_ZERO_COPY && !ctx.auto_zc_fallback) +
+ (ctx.flags & UBLK_F_AUTO_BUF_REG && !ctx.auto_zc_fallback) +
+ ctx.auto_zc_fallback > 1) {
+ fprintf(stderr, "too many data copy modes specified\n");
+ return -EINVAL;
+ }
+
i = optind;
while (i < argc && ctx.nr_files < MAX_BACK_FILES) {
ctx.files[ctx.nr_files++] = argv[i++];
}
diff --git a/tools/testing/selftests/ublk/test_stress_05.sh b/tools/testing/selftests/ublk/test_stress_05.sh
index 274295061042..68a194144302 100755
--- a/tools/testing/selftests/ublk/test_stress_05.sh
+++ b/tools/testing/selftests/ublk/test_stress_05.sh
@@ -56,21 +56,21 @@ for reissue in $(seq 0 1); do
wait
done
if _have_feature "ZERO_COPY"; then
for reissue in $(seq 0 1); do
- ublk_io_and_remove 8G -t null -q 4 -g -z -r 1 -i "$reissue" &
- ublk_io_and_remove 256M -t loop -q 4 -g -z -r 1 -i "$reissue" "${UBLK_BACKFILES[1]}" &
+ ublk_io_and_remove 8G -t null -q 4 -z -r 1 -i "$reissue" &
+ ublk_io_and_remove 256M -t loop -q 4 -z -r 1 -i "$reissue" "${UBLK_BACKFILES[1]}" &
wait
done
fi
if _have_feature "AUTO_BUF_REG"; then
for reissue in $(seq 0 1); do
- ublk_io_and_remove 8G -t null -q 4 -g --auto_zc -r 1 -i "$reissue" &
- ublk_io_and_remove 256M -t loop -q 4 -g --auto_zc -r 1 -i "$reissue" "${UBLK_BACKFILES[1]}" &
- ublk_io_and_remove 8G -t null -q 4 -g -z --auto_zc --auto_zc_fallback -r 1 -i "$reissue" &
+ ublk_io_and_remove 8G -t null -q 4 --auto_zc -r 1 -i "$reissue" &
+ ublk_io_and_remove 256M -t loop -q 4 --auto_zc -r 1 -i "$reissue" "${UBLK_BACKFILES[1]}" &
+ ublk_io_and_remove 8G -t null -q 4 -z --auto_zc --auto_zc_fallback -r 1 -i "$reissue" &
wait
done
fi
if _have_feature "PER_IO_DAEMON"; then
--
2.45.2
^ permalink raw reply related [flat|nested] 16+ messages in thread
* [PATCH v2 7/8] selftests: ublk: add support for user copy to kublk
2025-12-12 5:16 [PATCH v2 0/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
` (5 preceding siblings ...)
2025-12-12 5:16 ` [PATCH v2 6/8] selftests: ublk: forbid multiple data copy modes Caleb Sander Mateos
@ 2025-12-12 5:16 ` Caleb Sander Mateos
2025-12-12 11:16 ` Ming Lei
2025-12-12 5:16 ` [PATCH v2 8/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
7 siblings, 1 reply; 16+ messages in thread
From: Caleb Sander Mateos @ 2025-12-12 5:16 UTC (permalink / raw)
To: Ming Lei, Shuah Khan
Cc: linux-block, linux-kselftest, linux-kernel, Caleb Sander Mateos
The ublk selftests mock ublk server kublk supports every data copy mode
except user copy. Add support for user copy to kublk, enabled via the
--user_copy (-u) command line argument. On writes, issue pread() calls
to copy the write data into the ublk_io's buffer before dispatching the
write to the target implementation. On reads, issue pwrite() calls to
copy read data from the ublk_io's buffer before committing the request.
Copy in 2 KB chunks to provide some coverage of the offseting logic.
Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
---
tools/testing/selftests/ublk/file_backed.c | 7 +--
tools/testing/selftests/ublk/kublk.c | 53 ++++++++++++++++++++--
tools/testing/selftests/ublk/kublk.h | 11 +++++
tools/testing/selftests/ublk/stripe.c | 2 +-
4 files changed, 64 insertions(+), 9 deletions(-)
diff --git a/tools/testing/selftests/ublk/file_backed.c b/tools/testing/selftests/ublk/file_backed.c
index cd9fe69ecce2..269d5f124e06 100644
--- a/tools/testing/selftests/ublk/file_backed.c
+++ b/tools/testing/selftests/ublk/file_backed.c
@@ -32,12 +32,13 @@ static int loop_queue_tgt_rw_io(struct ublk_thread *t, struct ublk_queue *q,
{
unsigned ublk_op = ublksrv_get_op(iod);
unsigned zc = ublk_queue_use_zc(q);
unsigned auto_zc = ublk_queue_use_auto_zc(q);
enum io_uring_op op = ublk_to_uring_op(iod, zc | auto_zc);
+ struct ublk_io *io = ublk_get_io(q, tag);
struct io_uring_sqe *sqe[3];
- void *addr = (zc | auto_zc) ? NULL : (void *)iod->addr;
+ void *addr = io->buf_addr;
if (!zc || auto_zc) {
ublk_io_alloc_sqes(t, sqe, 1);
if (!sqe[0])
return -ENOMEM;
@@ -54,11 +55,11 @@ static int loop_queue_tgt_rw_io(struct ublk_thread *t, struct ublk_queue *q,
return 1;
}
ublk_io_alloc_sqes(t, sqe, 3);
- io_uring_prep_buf_register(sqe[0], q, tag, q->q_id, ublk_get_io(q, tag)->buf_index);
+ io_uring_prep_buf_register(sqe[0], q, tag, q->q_id, io->buf_index);
sqe[0]->flags |= IOSQE_CQE_SKIP_SUCCESS | IOSQE_IO_HARDLINK;
sqe[0]->user_data = build_user_data(tag,
ublk_cmd_op_nr(sqe[0]->cmd_op), 0, q->q_id, 1);
io_uring_prep_rw(op, sqe[1], ublk_get_registered_fd(q, 1) /*fds[1]*/, 0,
@@ -66,11 +67,11 @@ static int loop_queue_tgt_rw_io(struct ublk_thread *t, struct ublk_queue *q,
iod->start_sector << 9);
sqe[1]->buf_index = tag;
sqe[1]->flags |= IOSQE_FIXED_FILE | IOSQE_IO_HARDLINK;
sqe[1]->user_data = build_user_data(tag, ublk_op, 0, q->q_id, 1);
- io_uring_prep_buf_unregister(sqe[2], q, tag, q->q_id, ublk_get_io(q, tag)->buf_index);
+ io_uring_prep_buf_unregister(sqe[2], q, tag, q->q_id, io->buf_index);
sqe[2]->user_data = build_user_data(tag, ublk_cmd_op_nr(sqe[2]->cmd_op), 0, q->q_id, 1);
return 2;
}
diff --git a/tools/testing/selftests/ublk/kublk.c b/tools/testing/selftests/ublk/kublk.c
index 4dd02cb083ba..185ba553686a 100644
--- a/tools/testing/selftests/ublk/kublk.c
+++ b/tools/testing/selftests/ublk/kublk.c
@@ -594,10 +594,42 @@ static void ublk_set_auto_buf_reg(const struct ublk_queue *q,
buf.flags = UBLK_AUTO_BUF_REG_FALLBACK;
sqe->addr = ublk_auto_buf_reg_to_sqe_addr(&buf);
}
+/* Copy in pieces to test the buffer offset logic */
+#define UBLK_USER_COPY_LEN 2048
+
+static void ublk_user_copy(const struct ublk_io *io, __u8 match_ublk_op)
+{
+ const struct ublk_queue *q = ublk_io_to_queue(io);
+ const struct ublksrv_io_desc *iod = ublk_get_iod(q, io->tag);
+ __u64 off = ublk_user_copy_offset(q->q_id, io->tag);
+ __u8 ublk_op = ublksrv_get_op(iod);
+ __u32 len = iod->nr_sectors << 9;
+ void *addr = io->buf_addr;
+
+ if (ublk_op != match_ublk_op)
+ return;
+
+ while (len) {
+ __u32 copy_len = min(len, UBLK_USER_COPY_LEN);
+ ssize_t copied;
+
+ if (ublk_op == UBLK_IO_OP_WRITE)
+ copied = pread(q->ublk_fd, addr, copy_len, off);
+ else if (ublk_op == UBLK_IO_OP_READ)
+ copied = pwrite(q->ublk_fd, addr, copy_len, off);
+ else
+ assert(0);
+ assert(copied == (ssize_t)copy_len);
+ addr += copy_len;
+ off += copy_len;
+ len -= copy_len;
+ }
+}
+
int ublk_queue_io_cmd(struct ublk_thread *t, struct ublk_io *io)
{
struct ublk_queue *q = ublk_io_to_queue(io);
struct ublksrv_io_cmd *cmd;
struct io_uring_sqe *sqe[1];
@@ -616,13 +648,16 @@ int ublk_queue_io_cmd(struct ublk_thread *t, struct ublk_io *io)
(UBLKS_IO_NEED_FETCH_RQ | UBLKS_IO_NEED_COMMIT_RQ_COMP | UBLKS_IO_NEED_GET_DATA)))
return 0;
if (io->flags & UBLKS_IO_NEED_GET_DATA)
cmd_op = UBLK_U_IO_NEED_GET_DATA;
- else if (io->flags & UBLKS_IO_NEED_COMMIT_RQ_COMP)
+ else if (io->flags & UBLKS_IO_NEED_COMMIT_RQ_COMP) {
+ if (ublk_queue_use_user_copy(q))
+ ublk_user_copy(io, UBLK_IO_OP_READ);
+
cmd_op = UBLK_U_IO_COMMIT_AND_FETCH_REQ;
- else if (io->flags & UBLKS_IO_NEED_FETCH_RQ)
+ } else if (io->flags & UBLKS_IO_NEED_FETCH_RQ)
cmd_op = UBLK_U_IO_FETCH_REQ;
if (io_uring_sq_space_left(&t->ring) < 1)
io_uring_submit(&t->ring);
@@ -647,11 +682,11 @@ int ublk_queue_io_cmd(struct ublk_thread *t, struct ublk_io *io)
else
sqe[0]->flags = IOSQE_FIXED_FILE;
sqe[0]->rw_flags = 0;
cmd->tag = io->tag;
cmd->q_id = q->q_id;
- if (!ublk_queue_no_buf(q))
+ if (!ublk_queue_no_buf(q) && !ublk_queue_use_user_copy(q))
cmd->addr = (__u64) (uintptr_t) io->buf_addr;
else
cmd->addr = 0;
if (ublk_queue_use_auto_zc(q))
@@ -749,10 +784,14 @@ static void ublk_handle_uring_cmd(struct ublk_thread *t,
io->flags &= ~UBLKS_IO_NEED_FETCH_RQ;
}
if (cqe->res == UBLK_IO_RES_OK) {
assert(tag < q->q_depth);
+
+ if (ublk_queue_use_user_copy(q))
+ ublk_user_copy(io, UBLK_IO_OP_WRITE);
+
if (q->tgt_ops->queue_io)
q->tgt_ops->queue_io(t, q, tag);
} else if (cqe->res == UBLK_IO_RES_NEED_GET_DATA) {
io->flags |= UBLKS_IO_NEED_GET_DATA | UBLKS_IO_FREE;
ublk_queue_io_cmd(t, io);
@@ -1505,11 +1544,11 @@ static void __cmd_create_help(char *exe, bool recovery)
{
int i;
printf("%s %s -t [null|loop|stripe|fault_inject] [-q nr_queues] [-d depth] [-n dev_id]\n",
exe, recovery ? "recover" : "add");
- printf("\t[--foreground] [--quiet] [-z] [--auto_zc] [--auto_zc_fallback] [--debug_mask mask] [-r 0|1 ] [-g]\n");
+ printf("\t[--foreground] [--quiet] [-z] [--auto_zc] [--auto_zc_fallback] [--debug_mask mask] [-r 0|1] [-g] [-u]\n");
printf("\t[-e 0|1 ] [-i 0|1] [--no_ublk_fixed_fd]\n");
printf("\t[--nthreads threads] [--per_io_tasks]\n");
printf("\t[target options] [backfile1] [backfile2] ...\n");
printf("\tdefault: nr_queues=2(max 32), depth=128(max 1024), dev_id=-1(auto allocation)\n");
printf("\tdefault: nthreads=nr_queues");
@@ -1566,10 +1605,11 @@ int main(int argc, char *argv[])
{ "recovery_fail_io", 1, NULL, 'e'},
{ "recovery_reissue", 1, NULL, 'i'},
{ "get_data", 1, NULL, 'g'},
{ "auto_zc", 0, NULL, 0 },
{ "auto_zc_fallback", 0, NULL, 0 },
+ { "user_copy", 0, NULL, 'u'},
{ "size", 1, NULL, 's'},
{ "nthreads", 1, NULL, 0 },
{ "per_io_tasks", 0, NULL, 0 },
{ "no_ublk_fixed_fd", 0, NULL, 0 },
{ 0, 0, 0, 0 }
@@ -1591,11 +1631,11 @@ int main(int argc, char *argv[])
if (argc == 1)
return ret;
opterr = 0;
optind = 2;
- while ((opt = getopt_long(argc, argv, "t:n:d:q:r:e:i:s:gaz",
+ while ((opt = getopt_long(argc, argv, "t:n:d:q:r:e:i:s:gazu",
longopts, &option_idx)) != -1) {
switch (opt) {
case 'a':
ctx.all = 1;
break;
@@ -1631,10 +1671,13 @@ int main(int argc, char *argv[])
ctx.flags |= UBLK_F_USER_RECOVERY | UBLK_F_USER_RECOVERY_REISSUE;
break;
case 'g':
ctx.flags |= UBLK_F_NEED_GET_DATA;
break;
+ case 'u':
+ ctx.flags |= UBLK_F_USER_COPY;
+ break;
case 's':
ctx.size = strtoull(optarg, NULL, 10);
break;
case 0:
if (!strcmp(longopts[option_idx].name, "debug_mask"))
diff --git a/tools/testing/selftests/ublk/kublk.h b/tools/testing/selftests/ublk/kublk.h
index fe42705c6d42..fda72e19ef09 100644
--- a/tools/testing/selftests/ublk/kublk.h
+++ b/tools/testing/selftests/ublk/kublk.h
@@ -206,10 +206,16 @@ extern int ublk_queue_io_cmd(struct ublk_thread *t, struct ublk_io *io);
static inline int ublk_io_auto_zc_fallback(const struct ublksrv_io_desc *iod)
{
return !!(iod->op_flags & UBLK_IO_F_NEED_REG_BUF);
}
+static inline __u64 ublk_user_copy_offset(unsigned q_id, unsigned tag)
+{
+ return UBLKSRV_IO_BUF_OFFSET +
+ ((__u64)q_id << UBLK_QID_OFF | (__u64)tag << UBLK_TAG_OFF);
+}
+
static inline int is_target_io(__u64 user_data)
{
return (user_data & (1ULL << 63)) != 0;
}
@@ -403,10 +409,15 @@ static inline int ublk_queue_use_auto_zc(const struct ublk_queue *q)
static inline int ublk_queue_auto_zc_fallback(const struct ublk_queue *q)
{
return q->flags & UBLKS_Q_AUTO_BUF_REG_FALLBACK;
}
+static inline bool ublk_queue_use_user_copy(const struct ublk_queue *q)
+{
+ return !!(q->flags & UBLK_F_USER_COPY);
+}
+
static inline int ublk_queue_no_buf(const struct ublk_queue *q)
{
return ublk_queue_use_zc(q) || ublk_queue_use_auto_zc(q);
}
diff --git a/tools/testing/selftests/ublk/stripe.c b/tools/testing/selftests/ublk/stripe.c
index 791fa8dc1651..fd412e1f01c0 100644
--- a/tools/testing/selftests/ublk/stripe.c
+++ b/tools/testing/selftests/ublk/stripe.c
@@ -132,11 +132,11 @@ static int stripe_queue_tgt_rw_io(struct ublk_thread *t, struct ublk_queue *q,
enum io_uring_op op = stripe_to_uring_op(iod, zc | auto_zc);
struct io_uring_sqe *sqe[NR_STRIPE];
struct stripe_array *s = alloc_stripe_array(conf, iod);
struct ublk_io *io = ublk_get_io(q, tag);
int i, extra = zc ? 2 : 0;
- void *base = (zc | auto_zc) ? NULL : (void *)iod->addr;
+ void *base = io->buf_addr;
io->private_data = s;
calculate_stripe_array(conf, iod, s, base);
ublk_io_alloc_sqes(t, sqe, s->nr + extra);
--
2.45.2
^ permalink raw reply related [flat|nested] 16+ messages in thread
* [PATCH v2 8/8] selftests: ublk: add user copy test cases
2025-12-12 5:16 [PATCH v2 0/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
` (6 preceding siblings ...)
2025-12-12 5:16 ` [PATCH v2 7/8] selftests: ublk: add support for user copy to kublk Caleb Sander Mateos
@ 2025-12-12 5:16 ` Caleb Sander Mateos
2025-12-12 11:17 ` Ming Lei
7 siblings, 1 reply; 16+ messages in thread
From: Caleb Sander Mateos @ 2025-12-12 5:16 UTC (permalink / raw)
To: Ming Lei, Shuah Khan
Cc: linux-block, linux-kselftest, linux-kernel, Caleb Sander Mateos
The ublk selftests cover every data copy mode except user copy. Add
tests for user copy based on the existing test suite:
- generic_14 ("basic recover function verification (user copy)") based
on generic_04 and generic_05
- null_03 ("basic IO test with user copy") based on null_01 and null_02
- loop_06 ("write and verify over user copy") based on loop_01 and
loop_03
- loop_07 ("mkfs & mount & umount with user copy") based on loop_02 and
loop_04
- stripe_05 ("write and verify test on user copy") based on stripe_03
- stripe_06 ("mkfs & mount & umount on user copy") based on stripe_02
and stripe_04
- stress_06 ("run IO and remove device (user copy)") based on stress_01
and stress_03
- stress_07 ("run IO and kill ublk server (user copy)") based on
stress_02 and stress_04
Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
---
tools/testing/selftests/ublk/Makefile | 8 ++++
.../testing/selftests/ublk/test_generic_14.sh | 40 +++++++++++++++++++
tools/testing/selftests/ublk/test_loop_06.sh | 25 ++++++++++++
tools/testing/selftests/ublk/test_loop_07.sh | 21 ++++++++++
tools/testing/selftests/ublk/test_null_03.sh | 24 +++++++++++
.../testing/selftests/ublk/test_stress_06.sh | 39 ++++++++++++++++++
.../testing/selftests/ublk/test_stress_07.sh | 39 ++++++++++++++++++
.../testing/selftests/ublk/test_stripe_05.sh | 26 ++++++++++++
.../testing/selftests/ublk/test_stripe_06.sh | 21 ++++++++++
9 files changed, 243 insertions(+)
create mode 100755 tools/testing/selftests/ublk/test_generic_14.sh
create mode 100755 tools/testing/selftests/ublk/test_loop_06.sh
create mode 100755 tools/testing/selftests/ublk/test_loop_07.sh
create mode 100755 tools/testing/selftests/ublk/test_null_03.sh
create mode 100755 tools/testing/selftests/ublk/test_stress_06.sh
create mode 100755 tools/testing/selftests/ublk/test_stress_07.sh
create mode 100755 tools/testing/selftests/ublk/test_stripe_05.sh
create mode 100755 tools/testing/selftests/ublk/test_stripe_06.sh
diff --git a/tools/testing/selftests/ublk/Makefile b/tools/testing/selftests/ublk/Makefile
index 770269efe42a..837977b62417 100644
--- a/tools/testing/selftests/ublk/Makefile
+++ b/tools/testing/selftests/ublk/Makefile
@@ -19,28 +19,36 @@ TEST_PROGS += test_generic_08.sh
TEST_PROGS += test_generic_09.sh
TEST_PROGS += test_generic_10.sh
TEST_PROGS += test_generic_11.sh
TEST_PROGS += test_generic_12.sh
TEST_PROGS += test_generic_13.sh
+TEST_PROGS += test_generic_14.sh
TEST_PROGS += test_null_01.sh
TEST_PROGS += test_null_02.sh
+TEST_PROGS += test_null_03.sh
TEST_PROGS += test_loop_01.sh
TEST_PROGS += test_loop_02.sh
TEST_PROGS += test_loop_03.sh
TEST_PROGS += test_loop_04.sh
TEST_PROGS += test_loop_05.sh
+TEST_PROGS += test_loop_06.sh
+TEST_PROGS += test_loop_07.sh
TEST_PROGS += test_stripe_01.sh
TEST_PROGS += test_stripe_02.sh
TEST_PROGS += test_stripe_03.sh
TEST_PROGS += test_stripe_04.sh
+TEST_PROGS += test_stripe_05.sh
+TEST_PROGS += test_stripe_06.sh
TEST_PROGS += test_stress_01.sh
TEST_PROGS += test_stress_02.sh
TEST_PROGS += test_stress_03.sh
TEST_PROGS += test_stress_04.sh
TEST_PROGS += test_stress_05.sh
+TEST_PROGS += test_stress_06.sh
+TEST_PROGS += test_stress_07.sh
TEST_GEN_PROGS_EXTENDED = kublk
include ../lib.mk
diff --git a/tools/testing/selftests/ublk/test_generic_14.sh b/tools/testing/selftests/ublk/test_generic_14.sh
new file mode 100755
index 000000000000..cd9b44b97c24
--- /dev/null
+++ b/tools/testing/selftests/ublk/test_generic_14.sh
@@ -0,0 +1,40 @@
+#!/bin/bash
+# SPDX-License-Identifier: GPL-2.0
+
+. "$(cd "$(dirname "$0")" && pwd)"/test_common.sh
+
+TID="generic_14"
+ERR_CODE=0
+
+ublk_run_recover_test()
+{
+ run_io_and_recover 256M "kill_daemon" "$@"
+ ERR_CODE=$?
+ if [ ${ERR_CODE} -ne 0 ]; then
+ echo "$TID failure: $*"
+ _show_result $TID $ERR_CODE
+ fi
+}
+
+if ! _have_program fio; then
+ exit "$UBLK_SKIP_CODE"
+fi
+
+_prep_test "recover" "basic recover function verification (user copy)"
+
+_create_backfile 0 256M
+_create_backfile 1 128M
+_create_backfile 2 128M
+
+ublk_run_recover_test -t null -q 2 -r 1 -u &
+ublk_run_recover_test -t loop -q 2 -r 1 -u "${UBLK_BACKFILES[0]}" &
+ublk_run_recover_test -t stripe -q 2 -r 1 -u "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
+wait
+
+ublk_run_recover_test -t null -q 2 -r 1 -u -i 1 &
+ublk_run_recover_test -t loop -q 2 -r 1 -u -i 1 "${UBLK_BACKFILES[0]}" &
+ublk_run_recover_test -t stripe -q 2 -r 1 -u -i 1 "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
+wait
+
+_cleanup_test "recover"
+_show_result $TID $ERR_CODE
diff --git a/tools/testing/selftests/ublk/test_loop_06.sh b/tools/testing/selftests/ublk/test_loop_06.sh
new file mode 100755
index 000000000000..1d1a8a725502
--- /dev/null
+++ b/tools/testing/selftests/ublk/test_loop_06.sh
@@ -0,0 +1,25 @@
+#!/bin/bash
+# SPDX-License-Identifier: GPL-2.0
+
+. "$(cd "$(dirname "$0")" && pwd)"/test_common.sh
+
+TID="loop_06"
+ERR_CODE=0
+
+if ! _have_program fio; then
+ exit "$UBLK_SKIP_CODE"
+fi
+
+_prep_test "loop" "write and verify over user copy"
+
+_create_backfile 0 256M
+dev_id=$(_add_ublk_dev -t loop -u "${UBLK_BACKFILES[0]}")
+_check_add_dev $TID $?
+
+# run fio over the ublk disk
+_run_fio_verify_io --filename=/dev/ublkb"${dev_id}" --size=256M
+ERR_CODE=$?
+
+_cleanup_test "loop"
+
+_show_result $TID $ERR_CODE
diff --git a/tools/testing/selftests/ublk/test_loop_07.sh b/tools/testing/selftests/ublk/test_loop_07.sh
new file mode 100755
index 000000000000..493f3fb611a5
--- /dev/null
+++ b/tools/testing/selftests/ublk/test_loop_07.sh
@@ -0,0 +1,21 @@
+#!/bin/bash
+# SPDX-License-Identifier: GPL-2.0
+
+. "$(cd "$(dirname "$0")" && pwd)"/test_common.sh
+
+TID="loop_07"
+ERR_CODE=0
+
+_prep_test "loop" "mkfs & mount & umount with user copy"
+
+_create_backfile 0 256M
+
+dev_id=$(_add_ublk_dev -t loop -u "${UBLK_BACKFILES[0]}")
+_check_add_dev $TID $?
+
+_mkfs_mount_test /dev/ublkb"${dev_id}"
+ERR_CODE=$?
+
+_cleanup_test "loop"
+
+_show_result $TID $ERR_CODE
diff --git a/tools/testing/selftests/ublk/test_null_03.sh b/tools/testing/selftests/ublk/test_null_03.sh
new file mode 100755
index 000000000000..0051067b4686
--- /dev/null
+++ b/tools/testing/selftests/ublk/test_null_03.sh
@@ -0,0 +1,24 @@
+#!/bin/bash
+# SPDX-License-Identifier: GPL-2.0
+
+. "$(cd "$(dirname "$0")" && pwd)"/test_common.sh
+
+TID="null_03"
+ERR_CODE=0
+
+if ! _have_program fio; then
+ exit "$UBLK_SKIP_CODE"
+fi
+
+_prep_test "null" "basic IO test with user copy"
+
+dev_id=$(_add_ublk_dev -t null -u)
+_check_add_dev $TID $?
+
+# run fio over the two disks
+fio --name=job1 --filename=/dev/ublkb"${dev_id}" --ioengine=libaio --rw=readwrite --iodepth=32 --size=256M > /dev/null 2>&1
+ERR_CODE=$?
+
+_cleanup_test "null"
+
+_show_result $TID $ERR_CODE
diff --git a/tools/testing/selftests/ublk/test_stress_06.sh b/tools/testing/selftests/ublk/test_stress_06.sh
new file mode 100755
index 000000000000..37188ec2e1f7
--- /dev/null
+++ b/tools/testing/selftests/ublk/test_stress_06.sh
@@ -0,0 +1,39 @@
+#!/bin/bash
+# SPDX-License-Identifier: GPL-2.0
+
+. "$(cd "$(dirname "$0")" && pwd)"/test_common.sh
+TID="stress_06"
+ERR_CODE=0
+
+ublk_io_and_remove()
+{
+ run_io_and_remove "$@"
+ ERR_CODE=$?
+ if [ ${ERR_CODE} -ne 0 ]; then
+ echo "$TID failure: $*"
+ _show_result $TID $ERR_CODE
+ fi
+}
+
+if ! _have_program fio; then
+ exit "$UBLK_SKIP_CODE"
+fi
+
+_prep_test "stress" "run IO and remove device (user copy)"
+
+_create_backfile 0 256M
+_create_backfile 1 128M
+_create_backfile 2 128M
+
+ublk_io_and_remove 8G -t null -q 4 -u &
+ublk_io_and_remove 256M -t loop -q 4 -u "${UBLK_BACKFILES[0]}" &
+ublk_io_and_remove 256M -t stripe -q 4 -u "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
+wait
+
+ublk_io_and_remove 8G -t null -q 4 -u --nthreads 8 --per_io_tasks &
+ublk_io_and_remove 256M -t loop -q 4 -u --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[0]}" &
+ublk_io_and_remove 256M -t stripe -q 4 -u --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
+wait
+
+_cleanup_test "stress"
+_show_result $TID $ERR_CODE
diff --git a/tools/testing/selftests/ublk/test_stress_07.sh b/tools/testing/selftests/ublk/test_stress_07.sh
new file mode 100755
index 000000000000..fb061fc26d36
--- /dev/null
+++ b/tools/testing/selftests/ublk/test_stress_07.sh
@@ -0,0 +1,39 @@
+#!/bin/bash
+# SPDX-License-Identifier: GPL-2.0
+
+. "$(cd "$(dirname "$0")" && pwd)"/test_common.sh
+TID="stress_07"
+ERR_CODE=0
+
+ublk_io_and_kill_daemon()
+{
+ run_io_and_kill_daemon "$@"
+ ERR_CODE=$?
+ if [ ${ERR_CODE} -ne 0 ]; then
+ echo "$TID failure: $*"
+ _show_result $TID $ERR_CODE
+ fi
+}
+
+if ! _have_program fio; then
+ exit "$UBLK_SKIP_CODE"
+fi
+
+_prep_test "stress" "run IO and kill ublk server (user copy)"
+
+_create_backfile 0 256M
+_create_backfile 1 128M
+_create_backfile 2 128M
+
+ublk_io_and_kill_daemon 8G -t null -q 4 -u --no_ublk_fixed_fd &
+ublk_io_and_kill_daemon 256M -t loop -q 4 -u --no_ublk_fixed_fd "${UBLK_BACKFILES[0]}" &
+ublk_io_and_kill_daemon 256M -t stripe -q 4 -u "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
+wait
+
+ublk_io_and_kill_daemon 8G -t null -q 4 -u --nthreads 8 --per_io_tasks &
+ublk_io_and_kill_daemon 256M -t loop -q 4 -u --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[0]}" &
+ublk_io_and_kill_daemon 256M -t stripe -q 4 -u --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
+wait
+
+_cleanup_test "stress"
+_show_result $TID $ERR_CODE
diff --git a/tools/testing/selftests/ublk/test_stripe_05.sh b/tools/testing/selftests/ublk/test_stripe_05.sh
new file mode 100755
index 000000000000..05d71951d710
--- /dev/null
+++ b/tools/testing/selftests/ublk/test_stripe_05.sh
@@ -0,0 +1,26 @@
+#!/bin/bash
+# SPDX-License-Identifier: GPL-2.0
+
+. "$(cd "$(dirname "$0")" && pwd)"/test_common.sh
+
+TID="stripe_05"
+ERR_CODE=0
+
+if ! _have_program fio; then
+ exit "$UBLK_SKIP_CODE"
+fi
+
+_prep_test "stripe" "write and verify test on user copy"
+
+_create_backfile 0 256M
+_create_backfile 1 256M
+
+dev_id=$(_add_ublk_dev -t stripe -q 2 -u "${UBLK_BACKFILES[0]}" "${UBLK_BACKFILES[1]}")
+_check_add_dev $TID $?
+
+# run fio over the ublk disk
+_run_fio_verify_io --filename=/dev/ublkb"${dev_id}" --size=512M
+ERR_CODE=$?
+
+_cleanup_test "stripe"
+_show_result $TID $ERR_CODE
diff --git a/tools/testing/selftests/ublk/test_stripe_06.sh b/tools/testing/selftests/ublk/test_stripe_06.sh
new file mode 100755
index 000000000000..d06cac7626e2
--- /dev/null
+++ b/tools/testing/selftests/ublk/test_stripe_06.sh
@@ -0,0 +1,21 @@
+#!/bin/bash
+# SPDX-License-Identifier: GPL-2.0
+
+. "$(cd "$(dirname "$0")" && pwd)"/test_common.sh
+
+TID="stripe_06"
+ERR_CODE=0
+
+_prep_test "stripe" "mkfs & mount & umount on user copy"
+
+_create_backfile 0 256M
+_create_backfile 1 256M
+
+dev_id=$(_add_ublk_dev -t stripe -u -q 2 "${UBLK_BACKFILES[0]}" "${UBLK_BACKFILES[1]}")
+_check_add_dev $TID $?
+
+_mkfs_mount_test /dev/ublkb"${dev_id}"
+ERR_CODE=$?
+
+_cleanup_test "stripe"
+_show_result $TID $ERR_CODE
--
2.45.2
^ permalink raw reply related [flat|nested] 16+ messages in thread
* Re: [PATCH v2 4/8] selftests: ublk: use auto_zc for PER_IO_DAEMON tests in stress_04
2025-12-12 5:16 ` [PATCH v2 4/8] selftests: ublk: use auto_zc for PER_IO_DAEMON tests in stress_04 Caleb Sander Mateos
@ 2025-12-12 10:21 ` Ming Lei
2025-12-12 10:56 ` Ming Lei
1 sibling, 0 replies; 16+ messages in thread
From: Ming Lei @ 2025-12-12 10:21 UTC (permalink / raw)
To: Caleb Sander Mateos
Cc: Shuah Khan, linux-block, linux-kselftest, linux-kernel
On Thu, Dec 11, 2025 at 10:16:54PM -0700, Caleb Sander Mateos wrote:
> stress_04 is described as "run IO and kill ublk server(zero copy)" but
> the --per_io_tasks tests cases don't use zero copy. Plus, one of the
> test cases is duplicated. Add --auto_zc to these test cases and
> --auto_zc_fallback to one of the duplicated ones. This matches the test
> cases in stress_03.
>
> Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
Reviewed-by: Ming Lei <ming.lei@redhat.com>
Thanks,
Ming
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [PATCH v2 4/8] selftests: ublk: use auto_zc for PER_IO_DAEMON tests in stress_04
2025-12-12 5:16 ` [PATCH v2 4/8] selftests: ublk: use auto_zc for PER_IO_DAEMON tests in stress_04 Caleb Sander Mateos
2025-12-12 10:21 ` Ming Lei
@ 2025-12-12 10:56 ` Ming Lei
2025-12-12 16:50 ` Caleb Sander Mateos
1 sibling, 1 reply; 16+ messages in thread
From: Ming Lei @ 2025-12-12 10:56 UTC (permalink / raw)
To: Caleb Sander Mateos
Cc: Shuah Khan, linux-block, linux-kselftest, linux-kernel
On Thu, Dec 11, 2025 at 10:16:54PM -0700, Caleb Sander Mateos wrote:
> stress_04 is described as "run IO and kill ublk server(zero copy)" but
> the --per_io_tasks tests cases don't use zero copy. Plus, one of the
> test cases is duplicated. Add --auto_zc to these test cases and
> --auto_zc_fallback to one of the duplicated ones. This matches the test
> cases in stress_03.
>
> Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
> ---
> tools/testing/selftests/ublk/test_stress_04.sh | 8 ++++----
> 1 file changed, 4 insertions(+), 4 deletions(-)
>
> diff --git a/tools/testing/selftests/ublk/test_stress_04.sh b/tools/testing/selftests/ublk/test_stress_04.sh
> index 3f901db4d09d..965befcee830 100755
> --- a/tools/testing/selftests/ublk/test_stress_04.sh
> +++ b/tools/testing/selftests/ublk/test_stress_04.sh
> @@ -38,14 +38,14 @@ if _have_feature "AUTO_BUF_REG"; then
> ublk_io_and_kill_daemon 256M -t stripe -q 4 --auto_zc --no_ublk_fixed_fd "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
> ublk_io_and_kill_daemon 8G -t null -q 4 -z --auto_zc --auto_zc_fallback &
> fi
>
> if _have_feature "PER_IO_DAEMON"; then
> - ublk_io_and_kill_daemon 8G -t null -q 4 --nthreads 8 --per_io_tasks &
> - ublk_io_and_kill_daemon 256M -t loop -q 4 --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[0]}" &
> - ublk_io_and_kill_daemon 256M -t stripe -q 4 --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
> - ublk_io_and_kill_daemon 8G -t null -q 4 --nthreads 8 --per_io_tasks &
> + ublk_io_and_kill_daemon 8G -t null -q 4 --auto_zc --nthreads 8 --per_io_tasks &
> + ublk_io_and_kill_daemon 256M -t loop -q 4 --auto_zc --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[0]}" &
> + ublk_io_and_kill_daemon 256M -t stripe -q 4 --auto_zc --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
> + ublk_io_and_kill_daemon 8G -t null -q 4 --auto_zc --auto_zc_fallback --nthreads 8 --per_io_tasks &
The last line needs `-z`, otherwise the following warning is dumped:
```
# selftests: ublk: test_stress_04.sh
# main: auto_zc_fallback is set but neither F_AUTO_BUF_REG nor F_SUPPORT_ZERO_COPY is enabled
# stress_04 : [FAIL]
```
Thanks,
Ming
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [PATCH v2 6/8] selftests: ublk: forbid multiple data copy modes
2025-12-12 5:16 ` [PATCH v2 6/8] selftests: ublk: forbid multiple data copy modes Caleb Sander Mateos
@ 2025-12-12 11:09 ` Ming Lei
2025-12-12 11:13 ` Ming Lei
1 sibling, 0 replies; 16+ messages in thread
From: Ming Lei @ 2025-12-12 11:09 UTC (permalink / raw)
To: Caleb Sander Mateos
Cc: Shuah Khan, linux-block, linux-kselftest, linux-kernel
On Thu, Dec 11, 2025 at 10:16:56PM -0700, Caleb Sander Mateos wrote:
> The kublk mock ublk server allows multiple data copy mode arguments to
> be passed on the command line (--zero_copy, --get_data, and --auto_zc).
> The ublk device will be created with all the requested feature flags,
> however kublk will only use one of the modes to interact with request
> data (arbitrarily preferring auto_zc over zero_copy over get_data). To
> clarify the intent of the test, don't allow multiple data copy modes to
> be specified. --zero_copy and --auto_zc are allowed together for
> --auto_zc_fallback, which uses both copy modes.
> Don't set UBLK_F_USER_COPY for zero_copy, as it's a separate feature.
> Fix the test cases in test_stress_05 passing --get_data along with
> --zero_copy or --auto_zc.
>
> Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
Reviewed-by: Ming Lei <ming.lei@redhat.com>
Thanks,
Ming
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [PATCH v2 6/8] selftests: ublk: forbid multiple data copy modes
2025-12-12 5:16 ` [PATCH v2 6/8] selftests: ublk: forbid multiple data copy modes Caleb Sander Mateos
2025-12-12 11:09 ` Ming Lei
@ 2025-12-12 11:13 ` Ming Lei
1 sibling, 0 replies; 16+ messages in thread
From: Ming Lei @ 2025-12-12 11:13 UTC (permalink / raw)
To: Caleb Sander Mateos
Cc: Shuah Khan, linux-block, linux-kselftest, linux-kernel
On Thu, Dec 11, 2025 at 10:16:56PM -0700, Caleb Sander Mateos wrote:
> The kublk mock ublk server allows multiple data copy mode arguments to
> be passed on the command line (--zero_copy, --get_data, and --auto_zc).
> The ublk device will be created with all the requested feature flags,
> however kublk will only use one of the modes to interact with request
> data (arbitrarily preferring auto_zc over zero_copy over get_data). To
> clarify the intent of the test, don't allow multiple data copy modes to
> be specified. --zero_copy and --auto_zc are allowed together for
> --auto_zc_fallback, which uses both copy modes.
> Don't set UBLK_F_USER_COPY for zero_copy, as it's a separate feature.
> Fix the test cases in test_stress_05 passing --get_data along with
> --zero_copy or --auto_zc.
>
> Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
Reviewed-by: Ming Lei <ming.lei@redhat.com>
Thanks,
Ming
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [PATCH v2 7/8] selftests: ublk: add support for user copy to kublk
2025-12-12 5:16 ` [PATCH v2 7/8] selftests: ublk: add support for user copy to kublk Caleb Sander Mateos
@ 2025-12-12 11:16 ` Ming Lei
0 siblings, 0 replies; 16+ messages in thread
From: Ming Lei @ 2025-12-12 11:16 UTC (permalink / raw)
To: Caleb Sander Mateos
Cc: Shuah Khan, linux-block, linux-kselftest, linux-kernel
On Thu, Dec 11, 2025 at 10:16:57PM -0700, Caleb Sander Mateos wrote:
> The ublk selftests mock ublk server kublk supports every data copy mode
> except user copy. Add support for user copy to kublk, enabled via the
> --user_copy (-u) command line argument. On writes, issue pread() calls
> to copy the write data into the ublk_io's buffer before dispatching the
> write to the target implementation. On reads, issue pwrite() calls to
> copy read data from the ublk_io's buffer before committing the request.
> Copy in 2 KB chunks to provide some coverage of the offseting logic.
>
> Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
Reviewed-by: Ming Lei <ming.lei@redhat.com>
Thanks,
Ming
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [PATCH v2 8/8] selftests: ublk: add user copy test cases
2025-12-12 5:16 ` [PATCH v2 8/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
@ 2025-12-12 11:17 ` Ming Lei
0 siblings, 0 replies; 16+ messages in thread
From: Ming Lei @ 2025-12-12 11:17 UTC (permalink / raw)
To: Caleb Sander Mateos
Cc: Shuah Khan, linux-block, linux-kselftest, linux-kernel
On Thu, Dec 11, 2025 at 10:16:58PM -0700, Caleb Sander Mateos wrote:
> The ublk selftests cover every data copy mode except user copy. Add
> tests for user copy based on the existing test suite:
> - generic_14 ("basic recover function verification (user copy)") based
> on generic_04 and generic_05
> - null_03 ("basic IO test with user copy") based on null_01 and null_02
> - loop_06 ("write and verify over user copy") based on loop_01 and
> loop_03
> - loop_07 ("mkfs & mount & umount with user copy") based on loop_02 and
> loop_04
> - stripe_05 ("write and verify test on user copy") based on stripe_03
> - stripe_06 ("mkfs & mount & umount on user copy") based on stripe_02
> and stripe_04
> - stress_06 ("run IO and remove device (user copy)") based on stress_01
> and stress_03
> - stress_07 ("run IO and kill ublk server (user copy)") based on
> stress_02 and stress_04
>
> Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
Reviewed-by: Ming Lei <ming.lei@redhat.com>
Thanks,
Ming
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [PATCH v2 4/8] selftests: ublk: use auto_zc for PER_IO_DAEMON tests in stress_04
2025-12-12 10:56 ` Ming Lei
@ 2025-12-12 16:50 ` Caleb Sander Mateos
0 siblings, 0 replies; 16+ messages in thread
From: Caleb Sander Mateos @ 2025-12-12 16:50 UTC (permalink / raw)
To: Ming Lei; +Cc: Shuah Khan, linux-block, linux-kselftest, linux-kernel
On Fri, Dec 12, 2025 at 2:56 AM Ming Lei <ming.lei@redhat.com> wrote:
>
> On Thu, Dec 11, 2025 at 10:16:54PM -0700, Caleb Sander Mateos wrote:
> > stress_04 is described as "run IO and kill ublk server(zero copy)" but
> > the --per_io_tasks tests cases don't use zero copy. Plus, one of the
> > test cases is duplicated. Add --auto_zc to these test cases and
> > --auto_zc_fallback to one of the duplicated ones. This matches the test
> > cases in stress_03.
> >
> > Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
> > ---
> > tools/testing/selftests/ublk/test_stress_04.sh | 8 ++++----
> > 1 file changed, 4 insertions(+), 4 deletions(-)
> >
> > diff --git a/tools/testing/selftests/ublk/test_stress_04.sh b/tools/testing/selftests/ublk/test_stress_04.sh
> > index 3f901db4d09d..965befcee830 100755
> > --- a/tools/testing/selftests/ublk/test_stress_04.sh
> > +++ b/tools/testing/selftests/ublk/test_stress_04.sh
> > @@ -38,14 +38,14 @@ if _have_feature "AUTO_BUF_REG"; then
> > ublk_io_and_kill_daemon 256M -t stripe -q 4 --auto_zc --no_ublk_fixed_fd "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
> > ublk_io_and_kill_daemon 8G -t null -q 4 -z --auto_zc --auto_zc_fallback &
> > fi
> >
> > if _have_feature "PER_IO_DAEMON"; then
> > - ublk_io_and_kill_daemon 8G -t null -q 4 --nthreads 8 --per_io_tasks &
> > - ublk_io_and_kill_daemon 256M -t loop -q 4 --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[0]}" &
> > - ublk_io_and_kill_daemon 256M -t stripe -q 4 --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
> > - ublk_io_and_kill_daemon 8G -t null -q 4 --nthreads 8 --per_io_tasks &
> > + ublk_io_and_kill_daemon 8G -t null -q 4 --auto_zc --nthreads 8 --per_io_tasks &
> > + ublk_io_and_kill_daemon 256M -t loop -q 4 --auto_zc --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[0]}" &
> > + ublk_io_and_kill_daemon 256M -t stripe -q 4 --auto_zc --nthreads 8 --per_io_tasks "${UBLK_BACKFILES[1]}" "${UBLK_BACKFILES[2]}" &
> > + ublk_io_and_kill_daemon 8G -t null -q 4 --auto_zc --auto_zc_fallback --nthreads 8 --per_io_tasks &
>
> The last line needs `-z`, otherwise the following warning is dumped:
>
> ```
> # selftests: ublk: test_stress_04.sh
> # main: auto_zc_fallback is set but neither F_AUTO_BUF_REG nor F_SUPPORT_ZERO_COPY is enabled
> # stress_04 : [FAIL]
> ```
Yeah, duh! I swear I tested this... Oh, it's because I had revised
this patch following your initial feedback but replaced it with the
version from v1 right before sending it. Will fix.
Thanks,
Caleb
^ permalink raw reply [flat|nested] 16+ messages in thread
end of thread, other threads:[~2025-12-12 16:50 UTC | newest]
Thread overview: 16+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2025-12-12 5:16 [PATCH v2 0/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 1/8] selftests: ublk: correct last_rw map type in seq_io.bt Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 2/8] selftests: ublk: remove unused ios map " Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 3/8] selftests: ublk: fix fio arguments in run_io_and_recover() Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 4/8] selftests: ublk: use auto_zc for PER_IO_DAEMON tests in stress_04 Caleb Sander Mateos
2025-12-12 10:21 ` Ming Lei
2025-12-12 10:56 ` Ming Lei
2025-12-12 16:50 ` Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 5/8] selftests: ublk: don't share backing files between ublk servers Caleb Sander Mateos
2025-12-12 5:16 ` [PATCH v2 6/8] selftests: ublk: forbid multiple data copy modes Caleb Sander Mateos
2025-12-12 11:09 ` Ming Lei
2025-12-12 11:13 ` Ming Lei
2025-12-12 5:16 ` [PATCH v2 7/8] selftests: ublk: add support for user copy to kublk Caleb Sander Mateos
2025-12-12 11:16 ` Ming Lei
2025-12-12 5:16 ` [PATCH v2 8/8] selftests: ublk: add user copy test cases Caleb Sander Mateos
2025-12-12 11:17 ` Ming Lei
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).