From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from NAM02-DM3-obe.outbound.protection.outlook.com (mail-dm3nam07on2086.outbound.protection.outlook.com [40.107.95.86]) by sourceware.org (Postfix) with ESMTPS id CD6E93858D37 for ; Fri, 28 Jan 2022 11:03:58 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.1 sourceware.org CD6E93858D37 ARC-Seal: i=1; a=rsa-sha256; s=arcselector9901; d=microsoft.com; cv=none; b=IEShOEM+sD+5RUOIgi28P+lMpvT0yUYtRHOiJ5ojCj5qdgfurTyOKG7//5lnesj+EceZL/lKMEePcjfcBjFlkGJ/MKl7cJT1/p2rhASm//zxuQcNm2kdcqYnb7VC6TTwFF/W6paFzZbnGbi8ME8Lq8QjyvwmJ70bqpyMOU/CbEjPZOWAfLV95kuylmCOvQLNlUff/5ar0lUWDjfDJFtk6HVehBasuPNzqJy66t4srf0oGPzfVmKR4E/ZjH0gImKHhaVgKlLHj0PJ9eppjizlPpfAWKSPameEf1KqXw5c1Oeh9faVVltP0p056kdcFZQ+tYNukOlMqyxp41h7vv6Y+w== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector9901; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-AntiSpam-MessageData-ChunkCount:X-MS-Exchange-AntiSpam-MessageData-0:X-MS-Exchange-AntiSpam-MessageData-1; bh=LsbVLYC+xQJg7uwvGlesl7xLQoTB12364A/cFOsofjk=; b=JcnprnHBJadgS4RcBL7SrwfQGL+SgRSJciCtnM4KhECXPJwC+heCb7RkczQaV7vI2tNAPYzWHIX81zh5cby2UKWKyJWcl9NkRYh/VySJyf/cNV/FoJ1XVY/+WqFM1wgy7Um5YppWtVC6lS43ZhPqLYcUPCZyZlebOk5o7XRo/8QHdZGAyeHqeRFnH1PpRjp286cH9fdqiLTycBwfuZpQ2B9h3Nd51sv7RrK2Hio1tMBOQdNTWs2Wn3/OhsVGSiWPzHhIquQjZPVA07USbOSPQQWpiqBsc6ISeXFlQa723Qq71fVGroaiLw/KYUTZ2npPv+gYg2kBSJJRo0Z+mw+e6g== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 165.204.84.17) smtp.rcpttodomain=sourceware.org smtp.mailfrom=amd.com; dmarc=pass (p=quarantine sp=quarantine pct=100) action=none header.from=amd.com; dkim=none (message not signed); arc=none Received: from DS7PR05CA0011.namprd05.prod.outlook.com (2603:10b6:5:3b9::16) by MWHPR12MB1439.namprd12.prod.outlook.com (2603:10b6:300:12::11) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.4909.12; Fri, 28 Jan 2022 11:03:53 +0000 Received: from DM6NAM11FT017.eop-nam11.prod.protection.outlook.com (2603:10b6:5:3b9:cafe::3d) by DS7PR05CA0011.outlook.office365.com (2603:10b6:5:3b9::16) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.4951.5 via Frontend Transport; Fri, 28 Jan 2022 11:03:53 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 165.204.84.17) smtp.mailfrom=amd.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=amd.com; Received-SPF: Pass (protection.outlook.com: domain of amd.com designates 165.204.84.17 as permitted sender) receiver=protection.outlook.com; client-ip=165.204.84.17; helo=SATLEXMB04.amd.com; Received: from SATLEXMB04.amd.com (165.204.84.17) by DM6NAM11FT017.mail.protection.outlook.com (10.13.172.145) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.20.4930.15 via Frontend Transport; Fri, 28 Jan 2022 11:03:52 +0000 Received: from node-bp126-r03c.amd.com (10.180.168.240) by SATLEXMB04.amd.com (10.181.40.145) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.1.2375.18; Fri, 28 Jan 2022 05:03:51 -0600 From: Lancelot SIX To: CC: , Lancelot SIX Subject: [PATCH v2] gdb: make thread_info::m_thread_fsm a std::unique_ptr Date: Fri, 28 Jan 2022 05:01:07 -0600 Message-ID: <20220128110107.38775-1-lancelot.six@amd.com> X-Mailer: git-send-email 2.17.1 MIME-Version: 1.0 Content-Type: text/plain X-Originating-IP: [10.180.168.240] X-ClientProxiedBy: SATLEXMB03.amd.com (10.181.40.144) To SATLEXMB04.amd.com (10.181.40.145) X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-Office365-Filtering-Correlation-Id: 024e35f1-21ee-4222-a7bd-08d9e24dde98 X-MS-TrafficTypeDiagnostic: MWHPR12MB1439:EE_ X-Microsoft-Antispam-PRVS: X-MS-Oob-TLC-OOBClassifiers: OLM:669; X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0; X-Microsoft-Antispam-Message-Info: HA0cZFPez5PJndtqXe9aCRKc75tF6WB1AWz79gIzwdYRYmeyp/wTreY4uWLmHA7VcgaOLIXghwrQbGF/LImpj38DEIjJu5ZCIjHAd5rZvGVcnAiiEAKZvp4qOYb86clgTN0gsrtjgiAqOSX/FPes7IkqZXZiWXtVt9hxVJmfs2ZP+KsI48Q7klij8Lr3LLjx2u6ftNwa846BhTve1v+xpvD+ZoNJ7n90ZWliwh27lBdohHH63Zf+6sITAa5igoUgrtiQmjPC/CdElYwIFqSk3M/Xd98lCCVVd056hBU5XohGvUjIM9igCWYSN5kxAs+f0ndy2lygDyKQ9WEpW4nA5Vv6o/sT1S4ZDQqiNbMeLHcZN/+JXemvzWfYFtGt4PT72eDQ3bRQtzE3r3zGDMpO/AfwwXJyTQtPtDZg7GvbFqXkO87RoqhzsZy8sIogDIzjYgo/3ytWdrbCK42Cp+GdKHmBe37HHPUJWSN3IFbHLjMdwtnveoWVwg9LVnvBzZi+fe6Wgri/ZpBNdPU1Z76rs4IZ5b5Fw8k0FPyOzA0C0uLyWzOI+T02C3jjUKRKtWxQZXUveOPCb+/B/+XeWCVzwLcriVBzohDkLNWqekymx3hweE5ZEmKzmG4ubWNj81T7bzTlSCQCP8US+GdPNRLvMTnhNxXtnM6sJo/MUiAg1sI5G+BG1HTmAy20tyqcBY/XhIHqzPDaBK0vLettUsGIdMxK8WgSk5EAr9sr1UxQHmtCFR9C4cyHDl2NHpFfLqXRH8GWiyle+N5pJs8r8LIbW0+Nsxd7SKibFKo24pEfmLk99lh5nU5G1vULbLjcJPUqXCH9IDZfyOPVY/9j5qMmR43JmWogfWF8dEwgMT8reWM66/kT2sRmOd+SjaHoG0Ul X-Forefront-Antispam-Report: CIP:165.204.84.17; CTRY:US; LANG:en; SCL:1; SRV:; IPV:CAL; SFV:NSPM; H:SATLEXMB04.amd.com; PTR:InfoDomainNonexistent; CAT:NONE; SFS:(4636009)(46966006)(40470700004)(36840700001)(508600001)(81166007)(8676002)(356005)(83380400001)(966005)(70206006)(70586007)(316002)(2906002)(4326008)(30864003)(8936002)(426003)(6916009)(186003)(86362001)(1076003)(2616005)(336012)(26005)(82310400004)(36756003)(54906003)(40460700003)(7696005)(36860700001)(47076005)(16526019)(6666004)(5660300002)(36900700001); DIR:OUT; SFP:1101; X-OriginatorOrg: amd.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 28 Jan 2022 11:03:52.3603 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: 024e35f1-21ee-4222-a7bd-08d9e24dde98 X-MS-Exchange-CrossTenant-Id: 3dd8961f-e488-4e60-8e11-a82d994e183d X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=3dd8961f-e488-4e60-8e11-a82d994e183d; Ip=[165.204.84.17]; Helo=[SATLEXMB04.amd.com] X-MS-Exchange-CrossTenant-AuthSource: DM6NAM11FT017.eop-nam11.prod.protection.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: MWHPR12MB1439 X-Spam-Status: No, score=-11.4 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, RCVD_IN_DNSWL_NONE, RCVD_IN_MSPIKE_H2, SPF_HELO_PASS, SPF_PASS, TXREP, T_SCC_BODY_TEXT_LINE autolearn=ham autolearn_force=no version=3.4.4 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on server2.sourceware.org X-BeenThere: gdb-patches@sourceware.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Gdb-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Fri, 28 Jan 2022 11:04:02 -0000 This is V2 for https://sourceware.org/pipermail/gdb-patches/2022-January/185300.html. Noteworthy changes since V1: - thread_info::m_thread_fsm is now a private member, allowing assertions to be placed in the setter. - Ensure that the thread FSM is properly removed from the thread_info object even if thread::fsm::clean_up throws. - There was an instance where it was possible to leak a thread_fsm if an exception was thrown while evaluating a function argument. The pattern was: thread_fsm *fsm = new ...; some_call (std::unique_ptr (fsm), if_this_throws_fsm_could_leak ()); Fix this by ensuring that the unique_ptr manages the pointer before the function call. All feedback welcome. Best, Lancelot. --- While working on function calls, I realized that the thread_fsm member of struct thread_info is a raw pointer to a resource it owns. This commit changes the type of the thread_fsm member to a std::unique_ptr in order to signify this ownership relationship and slightly ease resource management (no need to manually call delete). To ensure consistent use, the field is made a private member (m_thread_fsm). The setter method (set_thread_fsm) can then check that it is incorrect to associate a FSM to a thread_info object if another one is already in place. This is ensured by an assertion. The function run_inferior_call takes an argument as a pointer to a call_thread_fsm and installs it in it in a thread_info instance. Also change this function's signature to accept a unique_ptr in order to signify that the ownership of the call_thread_fsm is transferred during the call. No user visible change expected after this commit. Tested on x86_64-linux with no regression observed. Change-Id: Ia1224f72a4afa247801ce6650ce82f90224a9ae8 --- gdb/breakpoint.c | 6 ++++-- gdb/cli/cli-interp.c | 6 +++--- gdb/gdbthread.h | 37 ++++++++++++++++++++++++++++----- gdb/infcall.c | 49 +++++++++++++++++++++++++------------------- gdb/infcmd.c | 8 ++++---- gdb/infrun.c | 44 +++++++++++++++++---------------------- gdb/mi/mi-interp.c | 6 +++--- gdb/thread.c | 7 +++---- 8 files changed, 96 insertions(+), 67 deletions(-) diff --git a/gdb/breakpoint.c b/gdb/breakpoint.c index 9567c737cab..3176f6b682b 100644 --- a/gdb/breakpoint.c +++ b/gdb/breakpoint.c @@ -10830,8 +10830,10 @@ until_break_command (const char *arg, int from_tty, int anywhere) breakpoints.emplace_back (std::move (location_breakpoint)); } - tp->thread_fsm = new until_break_fsm (command_interp (), tp->global_num, - std::move (breakpoints)); + tp->set_thread_fsm + (std::unique_ptr + (new until_break_fsm (command_interp (), tp->global_num, + std::move (breakpoints)))); if (lj_deleter) lj_deleter->release (); diff --git a/gdb/cli/cli-interp.c b/gdb/cli/cli-interp.c index 6dc3e6ae2fa..13f599dcde2 100644 --- a/gdb/cli/cli-interp.c +++ b/gdb/cli/cli-interp.c @@ -111,9 +111,9 @@ should_print_stop_to_console (struct interp *console_interp, { if ((bpstat_what (tp->control.stop_bpstat).main_action == BPSTAT_WHAT_STOP_NOISY) - || tp->thread_fsm == NULL - || tp->thread_fsm->command_interp == console_interp - || !tp->thread_fsm->finished_p ()) + || tp->get_thread_fsm () == nullptr + || tp->get_thread_fsm ()->command_interp == console_interp + || !tp->get_thread_fsm ()->finished_p ()) return 1; return 0; } diff --git a/gdb/gdbthread.h b/gdb/gdbthread.h index 9921dae7a71..f6e899a3b0c 100644 --- a/gdb/gdbthread.h +++ b/gdb/gdbthread.h @@ -34,6 +34,7 @@ struct symtab; #include "gdbsupport/forward-scope-exit.h" #include "displaced-stepping.h" #include "gdbsupport/intrusive_list.h" +#include "thread-fsm.h" struct inferior; struct process_stratum_target; @@ -443,6 +444,32 @@ class thread_info : public refcounted_object, m_suspend.stop_reason = reason; } + /* Get the FSM associated with the thread. */ + + struct thread_fsm *get_thread_fsm () const + { + return m_thread_fsm.get (); + } + + /* Get the owning reference to the FSM associated with the thread. + + After a call to this method, "get_thread_fsm == null". */ + + std::unique_ptr release_thread_fsm () + { + return std::move (m_thread_fsm); + } + + /* Set the FSM associated with the current thread. + + It is invalid to set the FSM if another FSM is already installed. */ + + void set_thread_fsm (std::unique_ptr fsm) + { + gdb_assert (m_thread_fsm == nullptr); + m_thread_fsm = std::move (fsm); + } + int current_line = 0; struct symtab *current_symtab = NULL; @@ -480,11 +507,6 @@ class thread_info : public refcounted_object, when GDB gets back SIGTRAP from step_resume_breakpoint. */ int step_after_step_resume_breakpoint = 0; - /* Pointer to the state machine manager object that handles what is - left to do for the thread's execution command after the target - stops. Several execution commands use it. */ - struct thread_fsm *thread_fsm = NULL; - /* This is used to remember when a fork or vfork event was caught by a catchpoint, and thus the event is to be followed at the next resume of the thread, and not immediately. */ @@ -550,6 +572,11 @@ class thread_info : public refcounted_object, Nullptr if the thread does not have a user-given name. */ gdb::unique_xmalloc_ptr m_name; + + /* Pointer to the state machine manager object that handles what is + left to do for the thread's execution command after the target + stops. Several execution commands use it. */ + std::unique_ptr m_thread_fsm; }; using thread_info_resumed_with_pending_wait_status_node diff --git a/gdb/infcall.c b/gdb/infcall.c index 05cf18f0a7f..d1c054bd10f 100644 --- a/gdb/infcall.c +++ b/gdb/infcall.c @@ -574,7 +574,7 @@ call_thread_fsm::should_notify_stop () thrown errors. The caller should rethrow if there's an error. */ static struct gdb_exception -run_inferior_call (struct call_thread_fsm *sm, +run_inferior_call (std::unique_ptr sm, struct thread_info *call_thread, CORE_ADDR real_pc) { struct gdb_exception caught_error; @@ -597,9 +597,8 @@ run_inferior_call (struct call_thread_fsm *sm, clear_proceed_status (0); /* Associate the FSM with the thread after clear_proceed_status - (otherwise it'd clear this FSM), and before anything throws, so - we don't leak it (and any resources it manages). */ - call_thread->thread_fsm = sm; + (otherwise it'd clear this FSM). */ + call_thread->set_thread_fsm (std::move (sm)); disable_watchpoints_before_interactive_call_start (); @@ -1251,12 +1250,9 @@ call_function_by_hand_dummy (struct value *function, just below is the place to chop this function in two.. */ { - struct thread_fsm *saved_sm; - struct call_thread_fsm *sm; - /* Save the current FSM. We'll override it. */ - saved_sm = call_thread->thread_fsm; - call_thread->thread_fsm = NULL; + std::unique_ptr saved_sm = call_thread->release_thread_fsm (); + struct call_thread_fsm *sm; /* Save this thread's ptid, we need it later but the thread may have exited. */ @@ -1273,17 +1269,19 @@ call_function_by_hand_dummy (struct value *function, values_type, return_method != return_method_normal, struct_addr); - - e = run_inferior_call (sm, call_thread.get (), real_pc); + { + std::unique_ptr sm_up (sm); + e = run_inferior_call (std::move (sm_up), call_thread.get (), real_pc); + } gdb::observers::inferior_call_post.notify (call_thread_ptid, funaddr); if (call_thread->state != THREAD_EXITED) { /* The FSM should still be the same. */ - gdb_assert (call_thread->thread_fsm == sm); + gdb_assert (call_thread->get_thread_fsm () == sm); - if (call_thread->thread_fsm->finished_p ()) + if (call_thread->get_thread_fsm ()->finished_p ()) { struct value *retval; @@ -1297,11 +1295,16 @@ call_function_by_hand_dummy (struct value *function, /* Get the return value. */ retval = sm->return_value; - /* Clean up / destroy the call FSM, and restore the - original one. */ - call_thread->thread_fsm->clean_up (call_thread.get ()); - delete call_thread->thread_fsm; - call_thread->thread_fsm = saved_sm; + /* Restore the original FSM and clean up / destroh the call FSM. + Doing it in this order ensures that if the call to clean_up + throws, the original FSM is properly restored. */ + { + std::unique_ptr finalizing + = call_thread->release_thread_fsm (); + call_thread->set_thread_fsm (std::move (saved_sm)); + + finalizing->clean_up (call_thread.get ()); + } maybe_remove_breakpoints (); @@ -1315,9 +1318,13 @@ call_function_by_hand_dummy (struct value *function, /* Didn't complete. Clean up / destroy the call FSM, and restore the previous state machine, and handle the error. */ - call_thread->thread_fsm->clean_up (call_thread.get ()); - delete call_thread->thread_fsm; - call_thread->thread_fsm = saved_sm; + { + std::unique_ptr finalizing + = call_thread->release_thread_fsm (); + call_thread->set_thread_fsm (std::move (saved_sm)); + + finalizing->clean_up (call_thread.get ()); + } } } diff --git a/gdb/infcmd.c b/gdb/infcmd.c index 994dd5b32a3..63f633e601f 100644 --- a/gdb/infcmd.c +++ b/gdb/infcmd.c @@ -848,7 +848,7 @@ step_1 (int skip_subroutines, int single_inst, const char *count_string) steps. */ thr = inferior_thread (); step_sm = new step_command_fsm (command_interp ()); - thr->thread_fsm = step_sm; + thr->set_thread_fsm (std::unique_ptr (step_sm)); step_command_fsm_prepare (step_sm, skip_subroutines, single_inst, count, thr); @@ -865,7 +865,7 @@ step_1 (int skip_subroutines, int single_inst, const char *count_string) /* Stepped into an inline frame. Pretend that we've stopped. */ - thr->thread_fsm->clean_up (thr); + thr->get_thread_fsm ()->clean_up (thr); proceeded = normal_stop (); if (!proceeded) inferior_event_handler (INF_EXEC_COMPLETE); @@ -1355,7 +1355,7 @@ until_next_command (int from_tty) delete_longjmp_breakpoint_cleanup lj_deleter (thread); sm = new until_next_fsm (command_interp (), tp->global_num); - tp->thread_fsm = sm; + tp->set_thread_fsm (std::unique_ptr (sm)); lj_deleter.release (); proceed ((CORE_ADDR) -1, GDB_SIGNAL_DEFAULT); @@ -1762,7 +1762,7 @@ finish_command (const char *arg, int from_tty) sm = new finish_command_fsm (command_interp ()); - tp->thread_fsm = sm; + tp->set_thread_fsm (std::unique_ptr (sm)); /* Finishing from an inline frame is completely different. We don't try to show the "return value" - no way to locate it. */ diff --git a/gdb/infrun.c b/gdb/infrun.c index 2e7ed15723f..6648028cbe2 100644 --- a/gdb/infrun.c +++ b/gdb/infrun.c @@ -698,7 +698,6 @@ follow_fork () int current_line = 0; symtab *current_symtab = NULL; struct frame_id step_frame_id = { 0 }; - struct thread_fsm *thread_fsm = NULL; if (!non_stop) { @@ -741,6 +740,7 @@ follow_fork () case TARGET_WAITKIND_VFORKED: { ptid_t parent, child; + std::unique_ptr thread_fsm; /* If the user did a next/step, etc, over a fork call, preserve the stepping state in the fork child. */ @@ -755,7 +755,7 @@ follow_fork () step_frame_id = tp->control.step_frame_id; exception_resume_breakpoint = clone_momentary_breakpoint (tp->control.exception_resume_breakpoint); - thread_fsm = tp->thread_fsm; + thread_fsm = tp->release_thread_fsm (); /* For now, delete the parent's sr breakpoint, otherwise, parent/child sr breakpoints are considered duplicates, @@ -767,7 +767,6 @@ follow_fork () tp->control.step_range_end = 0; tp->control.step_frame_id = null_frame_id; delete_exception_resume_breakpoint (tp); - tp->thread_fsm = NULL; } parent = inferior_ptid; @@ -809,7 +808,7 @@ follow_fork () tp->control.step_frame_id = step_frame_id; tp->control.exception_resume_breakpoint = exception_resume_breakpoint; - tp->thread_fsm = thread_fsm; + tp->set_thread_fsm (std::move (thread_fsm)); } else { @@ -2651,8 +2650,7 @@ clear_proceed_status_thread (struct thread_info *tp) if (!signal_pass_state (tp->stop_signal ())) tp->set_stop_signal (GDB_SIGNAL_0); - delete tp->thread_fsm; - tp->thread_fsm = NULL; + tp->release_thread_fsm (); tp->control.trap_expected = 0; tp->control.step_range_start = 0; @@ -3935,24 +3933,24 @@ reinstall_readline_callback_handler_cleanup () static void clean_up_just_stopped_threads_fsms (struct execution_control_state *ecs) { - if (ecs->event_thread != NULL - && ecs->event_thread->thread_fsm != NULL) - ecs->event_thread->thread_fsm->clean_up (ecs->event_thread); + if (ecs->event_thread != nullptr + && ecs->event_thread->get_thread_fsm () != nullptr) + ecs->event_thread->get_thread_fsm ()->clean_up (ecs->event_thread); if (!non_stop) { for (thread_info *thr : all_non_exited_threads ()) { - if (thr->thread_fsm == NULL) + if (thr->get_thread_fsm () == nullptr) continue; if (thr == ecs->event_thread) continue; switch_to_thread (thr); - thr->thread_fsm->clean_up (thr); + thr->get_thread_fsm ()->clean_up (thr); } - if (ecs->event_thread != NULL) + if (ecs->event_thread != nullptr) switch_to_thread (ecs->event_thread); } } @@ -4103,13 +4101,8 @@ fetch_inferior_event () delete_just_stopped_threads_infrun_breakpoints (); - if (thr != NULL) - { - struct thread_fsm *thread_fsm = thr->thread_fsm; - - if (thread_fsm != NULL) - should_stop = thread_fsm->should_stop (thr); - } + if (thr != nullptr && thr->get_thread_fsm () != nullptr) + should_stop = thr->get_thread_fsm ()->should_stop (thr); if (!should_stop) { @@ -4122,8 +4115,9 @@ fetch_inferior_event () clean_up_just_stopped_threads_fsms (ecs); - if (thr != NULL && thr->thread_fsm != NULL) - should_notify_stop = thr->thread_fsm->should_notify_stop (); + if (thr != nullptr && thr->get_thread_fsm () != nullptr) + should_notify_stop + = thr->get_thread_fsm ()->should_notify_stop (); if (should_notify_stop) { @@ -8340,13 +8334,13 @@ print_stop_event (struct ui_out *uiout, bool displays) } tp = inferior_thread (); - if (tp->thread_fsm != NULL - && tp->thread_fsm->finished_p ()) + if (tp->get_thread_fsm () != nullptr + && tp->get_thread_fsm ()->finished_p ()) { struct return_value_info *rv; - rv = tp->thread_fsm->return_value (); - if (rv != NULL) + rv = tp->get_thread_fsm ()->return_value (); + if (rv != nullptr) print_return_value (uiout, rv); } } diff --git a/gdb/mi/mi-interp.c b/gdb/mi/mi-interp.c index e69ad9aff2d..3cb5e53995e 100644 --- a/gdb/mi/mi-interp.c +++ b/gdb/mi/mi-interp.c @@ -630,12 +630,12 @@ mi_on_normal_stop_1 (struct bpstat *bs, int print_frame) tp = inferior_thread (); - if (tp->thread_fsm != NULL - && tp->thread_fsm->finished_p ()) + if (tp->get_thread_fsm () != nullptr + && tp->get_thread_fsm ()->finished_p ()) { enum async_reply_reason reason; - reason = tp->thread_fsm->async_reply_reason (); + reason = tp->get_thread_fsm ()->async_reply_reason (); mi_uiout->field_string ("reason", async_reason_lookup (reason)); } diff --git a/gdb/thread.c b/gdb/thread.c index 611be3f4633..cd2004a555d 100644 --- a/gdb/thread.c +++ b/gdb/thread.c @@ -160,11 +160,10 @@ thread_has_single_step_breakpoint_here (struct thread_info *tp, void thread_cancel_execution_command (struct thread_info *thr) { - if (thr->thread_fsm != NULL) + if (thr->get_thread_fsm () != nullptr) { - thr->thread_fsm->clean_up (thr); - delete thr->thread_fsm; - thr->thread_fsm = NULL; + std::unique_ptr fsm = thr->release_thread_fsm (); + fsm->clean_up (thr); } } base-commit: 0d8cbc5f2fcbcb9eb207f12507fdfe04f3d3ae14 -- 2.25.1