1# This testcase is part of GDB, the GNU debugger. 2 3# Copyright 2004 Free Software Foundation, Inc. 4 5# This program is free software; you can redistribute it and/or modify 6# it under the terms of the GNU General Public License as published by 7# the Free Software Foundation; either version 2 of the License, or 8# (at your option) any later version. 9# 10# This program is distributed in the hope that it will be useful, 11# but WITHOUT ANY WARRANTY; without even the implied warranty of 12# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13# GNU General Public License for more details. 14# 15# You should have received a copy of the GNU General Public License 16# along with this program; if not, write to the Free Software 17# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 18 19# Check that GDB can trigger and backtrace SIGSEGV signal stacks 20# caused by both accessing (data) and executing (code) at address 21# zero. 22 23# On function descriptor architectures, a zero descriptor, instead of 24# a NULL pointer, is used. That way the NULL code test always 25# contains a zero code reference. 26 27# For recovery, sigjmp/longjmp are used. 28 29# This also tests backtrace/gdb1476. 30 31if $tracelevel { 32 strace $tracelevel 33} 34 35set prms_id 0 36set bug_id 0 37 38set testfile "signull" 39set srcfile ${testfile}.c 40set binfile ${objdir}/${subdir}/${testfile} 41if { [gdb_compile "${srcdir}/${subdir}/${srcfile}" "${binfile}" executable {debug}] != "" } { 42 gdb_suppress_entire_file "Testcase compile failed, so all tests in this file will automatically fail." 43} 44 45gdb_exit 46gdb_start 47gdb_reinitialize_dir $srcdir/$subdir 48gdb_load ${binfile} 49 50# 51# Run to `main' where we begin our tests. 52# 53 54if ![runto_main] then { 55 gdb_suppress_tests 56} 57 58# If we can examine what's at memory address 0, it is possible that we 59# could also execute it. This could probably make us run away, 60# executing random code, which could have all sorts of ill effects, 61# especially on targets without an MMU. Don't run the tests in that 62# case. 63 64send_gdb "x 0\n" 65gdb_expect { 66 -re "0x0:.*Cannot access memory at address 0x0.*$gdb_prompt $" { } 67 -re "0x0:.*Error accessing memory address 0x0.*$gdb_prompt $" { } 68 -re ".*$gdb_prompt $" { 69 untested "Memory at address 0 is possibly executable" 70 return 71 } 72} 73 74# If an attempt to call a NULL pointer leaves the inferior in main, 75# then function pointers are descriptors, probe this and remember the 76# result. 77 78gdb_test "set test = code_entry_point" "" "set for function pointer probe" 79set test "probe function pointer" 80set function_pointer code_entry_point 81gdb_test_multiple "continue" "$test" { 82 -re "Program received signal SIGSEGV.*bowler .*$gdb_prompt $" { 83 set function_pointer code_descriptor 84 pass "$test (function descriptor)" 85 } 86 -re "Program received signal SIGSEGV.*0.*$gdb_prompt $" { 87 pass "$test (function entry-point)" 88 } 89} 90 91# Re-start from scratch, breakpoint the bowler so that control is 92# regained after each test, and run up to that. 93rerun_to_main 94gdb_test "break bowler" 95gdb_test "break keeper" 96# By default Stop:Yes Print:Yes Pass:Yes 97gdb_test "handle SIGSEGV" "SIGSEGV.*Yes.*Yes.*Yes.*Segmentation fault" 98 99# For the given signal type, check that: the SIGSEGV occures; a 100# backtrace from the SEGV works; the sigsegv is delivered; a backtrace 101# through the SEGV works. 102 103proc test_segv { name tag bt_from_segv bt_from_keeper } { 104 gdb_test continue "Breakpoint.* bowler.*" "${name}; start with the bowler" 105 # NB: Don't use $tag in the testname - changes across systems. 106 gdb_test "set test = $tag" "" "${name}; select the pointer type" 107 gdb_test continue "Program received signal SIGSEGV.*" \ 108 "${name}; take the SIGSEGV" 109 gdb_test backtrace $bt_from_segv "${name}; backtrace from SIGSEGV" 110 gdb_test continue "Breakpoint.* keeper.*" "${name}; continue to the keeper" 111 gdb_test backtrace $bt_from_keeper "${name}; backtrace from keeper through SIGSEGV" 112} 113 114test_segv "data read" data_read \ 115 {#0 .* bowler .*#1 .* main .*} \ 116 {#0 .* keeper .*#1 .* handler .*#2 .* bowler .*#3 .* main .*} 117test_segv "data write" data_write \ 118 {#0 .* bowler .*#1 .* main .*} \ 119 {#0 .* keeper .*#1 .* handler .*#2 .* bowler .*#3 .* main .*} 120test_segv code $function_pointer \ 121 {#0 .* 0x0+ .*#1 .* bowler .*#2 .* main .*} \ 122 {#0 .* keeper .*#1 .* handler .*#2 .* 0x0+ .*#3 .* bowler .*#4 .* main .*} 123