1# Copyright 2013-2023 Free Software Foundation, Inc. 2 3# This program is free software; you can redistribute it and/or modify 4# it under the terms of the GNU General Public License as published by 5# the Free Software Foundation; either version 3 of the License, or 6# (at your option) any later version. 7# 8# This program is distributed in the hope that it will be useful, 9# but WITHOUT ANY WARRANTY; without even the implied warranty of 10# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11# GNU General Public License for more details. 12# 13# You should have received a copy of the GNU General Public License 14# along with this program. If not, see <http://www.gnu.org/licenses/>. 15 16# Test relies on checking gdb debug output. Do not run if gdb debug is 17# enabled as any debug will be redirected to the log. 18if [gdb_debug_enabled] { 19 untested "debug is enabled" 20 return 0 21} 22 23standard_testfile 24set executable ${testfile} 25 26if { [gdb_compile_pthreads \ 27 "${srcdir}/${subdir}/${srcfile}" \ 28 "${binfile}" \ 29 executable {debug}] != "" } { 30 untested "failed to compile" 31 return -1 32} 33 34clean_restart $executable 35 36# Start the second thread. 37if ![runto start] { 38 return -1 39} 40 41# Go back to the main thread, and leave it in the loop, where we're 42# reasonably sure we don't have 'conditional jmp $pc'-like 43# instructions. We wouldn't be able to detect whether a stepi makes 44# progress over those. 45gdb_test_no_output "set scheduler-locking on" 46gdb_test "thread 1" "Switching to .*" 47gdb_breakpoint $srcfile:[gdb_get_line_number "set break 2 here"] 48gdb_continue_to_breakpoint "loop" ".* set break 2 here .*" 49 50# Now back to thread 2, and let it queue a signal in thread 1. 51gdb_test "thread 2" "Switching to .*" 52gdb_breakpoint $srcfile:[gdb_get_line_number "set break here"] 53gdb_continue_to_breakpoint "after pthread_kill" ".* set break here .*" 54 55# We're now ready to stepi thread 1. It should immediately dequeue 56# the signal. 57gdb_test "thread 1" "Switching to .*" "thread 1 again" 58 59# No longer need these. 60delete_breakpoints 61 62# Turn on infrun debugging, so we can tell whether the signal is 63# really dequeued and that GDB sees it. 64gdb_test_no_output "set debug infrun 1" 65 66# Make sure the target backend reports the signal to GDB core. Some 67# backends (like Linux) skip reporting a signal if set to 68# pass/nostop/noprint, resuming the thread immediately instead. 69gdb_test "handle SIGCHLD print" 70 71# Helper to extract the current PC. PREFIX is used to make each call 72# have its own unique test name. 73 74proc get_pc { prefix } { 75 with_test_prefix "$prefix" { 76 return [get_hexadecimal_valueof "\$pc" ""] 77 } 78} 79 80set prev_addr [get_pc "before stepi"] 81if {$prev_addr == ""} { 82 return 83} 84 85# True if we saw the infrun path we want to test be exercised. 86set seen 0 87 88set test "stepi" 89set prompt "$gdb_prompt \\\[infrun\\\] fetch_inferior_event: exit\r\n$" 90if {[gdb_test_multiple "stepi" "$test" -prompt $prompt { 91 -re {\[infrun\] handle_signal_stop: random signal} { 92 set seen 1 93 exp_continue 94 } 95 -re "$prompt$" { 96 } 97}] != 0} { 98 return 99} 100 101if {$seen} { 102 pass "$test" 103} else { 104 fail "$test (no random signal)" 105} 106 107set addr [get_pc "after stepi"] 108if {$addr == ""} { 109 return 110} 111 112set test "stepi interfered by signal makes progress" 113if {$addr == $prev_addr} { 114 fail "$test" 115} else { 116 pass "$test" 117} 118