From mboxrd@z Thu Jan 1 00:00:00 1970 From: Ulrich Weigand To: gdb-patches@sources.redhat.com Cc: eliz@gnu.org, orjan.friberg@axis.com, kettenis@chello.nl, drow@false.org Subject: [PATCH] Fix watchpoints on s390 Date: Mon, 10 May 2004 17:39:00 -0000 Message-id: <200405101738.TAA07374@faui1d.informatik.uni-erlangen.de> References: <6654-Fri07May2004110644+0300-eliz@gnu.org> X-SW-Source: 2004-05/msg00290.html Hello, this is the second attempt to fix watchpoints on s390 by using STOPPED_BY_WATCHPOINT instead of target_stopped_data_address in bpstat_stop_status to find out whether the target stopped due to a hardware watchpoint. As STOPPED_BY_WATCHPOINT requires an argument not available in breakpoint.c, and furthermore some targets define this macro so as to access other local variables not even passed as arguments, calling this macro from anywhere else is not trivial. Thus, this patch simply remembers the return value of STOPPED_BY_WATCHPOINT in handle_inferior_event, and passes *that* as argument to bpstat_stop_status. This should work on all targets ... Tested on s390-ibm-linux and s390x-ibm-linux, fixes all watchpoint related regressions. Bye, Ulrich ChangeLog: * breakpoint.c (bpstat_stop_status): Add new argument STOPPED_BY_WATCHPOINT. Use it instead of testing target_stopped_data_address agaist 0 to check whether or not we stopped due to a hardware watchpoint. * breakpoint.h (bpstat_stop_status): Adapt prototype. * infrun.c (handle_inferior_event): Call bpstat_stop_status with new argument. Index: gdb/breakpoint.c =================================================================== RCS file: /cvs/src/src/gdb/breakpoint.c,v retrieving revision 1.170 diff -c -p -r1.170 breakpoint.c *** gdb/breakpoint.c 2 May 2004 00:21:41 -0000 1.170 --- gdb/breakpoint.c 10 May 2004 17:13:49 -0000 *************** which its expression is valid.\n"); *** 2590,2596 **** } /* Get a bpstat associated with having just stopped at address ! BP_ADDR. */ /* Determine whether we stopped at a breakpoint, etc, or whether we don't understand this stop. Result is a chain of bpstat's such that: --- 2590,2597 ---- } /* Get a bpstat associated with having just stopped at address ! BP_ADDR in thread PTID. STOPPED_BY_WATCHPOINT is true if the ! target thinks we stopped due to a hardware watchpoint. */ /* Determine whether we stopped at a breakpoint, etc, or whether we don't understand this stop. Result is a chain of bpstat's such that: *************** which its expression is valid.\n"); *** 2607,2613 **** commands, FIXME??? fields. */ bpstat ! bpstat_stop_status (CORE_ADDR bp_addr, ptid_t ptid) { struct breakpoint *b, *temp; /* True if we've hit a breakpoint (as opposed to a watchpoint). */ --- 2608,2614 ---- commands, FIXME??? fields. */ bpstat ! bpstat_stop_status (CORE_ADDR bp_addr, ptid_t ptid, int stopped_by_watchpoint) { struct breakpoint *b, *temp; /* True if we've hit a breakpoint (as opposed to a watchpoint). */ *************** bpstat_stop_status (CORE_ADDR bp_addr, p *** 2631,2637 **** && !((b->type == bp_hardware_watchpoint || b->type == bp_read_watchpoint || b->type == bp_access_watchpoint) ! && target_stopped_data_address () != 0) && b->type != bp_hardware_breakpoint && b->type != bp_catch_fork && b->type != bp_catch_vfork --- 2632,2638 ---- && !((b->type == bp_hardware_watchpoint || b->type == bp_read_watchpoint || b->type == bp_access_watchpoint) ! && stopped_by_watchpoint) && b->type != bp_hardware_breakpoint && b->type != bp_catch_fork && b->type != bp_catch_vfork Index: gdb/breakpoint.h =================================================================== RCS file: /cvs/src/src/gdb/breakpoint.h,v retrieving revision 1.32 diff -c -p -r1.32 breakpoint.h *** gdb/breakpoint.h 8 Apr 2004 21:18:12 -0000 1.32 --- gdb/breakpoint.h 10 May 2004 17:13:49 -0000 *************** extern void bpstat_clear (bpstat *); *** 414,420 **** is part of the bpstat is copied as well. */ extern bpstat bpstat_copy (bpstat); ! extern bpstat bpstat_stop_status (CORE_ADDR pc, ptid_t ptid); /* This bpstat_what stuff tells wait_for_inferior what to do with a breakpoint (a challenging task). */ --- 414,421 ---- is part of the bpstat is copied as well. */ extern bpstat bpstat_copy (bpstat); ! extern bpstat bpstat_stop_status (CORE_ADDR pc, ptid_t ptid, ! int stopped_by_watchpoint); /* This bpstat_what stuff tells wait_for_inferior what to do with a breakpoint (a challenging task). */ Index: gdb/infrun.c =================================================================== RCS file: /cvs/src/src/gdb/infrun.c,v retrieving revision 1.151 diff -c -p -r1.151 infrun.c *** gdb/infrun.c 1 May 2004 14:15:19 -0000 1.151 --- gdb/infrun.c 10 May 2004 17:13:49 -0000 *************** handle_inferior_event (struct execution_ *** 1367,1372 **** --- 1367,1373 ---- defined in the file "config/pa/nm-hppah.h", accesses the variable indirectly. Mutter something rude about the HP merge. */ int sw_single_step_trap_p = 0; + int stopped_by_watchpoint = 0; /* Cache the last pid/waitstatus. */ target_last_wait_ptid = ecs->ptid; *************** handle_inferior_event (struct execution_ *** 1556,1562 **** stop_pc = read_pc (); ! stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid); ecs->random_signal = !bpstat_explains_signal (stop_bpstat); --- 1557,1563 ---- stop_pc = read_pc (); ! stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid, 0); ecs->random_signal = !bpstat_explains_signal (stop_bpstat); *************** handle_inferior_event (struct execution_ *** 1605,1611 **** ecs->saved_inferior_ptid = inferior_ptid; inferior_ptid = ecs->ptid; ! stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid); ecs->random_signal = !bpstat_explains_signal (stop_bpstat); inferior_ptid = ecs->saved_inferior_ptid; --- 1606,1612 ---- ecs->saved_inferior_ptid = inferior_ptid; inferior_ptid = ecs->ptid; ! stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid, 0); ecs->random_signal = !bpstat_explains_signal (stop_bpstat); inferior_ptid = ecs->saved_inferior_ptid; *************** handle_inferior_event (struct execution_ *** 1921,1927 **** /* It may be possible to simply continue after a watchpoint. */ if (HAVE_CONTINUABLE_WATCHPOINT) ! STOPPED_BY_WATCHPOINT (ecs->ws); ecs->stop_func_start = 0; ecs->stop_func_end = 0; --- 1922,1928 ---- /* It may be possible to simply continue after a watchpoint. */ if (HAVE_CONTINUABLE_WATCHPOINT) ! stopped_by_watchpoint = STOPPED_BY_WATCHPOINT (ecs->ws); ecs->stop_func_start = 0; ecs->stop_func_end = 0; *************** handle_inferior_event (struct execution_ *** 2007,2013 **** else { /* See if there is a breakpoint at the current PC. */ ! stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid); /* Following in case break condition called a function. */ --- 2008,2015 ---- else { /* See if there is a breakpoint at the current PC. */ ! stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid, ! stopped_by_watchpoint); /* Following in case break condition called a function. */ -- Dr. Ulrich Weigand weigand@informatik.uni-erlangen.de