From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 13081 invoked by alias); 11 Apr 2013 02:44:05 -0000 Mailing-List: contact gdb-patches-help@sourceware.org; run by ezmlm Precedence: bulk List-Id: List-Subscribe: List-Archive: List-Post: List-Help: , Sender: gdb-patches-owner@sourceware.org Received: (qmail 13039 invoked by uid 89); 11 Apr 2013 02:44:05 -0000 X-Spam-SWARE-Status: No, score=-3.8 required=5.0 tests=AWL,BAYES_00,KAM_STOCKGEN,KHOP_RCVD_UNTRUST,KHOP_THREADED,RCVD_IN_HOSTKARMA_W,RCVD_IN_HOSTKARMA_WL,TW_XP autolearn=no version=3.3.1 Received: from relay1.mentorg.com (HELO relay1.mentorg.com) (192.94.38.131) by sourceware.org (qpsmtpd/0.84/v0.84-167-ge50287c) with ESMTP; Thu, 11 Apr 2013 02:44:03 +0000 Received: from svr-orw-fem-01.mgc.mentorg.com ([147.34.98.93]) by relay1.mentorg.com with esmtp id 1UQ7UX-00037C-MG from Yao_Qi@mentor.com for gdb-patches@sourceware.org; Wed, 10 Apr 2013 19:44:01 -0700 Received: from SVR-ORW-FEM-04.mgc.mentorg.com ([147.34.97.41]) by svr-orw-fem-01.mgc.mentorg.com over TLS secured channel with Microsoft SMTPSVC(6.0.3790.4675); Wed, 10 Apr 2013 19:44:00 -0700 Received: from qiyao.dyndns.org.dyndns.org (147.34.91.1) by svr-orw-fem-04.mgc.mentorg.com (147.34.97.41) with Microsoft SMTP Server id 14.1.289.1; Wed, 10 Apr 2013 19:44:00 -0700 From: Yao Qi To: Subject: [PATCH 6/7] range stepping: test case Date: Thu, 11 Apr 2013 06:38:00 -0000 Message-ID: <1365648222-12540-7-git-send-email-yao@codesourcery.com> In-Reply-To: <1365648222-12540-1-git-send-email-yao@codesourcery.com> References: <1363006291-13334-1-git-send-email-yao@codesourcery.com> <1365648222-12540-1-git-send-email-yao@codesourcery.com> MIME-Version: 1.0 Content-Type: text/plain X-SW-Source: 2013-04/txt/msg00303.txt.bz2 This test case is used to verify range stepping is used by means of checking the internalvar '$range_stepping_counter'. In V2, the test cases check the value of '$range_stepping_counter' instead of parsing RSP packets. gdb/testsuite: 2013-04-10 Yao Qi * gdb.base/range-stepping.c: New. * gdb.base/range-stepping.exp: New. * gdb.trace/range-stepping.c: New. * gdb.trace/range-stepping.exp: New. --- gdb/testsuite/gdb.base/range-stepping.c | 69 +++++++++ gdb/testsuite/gdb.base/range-stepping.exp | 222 ++++++++++++++++++++++++++++ gdb/testsuite/gdb.trace/range-stepping.c | 61 ++++++++ gdb/testsuite/gdb.trace/range-stepping.exp | 89 +++++++++++ 4 files changed, 441 insertions(+), 0 deletions(-) create mode 100644 gdb/testsuite/gdb.base/range-stepping.c create mode 100644 gdb/testsuite/gdb.base/range-stepping.exp create mode 100644 gdb/testsuite/gdb.trace/range-stepping.c create mode 100644 gdb/testsuite/gdb.trace/range-stepping.exp diff --git a/gdb/testsuite/gdb.base/range-stepping.c b/gdb/testsuite/gdb.base/range-stepping.c new file mode 100644 index 0000000..930cb8d --- /dev/null +++ b/gdb/testsuite/gdb.base/range-stepping.c @@ -0,0 +1,69 @@ +/* This testcase is part of GDB, the GNU debugger. + + Copyright 2013 Free Software Foundation, Inc. + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . */ + +static int +func1 (int a, int b) +{ + int r = a * b; + + r =+ (a | b); + r =+ (a - b); + + return r; +} + +int +main(void) +{ + int a = 0; + int b = 1; + int c = 2; + int d = 3; + int e = 4; + double d1 = 1.0; + double d2 = 2.0; + + /* A line of source will be generated to a number of + instructions by compiler. */ + a = b + c + d * e - a; /* location 1 */ + + /* To compose multiple instructions before and after + 'function call' or 'branch' instruction. This line + of source will be generated to the following instructions, + +addr1: + insn1; + insn2; + ... + call func1; + ... + insn3; +addr2: + insn4; */ + e = 10 + func1 (a + b, c * d); /* location 2 */ + + e = 10 + func1 (a + b, c * d); + /* Generate a range that includes a loop in it. */ + for (a = 0, e = 0; a < 15; a++) { e += a;} + /* Generate a range that includes a loop in it. */ + for (a = 0, e = 0; a < 15; a++) { e += a;} + /* Generate a range that includes a loop, which is time consuming. + Variable C is used to terminate the loop earlier when GDB + wants. */ + for (c = 1, a = 0; a < 65535 && c; a++) {for (b = 0; b < 65535 && c; b++) { d1 = d2 * a / b; d2 = d1 * a;}} + return 0; +} diff --git a/gdb/testsuite/gdb.base/range-stepping.exp b/gdb/testsuite/gdb.base/range-stepping.exp new file mode 100644 index 0000000..0f2a2dd --- /dev/null +++ b/gdb/testsuite/gdb.base/range-stepping.exp @@ -0,0 +1,222 @@ +# Copyright 2013 Free Software Foundation, Inc. + +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . + +standard_testfile .c +set executable $testfile + +if { [gdb_compile "${srcdir}/${subdir}/${srcfile}" "${binfile}" \ + executable {debug nowarnings}] != "" } { + untested ${testfile}.exp + return -1 +} + +clean_restart $executable + +if ![runto_main] { + fail "Can't run to main" + return -1 +} + +# Check range stepping is supported by target or not. +set test "range-stepping is supported" +gdb_test_multiple "maintenance show range-stepping" "show range-stepping" { + -re "Debugger's willingness to do range-stepping is off.*\r\n$gdb_prompt $" { + unsupported $test + return -1 + } + -re "Debugger's willingness to do range-stepping is on.*\r\n$gdb_prompt $" { + pass $test + } +} + +# Check range stepping can step a range of multiple instructions. + +with_test_prefix "multi insns" { + global executable + global hex decimal + global gdb_prompt + + gdb_breakpoint [gdb_get_line_number "location 1"] + gdb_continue_to_breakpoint "location 1" + + set pc_before_stepping "" + set test "pc before stepping" + gdb_test_multiple "print/x \$pc" $test { + -re "\\\$$decimal = (\[^\r\n\]*)\r\n$gdb_prompt $" { + set pc_before_stepping $expect_out(1,string) + pass $test + } + } + + # When execute command "next", GDB should send one vCont;s and + # vCont;r and receive two stop replies. + # --> vCont;s (step over breakpoint) + # <-- T0505:XXX + # --> vCont;rSTART,END (do range stepping) + # <-- T0505:XXX + gdb_test_no_output "set \$range_stepping_counter = 0" "" + gdb_test "next" + gdb_test "p \$range_stepping_counter" " = 1" + + set pc_after_stepping "" + set msg "pc before stepping" + gdb_test_multiple "print/x \$pc" $msg { + -re "\\\$$decimal = (\[^\r\n\]*)\r\n$gdb_prompt $" { + set pc_after_stepping $expect_out(1,string) + pass $msg + } + } + + # At least, there are two instructions between + # PC_BEFORE_STEPPING and PC_AFTER_STEPPING. + gdb_test "disassemble ${pc_before_stepping},${pc_after_stepping}" \ + "${hex} :.*${hex} :.*" \ + "stepped multiple insns" +} + +# Check range stepping can step over a function. + +with_test_prefix "step over func" { + global srcfile + + set line_num [gdb_get_line_number "location 2"] + gdb_test "where" "main \\(\\) at .*${srcfile}:${line_num}.*" + + # It is expected to get three stops and two 'vCont;r'. In the C + # code, the line of C source produces the following instructions, + # + # addr1: + # insn1; + # insn2; + # ... + # call func1; + # addr2: + # ... + # insn3; + # addr3: + # insn4; + # + # Something like this will happen: + # --> vCont;rADDR1,ADDR3 (do range stepping from ADDR1 to ADDR3) + # <-- T0505:XXXX + # (inferior is single-stepping to func, which is out of the range) + # --> $Z0,ADDR2 + # --> vCont;c (set step-resume breakpoint on ADDR2, and resume) + # <-- T0505:XXXX (inferior stops at ADD2) + # --> vCont;rADDR1,ADDR3 (continues to do range stepping) + # <-- T0505:XXXX + gdb_test_no_output "set \$range_stepping_counter = 0" "" + gdb_test "next" + gdb_test "p \$range_stepping_counter" " = 2" +} + +# Check range stepping works well with breakpoint. + +with_test_prefix "breakpoint" { + gdb_breakpoint "func1" + # Something like this will happen: + # --> vCont;rADDR1,ADDR3 + # <-- T0505:XXXX + # (inferior is single-stepping to func1, which is out of the range) + # --> $Z0,ADDR2 + # --> vCont;c (set step-resume breakpoint on ADDR2, and resume) + # <-- T0505:XXXX (inferior hits the breakpoint on fun1) + gdb_test_no_output "set \$range_stepping_counter = 0" "" + gdb_test "next" "." "" + gdb_test "p \$range_stepping_counter" " = 1" \ + "range-stepping-counter is 1" + + gdb_test "backtrace" "#0 .* func1 .*#1 .* main .*" \ + "backtrace from func1" + # The range stepping was interrupted by a breakpoint, but the + # state related to range stepping should be cleared. + gdb_test_no_output "set \$range_stepping_counter = 0" "" + gdb_test "stepi" + gdb_test "p \$range_stepping_counter" " = 0" \ + "range-stepping-counter is 0" + gdb_test "finish" ".*" + + gdb_test "next" ".*" + delete_breakpoints +} + +# Check range stepping works well with a loop in the range. + +with_test_prefix "loop" { + + # GDB should send one vCont;r and receive one stop reply. + # --> vCont;rSTART,END (do range stepping) + # <-- T0505:XXX + gdb_test_no_output "set \$range_stepping_counter = 0" "" + gdb_test "next" + gdb_test "p \$range_stepping_counter" " = 1" + + # Check loop is done. + gdb_test "print a" "\\$${decimal} = 15\[\r\n\].*" + gdb_test "print e" "\\$${decimal} = 105\[\r\n\].*" +} + +# Check range stepping works well when PC has already within the loop +# body. + +with_test_prefix "loop" { + # Stepi into the loop body. 15 is large enough to make sure + # program goes to loop body. + gdb_test "stepi 15" ".*" + # GDB should send one vCont;r and receive one stop reply. + # --> vCont;rSTART,END (do range stepping) + # <-- T0505:XXX + gdb_test_no_output "set \$range_stepping_counter = 0" "" + gdb_test "next" + gdb_test "p \$range_stepping_counter" " = 1" + + # Check loop is done. + gdb_test "print a" "\\$${decimal} = 15\[\r\n\].*" + gdb_test "print e" "\\$${decimal} = 105\[\r\n\].*" +} + +# Check range stepping works well when it is interrupted by ctrl-c. + +with_test_prefix "interrupt" { + gdb_test_no_output "set \$range_stepping_counter = 0" "" + + send_gdb "next\n" + sleep 1 + send_gdb "\003" + + # GDB should send one vCont;r and receive one stop reply about + # SIGINT. + # --> vCont;rSTART,END (do range stepping) + # <-- T0205:XXX + + set test "send gdb ctrl-c" + gdb_expect { + -re "Program received signal SIGINT.*$gdb_prompt $" { + pass $test + } + timeout { fail "${test} (timeout)" } + eof { fail "${test} (eof)" } + } + gdb_test "p \$range_stepping_counter" " = 1" \ + "range-stepping-counter is 1" + + # Terminate the loop earlier and continue to do range stepping. + gdb_test "set variable c = 0" + gdb_test "next" + gdb_test "p \$range_stepping_counter" " = 2" \ + "range-stepping-counter is 2" +} + +return 0 diff --git a/gdb/testsuite/gdb.trace/range-stepping.c b/gdb/testsuite/gdb.trace/range-stepping.c new file mode 100644 index 0000000..50db5a0 --- /dev/null +++ b/gdb/testsuite/gdb.trace/range-stepping.c @@ -0,0 +1,61 @@ +/* This testcase is part of GDB, the GNU debugger. + + Copyright 2013 Free Software Foundation, Inc. + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . */ + +#ifdef SYMBOL_PREFIX +#define SYMBOL(str) SYMBOL_PREFIX #str +#else +#define SYMBOL(str) #str +#endif + +/* Called from asm. */ +static void __attribute__((used)) +func2 (void) +{} + +static int +func1 (int a, int b) +{ + int r = a * b; + + /* `set_point' is the label where we'll set tracepoint at. The insn + at the label must the large enough to fit a fast tracepoint + jump. */ + asm (" .global " SYMBOL(set_point) "\n" + SYMBOL(set_point) ":\n" +#if (defined __x86_64__ || defined __i386__) + " call " SYMBOL(func2) "\n" +#endif + ); + + r =+ (a | b); + r =+ (a - b); + + return r; +} + +int +main(void) +{ + int a = 0; + int b = 1; + int c = 2; + int d = 3; + int e = 4; + + e = 10 + func1 (a + b, c * d); /* location 1 */ + return 0; +} diff --git a/gdb/testsuite/gdb.trace/range-stepping.exp b/gdb/testsuite/gdb.trace/range-stepping.exp new file mode 100644 index 0000000..22c705d --- /dev/null +++ b/gdb/testsuite/gdb.trace/range-stepping.exp @@ -0,0 +1,89 @@ +# Copyright 2013 Free Software Foundation, Inc. + +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . + +load_lib "trace-support.exp" + +standard_testfile +set executable $testfile +set expfile $testfile.exp + +if [prepare_for_testing $expfile $executable $srcfile \ + {debug nowarnings}] { + untested "failed to prepare for trace tests" + return -1 +} + +if ![runto_main] { + fail "Can't run to main to check for trace support" + return -1 +} + +if ![gdb_target_supports_trace] { + unsupported "target does not support trace" + return -1; +} + +# Check range stepping works well with tracepoint. +proc range_stepping_with_tracepoint { type } { + with_test_prefix "${type}" { + + gdb_breakpoint [gdb_get_line_number "location 1"] + gdb_continue_to_breakpoint "location 1" + delete_breakpoints + + gdb_test "${type} set_point" ".*" + gdb_test_no_output "tstart" + + # GDB will step over function func1, in which a tracepoint is + # set. GDB will send two vCont;r packets because calling to + # func1 is out of the range. However, tracepoint itself + # shouldn't have any effect on range stepping. + gdb_test_no_output "set \$range_stepping_counter = 0" "" + gdb_test "next" + gdb_test "p \$range_stepping_counter" " = 2" + gdb_test_no_output "tstop" + gdb_test "tfind" "Found trace frame 0.*" "tfind 0" + gdb_test "tfind" \ + "Target failed to find requested trace frame.*" \ + "tfind 1" + + delete_breakpoints + } +} + +range_stepping_with_tracepoint "trace" + +set libipa [get_in_proc_agent] +gdb_load_shlibs $libipa + +if { [gdb_compile "$srcdir/$subdir/$srcfile" $binfile \ + executable [list debug nowarnings shlib=$libipa] ] != "" } { + untested "failed to compile ftrace tests" + return -1 +} + +clean_restart ${executable} + +if ![runto_main] { + fail "Can't run to main for ftrace tests" + return 0 +} + +gdb_reinitialize_dir $srcdir/$subdir +if { [gdb_test "info sharedlibrary" ".*${libipa}.*" "IPA loaded"] != 0 } { + untested "Could not find IPA lib loaded" +} else { + range_stepping_with_tracepoint "ftrace" +} -- 1.7.7.6