3 # Copyright (C) 2016 Julien Desfossez <jdesfossez@efficios.com>
5 # SPDX-License-Identifier: GPL-2.0-only
8 TEST_DESC
="Kernel tracer - select, poll and epoll payload extraction"
10 CURDIR
=$
(dirname "$0")/
12 VALIDATE_SCRIPT
="$CURDIR/validate_select_poll_epoll.py"
15 # Only run this test on x86 and arm
16 uname
-m |
grep -E "x86|i686|arm|aarch64" >/dev
/null
2>&1
22 # Babeltrace python bindings are required for the validation, but
23 # it is not a mandatory dependancy of the project, so fail run the
24 # without the content validation, at least we test that we are not
25 # crashing the kernel.
26 $VALIDATE_SCRIPT --help >/dev
/null
2>&1
28 echo "# Failed to run the validation script, Babeltrace Python bindings might be missing"
32 LAST_WARNING
=$
(dmesg |
grep " WARNING:" | cut
-d' ' -f1 |
tail -1)
33 LAST_OOPS
=$
(dmesg |
grep " OOPS:" | cut
-d' ' -f1 |
tail -1)
34 LAST_BUG
=$
(dmesg |
grep " BUG:" | cut
-d' ' -f1 |
tail -1)
36 # shellcheck source=../../utils/utils.sh
37 source $TESTDIR/utils
/utils.sh
39 function check_trace_content
()
41 if test $DISABLE_VALIDATE == 1; then
42 ok
0 "Validation skipped"
48 ok
0 "Validation success"
54 function test_working_cases
()
56 SESSION_NAME
="syscall_payload"
57 TRACE_PATH
=$
(mktemp
--tmpdir -d "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_trace_path.XXXXXX")
58 TEST_VALIDATION_OUTPUT_PATH
=$
(mktemp
--tmpdir -u "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_validation.XXXXXX")
60 # arm64 does not have epoll_wait
61 uname
-m |
grep -E "aarch64" >/dev
/null
2>&1
63 SYSCALL_LIST
="select,pselect6,poll,ppoll,epoll_ctl,epoll_pwait"
65 SYSCALL_LIST
="select,pselect6,poll,ppoll,epoll_ctl,epoll_wait,epoll_pwait"
68 diag
"Working cases for select, pselect6, poll, ppoll and epoll, waiting for input"
70 create_lttng_session_ok
$SESSION_NAME "$TRACE_PATH"
72 lttng_enable_kernel_syscall_ok
$SESSION_NAME $SYSCALL_LIST
73 add_context_kernel_ok
$SESSION_NAME channel0 pid
75 start_lttng_tracing_ok
76 yes |
"$CURDIR"/select_poll_epoll
--validation-file "$TEST_VALIDATION_OUTPUT_PATH" -t 1
79 validate_trace
"$SYSCALL_LIST" "$TRACE_PATH"
80 check_trace_content
-t 1 --validation-file "$TEST_VALIDATION_OUTPUT_PATH" "$TRACE_PATH"
82 destroy_lttng_session_ok
$SESSION_NAME
85 rm -f "$TEST_VALIDATION_OUTPUT_PATH"
88 function test_timeout_cases
()
90 SESSION_NAME
="syscall_payload"
91 TRACE_PATH
=$
(mktemp
--tmpdir -d "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_trace_path.XXXXXX")
92 TEST_VALIDATION_OUTPUT_PATH
=$
(mktemp
--tmpdir -u "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_validation.XXXXXX")
94 # arm64 does not have epoll_wait
95 uname
-m |
grep -E "aarch64" >/dev
/null
2>&1
97 SYSCALL_LIST
="select,pselect6,poll,ppoll,epoll_ctl,epoll_pwait"
99 SYSCALL_LIST
="select,pselect6,poll,ppoll,epoll_ctl,epoll_wait,epoll_pwait"
102 diag
"Timeout cases (1ms) for select, pselect6, poll, ppoll and epoll"
104 create_lttng_session_ok
$SESSION_NAME "$TRACE_PATH"
106 lttng_enable_kernel_syscall_ok
$SESSION_NAME "$SYSCALL_LIST"
107 add_context_kernel_ok
$SESSION_NAME channel0 pid
109 start_lttng_tracing_ok
110 yes |
"$CURDIR"/select_poll_epoll
--validation-file "$TEST_VALIDATION_OUTPUT_PATH" -t 2
111 stop_lttng_tracing_ok
113 validate_trace
"$SYSCALL_LIST" "$TRACE_PATH"
114 check_trace_content
-t 2 --validation-file "$TEST_VALIDATION_OUTPUT_PATH" "$TRACE_PATH" 2>/dev
/null
116 destroy_lttng_session_ok
$SESSION_NAME
119 rm -f "$TEST_VALIDATION_OUTPUT_PATH"
122 function test_pselect_invalid_fd
()
124 SESSION_NAME
="syscall_payload"
125 SYSCALL_LIST
="pselect6"
126 TRACE_PATH
=$
(mktemp
--tmpdir -d "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_trace_path.XXXXXX")
127 TEST_VALIDATION_OUTPUT_PATH
=$
(mktemp
--tmpdir -u "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_validation.XXXXXX")
129 diag
"pselect with invalid FD"
131 create_lttng_session_ok
$SESSION_NAME "$TRACE_PATH"
133 lttng_enable_kernel_syscall_ok
$SESSION_NAME $SYSCALL_LIST
134 add_context_kernel_ok
$SESSION_NAME channel0 pid
136 start_lttng_tracing_ok
137 yes |
"$CURDIR"/select_poll_epoll
--validation-file "$TEST_VALIDATION_OUTPUT_PATH" -t 3
138 stop_lttng_tracing_ok
140 validate_trace
"$SYSCALL_LIST" "$TRACE_PATH"
141 check_trace_content
-t 3 --validation-file "$TEST_VALIDATION_OUTPUT_PATH" "$TRACE_PATH" 2>/dev
/null
143 destroy_lttng_session_ok
$SESSION_NAME
146 rm -f "$TEST_VALIDATION_OUTPUT_PATH"
149 function test_big_ppoll
()
151 SESSION_NAME
="syscall_payload"
153 TRACE_PATH
=$
(mktemp
--tmpdir -d "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_trace_path.XXXXXX")
154 TEST_VALIDATION_OUTPUT_PATH
=$
(mktemp
--tmpdir -u "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_validation.XXXXXX")
156 diag
"ppoll with 2047 FDs"
158 create_lttng_session_ok
$SESSION_NAME "$TRACE_PATH"
160 lttng_enable_kernel_syscall_ok
$SESSION_NAME $SYSCALL_LIST
161 add_context_kernel_ok
$SESSION_NAME channel0 pid
163 start_lttng_tracing_ok
164 yes |
"$CURDIR"/select_poll_epoll
--validation-file "$TEST_VALIDATION_OUTPUT_PATH" -t 4
165 stop_lttng_tracing_ok
167 validate_trace
"$SYSCALL_LIST" "$TRACE_PATH"
168 check_trace_content
-t 4 --validation-file "$TEST_VALIDATION_OUTPUT_PATH" "$TRACE_PATH" 2>/dev
/null
170 destroy_lttng_session_ok
$SESSION_NAME
173 rm -f "$TEST_VALIDATION_OUTPUT_PATH"
176 function test_ppoll_overflow
()
178 SESSION_NAME
="syscall_payload"
180 TRACE_PATH
=$
(mktemp
--tmpdir -d "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_trace_path.XXXXXX")
181 TEST_VALIDATION_OUTPUT_PATH
=$
(mktemp
--tmpdir -u "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_validation.XXXXXX")
183 diag
"ppoll buffer overflow, should segfault, waits for input"
185 create_lttng_session_ok
$SESSION_NAME "$TRACE_PATH"
187 lttng_enable_kernel_syscall_ok
$SESSION_NAME $SYSCALL_LIST
188 add_context_kernel_ok
$SESSION_NAME channel0 pid
190 start_lttng_tracing_ok
191 diag
"Expect segfaults"
192 yes |
"$CURDIR"/select_poll_epoll
--validation-file "$TEST_VALIDATION_OUTPUT_PATH" -t 5
193 stop_lttng_tracing_ok
195 validate_trace
"$SYSCALL_LIST" "$TRACE_PATH"
197 check_trace_content
-t 5 --validation-file "$TEST_VALIDATION_OUTPUT_PATH" "$TRACE_PATH" 2>/dev
/null
199 destroy_lttng_session_ok
$SESSION_NAME
202 rm -f "$TEST_VALIDATION_OUTPUT_PATH"
205 function test_pselect_invalid_ptr
()
207 SESSION_NAME
="syscall_payload"
208 SYSCALL_LIST
="pselect6"
209 TRACE_PATH
=$
(mktemp
--tmpdir -d "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_trace_path.XXXXXX")
210 TEST_VALIDATION_OUTPUT_PATH
=$
(mktemp
--tmpdir -u "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_validation.XXXXXX")
212 diag
"pselect with invalid pointer, waits for input"
214 create_lttng_session_ok
$SESSION_NAME "$TRACE_PATH"
216 lttng_enable_kernel_syscall_ok
$SESSION_NAME $SYSCALL_LIST
217 add_context_kernel_ok
$SESSION_NAME channel0 pid
219 start_lttng_tracing_ok
220 yes |
"$CURDIR"/select_poll_epoll
--validation-file "$TEST_VALIDATION_OUTPUT_PATH" -t 6
221 stop_lttng_tracing_ok
223 validate_trace
"$SYSCALL_LIST" "$TRACE_PATH"
224 check_trace_content
-t 6 --validation-file "$TEST_VALIDATION_OUTPUT_PATH" "$TRACE_PATH" 2>/dev
/null
226 destroy_lttng_session_ok
$SESSION_NAME
229 rm -f "$TEST_VALIDATION_OUTPUT_PATH"
232 function test_ppoll_ulong_max
()
234 SESSION_NAME
="syscall_payload"
236 TRACE_PATH
=$
(mktemp
--tmpdir -d "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_trace_path.XXXXXX")
237 TEST_VALIDATION_OUTPUT_PATH
=$
(mktemp
--tmpdir -u "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_validation.XXXXXX")
239 diag
"ppoll with ulong_max fds, waits for input"
241 create_lttng_session_ok
$SESSION_NAME "$TRACE_PATH"
243 lttng_enable_kernel_syscall_ok
$SESSION_NAME $SYSCALL_LIST
244 add_context_kernel_ok
$SESSION_NAME channel0 pid
246 start_lttng_tracing_ok
247 yes |
"$CURDIR"/select_poll_epoll
--validation-file "$TEST_VALIDATION_OUTPUT_PATH" -t 7
248 stop_lttng_tracing_ok
250 validate_trace
"$SYSCALL_LIST" "$TRACE_PATH"
251 check_trace_content
-t 7 --validation-file "$TEST_VALIDATION_OUTPUT_PATH" "$TRACE_PATH" 2>/dev
/null
253 destroy_lttng_session_ok
$SESSION_NAME
256 rm -f "$TEST_VALIDATION_OUTPUT_PATH"
259 function test_epoll_pwait_invalid_ptr
()
261 SESSION_NAME
="syscall_payload"
262 SYSCALL_LIST
="epoll_pwait"
263 TRACE_PATH
=$
(mktemp
--tmpdir -d "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_trace_path.XXXXXX")
264 TEST_VALIDATION_OUTPUT_PATH
=$
(mktemp
--tmpdir -u "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_validation.XXXXXX")
266 diag
"epoll_pwait with invalid pointer, waits for input"
268 create_lttng_session_ok
$SESSION_NAME "$TRACE_PATH"
270 lttng_enable_kernel_syscall_ok
$SESSION_NAME $SYSCALL_LIST
271 add_context_kernel_ok
$SESSION_NAME channel0 pid
273 start_lttng_tracing_ok
274 yes |
"$CURDIR"/select_poll_epoll
--validation-file "$TEST_VALIDATION_OUTPUT_PATH" -t 8
275 stop_lttng_tracing_ok
277 validate_trace
"$SYSCALL_LIST" "$TRACE_PATH"
278 check_trace_content
-t 8 --validation-file "$TEST_VALIDATION_OUTPUT_PATH" "$TRACE_PATH" 2>/dev
/null
280 destroy_lttng_session_ok
$SESSION_NAME
283 rm -f "$TEST_VALIDATION_OUTPUT_PATH"
286 function test_epoll_pwait_int_max
()
288 SESSION_NAME
="syscall_payload"
289 SYSCALL_LIST
="epoll_pwait"
290 TRACE_PATH
=$
(mktemp
--tmpdir -d "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_trace_path.XXXXXX")
291 TEST_VALIDATION_OUTPUT_PATH
=$
(mktemp
--tmpdir -u "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_validation.XXXXXX")
293 diag
"epoll_pwait with maxevents set to INT_MAX, waits for input"
295 create_lttng_session_ok
$SESSION_NAME "$TRACE_PATH"
297 lttng_enable_kernel_syscall_ok
$SESSION_NAME $SYSCALL_LIST
298 add_context_kernel_ok
$SESSION_NAME channel0 pid
300 start_lttng_tracing_ok
301 yes |
"$CURDIR"/select_poll_epoll
--validation-file "$TEST_VALIDATION_OUTPUT_PATH" -t 9
302 stop_lttng_tracing_ok
304 validate_trace
"$SYSCALL_LIST" "$TRACE_PATH"
305 check_trace_content
-t 9 --validation-file "$TEST_VALIDATION_OUTPUT_PATH" "$TRACE_PATH" 2>/dev
/null
307 destroy_lttng_session_ok
$SESSION_NAME
310 rm -f "$TEST_VALIDATION_OUTPUT_PATH"
313 function test_ppoll_concurrent
()
315 SESSION_NAME
="syscall_payload"
317 TRACE_PATH
=$
(mktemp
--tmpdir -d "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_trace_path.XXXXXX")
318 TEST_VALIDATION_OUTPUT_PATH
=$
(mktemp
--tmpdir -u "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_validation.XXXXXX")
320 diag
"ppoll with concurrent updates of the structure from user-space, stress test (3000 iterations), waits for input + timeout 1ms"
322 create_lttng_session_ok
$SESSION_NAME "$TRACE_PATH"
324 lttng_enable_kernel_syscall_ok
$SESSION_NAME $SYSCALL_LIST
325 add_context_kernel_ok
$SESSION_NAME channel0 pid
327 start_lttng_tracing_ok
328 yes |
"$CURDIR"/select_poll_epoll
--validation-file "$TEST_VALIDATION_OUTPUT_PATH" -t 10
329 stop_lttng_tracing_ok
331 validate_trace
"$SYSCALL_LIST" "$TRACE_PATH"
332 check_trace_content
-t 10 --validation-file "$TEST_VALIDATION_OUTPUT_PATH" "$TRACE_PATH" 2>/dev
/null
334 destroy_lttng_session_ok
$SESSION_NAME
337 rm -f "$TEST_VALIDATION_OUTPUT_PATH"
340 function test_epoll_pwait_concurrent
()
342 SESSION_NAME
="syscall_payload"
343 SYSCALL_LIST
="epoll_ctl,epoll_pwait"
344 TRACE_PATH
=$
(mktemp
--tmpdir -d "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_trace_path.XXXXXX")
345 TEST_VALIDATION_OUTPUT_PATH
=$
(mktemp
--tmpdir -u "tmp.test_kernel_select_poll_epoll_${FUNCNAME[0]}_validation.XXXXXX")
347 diag
"epoll_pwait with concurrent munmap of the buffer from user-space, should randomly segfault, run multiple times, waits for input + timeout 1ms"
349 create_lttng_session_ok
$SESSION_NAME "$TRACE_PATH"
351 lttng_enable_kernel_syscall_ok
$SESSION_NAME $SYSCALL_LIST
352 add_context_kernel_ok
$SESSION_NAME channel0 pid
354 start_lttng_tracing_ok
355 diag
"Expect segfaults"
356 for i
in $
(seq 1 100); do
357 yes |
"$CURDIR"/select_poll_epoll
--validation-file "$TEST_VALIDATION_OUTPUT_PATH" -t 11
359 stop_lttng_tracing_ok
361 # epoll_wait is not always generated in the trace (stress test)
362 validate_trace
"epoll_ctl" "$TRACE_PATH"
363 check_trace_content
-t 11 --validation-file "$TEST_VALIDATION_OUTPUT_PATH" "$TRACE_PATH" 2>/dev
/null
365 destroy_lttng_session_ok
$SESSION_NAME
368 rm -f "$TEST_VALIDATION_OUTPUT_PATH"
371 # MUST set TESTDIR before calling those functions
372 plan_tests
$NUM_TESTS
374 print_test_banner
"$TEST_DESC"
376 if [ "$(id -u)" == "0" ]; then
382 skip
$isroot "Root access is needed. Skipping all tests." $NUM_TESTS ||
384 validate_lttng_modules_present
390 test_pselect_invalid_fd
393 test_pselect_invalid_ptr
395 test_epoll_pwait_invalid_ptr
396 test_epoll_pwait_int_max
397 test_ppoll_concurrent
398 test_epoll_pwait_concurrent
402 NEW_WARNING
=$
(dmesg |
grep " WARNING:" | cut
-d' ' -f1 |
tail -1)
403 NEW_OOPS
=$
(dmesg |
grep " OOPS:" | cut
-d' ' -f1 |
tail -1)
404 NEW_BUG
=$
(dmesg |
grep " BUG:" | cut
-d' ' -f1 |
tail -1)
406 if test "$LAST_WARNING" != "$NEW_WARNING"; then
407 fail
"New WARNING generated"
409 if test "$LAST_OOPS" != "$NEW_OOPS"; then
410 fail
"New OOPS generated"
412 if test "$LAST_BUG" != "$NEW_BUG"; then
413 fail
"New BUG generated"