1# Copyright 2003-2013 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 17# This is a regression test for the following bug, as of 2003-12-12: 18# 19# Set a breakpoint which will be hit many times. Attach a complex set 20# of commands to it, including a "continue" command. Run the program, 21# so that the breakpoint is hit, its commands get executed, and the 22# program continues and hits the breakpoint again. You will see 23# messages like "warning: Invalid control type in command structure.", 24# or maybe GDB will crash. 25# 26# When the breakpoint is hit, bpstat_stop_status copies the 27# breakpoint's command tree to the bpstat. bpstat_do_actions then 28# calls execute_control_command to run the commands. The 'continue' 29# command invokes the following chain of calls: 30# 31# continue_command 32# -> clear_proceed_status 33# -> bpstat_clear 34# -> free_command_lines 35# -> frees the commands we are currently running. 36# 37# When control does eventually return to execute_control_command, GDB 38# continues to walk the tree of freed command nodes, resulting in the 39# error messages and / or crashes. 40# 41# Since this bug depends on storage being reused between the time that 42# we continue and the time that we fall back to bpstat_do_actions, the 43# reproduction recipe is more delicate than I would like. I welcome 44# suggestions for improving this. 45 46 47set testfile "freebpcmd" 48set srcfile ${testfile}.c 49set binfile ${objdir}/${subdir}/${testfile} 50 51if { [gdb_compile "${srcdir}/${subdir}/${srcfile}" "${binfile}" executable {debug}] != "" } { 52 untested freebpcmd.exp 53 return -1 54} 55 56gdb_exit 57gdb_start 58gdb_reinitialize_dir $srcdir/$subdir 59gdb_load ${binfile} 60 61gdb_test "break ${srcfile}:[gdb_get_line_number "euphonium"]" ".*" \ 62 "set breakpoint" 63 64# The goal of all this is to make sure that there's plenty of memory 65# churn, and different amounts of it each time the inferior stops; 66# this seems to make GDB crash more reliably. 67set lines {{if i<0 || i > 100} 68 {echo Invalid i value\n} 69 {else} 70 {if (i%2) == 0} 71 {echo "even "} 72 {print i} 73 {else} 74 {echo "odd "} 75 {print i} 76 {end} 77 {set variable $foo = 0} 78 {set variable $j = 0} 79 {while $j < i} 80 {set variable $foo += $j} 81 {set variable $j++} 82 {end} 83 {print $foo} 84 {if i != 40} 85 {c} 86 {end} 87 {end} 88 {end}} 89 90send_gdb "commands\n" 91for {set i 0} {$i < [llength $lines]} {incr i} { 92 gdb_expect { 93 -re ".*>" { 94 send_gdb "[lindex $lines $i]\n" 95 } 96 -re "$gdb_prompt $" { 97 set reason "got top-level prompt early" 98 break 99 } 100 timeout { 101 set reason "timeout" 102 break 103 } 104 } 105} 106if {$i >= [llength $lines]} { 107 pass "send breakpoint commands" 108} else { 109 fail "send breakpoint commands ($reason)" 110} 111 112gdb_run_cmd 113 114set prev_timeout $timeout 115set timeout 120 116 117gdb_test_multiple "" "run program with breakpoint commands" { 118 -re "warning: Invalid control type in command structure" { 119 kfail "gdb/1489" "run program with breakpoint commands" 120 } 121 -re "Invalid i value\r\n$gdb_prompt $" { 122 xfail "run program with breakpoint commands (i value not readable)" 123 } 124 -re "$gdb_prompt $" { 125 pass "run program with breakpoint commands" 126 } 127 eof { 128 kfail "gdb/1489" "run program with breakpoint commands (GDB died)" 129 } 130} 131 132set timeout $prev_timeout 133