Skip to content

Commit ad45510

Browse files
Thomas Gleixnergregkh
authored andcommitted
selftests/rseq: Expand for optimized RSEQ ABI v2
commit e744060 upstream. Update the selftests so they are executed for legacy (32 bytes RSEQ region) and optimized RSEQ ABI v2 mode. Fixes: d620024 ("rseq: Allow registering RSEQ with slice extension") Signed-off-by: Thomas Gleixner <tglx@kernel.org> Signed-off-by: Peter Zijlstra (Intel) <peterz@infradead.org> Reviewed-by: Dmitry Vyukov <dvyukov@google.com> Tested-by: Dmitry Vyukov <dvyukov@google.com> Link: https://patch.msgid.link/20260428224428.009121296%40kernel.org Cc: stable@vger.kernel.org Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
1 parent a23a114 commit ad45510

6 files changed

Lines changed: 95 additions & 13 deletions

File tree

tools/testing/selftests/rseq/Makefile

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -15,17 +15,19 @@ LDLIBS += -lpthread -ldl
1515
OVERRIDE_TARGETS = 1
1616

1717
TEST_GEN_PROGS = basic_test basic_percpu_ops_test basic_percpu_ops_mm_cid_test \
18-
param_test_benchmark param_test_mm_cid_benchmark slice_test
18+
param_test_benchmark param_test_mm_cid_benchmark
1919

2020
TEST_GEN_PROGS_EXTENDED = librseq.so \
2121
param_test \
2222
param_test_compare_twice \
2323
param_test_mm_cid \
2424
param_test_mm_cid_compare_twice \
2525
syscall_errors_test \
26-
legacy_check
26+
legacy_check \
27+
slice_test \
28+
check_optimized
2729

28-
TEST_PROGS = run_param_test.sh run_syscall_errors_test.sh run_legacy_check.sh
30+
TEST_PROGS = run_param_test.sh run_syscall_errors_test.sh run_legacy_check.sh run_timeslice_test.sh
2931

3032
TEST_FILES := settings
3133

@@ -66,3 +68,6 @@ $(OUTPUT)/syscall_errors_test: syscall_errors_test.c $(TEST_GEN_PROGS_EXTENDED)
6668

6769
$(OUTPUT)/slice_test: slice_test.c $(TEST_GEN_PROGS_EXTENDED) rseq.h rseq-*.h
6870
$(CC) $(CFLAGS) $< $(LDLIBS) -lrseq -o $@
71+
72+
$(OUTPUT)/check_optimized: check_optimized.c $(TEST_GEN_PROGS_EXTENDED) rseq.h rseq-*.h
73+
$(CC) $(CFLAGS) $< $(LDLIBS) -lrseq -o $@
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// SPDX-License-Identifier: LGPL-2.1
2+
#define _GNU_SOURCE
3+
#include <assert.h>
4+
#include <sched.h>
5+
#include <signal.h>
6+
#include <stdio.h>
7+
#include <string.h>
8+
#include <sys/time.h>
9+
10+
#include "rseq.h"
11+
12+
int main(int argc, char **argv)
13+
{
14+
if (__rseq_register_current_thread(true, false))
15+
return -1;
16+
return 0;
17+
}

tools/testing/selftests/rseq/param_test.c

Lines changed: 16 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@ static int opt_modulo, verbose;
3838
static int opt_yield, opt_signal, opt_sleep,
3939
opt_disable_rseq, opt_threads = 200,
4040
opt_disable_mod = 0, opt_test = 's';
41-
41+
static bool opt_rseq_legacy;
4242
static long long opt_reps = 5000;
4343

4444
static __thread __attribute__((tls_model("initial-exec")))
@@ -281,9 +281,12 @@ unsigned int yield_mod_cnt, nr_abort;
281281
} \
282282
}
283283

284+
#define rseq_no_glibc true
285+
284286
#else
285287

286288
#define printf_verbose(fmt, ...)
289+
#define rseq_no_glibc false
287290

