- Archer update to the snapshot: a99e30d08ade4a2df0f943b036cd653bcd12b04d
- Fixes internal error on breaking at a multi-locations C++ caller (BZ 488572).
This commit is contained in:
parent
1a30f6fafe
commit
5e5008a2ef
247
gdb-archer.patch
247
gdb-archer.patch
@ -2,7 +2,7 @@ http://sourceware.org/gdb/wiki/ProjectArcher
|
|||||||
http://sourceware.org/gdb/wiki/ArcherBranchManagement
|
http://sourceware.org/gdb/wiki/ArcherBranchManagement
|
||||||
|
|
||||||
GIT snapshot:
|
GIT snapshot:
|
||||||
commit ec29855686f2a78d90ebcc63765681249bbbe808
|
commit a99e30d08ade4a2df0f943b036cd653bcd12b04d
|
||||||
|
|
||||||
branch `archer' - the merge of branches:
|
branch `archer' - the merge of branches:
|
||||||
archer-jankratochvil-merge-expr
|
archer-jankratochvil-merge-expr
|
||||||
@ -866,7 +866,7 @@ index 8f0140c..d451769 100644
|
|||||||
|
|
||||||
/* Set BLOCK's using member to USING; if needed, allocate memory via
|
/* Set BLOCK's using member to USING; if needed, allocate memory via
|
||||||
diff --git a/gdb/breakpoint.c b/gdb/breakpoint.c
|
diff --git a/gdb/breakpoint.c b/gdb/breakpoint.c
|
||||||
index b23b294..38a17a1 100644
|
index b23b294..531c43d 100644
|
||||||
--- a/gdb/breakpoint.c
|
--- a/gdb/breakpoint.c
|
||||||
+++ b/gdb/breakpoint.c
|
+++ b/gdb/breakpoint.c
|
||||||
@@ -191,6 +191,8 @@ static int is_hardware_watchpoint (struct breakpoint *bpt);
|
@@ -191,6 +191,8 @@ static int is_hardware_watchpoint (struct breakpoint *bpt);
|
||||||
@ -1344,7 +1344,65 @@ index b23b294..38a17a1 100644
|
|||||||
static int
|
static int
|
||||||
hw_breakpoint_used_count (void)
|
hw_breakpoint_used_count (void)
|
||||||
{
|
{
|
||||||
@@ -5310,8 +5604,6 @@ create_breakpoints (struct symtabs_and_lines sals, char **addr_string,
|
@@ -5188,7 +5482,6 @@ expand_line_sal_maybe (struct symtab_and_line sal)
|
||||||
|
struct symtabs_and_lines expanded;
|
||||||
|
CORE_ADDR original_pc = sal.pc;
|
||||||
|
char *original_function = NULL;
|
||||||
|
- int found;
|
||||||
|
int i;
|
||||||
|
|
||||||
|
/* If we have explicit pc, don't expand.
|
||||||
|
@@ -5264,14 +5557,42 @@ expand_line_sal_maybe (struct symtab_and_line sal)
|
||||||
|
|
||||||
|
if (original_pc)
|
||||||
|
{
|
||||||
|
- found = 0;
|
||||||
|
+ /* Find all the other PCs for a line of code with multiple instances
|
||||||
|
+ (locations). If the instruction is in the middle of an instruction
|
||||||
|
+ block for source line GDB cannot safely find the same instruction in
|
||||||
|
+ the other compiled instances of the same source line because the other
|
||||||
|
+ instances may have been compiled completely differently.
|
||||||
|
+
|
||||||
|
+ The testcase gdb.cp/expand-sals.exp shows that breaking at the return
|
||||||
|
+ address in a caller of the current frame works for the current
|
||||||
|
+ instance but the breakpoint cannot catch the point (instruction) where
|
||||||
|
+ the callee returns in the other compiled instances of this source line.
|
||||||
|
+
|
||||||
|
+ The current implementation will place the breakpoint at the expected
|
||||||
|
+ returning address of the current instance of the caller. But the
|
||||||
|
+ other instances will get the breakpoint at the first instruction of
|
||||||
|
+ the source line - therefore before the call would be made. Another
|
||||||
|
+ possibility would be to place the breakpoint in the other instances at
|
||||||
|
+ the start of the next source line.
|
||||||
|
+
|
||||||
|
+ A possible heuristics would compare the instructions length of each of
|
||||||
|
+ the instances of the current source line and if it matches it would
|
||||||
|
+ place the breakpoint at the same offset. Unfortunately a mistaken
|
||||||
|
+ guess would possibly crash the inferior. */
|
||||||
|
+
|
||||||
|
+ CORE_ADDR best = -1;
|
||||||
|
+
|
||||||
|
+ /* Find the nearest preceding PC and set it to ORIGINAL_PC. */
|
||||||
|
for (i = 0; i < expanded.nelts; ++i)
|
||||||
|
- if (expanded.sals[i].pc == original_pc)
|
||||||
|
- {
|
||||||
|
- found = 1;
|
||||||
|
- break;
|
||||||
|
- }
|
||||||
|
- gdb_assert (found);
|
||||||
|
+ if (expanded.sals[i].pc <= original_pc
|
||||||
|
+ && (best == -1 || expanded.sals[best].pc < expanded.sals[i].pc))
|
||||||
|
+ best = i;
|
||||||
|
+
|
||||||
|
+ if (best == -1)
|
||||||
|
+ error (_("Cannot find the best address for %s out of the %d locations"),
|
||||||
|
+ paddr (original_pc), expanded.nelts);
|
||||||
|
+
|
||||||
|
+ expanded.sals[best].pc = original_pc;
|
||||||
|
}
|
||||||
|
|
||||||
|
return expanded;
|
||||||
|
@@ -5310,8 +5631,6 @@ create_breakpoints (struct symtabs_and_lines sals, char **addr_string,
|
||||||
cond_string, type, disposition,
|
cond_string, type, disposition,
|
||||||
thread, ignore_count, ops, from_tty, enabled);
|
thread, ignore_count, ops, from_tty, enabled);
|
||||||
}
|
}
|
||||||
@ -1353,7 +1411,7 @@ index b23b294..38a17a1 100644
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Parse ARG which is assumed to be a SAL specification possibly
|
/* Parse ARG which is assumed to be a SAL specification possibly
|
||||||
@@ -5637,7 +5929,6 @@ break_command_really (char *arg, char *cond_string, int thread,
|
@@ -5637,7 +5956,6 @@ break_command_really (char *arg, char *cond_string, int thread,
|
||||||
b->ops = ops;
|
b->ops = ops;
|
||||||
b->enable_state = enabled ? bp_enabled : bp_disabled;
|
b->enable_state = enabled ? bp_enabled : bp_disabled;
|
||||||
|
|
||||||
@ -1361,7 +1419,7 @@ index b23b294..38a17a1 100644
|
|||||||
mention (b);
|
mention (b);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -5649,6 +5940,11 @@ break_command_really (char *arg, char *cond_string, int thread,
|
@@ -5649,6 +5967,11 @@ break_command_really (char *arg, char *cond_string, int thread,
|
||||||
discard_cleanups (breakpoint_chain);
|
discard_cleanups (breakpoint_chain);
|
||||||
/* But cleanup everything else. */
|
/* But cleanup everything else. */
|
||||||
do_cleanups (old_chain);
|
do_cleanups (old_chain);
|
||||||
@ -1373,7 +1431,7 @@ index b23b294..38a17a1 100644
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Set a breakpoint.
|
/* Set a breakpoint.
|
||||||
@@ -6131,7 +6427,7 @@ can_use_hardware_watchpoint (struct value *v)
|
@@ -6131,7 +6454,7 @@ can_use_hardware_watchpoint (struct value *v)
|
||||||
|| (TYPE_CODE (vtype) != TYPE_CODE_STRUCT
|
|| (TYPE_CODE (vtype) != TYPE_CODE_STRUCT
|
||||||
&& TYPE_CODE (vtype) != TYPE_CODE_ARRAY))
|
&& TYPE_CODE (vtype) != TYPE_CODE_ARRAY))
|
||||||
{
|
{
|
||||||
@ -1382,7 +1440,7 @@ index b23b294..38a17a1 100644
|
|||||||
int len = TYPE_LENGTH (value_type (v));
|
int len = TYPE_LENGTH (value_type (v));
|
||||||
|
|
||||||
if (!TARGET_REGION_OK_FOR_HW_WATCHPOINT (vaddr, len))
|
if (!TARGET_REGION_OK_FOR_HW_WATCHPOINT (vaddr, len))
|
||||||
@@ -6668,6 +6964,122 @@ catch_ada_exception_command (char *arg, int from_tty,
|
@@ -6668,6 +6991,122 @@ catch_ada_exception_command (char *arg, int from_tty,
|
||||||
from_tty);
|
from_tty);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1505,7 +1563,7 @@ index b23b294..38a17a1 100644
|
|||||||
/* Implement the "catch assert" command. */
|
/* Implement the "catch assert" command. */
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@@ -7134,6 +7546,7 @@ delete_breakpoint (struct breakpoint *bpt)
|
@@ -7134,6 +7573,7 @@ delete_breakpoint (struct breakpoint *bpt)
|
||||||
xfree (bpt->source_file);
|
xfree (bpt->source_file);
|
||||||
if (bpt->exec_pathname != NULL)
|
if (bpt->exec_pathname != NULL)
|
||||||
xfree (bpt->exec_pathname);
|
xfree (bpt->exec_pathname);
|
||||||
@ -1513,7 +1571,7 @@ index b23b294..38a17a1 100644
|
|||||||
|
|
||||||
/* Be sure no bpstat's are pointing at it after it's been freed. */
|
/* Be sure no bpstat's are pointing at it after it's been freed. */
|
||||||
/* FIXME, how can we find all bpstat's?
|
/* FIXME, how can we find all bpstat's?
|
||||||
@@ -8041,6 +8454,56 @@ single_step_breakpoint_inserted_here_p (CORE_ADDR pc)
|
@@ -8041,6 +8481,56 @@ single_step_breakpoint_inserted_here_p (CORE_ADDR pc)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1570,7 +1628,7 @@ index b23b294..38a17a1 100644
|
|||||||
|
|
||||||
/* This help string is used for the break, hbreak, tbreak and thbreak commands.
|
/* This help string is used for the break, hbreak, tbreak and thbreak commands.
|
||||||
It is defined as a macro to prevent duplication.
|
It is defined as a macro to prevent duplication.
|
||||||
@@ -8073,6 +8536,8 @@ static void
|
@@ -8073,6 +8563,8 @@ static void
|
||||||
add_catch_command (char *name, char *docstring,
|
add_catch_command (char *name, char *docstring,
|
||||||
void (*sfunc) (char *args, int from_tty,
|
void (*sfunc) (char *args, int from_tty,
|
||||||
struct cmd_list_element *command),
|
struct cmd_list_element *command),
|
||||||
@ -1579,7 +1637,7 @@ index b23b294..38a17a1 100644
|
|||||||
void *user_data_catch,
|
void *user_data_catch,
|
||||||
void *user_data_tcatch)
|
void *user_data_tcatch)
|
||||||
{
|
{
|
||||||
@@ -8082,11 +8547,13 @@ add_catch_command (char *name, char *docstring,
|
@@ -8082,11 +8574,13 @@ add_catch_command (char *name, char *docstring,
|
||||||
&catch_cmdlist);
|
&catch_cmdlist);
|
||||||
set_cmd_sfunc (command, sfunc);
|
set_cmd_sfunc (command, sfunc);
|
||||||
set_cmd_context (command, user_data_catch);
|
set_cmd_context (command, user_data_catch);
|
||||||
@ -1593,7 +1651,7 @@ index b23b294..38a17a1 100644
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
@@ -8361,36 +8828,50 @@ Set temporary catchpoints to catch events."),
|
@@ -8361,36 +8855,50 @@ Set temporary catchpoints to catch events."),
|
||||||
Catch an exception, when caught.\n\
|
Catch an exception, when caught.\n\
|
||||||
With an argument, catch only exceptions with the given name."),
|
With an argument, catch only exceptions with the given name."),
|
||||||
catch_catch_command,
|
catch_catch_command,
|
||||||
@ -33471,6 +33529,171 @@ index 5e08768..8c8e038 100644
|
|||||||
}
|
}
|
||||||
|
|
||||||
proc do_tests {} {
|
proc do_tests {} {
|
||||||
|
diff --git a/gdb/testsuite/gdb.cp/expand-sals.cc b/gdb/testsuite/gdb.cp/expand-sals.cc
|
||||||
|
new file mode 100644
|
||||||
|
index 0000000..6169a05
|
||||||
|
--- /dev/null
|
||||||
|
+++ b/gdb/testsuite/gdb.cp/expand-sals.cc
|
||||||
|
@@ -0,0 +1,53 @@
|
||||||
|
+/* This testcase is part of GDB, the GNU debugger.
|
||||||
|
+
|
||||||
|
+ Copyright (C) 2009 Free Software Foundation, Inc.
|
||||||
|
+
|
||||||
|
+ This file is part of GDB.
|
||||||
|
+
|
||||||
|
+ 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 <http://www.gnu.org/licenses/>. */
|
||||||
|
+
|
||||||
|
+int
|
||||||
|
+func ()
|
||||||
|
+{
|
||||||
|
+ return 42; /* func-line */
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+volatile int global_x;
|
||||||
|
+
|
||||||
|
+class A
|
||||||
|
+{
|
||||||
|
+public:
|
||||||
|
+ A ()
|
||||||
|
+ {
|
||||||
|
+ global_x = func (); /* caller-line */
|
||||||
|
+ }
|
||||||
|
+};
|
||||||
|
+
|
||||||
|
+/* class B is here just to make the `func' calling line above having multiple
|
||||||
|
+ instances - multiple locations. Template cannot be used as its instances
|
||||||
|
+ would have different function names which get discarded by GDB
|
||||||
|
+ expand_line_sal_maybe. */
|
||||||
|
+
|
||||||
|
+class B : public A
|
||||||
|
+{
|
||||||
|
+};
|
||||||
|
+
|
||||||
|
+int
|
||||||
|
+main (void)
|
||||||
|
+{
|
||||||
|
+ A a;
|
||||||
|
+ B b;
|
||||||
|
+
|
||||||
|
+ return 0; /* exit-line */
|
||||||
|
+}
|
||||||
|
diff --git a/gdb/testsuite/gdb.cp/expand-sals.exp b/gdb/testsuite/gdb.cp/expand-sals.exp
|
||||||
|
new file mode 100644
|
||||||
|
index 0000000..a2631fb
|
||||||
|
--- /dev/null
|
||||||
|
+++ b/gdb/testsuite/gdb.cp/expand-sals.exp
|
||||||
|
@@ -0,0 +1,100 @@
|
||||||
|
+# Copyright 2009 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 <http://www.gnu.org/licenses/>.
|
||||||
|
+
|
||||||
|
+if { [skip_cplus_tests] } { continue }
|
||||||
|
+
|
||||||
|
+set srcfile expand-sals.cc
|
||||||
|
+if { [prepare_for_testing expand-sals.exp expand-sals $srcfile {debug c++}] } {
|
||||||
|
+ return -1
|
||||||
|
+}
|
||||||
|
+if ![runto_main] {
|
||||||
|
+ return -1
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+gdb_breakpoint [gdb_get_line_number "exit-line"]
|
||||||
|
+
|
||||||
|
+gdb_breakpoint [gdb_get_line_number "func-line"]
|
||||||
|
+gdb_continue_to_breakpoint "func" ".*func-line.*"
|
||||||
|
+
|
||||||
|
+gdb_test "up" "caller-line.*"
|
||||||
|
+
|
||||||
|
+# PC should not be at the boundary of source lines to make the original bug
|
||||||
|
+# exploitable.
|
||||||
|
+
|
||||||
|
+set test "p/x \$pc"
|
||||||
|
+set pc {}
|
||||||
|
+gdb_test_multiple $test $test {
|
||||||
|
+ -re "\\$\[0-9\]+ = (0x\[0-9a-f\]+)\r\n$gdb_prompt $" {
|
||||||
|
+ set pc $expect_out(1,string)
|
||||||
|
+ pass $test
|
||||||
|
+ }
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+set test "info line"
|
||||||
|
+set end {}
|
||||||
|
+gdb_test_multiple $test $test {
|
||||||
|
+ -re "Line \[0-9\]+ of .* starts at address 0x\[0-9a-f\]+.* and ends at (0x\[0-9a-f\]+).*\\.\r\n$gdb_prompt $" {
|
||||||
|
+ set end $expect_out(1,string)
|
||||||
|
+ pass $test
|
||||||
|
+ }
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+set test "caller line has trailing code"
|
||||||
|
+if {$pc != $end} {
|
||||||
|
+ pass $test
|
||||||
|
+} else {
|
||||||
|
+ fail $test
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+# Original problem was an internal error here. Still sanity multiple locations
|
||||||
|
+# were found at this code place as otherwise this test would not test anything.
|
||||||
|
+set test "break"
|
||||||
|
+gdb_test_multiple $test $test {
|
||||||
|
+ -re "Breakpoint \[0-9\]+ at .*, line \[0-9\]+\\. \\(\[2-9\] locations\\)\r\n$gdb_prompt $" {
|
||||||
|
+ pass $test
|
||||||
|
+ }
|
||||||
|
+ -re "Breakpoint \[0-9\]+ at .*, line \[0-9\]+\\.\r\n$gdb_prompt $" {
|
||||||
|
+ # It just could not be decided if GDB is OK by this testcase.
|
||||||
|
+ setup_xfail *-*-*
|
||||||
|
+ fail $test
|
||||||
|
+ return 0
|
||||||
|
+ }
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+gdb_continue_to_breakpoint "caller" ".*caller-line.*"
|
||||||
|
+
|
||||||
|
+# Test GDB caught this return call and not the next one through B::B()
|
||||||
|
+gdb_test "bt" \
|
||||||
|
+ "#0 \[^\r\n\]* A \[^\r\n\]*\r\n#1 \[^\r\n\]* main \[^\r\n\]*" \
|
||||||
|
+ "bt from A"
|
||||||
|
+
|
||||||
|
+gdb_continue_to_breakpoint "next caller instance" ".*caller-line.*"
|
||||||
|
+
|
||||||
|
+# Test that GDB caught now already A through B::B() in the other instance.
|
||||||
|
+# As discussed in GDB expand_line_sal_maybe it would more match the original
|
||||||
|
+# instance behavior to catch here the `func' breakpoint and catch the
|
||||||
|
+# multiple-locations breakpoint only during the call return. This is not the
|
||||||
|
+# case, expecting here to catch the breakpoint before the call happens.
|
||||||
|
+
|
||||||
|
+gdb_test "bt" \
|
||||||
|
+ "#0 \[^\r\n\]* A \[^\r\n\]*\r\n#1 \[^\r\n\]* B \[^\r\n\]*\r\n#2 \[^\r\n\]* main \[^\r\n\]*" \
|
||||||
|
+ "bt from B before the call"
|
||||||
|
+
|
||||||
|
+gdb_continue_to_breakpoint "next caller func" ".*func-line.*"
|
||||||
|
+
|
||||||
|
+# Verify GDB really could not catch the originally intended point of the return
|
||||||
|
+# from func.
|
||||||
|
+
|
||||||
|
+gdb_continue_to_breakpoint "uncaught return" ".*exit-line.*"
|
||||||
diff --git a/gdb/testsuite/gdb.cp/gdb1355.exp b/gdb/testsuite/gdb.cp/gdb1355.exp
|
diff --git a/gdb/testsuite/gdb.cp/gdb1355.exp b/gdb/testsuite/gdb.cp/gdb1355.exp
|
||||||
index 77687a6..66d16cf 100644
|
index 77687a6..66d16cf 100644
|
||||||
--- a/gdb/testsuite/gdb.cp/gdb1355.exp
|
--- a/gdb/testsuite/gdb.cp/gdb1355.exp
|
||||||
|
6
gdb.spec
6
gdb.spec
@ -13,7 +13,7 @@ Version: 6.8.50.20090302
|
|||||||
|
|
||||||
# The release always contains a leading reserved number, start it at 1.
|
# The release always contains a leading reserved number, start it at 1.
|
||||||
# `upstream' is not a part of `name' to stay fully rpm dependencies compatible for the testing.
|
# `upstream' is not a part of `name' to stay fully rpm dependencies compatible for the testing.
|
||||||
Release: 7%{?_with_upstream:.upstream}%{?dist}
|
Release: 8%{?_with_upstream:.upstream}%{?dist}
|
||||||
|
|
||||||
License: GPLv3+
|
License: GPLv3+
|
||||||
Group: Development/Debuggers
|
Group: Development/Debuggers
|
||||||
@ -851,6 +851,10 @@ fi
|
|||||||
%endif
|
%endif
|
||||||
|
|
||||||
%changelog
|
%changelog
|
||||||
|
* Mon Mar 9 2009 Jan Kratochvil <jan.kratochvil@redhat.com> - 6.8.50.20090302-8
|
||||||
|
- Archer update to the snapshot: a99e30d08ade4a2df0f943b036cd653bcd12b04d
|
||||||
|
- Fixes internal error on breaking at a multi-locations C++ caller (BZ 488572).
|
||||||
|
|
||||||
* Mon Mar 9 2009 Jan Kratochvil <jan.kratochvil@redhat.com> - 6.8.50.20090302-7
|
* Mon Mar 9 2009 Jan Kratochvil <jan.kratochvil@redhat.com> - 6.8.50.20090302-7
|
||||||
- Archer update to the snapshot: ec29855686f2a78d90ebcc63765681249bbbe808
|
- Archer update to the snapshot: ec29855686f2a78d90ebcc63765681249bbbe808
|
||||||
- Temporarily place libstdc++ pretty printers in this gdb.rpm.
|
- Temporarily place libstdc++ pretty printers in this gdb.rpm.
|
||||||
|
Loading…
Reference in New Issue
Block a user