From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 17081 invoked by alias); 5 Dec 2007 12:17:44 -0000 Received: (qmail 17065 invoked by uid 22791); 5 Dec 2007 12:17:41 -0000 X-Spam-Check-By: sourceware.org Received: from mail.codesourcery.com (HELO mail.codesourcery.com) (65.74.133.4) by sourceware.org (qpsmtpd/0.31) with ESMTP; Wed, 05 Dec 2007 12:17:33 +0000 Received: (qmail 14484 invoked from network); 5 Dec 2007 12:17:30 -0000 Received: from unknown (HELO wind.local) (vladimir@127.0.0.2) by mail.codesourcery.com with ESMTPA; 5 Dec 2007 12:17:30 -0000 From: Vladimir Prus To: Jim Blandy Subject: Re: [RFA] Clarify infrun variable naming. Date: Wed, 05 Dec 2007 14:13:00 -0000 User-Agent: KMail/1.9.6 Cc: gdb-patches@sources.redhat.com References: <200711231623.04823.vladimir@codesourcery.com> In-Reply-To: MIME-Version: 1.0 Content-Type: Multipart/Mixed; boundary="Boundary-00=_NbpVHPDLeyYgEUP" Message-Id: <200712051517.17764.vladimir@codesourcery.com> 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 X-SW-Source: 2007-12/txt/msg00080.txt.bz2 --Boundary-00=_NbpVHPDLeyYgEUP Content-Type: text/plain; charset="iso-8859-1" Content-Transfer-Encoding: quoted-printable Content-Disposition: inline Content-length: 24934 On Wednesday 05 December 2007 04:17:52 Jim Blandy wrote: >=20 > Vladimir Prus writes: > > The infrun.c file has a variable named trap_expected, which > > is a bit misleading -- after all, most times when we resume > > inferior, we get SIGTRAP. As it turns out, that variable > > is set when we're stepping over breakpoints, so a better > > name would be stepping_over_breakpoint. Likewise, > > ecs->another_trap also indicates that keep_going should > > be stepping over breakpoint. The attached patch clarifies > > the naming and adds comments, and has no behaviour changes. > > (The patch is on top of my previous breakpoints_inserted > > removing patch). > > OK? ... > So, my suggestions were: >=20 > - We should replace stepping_past_breakpoint and > stepping_past_breakpoint_ptid with a single ptid_t variable, > deferred_step_ptid. >=20 > - We should rename trap_expected to stepped_over_breakpoint. The past > tense 'stepped' suggests that we're talking about a step which has > already happened (which is true by the time we reach > handle_inferior_event). >=20 > (And if I meditate carefully enough on the best possible names, it'll > be quite some time before I have to look at Vlad's harder patches. :)) Here's the patch that renamed stepping_past_breakpoint_ptid. I attach both patch and the delta relative to the previous revision. The 'stepped' vs. 'stepping' change was not done -- for reason I've posted already. OK? - Volodya =A0=A0=A0=A0=A0=A0=A0* infrun.c (trap_expected): Rename =A0=A0=A0=A0=A0=A0=A0=A0to stepping_over_breakpoint. =A0Document. =A0=A0=A0=A0=A0=A0=A0=A0(stepping_past_breakpoint): Remove. =A0=A0=A0=A0=A0=A0=A0=A0(stepping_past_breakpoint_ptdi): Renamed =A0=A0=A0=A0=A0=A0=A0=A0to deferred_step_ptid. =A0=A0=A0=A0=A0=A0=A0=A0(struct execution_control_state): Rename =A0=A0=A0=A0=A0=A0=A0=A0the another_trap field to stepping_over_breakpoint. =A0=A0=A0=A0=A0=A0=A0=A0(struct inferior_status): Rename the trap_expected =A0=A0=A0=A0=A0=A0=A0=A0field to stepping_over_breakpoint. =A0=A0=A0=A0=A0=A0=A0=A0(clear_proceed_status, proceed) =A0=A0=A0=A0=A0=A0=A0=A0(init_execution_control_state, context_switch) =A0=A0=A0=A0=A0=A0=A0=A0(handle_inferior_event, currently_stepping) =A0=A0=A0=A0=A0=A0=A0=A0(keep_going, save_inferior_status) =A0=A0=A0=A0=A0=A0=A0=A0(restore_inferior_status, prepare_to_proceed): Adju= st. =A0=A0=A0=A0=A0=A0=A0=A0* gdbthread.h (struct thread_info): Rename the =A0=A0=A0=A0=A0=A0=A0=A0trap_expected field to stepping_over_breakpoint. =A0=A0=A0=A0=A0=A0=A0=A0* thread.c (load_infrun_state, save_infrun_state): =A0=A0=A0=A0=A0=A0=A0=A0Adjust. --- =A0gdb/gdbthread.h | =A0 =A02 +- =A0gdb/infrun.c =A0 =A0| =A0117 ++++++++++++++++++++++++++++++++++---------= ------------ =A0gdb/thread.c =A0 =A0| =A0 =A08 ++-- =A03 files changed, 77 insertions(+), 50 deletions(-) diff --git a/gdb/gdbthread.h b/gdb/gdbthread.h index aeb4a40..12e0bcc 100644 --- a/gdb/gdbthread.h +++ b/gdb/gdbthread.h @@ -49,7 +49,7 @@ struct thread_info =A0 =A0struct symtab *current_symtab; =A0 =A0int trap_expected; =A0 =A0int handling_longjmp; - =A0int another_trap; + =A0int stepping_over_breakpoint; =A0 =A0 =A0/* This is set TRUE when a catchpoint of a shared library event =A0 =A0 =A0 triggers. =A0Since we don't wish to leave the inferior in the diff --git a/gdb/infrun.c b/gdb/infrun.c index c608f72..77623b6 100644 --- a/gdb/infrun.c +++ b/gdb/infrun.c @@ -218,9 +218,30 @@ static struct cmd_list_element *stop_command; =A0 =A0static struct symbol *step_start_function; =A0 -/* Nonzero if we are expecting a trace trap and should proceed from it. = =A0*/ +/* Nonzero if we are presenting stepping over breakpoint. =A0 -static int trap_expected; + =A0 If we hit a breakpoint or watchpoint, and then continue, + =A0 we need to single step the current thread with breakpoints + =A0 disabled, so that to avoid hitting the same breakpoint or + =A0 watchpoint again. =A0And we should step just a single + =A0 thread and keep other threads stopped, so that=20 + =A0 other threads don't miss breakpoints while they are removed. + + =A0 So, this variable simultaneously means that we need to single + =A0 step current thread, keep other threads stopped, and that + =A0 breakpoints should be removed while we step. + + =A0 This variable is set either: + =A0 - in proceed, when we resume inferior on explicit user's request + =A0 - in keep_going, if handle_inferior_event decides we need to + =A0 step over breakpoint. =A0 + + =A0 The variable is cleared in clear_proceed_status, called every + =A0 time before we call proceed. =A0The proceed calls wait_for_inferior, + =A0 which calls handle_inferior_event in a loop, and until=20 + =A0 wait_for_inferior exits, this variable is changed only by keep_going.= =A0*/ + +static int stepping_over_breakpoint; =A0 =A0/* Nonzero if we want to give control to the user when we're notified =A0 =A0 of shared library events by the dynamic linker. =A0*/ @@ -442,10 +463,14 @@ static CORE_ADDR singlestep_pc; =A0static ptid_t saved_singlestep_ptid; =A0static int stepping_past_singlestep_breakpoint; =A0 -/* Similarly, if we are stepping another thread past a breakpoint, - =A0 save the original thread here so that we can resume stepping it later= . =A0*/ -static ptid_t stepping_past_breakpoint_ptid; -static int stepping_past_breakpoint; +/* If not equal to null_ptid, means that after stepping over breakpoint + =A0 is finished, we need to switch to deferred_step_ptid, and step it. + + =A0 The use case is when a breakpoint in one thread, and then the user=20 + =A0 has switched to another thread and issued 'step'. We need to step over + =A0 breakpoint in the thread which hit breakpoint, but then continue + =A0 stepping the thread user has selected. =A0*/ +static ptid_t deferred_step_ptid; =A0=20 =A0 =A0/* Things to clean up if we QUIT out of resume (). =A0*/ @@ -647,7 +672,7 @@ a command like `return' or `jump' to continue execution= .")); =A0void =A0clear_proceed_status (void) =A0{ - =A0trap_expected =3D 0; + =A0stepping_over_breakpoint =3D 0; =A0 =A0step_range_start =3D 0; =A0 =A0step_range_end =3D 0; =A0 =A0step_frame_id =3D null_frame_id; @@ -693,8 +718,7 @@ prepare_to_proceed (int step) =A0 =A0 =A0 =A0/* If stepping, remember current thread to switch back to. = =A0*/ =A0 =A0 =A0 =A0if (step) =A0=A0=A0=A0=A0=A0=A0=A0{ -=A0=A0=A0=A0=A0=A0=A0 =A0stepping_past_breakpoint =3D 1; -=A0=A0=A0=A0=A0=A0=A0 =A0stepping_past_breakpoint_ptid =3D inferior_ptid; +=A0=A0=A0=A0=A0=A0=A0 =A0deferred_step_ptid =3D inferior_ptid; =A0=A0=A0=A0=A0=A0=A0=A0} =A0 =A0 =A0 =A0 =A0/* Switch back to WAIT_PID thread. =A0*/ @@ -778,7 +802,7 @@ proceed (CORE_ADDR addr, enum target_signal siggnal, in= t step) =A0 =A0if (oneproc) =A0 =A0 =A0/* We will get a trace trap after one instruction. =A0 =A0 =A0 =A0 Continue it automatically and insert breakpoints then. =A0*/ - =A0 =A0trap_expected =3D 1; + =A0 =A0stepping_over_breakpoint =3D 1; =A0 =A0else =A0 =A0 =A0insert_breakpoints (); =A0 @@ -842,7 +866,7 @@ start_remote (int from_tty) =A0 =A0init_thread_list (); =A0 =A0init_wait_for_inferior (); =A0 =A0stop_soon =3D STOP_QUIETLY_REMOTE; - =A0trap_expected =3D 0; + =A0stepping_over_breakpoint =3D 0; =A0 =A0 =A0/* Always go on waiting for the target, regardless of the mode. */ =A0 =A0/* FIXME: cagney/1999-09-23: At present it isn't possible to @@ -887,7 +911,7 @@ init_wait_for_inferior (void) =A0 =A0clear_proceed_status (); =A0 =A0 =A0stepping_past_singlestep_breakpoint =3D 0; - =A0stepping_past_breakpoint =3D 0; + =A0deferred_step_ptid =3D null_ptid; =A0} =A0=20 =A0/* This enum encodes possible reasons for doing a target_wait, so that @@ -924,7 +948,9 @@ struct execution_control_state =A0{ =A0 =A0struct target_waitstatus ws; =A0 =A0struct target_waitstatus *wp; - =A0int another_trap; + =A0/* Should we step over breakpoint next time keep_going=20 + =A0 =A0 is called? =A0*/ + =A0int stepping_over_breakpoint; =A0 =A0int random_signal; =A0 =A0CORE_ADDR stop_func_start; =A0 =A0CORE_ADDR stop_func_end; @@ -1085,7 +1111,7 @@ fetch_inferior_event (void *client_data) =A0void =A0init_execution_control_state (struct execution_control_state *ecs) =A0{ - =A0ecs->another_trap =3D 0; + =A0ecs->stepping_over_breakpoint =3D 0; =A0 =A0ecs->random_signal =3D 0; =A0 =A0ecs->step_after_step_resume_breakpoint =3D 0; =A0 =A0ecs->handling_longjmp =3D 0;=A0=A0=A0/* FIXME */ @@ -1140,20 +1166,20 @@ context_switch (struct execution_control_state *ecs) =A0 =A0 =A0{=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0= =A0=A0=A0=A0=A0/* Perform infrun state context switch: */ =A0 =A0 =A0 =A0/* Save infrun state for the old thread. =A0*/ =A0 =A0 =A0 =A0save_infrun_state (inferior_ptid, prev_pc, -=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 trap= _expected, step_resume_breakpoint, +=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 step= ping_over_breakpoint, step_resume_breakpoint, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 st= ep_range_start, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 st= ep_range_end, &step_frame_id, -=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 ecs-= >handling_longjmp, ecs->another_trap, +=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 ecs-= >handling_longjmp, ecs->stepping_over_breakpoint, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 ec= s->stepping_through_solib_after_catch, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 ec= s->stepping_through_solib_catchpoints, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 ec= s->current_line, ecs->current_symtab); =A0 =A0 =A0 =A0 =A0/* Load infrun state for the new thread. =A0*/ =A0 =A0 =A0 =A0load_infrun_state (ecs->ptid, &prev_pc, -=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 &tra= p_expected, &step_resume_breakpoint, +=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 &ste= pping_over_breakpoint, &step_resume_breakpoint, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 &s= tep_range_start, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 &s= tep_range_end, &step_frame_id, -=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 &ecs= ->handling_longjmp, &ecs->another_trap, +=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 &ecs= ->handling_longjmp, &ecs->stepping_over_breakpoint, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 &e= cs->stepping_through_solib_after_catch, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 &e= cs->stepping_through_solib_catchpoints, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 &e= cs->current_line, &ecs->current_symtab); @@ -1620,17 +1646,15 @@ handle_inferior_event (struct execution_control_sta= te *ecs) =A0 =A0 =A0stepping_past_singlestep_breakpoint =3D 0; =A0 - =A0if (stepping_past_breakpoint) + =A0if (!ptid_equal (deferred_step_ptid, null_ptid)) =A0 =A0 =A0{ - =A0 =A0 =A0stepping_past_breakpoint =3D 0; - =A0 =A0 =A0 =A0/* If we stopped for some other reason than single-stepping,= ignore =A0=A0=A0=A0=A0=A0=A0=A0 the fact that we were supposed to switch back. =A0= */ =A0 =A0 =A0 =A0if (stop_signal =3D=3D TARGET_SIGNAL_TRAP) =A0=A0=A0=A0=A0=A0=A0=A0{ =A0=A0=A0=A0=A0=A0=A0=A0 =A0if (debug_infrun) =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0fprintf_unfiltered (gdb_stdlog, -=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0= =A0=A0=A0=A0=A0=A0=A0"infrun: stepping_past_breakpoint\n"); +=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0= =A0=A0=A0=A0=A0=A0=A0"infrun: handling deferred step\n"); =A0 =A0=A0=A0=A0=A0=A0=A0=A0 =A0/* Pull the single step breakpoints out of the = target. =A0*/ =A0=A0=A0=A0=A0=A0=A0=A0 =A0if (singlestep_breakpoints_inserted_p) @@ -1641,7 +1665,8 @@ handle_inferior_event (struct execution_control_state= *ecs) =A0 =A0=A0=A0=A0=A0=A0=A0=A0 =A0/* Note: We do not call context_switch at this = point, as the =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 context is already set up for stepping the= original thread. =A0*/ -=A0=A0=A0=A0=A0=A0=A0 =A0switch_to_thread (stepping_past_breakpoint_ptid); +=A0=A0=A0=A0=A0=A0=A0 =A0switch_to_thread (deferred_step_ptid); +=A0=A0=A0=A0=A0=A0=A0 =A0deferred_step_ptid =3D null_ptid; =A0=A0=A0=A0=A0=A0=A0=A0 =A0/* Suppress spurious "Switching to ..." message= . =A0*/ =A0=A0=A0=A0=A0=A0=A0=A0 =A0previous_inferior_ptid =3D inferior_ptid; =A0 @@ -1649,6 +1674,8 @@ handle_inferior_event (struct execution_control_state= *ecs) =A0=A0=A0=A0=A0=A0=A0=A0 =A0prepare_to_wait (ecs); =A0=A0=A0=A0=A0=A0=A0=A0 =A0return; =A0=A0=A0=A0=A0=A0=A0=A0} + + =A0 =A0 =A0deferred_step_ptid =3D null_ptid; =A0 =A0 =A0} =A0 =A0 =A0/* See if a thread hit a thread-specific breakpoint that was meant f= or @@ -1779,7 +1806,7 @@ handle_inferior_event (struct execution_control_state= *ecs) =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0context_switch (ecs); =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0ecs->waiton_ptid =3D ecs->ptid; =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0ecs->wp =3D &(ecs->ws); -=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0ecs->another_trap =3D 1; +=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0ecs->stepping_over_breakpoint =3D 1; =A0 =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0ecs->infwait_state =3D infwait_thread_h= op_state; =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0keep_going (ecs); @@ -1870,7 +1897,7 @@ handle_inferior_event (struct execution_control_state= *ecs) =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 = =A0 =A0&ecs->stop_func_start, &ecs->stop_func_end); =A0 =A0ecs->stop_func_start =A0 =A0 =A0+=3D gdbarch_deprecated_function_start_offset (current_gdbarch); - =A0ecs->another_trap =3D 0; + =A0ecs->stepping_over_breakpoint =3D 0; =A0 =A0bpstat_clear (&stop_bpstat); =A0 =A0stop_step =3D 0; =A0 =A0stop_stack_dummy =3D 0; @@ -1879,7 +1906,7 @@ handle_inferior_event (struct execution_control_state= *ecs) =A0 =A0stopped_by_random_signal =3D 0; =A0 =A0 =A0if (stop_signal =3D=3D TARGET_SIGNAL_TRAP - =A0 =A0 =A0&& trap_expected + =A0 =A0 =A0&& stepping_over_breakpoint =A0 =A0 =A0 =A0&& gdbarch_single_step_through_delay_p (current_gdbarch) =A0 =A0 =A0 =A0&& currently_stepping (ecs)) =A0 =A0 =A0{ @@ -1897,7 +1924,7 @@ handle_inferior_event (struct execution_control_state= *ecs) =A0=A0=A0=A0=A0=A0=A0=A0{ =A0=A0=A0=A0=A0=A0=A0=A0 =A0/* The user issued a continue when stopped at a= breakpoint. =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 Set up for another trap and get out of her= e. =A0*/ - =A0 =A0 =A0 =A0 ecs->another_trap =3D 1; + =A0 =A0 =A0 =A0 ecs->stepping_over_breakpoint =3D 1; =A0 =A0 =A0 =A0 =A0 keep_going (ecs); =A0 =A0 =A0 =A0 =A0 return; =A0=A0=A0=A0=A0=A0=A0=A0} @@ -1906,10 +1933,10 @@ handle_inferior_event (struct execution_control_sta= te *ecs) =A0=A0=A0=A0=A0=A0=A0=A0 =A0/* The user issued a step when stopped at a bre= akpoint. =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 Maybe we should stop, maybe we should not = - the delay =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 slot *might* correspond to a line of sourc= e. =A0In any -=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 case, don't decide that here, just set ecs->= another_trap, -=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 making sure we single-step again before brea= kpoints are -=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 re-inserted. =A0*/ -=A0=A0=A0=A0=A0=A0=A0 =A0ecs->another_trap =3D 1; +=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 case, don't decide that here, just set=20 +=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 ecs->stepping_over_breakpoint, making sure w= e=20 +=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 single-step again before breakpoints are re-= inserted. =A0*/ +=A0=A0=A0=A0=A0=A0=A0 =A0ecs->stepping_over_breakpoint =3D 1; =A0=A0=A0=A0=A0=A0=A0=A0} =A0 =A0 =A0} =A0 @@ -1917,7 +1944,7 @@ handle_inferior_event (struct execution_control_state= *ecs) =A0 =A0 =A0 The alternatives are: =A0 =A0 =A0 1) break; to really stop and return to the debugger, =A0 =A0 =A0 2) drop through to start up again - =A0 =A0 (set ecs->another_trap to 1 to single step once) + =A0 =A0 (set ecs->stepping_over_breakpoint to 1 to single step once) =A0 =A0 =A0 3) set ecs->random_signal to 1, and the decision between 1 and 2 =A0 =A0 =A0 will be made according to the signal handling tables. =A0*/ =A0 @@ -2001,7 +2028,7 @@ handle_inferior_event (struct execution_control_state= *ecs) =A0 =A0 =A0 =A0if (stop_signal =3D=3D TARGET_SIGNAL_TRAP) =A0=A0=A0=A0=A0=A0=A0=A0ecs->random_signal =A0=A0=A0=A0=A0=A0=A0=A0 =A0=3D !(bpstat_explains_signal (stop_bpstat) -=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0|| trap_expected +=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0|| stepping_over_breakpoint =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0|| (step_range_end && step_resume_break= point =3D=3D NULL)); =A0 =A0 =A0 =A0else =A0=A0=A0=A0=A0=A0=A0=A0{ @@ -2162,7 +2189,7 @@ process_event_stop_test: =A0 =A0 =A0 =A0 =A0if (debug_infrun) =A0=A0=A0=A0=A0=A0=A0=A0 =A0fprintf_unfiltered (gdb_stdlog, "infrun: BPSTAT= _WHAT_SINGLE\n"); =A0=A0=A0=A0=A0=A0=A0=A0remove_breakpoints (); -=A0=A0=A0=A0=A0=A0=A0ecs->another_trap =3D 1; +=A0=A0=A0=A0=A0=A0=A0ecs->stepping_over_breakpoint =3D 1; =A0=A0=A0=A0=A0=A0=A0=A0/* Still need to check other stuff, at least the ca= se =A0=A0=A0=A0=A0=A0=A0=A0 =A0 where we are stepping and step out of the righ= t range. =A0*/ =A0=A0=A0=A0=A0=A0=A0=A0break; @@ -2223,7 +2250,7 @@ process_event_stop_test: =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0 to doing that. =A0*/ =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0ecs->step_after_step_resume_breakpoint =3D = 0; =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0remove_breakpoints (); -=A0=A0=A0=A0=A0=A0=A0 =A0 =A0ecs->another_trap =3D 1; +=A0=A0=A0=A0=A0=A0=A0 =A0 =A0ecs->stepping_over_breakpoint =3D 1; =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0keep_going (ecs); =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0return; =A0=A0=A0=A0=A0=A0=A0=A0 =A0} @@ -2308,13 +2335,13 @@ process_event_stop_test: =A0 =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0/* Be sure to lift all breakpoints, so = the inferior does =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0 =A0 actually step past this point... */ -=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0ecs->another_trap =3D 1; +=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0ecs->stepping_over_breakpoint =3D 1; =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0break; =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0} =A0=A0=A0=A0=A0=A0=A0=A0 =A0else =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0{ =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0/* We want to step over this breakpoint= , then keep going. =A0*/ -=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0ecs->another_trap =3D 1; +=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0ecs->stepping_over_breakpoint =3D 1; =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0break; =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0} =A0=A0=A0=A0=A0=A0=A0=A0} @@ -2345,7 +2372,7 @@ process_event_stop_test: =A0=A0=A0=A0=A0=A0=A0=A0{ =A0 =A0 =A0 =A0 =A0 =A0if (debug_infrun) =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0fprintf_unfiltered (gdb_stdlog, "infrun: st= epping in dynamic linker\n"); -=A0=A0=A0=A0=A0=A0=A0 =A0ecs->another_trap =3D 1; +=A0=A0=A0=A0=A0=A0=A0 =A0ecs->stepping_over_breakpoint =3D 1; =A0=A0=A0=A0=A0=A0=A0=A0 =A0keep_going (ecs); =A0=A0=A0=A0=A0=A0=A0=A0 =A0return; =A0=A0=A0=A0=A0=A0=A0=A0} @@ -2741,7 +2768,7 @@ currently_stepping (struct execution_control_state *e= cs) =A0{ =A0 =A0return ((!ecs->handling_longjmp =A0=A0=A0=A0=A0=A0=A0=A0 =A0 && ((step_range_end && step_resume_breakpoint = =3D=3D NULL) -=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0 || trap_expected)) +=A0=A0=A0=A0=A0=A0=A0 =A0 =A0 =A0 || stepping_over_breakpoint)) =A0=A0=A0=A0=A0=A0=A0=A0 =A0|| ecs->stepping_through_solib_after_catch =A0=A0=A0=A0=A0=A0=A0=A0 =A0|| bpstat_should_step ()); =A0} @@ -2920,7 +2947,7 @@ keep_going (struct execution_control_state *ecs) =A0 =A0/* If we did not do break;, it means we should keep running the =A0 =A0 =A0 inferior and not return to debugger. =A0*/ =A0 - =A0if (trap_expected && stop_signal !=3D TARGET_SIGNAL_TRAP) + =A0if (stepping_over_breakpoint && stop_signal !=3D TARGET_SIGNAL_TRAP) =A0 =A0 =A0{ =A0 =A0 =A0 =A0/* We took a signal (which we are supposed to pass through to =A0 =A0 =A0 =A0 =A0 the inferior, else we'd have done a break above) and we @@ -2942,7 +2969,7 @@ keep_going (struct execution_control_state *ecs) =A0=A0=A0=A0=A0=A0=A0=A0 already inserted breakpoints. =A0Therefore, we don= 't =A0=A0=A0=A0=A0=A0=A0=A0 care if breakpoints were already inserted, or not.= =A0*/ =A0 =A0 =A0 =A0 - =A0 =A0 =A0if (!ecs->another_trap) + =A0 =A0 =A0if (!ecs->stepping_over_breakpoint) =A0=A0=A0=A0=A0=A0=A0=A0{ =A0=A0=A0=A0=A0=A0=A0=A0 =A0struct gdb_exception e; =A0=A0=A0=A0=A0=A0=A0=A0 =A0/* Stop stepping when inserting breakpoints @@ -2958,7 +2985,7 @@ keep_going (struct execution_control_state *ecs) =A0=A0=A0=A0=A0=A0=A0=A0 =A0 =A0} =A0=A0=A0=A0=A0=A0=A0=A0} =A0 - =A0 =A0 =A0trap_expected =3D ecs->another_trap; + =A0 =A0 =A0stepping_over_breakpoint =3D ecs->stepping_over_breakpoint; =A0 =A0 =A0 =A0 =A0/* Do not deliver SIGNAL_TRAP (except when the user explicit= ly =A0 =A0 =A0 =A0 =A0 specifies that such a signal should be delivered to the @@ -3676,7 +3703,7 @@ struct inferior_status =A0 =A0int stop_step; =A0 =A0int stop_stack_dummy; =A0 =A0int stopped_by_random_signal; - =A0int trap_expected; + =A0int stepping_over_breakpoint; =A0 =A0CORE_ADDR step_range_start; =A0 =A0CORE_ADDR step_range_end; =A0 =A0struct frame_id step_frame_id; @@ -3722,7 +3749,7 @@ save_inferior_status (int restore_stack_info) =A0 =A0inf_status->stop_step =3D stop_step; =A0 =A0inf_status->stop_stack_dummy =3D stop_stack_dummy; =A0 =A0inf_status->stopped_by_random_signal =3D stopped_by_random_signal; - =A0inf_status->trap_expected =3D trap_expected; + =A0inf_status->stepping_over_breakpoint =3D stepping_over_breakpoint; =A0 =A0inf_status->step_range_start =3D step_range_start; =A0 =A0inf_status->step_range_end =3D step_range_end; =A0 =A0inf_status->step_frame_id =3D step_frame_id; @@ -3774,7 +3801,7 @@ restore_inferior_status (struct inferior_status *inf_= status) =A0 =A0stop_step =3D inf_status->stop_step; =A0 =A0stop_stack_dummy =3D inf_status->stop_stack_dummy; =A0 =A0stopped_by_random_signal =3D inf_status->stopped_by_random_signal; - =A0trap_expected =3D inf_status->trap_expected; + =A0stepping_over_breakpoint =3D inf_status->stepping_over_breakpoint; =A0 =A0step_range_start =3D inf_status->step_range_start; =A0 =A0step_range_end =3D inf_status->step_range_end; =A0 =A0step_frame_id =3D inf_status->step_frame_id; diff --git a/gdb/thread.c b/gdb/thread.c index b6762e1..3c8644b 100644 --- a/gdb/thread.c +++ b/gdb/thread.c @@ -300,7 +300,7 @@ load_infrun_state (ptid_t ptid, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 CORE_ADDR *step_range_= end, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 struct frame_id *step_= frame_id, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 int *handling_longjmp, -=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 int *another_trap, +=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 int *stepping_over_break= point, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 int *stepping_through_= solib_after_catch, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 bpstat *stepping_throu= gh_solib_catchpoints, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 int *current_line, @@ -321,7 +321,7 @@ load_infrun_state (ptid_t ptid, =A0 =A0*step_range_end =3D tp->step_range_end; =A0 =A0*step_frame_id =3D tp->step_frame_id; =A0 =A0*handling_longjmp =3D tp->handling_longjmp; - =A0*another_trap =3D tp->another_trap; + =A0*stepping_over_breakpoint =3D tp->stepping_over_breakpoint; =A0 =A0*stepping_through_solib_after_catch =3D =A0 =A0 =A0tp->stepping_through_solib_after_catch; =A0 =A0*stepping_through_solib_catchpoints =3D @@ -341,7 +341,7 @@ save_infrun_state (ptid_t ptid, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 CORE_ADDR step_range_e= nd, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 const struct frame_id = *step_frame_id, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 int handling_longjmp, -=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 int another_trap, +=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 int stepping_over_breakp= oint, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 int stepping_through_s= olib_after_catch, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 bpstat stepping_throug= h_solib_catchpoints, =A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0=A0 =A0 int current_line, @@ -362,7 +362,7 @@ save_infrun_state (ptid_t ptid, =A0 =A0tp->step_range_end =3D step_range_end; =A0 =A0tp->step_frame_id =3D (*step_frame_id); =A0 =A0tp->handling_longjmp =3D handling_longjmp; - =A0tp->another_trap =3D another_trap; + =A0tp->stepping_over_breakpoint =3D stepping_over_breakpoint; =A0 =A0tp->stepping_through_solib_after_catch =3D stepping_through_solib_af= ter_catch; =A0 =A0tp->stepping_through_solib_catchpoints =3D stepping_through_solib_ca= tchpoints; =A0 =A0tp->current_line =3D current_line; --=20 1.5.3.5 --Boundary-00=_NbpVHPDLeyYgEUP Content-Type: text/x-diff; charset="iso-8859-1"; name="delta.diff" Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename="delta.diff" Content-length: 2977 diff --git a/gdb/infrun.c b/gdb/infrun.c index 043d8f1..77623b6 100644 --- a/gdb/infrun.c +++ b/gdb/infrun.c @@ -463,10 +463,14 @@ static CORE_ADDR singlestep_pc; static ptid_t saved_singlestep_ptid; static int stepping_past_singlestep_breakpoint; -/* Similarly, if we are stepping another thread past a breakpoint, - save the original thread here so that we can resume stepping it later. */ -static ptid_t stepping_past_breakpoint_ptid; -static int stepping_past_breakpoint; +/* If not equal to null_ptid, means that after stepping over breakpoint + is finished, we need to switch to deferred_step_ptid, and step it. + + The use case is when a breakpoint in one thread, and then the user + has switched to another thread and issued 'step'. We need to step over + breakpoint in the thread which hit breakpoint, but then continue + stepping the thread user has selected. */ +static ptid_t deferred_step_ptid; /* Things to clean up if we QUIT out of resume (). */ @@ -714,8 +718,7 @@ prepare_to_proceed (int step) /* If stepping, remember current thread to switch back to. */ if (step) { - stepping_past_breakpoint = 1; - stepping_past_breakpoint_ptid = inferior_ptid; + deferred_step_ptid = inferior_ptid; } /* Switch back to WAIT_PID thread. */ @@ -908,7 +911,7 @@ init_wait_for_inferior (void) clear_proceed_status (); stepping_past_singlestep_breakpoint = 0; - stepping_past_breakpoint = 0; + deferred_step_ptid = null_ptid; } /* This enum encodes possible reasons for doing a target_wait, so that @@ -1643,17 +1646,15 @@ handle_inferior_event (struct execution_control_state *ecs) stepping_past_singlestep_breakpoint = 0; - if (stepping_past_breakpoint) + if (!ptid_equal (deferred_step_ptid, null_ptid)) { - stepping_past_breakpoint = 0; - /* If we stopped for some other reason than single-stepping, ignore the fact that we were supposed to switch back. */ if (stop_signal == TARGET_SIGNAL_TRAP) { if (debug_infrun) fprintf_unfiltered (gdb_stdlog, - "infrun: stepping_past_breakpoint\n"); + "infrun: handling deferred step\n"); /* Pull the single step breakpoints out of the target. */ if (singlestep_breakpoints_inserted_p) @@ -1664,7 +1665,8 @@ handle_inferior_event (struct execution_control_state *ecs) /* Note: We do not call context_switch at this point, as the context is already set up for stepping the original thread. */ - switch_to_thread (stepping_past_breakpoint_ptid); + switch_to_thread (deferred_step_ptid); + deferred_step_ptid = null_ptid; /* Suppress spurious "Switching to ..." message. */ previous_inferior_ptid = inferior_ptid; @@ -1672,6 +1674,8 @@ handle_inferior_event (struct execution_control_state *ecs) prepare_to_wait (ecs); return; } + + deferred_step_ptid = null_ptid; } /* See if a thread hit a thread-specific breakpoint that was meant for --Boundary-00=_NbpVHPDLeyYgEUP--