288291
#endif /* BENCHMARK */
289292

@@ -481,7 +484,7 @@ void *test_percpu_spinlock_thread(void *arg)
481484
long long i, reps;
482485

483486
if (!opt_disable_rseq && thread_data->reg &&
484-
rseq_register_current_thread())
487+
__rseq_register_current_thread(rseq_no_glibc, opt_rseq_legacy))
485488
abort();
486489
reps = thread_data->reps;
487490
for (i = 0; i < reps; i++) {
@@ -558,7 +561,7 @@ void *test_percpu_inc_thread(void *arg)
558561
long long i, reps;
559562

560563
if (!opt_disable_rseq && thread_data->reg &&
561-
rseq_register_current_thread())
564+
__rseq_register_current_thread(rseq_no_glibc, opt_rseq_legacy))
562565
abort();
563566
reps = thread_data->reps;
564567
for (i = 0; i < reps; i++) {
@@ -712,7 +715,7 @@ void *test_percpu_list_thread(void *arg)
712715
long long i, reps;
713716
struct percpu_list *list = (struct percpu_list *)arg;
714717

715-
if (!opt_disable_rseq && rseq_register_current_thread())
718+
if (!opt_disable_rseq && __rseq_register_current_thread(rseq_no_glibc, opt_rseq_legacy))
716719
abort();
717720

718721
reps = opt_reps;
@@ -895,7 +898,7 @@ void *test_percpu_buffer_thread(void *arg)
895898
long long i, reps;
896899
struct percpu_buffer *buffer = (struct percpu_buffer *)arg;
897900

898-
if (!opt_disable_rseq && rseq_register_current_thread())
901+
if (!opt_disable_rseq && __rseq_register_current_thread(rseq_no_glibc, opt_rseq_legacy))
899902
abort();
900903

901904
reps = opt_reps;
@@ -1105,7 +1108,7 @@ void *test_percpu_memcpy_buffer_thread(void *arg)
11051108
long long i, reps;
11061109
struct percpu_memcpy_buffer *buffer = (struct percpu_memcpy_buffer *)arg;
11071110

1108-
if (!opt_disable_rseq && rseq_register_current_thread())
1111+
if (!opt_disable_rseq && __rseq_register_current_thread(rseq_no_glibc, opt_rseq_legacy))
11091112
abort();
11101113

11111114
reps = opt_reps;
@@ -1258,7 +1261,7 @@ void *test_membarrier_worker_thread(void *arg)
12581261
const int iters = opt_reps;
12591262
int i;
12601263

1261-
if (rseq_register_current_thread()) {
1264+
if (__rseq_register_current_thread(rseq_no_glibc, opt_rseq_legacy)) {
12621265
fprintf(stderr, "Error: rseq_register_current_thread(...) failed(%d): %s\n",
12631266
errno, strerror(errno));
12641267
abort();
@@ -1323,7 +1326,7 @@ void *test_membarrier_manager_thread(void *arg)
13231326
intptr_t expect_a = 0, expect_b = 0;
13241327
int cpu_a = 0, cpu_b = 0;
13251328

1326-
if (rseq_register_current_thread()) {
1329+
if (__rseq_register_current_thread(rseq_no_glibc, opt_rseq_legacy)) {
13271330
fprintf(stderr, "Error: rseq_register_current_thread(...) failed(%d): %s\n",
13281331
errno, strerror(errno));
13291332
abort();
@@ -1475,6 +1478,7 @@ static void show_usage(int argc, char **argv)
14751478
printf(" [-D M] Disable rseq for each M threads\n");
14761479
printf(" [-T test] Choose test: (s)pinlock, (l)ist, (b)uffer, (m)emcpy, (i)ncrement, membarrie(r)\n");
14771480
printf(" [-M] Push into buffer and memcpy buffer with memory barriers.\n");
1481+
printf(" [-O] Test with optimized RSEQ\n");
14781482
printf(" [-v] Verbose output.\n");
14791483
printf(" [-h] Show this help.\n");
14801484
printf("\n");
@@ -1602,6 +1606,9 @@ int main(int argc, char **argv)
16021606
case 'M':
16031607
opt_mo = RSEQ_MO_RELEASE;
16041608
break;
1609+
case 'L':
1610+
opt_rseq_legacy = true;
1611+
break;
16051612
default:
16061613
show_usage(argc, argv);
16071614
goto error;
@@ -1618,7 +1625,7 @@ int main(int argc, char **argv)
16181625
if (set_signal_handler())
16191626
goto error;
16201627

1621-
if (!opt_disable_rseq && rseq_register_current_thread())
1628+
if (!opt_disable_rseq && __rseq_register_current_thread(rseq_no_glibc, opt_rseq_legacy))
16221629
goto error;
16231630
if (!opt_disable_rseq && !rseq_validate_cpu_id()) {
16241631
fprintf(stderr, "Error: cpu id getter unavailable\n");

tools/testing/selftests/rseq/run_param_test.sh

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,11 @@ REPS=1000
3434
SLOW_REPS=100
3535
NR_THREADS=$((6*${NR_CPUS}))
3636

37+
# Prevent GLIBC from registering RSEQ so the selftest can run in legacy and
38+
# performance optimized mode.
39+
GLIBC_TUNABLES="${GLIBC_TUNABLES:-}:glibc.pthread.rseq=0"
40+
export GLIBC_TUNABLES
41+
3742
function do_tests()
3843
{
3944
local i=0
@@ -103,6 +108,40 @@ function inject_blocking()
103108
NR_LOOPS=
104109
}
105110

111+
echo "Testing in legacy RSEQ mode"
112+
echo "Yield injection (25%)"
113+
inject_blocking -m 4 -y -L
114+
115+
echo "Yield injection (50%)"
116+
inject_blocking -m 2 -y -L
117+
118+
echo "Yield injection (100%)"
119+
inject_blocking -m 1 -y -L
120+
121+
echo "Kill injection (25%)"
122+
inject_blocking -m 4 -k -L
123+
124+
echo "Kill injection (50%)"
125+
inject_blocking -m 2 -k -L
126+
127+
echo "Kill injection (100%)"
128+
inject_blocking -m 1 -k -L
129+
130+
echo "Sleep injection (1ms, 25%)"
131+
inject_blocking -m 4 -s 1 -L
132+
133+
echo "Sleep injection (1ms, 50%)"
134+
inject_blocking -m 2 -s 1 -L
135+
136+
echo "Sleep injection (1ms, 100%)"
137+
inject_blocking -m 1 -s 1 -L
138+
139+
./check_optimized || {
140+
echo "Skipping optimized RSEQ mode test. Not supported";
141+
exit 0
142+
}
143+
144+
echo "Testing in optimized RSEQ mode"
106145
echo "Yield injection (25%)"
107146
inject_blocking -m 4 -y
108147

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
#!/bin/bash
2+
# SPDX-License-Identifier: GPL-2.0+
3+
4+
# Prevent GLIBC from registering RSEQ so the selftest can run in legacy
5+
# and performance optimized mode.
6+
GLIBC_TUNABLES="${GLIBC_TUNABLES:-}:glibc.pthread.rseq=0"
7+
export GLIBC_TUNABLES
8+
9+
./check_optimized || {
10+
echo "Skipping optimized RSEQ mode test. Not supported";
11+
exit 0
12+
}
13+
14+
./slice_test

tools/testing/selftests/rseq/slice_test.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -124,7 +124,7 @@ FIXTURE_SETUP(slice_ext)
124124
{
125125
cpu_set_t affinity;
126126

127-
if (rseq_register_current_thread())
127+
if (__rseq_register_current_thread(true, false))
128128
SKIP(return, "RSEQ not supported\n");
129129

130130
if (prctl(PR_RSEQ_SLICE_EXTENSION, PR_RSEQ_SLICE_EXTENSION_SET,

0 commit comments

Comments
 (0)