1cfca06d7SDimitry Andric //===-- SBBreakpoint.cpp --------------------------------------------------===//
2f034231aSEd Maste //
35f29bb8aSDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
45f29bb8aSDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
55f29bb8aSDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6f034231aSEd Maste //
7f034231aSEd Maste //===----------------------------------------------------------------------===//
8f034231aSEd Maste
9f034231aSEd Maste #include "lldb/API/SBBreakpoint.h"
10f034231aSEd Maste #include "lldb/API/SBBreakpointLocation.h"
11f034231aSEd Maste #include "lldb/API/SBDebugger.h"
12f034231aSEd Maste #include "lldb/API/SBEvent.h"
13f034231aSEd Maste #include "lldb/API/SBProcess.h"
14f034231aSEd Maste #include "lldb/API/SBStream.h"
15205afe67SEd Maste #include "lldb/API/SBStringList.h"
16706b4fc4SDimitry Andric #include "lldb/API/SBStructuredData.h"
17f034231aSEd Maste #include "lldb/API/SBThread.h"
186f8fc217SDimitry Andric #include "lldb/Utility/Instrumentation.h"
19f034231aSEd Maste
20f034231aSEd Maste #include "lldb/Breakpoint/Breakpoint.h"
2114f1b3e8SDimitry Andric #include "lldb/Breakpoint/BreakpointIDList.h"
22f034231aSEd Maste #include "lldb/Breakpoint/BreakpointLocation.h"
2394994d37SDimitry Andric #include "lldb/Breakpoint/BreakpointResolver.h"
2494994d37SDimitry Andric #include "lldb/Breakpoint/BreakpointResolverScripted.h"
25f034231aSEd Maste #include "lldb/Breakpoint/StoppointCallbackContext.h"
26f034231aSEd Maste #include "lldb/Core/Address.h"
270cac4ca3SEd Maste #include "lldb/Core/Debugger.h"
28706b4fc4SDimitry Andric #include "lldb/Core/StructuredDataImpl.h"
290cac4ca3SEd Maste #include "lldb/Interpreter/CommandInterpreter.h"
300cac4ca3SEd Maste #include "lldb/Interpreter/ScriptInterpreter.h"
31f034231aSEd Maste #include "lldb/Target/Process.h"
32866dcdacSEd Maste #include "lldb/Target/SectionLoadList.h"
33f034231aSEd Maste #include "lldb/Target/Target.h"
34f034231aSEd Maste #include "lldb/Target/Thread.h"
35f034231aSEd Maste #include "lldb/Target/ThreadSpec.h"
3674a628f7SDimitry Andric #include "lldb/Utility/Stream.h"
37f034231aSEd Maste
38ef5d0b5eSDimitry Andric #include "SBBreakpointOptionCommon.h"
39ef5d0b5eSDimitry Andric
40f034231aSEd Maste #include "lldb/lldb-enumerations.h"
41f034231aSEd Maste
4214f1b3e8SDimitry Andric #include "llvm/ADT/STLExtras.h"
4314f1b3e8SDimitry Andric
44f034231aSEd Maste using namespace lldb;
45f034231aSEd Maste using namespace lldb_private;
46f034231aSEd Maste
SBBreakpoint()476f8fc217SDimitry Andric SBBreakpoint::SBBreakpoint() { LLDB_INSTRUMENT_VA(this); }
48f034231aSEd Maste
SBBreakpoint(const SBBreakpoint & rhs)4914f1b3e8SDimitry Andric SBBreakpoint::SBBreakpoint(const SBBreakpoint &rhs)
505f29bb8aSDimitry Andric : m_opaque_wp(rhs.m_opaque_wp) {
516f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, rhs);
525f29bb8aSDimitry Andric }
53f034231aSEd Maste
SBBreakpoint(const lldb::BreakpointSP & bp_sp)5414f1b3e8SDimitry Andric SBBreakpoint::SBBreakpoint(const lldb::BreakpointSP &bp_sp)
555f29bb8aSDimitry Andric : m_opaque_wp(bp_sp) {
566f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, bp_sp);
575f29bb8aSDimitry Andric }
58f034231aSEd Maste
59e81d9d49SDimitry Andric SBBreakpoint::~SBBreakpoint() = default;
60f034231aSEd Maste
operator =(const SBBreakpoint & rhs)6114f1b3e8SDimitry Andric const SBBreakpoint &SBBreakpoint::operator=(const SBBreakpoint &rhs) {
626f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, rhs);
635f29bb8aSDimitry Andric
6474a628f7SDimitry Andric m_opaque_wp = rhs.m_opaque_wp;
656f8fc217SDimitry Andric return *this;
66f034231aSEd Maste }
67f034231aSEd Maste
operator ==(const lldb::SBBreakpoint & rhs)6814f1b3e8SDimitry Andric bool SBBreakpoint::operator==(const lldb::SBBreakpoint &rhs) {
696f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, rhs);
705f29bb8aSDimitry Andric
7174a628f7SDimitry Andric return m_opaque_wp.lock() == rhs.m_opaque_wp.lock();
72f034231aSEd Maste }
73f034231aSEd Maste
operator !=(const lldb::SBBreakpoint & rhs)7414f1b3e8SDimitry Andric bool SBBreakpoint::operator!=(const lldb::SBBreakpoint &rhs) {
756f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, rhs);
765f29bb8aSDimitry Andric
7774a628f7SDimitry Andric return m_opaque_wp.lock() != rhs.m_opaque_wp.lock();
78f034231aSEd Maste }
79f034231aSEd Maste
GetTarget() const80b60736ecSDimitry Andric SBTarget SBBreakpoint::GetTarget() const {
816f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
82b60736ecSDimitry Andric
83b60736ecSDimitry Andric BreakpointSP bkpt_sp = GetSP();
84b60736ecSDimitry Andric if (bkpt_sp)
856f8fc217SDimitry Andric return SBTarget(bkpt_sp->GetTargetSP());
86b60736ecSDimitry Andric
876f8fc217SDimitry Andric return SBTarget();
88b60736ecSDimitry Andric }
89b60736ecSDimitry Andric
GetID() const9014f1b3e8SDimitry Andric break_id_t SBBreakpoint::GetID() const {
916f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
92f034231aSEd Maste
93f034231aSEd Maste break_id_t break_id = LLDB_INVALID_BREAK_ID;
9474a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
9574a628f7SDimitry Andric if (bkpt_sp)
9674a628f7SDimitry Andric break_id = bkpt_sp->GetID();
97f034231aSEd Maste
98f034231aSEd Maste return break_id;
99f034231aSEd Maste }
100f034231aSEd Maste
IsValid() const10114f1b3e8SDimitry Andric bool SBBreakpoint::IsValid() const {
1026f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
1035f29bb8aSDimitry Andric return this->operator bool();
1045f29bb8aSDimitry Andric }
operator bool() const1055f29bb8aSDimitry Andric SBBreakpoint::operator bool() const {
1066f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
1075f29bb8aSDimitry Andric
10874a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
10974a628f7SDimitry Andric if (!bkpt_sp)
1100cac4ca3SEd Maste return false;
11174a628f7SDimitry Andric else if (bkpt_sp->GetTarget().GetBreakpointByID(bkpt_sp->GetID()))
1120cac4ca3SEd Maste return true;
1130cac4ca3SEd Maste else
1140cac4ca3SEd Maste return false;
115f034231aSEd Maste }
116f034231aSEd Maste
ClearAllBreakpointSites()11714f1b3e8SDimitry Andric void SBBreakpoint::ClearAllBreakpointSites() {
1186f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
1195f29bb8aSDimitry Andric
12074a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
12174a628f7SDimitry Andric if (bkpt_sp) {
12214f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
12374a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
12474a628f7SDimitry Andric bkpt_sp->ClearAllBreakpointSites();
125f034231aSEd Maste }
126f034231aSEd Maste }
127f034231aSEd Maste
FindLocationByAddress(addr_t vm_addr)12814f1b3e8SDimitry Andric SBBreakpointLocation SBBreakpoint::FindLocationByAddress(addr_t vm_addr) {
1296f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, vm_addr);
1305f29bb8aSDimitry Andric
131f034231aSEd Maste SBBreakpointLocation sb_bp_location;
132f034231aSEd Maste
13374a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
13474a628f7SDimitry Andric if (bkpt_sp) {
13514f1b3e8SDimitry Andric if (vm_addr != LLDB_INVALID_ADDRESS) {
13614f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
13774a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
138f034231aSEd Maste Address address;
13974a628f7SDimitry Andric Target &target = bkpt_sp->GetTarget();
14014f1b3e8SDimitry Andric if (!target.GetSectionLoadList().ResolveLoadAddress(vm_addr, address)) {
141f034231aSEd Maste address.SetRawAddress(vm_addr);
142f034231aSEd Maste }
14374a628f7SDimitry Andric sb_bp_location.SetLocation(bkpt_sp->FindLocationByAddress(address));
144f034231aSEd Maste }
145f034231aSEd Maste }
1466f8fc217SDimitry Andric return sb_bp_location;
147f034231aSEd Maste }
148f034231aSEd Maste
FindLocationIDByAddress(addr_t vm_addr)14914f1b3e8SDimitry Andric break_id_t SBBreakpoint::FindLocationIDByAddress(addr_t vm_addr) {
1506f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, vm_addr);
1515f29bb8aSDimitry Andric
152f034231aSEd Maste break_id_t break_id = LLDB_INVALID_BREAK_ID;
15374a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
154f034231aSEd Maste
15574a628f7SDimitry Andric if (bkpt_sp && vm_addr != LLDB_INVALID_ADDRESS) {
15614f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
15774a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
158f034231aSEd Maste Address address;
15974a628f7SDimitry Andric Target &target = bkpt_sp->GetTarget();
16014f1b3e8SDimitry Andric if (!target.GetSectionLoadList().ResolveLoadAddress(vm_addr, address)) {
161f034231aSEd Maste address.SetRawAddress(vm_addr);
162f034231aSEd Maste }
16374a628f7SDimitry Andric break_id = bkpt_sp->FindLocationIDByAddress(address);
164f034231aSEd Maste }
165f034231aSEd Maste
166f034231aSEd Maste return break_id;
167f034231aSEd Maste }
168f034231aSEd Maste
FindLocationByID(break_id_t bp_loc_id)16914f1b3e8SDimitry Andric SBBreakpointLocation SBBreakpoint::FindLocationByID(break_id_t bp_loc_id) {
1706f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, bp_loc_id);
1715f29bb8aSDimitry Andric
172f034231aSEd Maste SBBreakpointLocation sb_bp_location;
17374a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
174f034231aSEd Maste
17574a628f7SDimitry Andric if (bkpt_sp) {
17614f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
17774a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
17874a628f7SDimitry Andric sb_bp_location.SetLocation(bkpt_sp->FindLocationByID(bp_loc_id));
179f034231aSEd Maste }
180f034231aSEd Maste
1816f8fc217SDimitry Andric return sb_bp_location;
182f034231aSEd Maste }
183f034231aSEd Maste
GetLocationAtIndex(uint32_t index)18414f1b3e8SDimitry Andric SBBreakpointLocation SBBreakpoint::GetLocationAtIndex(uint32_t index) {
1856f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, index);
1865f29bb8aSDimitry Andric
187f034231aSEd Maste SBBreakpointLocation sb_bp_location;
18874a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
189f034231aSEd Maste
19074a628f7SDimitry Andric if (bkpt_sp) {
19114f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
19274a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
19374a628f7SDimitry Andric sb_bp_location.SetLocation(bkpt_sp->GetLocationAtIndex(index));
194f034231aSEd Maste }
195f034231aSEd Maste
1966f8fc217SDimitry Andric return sb_bp_location;
197f034231aSEd Maste }
198f034231aSEd Maste
SetEnabled(bool enable)19914f1b3e8SDimitry Andric void SBBreakpoint::SetEnabled(bool enable) {
2006f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, enable);
201f034231aSEd Maste
2025f29bb8aSDimitry Andric BreakpointSP bkpt_sp = GetSP();
203f034231aSEd Maste
20474a628f7SDimitry Andric if (bkpt_sp) {
20514f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
20674a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
20774a628f7SDimitry Andric bkpt_sp->SetEnabled(enable);
208f034231aSEd Maste }
209f034231aSEd Maste }
210f034231aSEd Maste
IsEnabled()21114f1b3e8SDimitry Andric bool SBBreakpoint::IsEnabled() {
2126f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
2135f29bb8aSDimitry Andric
21474a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
21574a628f7SDimitry Andric if (bkpt_sp) {
21614f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
21774a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
21874a628f7SDimitry Andric return bkpt_sp->IsEnabled();
21914f1b3e8SDimitry Andric } else
220f034231aSEd Maste return false;
221f034231aSEd Maste }
222f034231aSEd Maste
SetOneShot(bool one_shot)22314f1b3e8SDimitry Andric void SBBreakpoint::SetOneShot(bool one_shot) {
2246f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, one_shot);
225f034231aSEd Maste
2265f29bb8aSDimitry Andric BreakpointSP bkpt_sp = GetSP();
227f034231aSEd Maste
22874a628f7SDimitry Andric if (bkpt_sp) {
22914f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
23074a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
23174a628f7SDimitry Andric bkpt_sp->SetOneShot(one_shot);
232f034231aSEd Maste }
233f034231aSEd Maste }
234f034231aSEd Maste
IsOneShot() const23514f1b3e8SDimitry Andric bool SBBreakpoint::IsOneShot() const {
2366f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
2375f29bb8aSDimitry Andric
23874a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
23974a628f7SDimitry Andric if (bkpt_sp) {
24014f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
24174a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
24274a628f7SDimitry Andric return bkpt_sp->IsOneShot();
24314f1b3e8SDimitry Andric } else
244f034231aSEd Maste return false;
245f034231aSEd Maste }
246f034231aSEd Maste
IsInternal()24714f1b3e8SDimitry Andric bool SBBreakpoint::IsInternal() {
2486f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
2495f29bb8aSDimitry Andric
25074a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
25174a628f7SDimitry Andric if (bkpt_sp) {
25214f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
25374a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
25474a628f7SDimitry Andric return bkpt_sp->IsInternal();
25514f1b3e8SDimitry Andric } else
256f034231aSEd Maste return false;
257f034231aSEd Maste }
258f034231aSEd Maste
SetIgnoreCount(uint32_t count)25914f1b3e8SDimitry Andric void SBBreakpoint::SetIgnoreCount(uint32_t count) {
2606f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, count);
261f034231aSEd Maste
2625f29bb8aSDimitry Andric BreakpointSP bkpt_sp = GetSP();
263f034231aSEd Maste
26474a628f7SDimitry Andric if (bkpt_sp) {
26514f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
26674a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
26774a628f7SDimitry Andric bkpt_sp->SetIgnoreCount(count);
268f034231aSEd Maste }
269f034231aSEd Maste }
270f034231aSEd Maste
SetCondition(const char * condition)27114f1b3e8SDimitry Andric void SBBreakpoint::SetCondition(const char *condition) {
2726f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, condition);
2735f29bb8aSDimitry Andric
27474a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
27574a628f7SDimitry Andric if (bkpt_sp) {
27614f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
27774a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
27874a628f7SDimitry Andric bkpt_sp->SetCondition(condition);
279f034231aSEd Maste }
280f034231aSEd Maste }
281f034231aSEd Maste
GetCondition()28214f1b3e8SDimitry Andric const char *SBBreakpoint::GetCondition() {
2836f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
2845f29bb8aSDimitry Andric
28574a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
2867fa27ce4SDimitry Andric if (!bkpt_sp)
2877fa27ce4SDimitry Andric return nullptr;
2887fa27ce4SDimitry Andric
28914f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
29074a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
2917fa27ce4SDimitry Andric return ConstString(bkpt_sp->GetConditionText()).GetCString();
292f034231aSEd Maste }
293f034231aSEd Maste
SetAutoContinue(bool auto_continue)294ef5d0b5eSDimitry Andric void SBBreakpoint::SetAutoContinue(bool auto_continue) {
2956f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, auto_continue);
2965f29bb8aSDimitry Andric
297ef5d0b5eSDimitry Andric BreakpointSP bkpt_sp = GetSP();
298ef5d0b5eSDimitry Andric if (bkpt_sp) {
299ef5d0b5eSDimitry Andric std::lock_guard<std::recursive_mutex> guard(
300ef5d0b5eSDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
301ef5d0b5eSDimitry Andric bkpt_sp->SetAutoContinue(auto_continue);
302ef5d0b5eSDimitry Andric }
303ef5d0b5eSDimitry Andric }
304ef5d0b5eSDimitry Andric
GetAutoContinue()305ef5d0b5eSDimitry Andric bool SBBreakpoint::GetAutoContinue() {
3066f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
3075f29bb8aSDimitry Andric
308ef5d0b5eSDimitry Andric BreakpointSP bkpt_sp = GetSP();
309ef5d0b5eSDimitry Andric if (bkpt_sp) {
310ef5d0b5eSDimitry Andric std::lock_guard<std::recursive_mutex> guard(
311ef5d0b5eSDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
312ef5d0b5eSDimitry Andric return bkpt_sp->IsAutoContinue();
313ef5d0b5eSDimitry Andric }
314ef5d0b5eSDimitry Andric return false;
315ef5d0b5eSDimitry Andric }
316ef5d0b5eSDimitry Andric
GetHitCount() const31714f1b3e8SDimitry Andric uint32_t SBBreakpoint::GetHitCount() const {
3186f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
3195f29bb8aSDimitry Andric
320f034231aSEd Maste uint32_t count = 0;
32174a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
32274a628f7SDimitry Andric if (bkpt_sp) {
32314f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
32474a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
32574a628f7SDimitry Andric count = bkpt_sp->GetHitCount();
326f034231aSEd Maste }
327f034231aSEd Maste
328f034231aSEd Maste return count;
329f034231aSEd Maste }
330f034231aSEd Maste
GetIgnoreCount() const33114f1b3e8SDimitry Andric uint32_t SBBreakpoint::GetIgnoreCount() const {
3326f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
3335f29bb8aSDimitry Andric
334f034231aSEd Maste uint32_t count = 0;
33574a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
33674a628f7SDimitry Andric if (bkpt_sp) {
33714f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
33874a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
33974a628f7SDimitry Andric count = bkpt_sp->GetIgnoreCount();
340f034231aSEd Maste }
341f034231aSEd Maste
342f034231aSEd Maste return count;
343f034231aSEd Maste }
344f034231aSEd Maste
SetThreadID(tid_t tid)34514f1b3e8SDimitry Andric void SBBreakpoint::SetThreadID(tid_t tid) {
3466f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, tid);
3475f29bb8aSDimitry Andric
34874a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
34974a628f7SDimitry Andric if (bkpt_sp) {
35014f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
35174a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
35274a628f7SDimitry Andric bkpt_sp->SetThreadID(tid);
353f034231aSEd Maste }
354f034231aSEd Maste }
355f034231aSEd Maste
GetThreadID()35614f1b3e8SDimitry Andric tid_t SBBreakpoint::GetThreadID() {
3576f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
3585f29bb8aSDimitry Andric
359f034231aSEd Maste tid_t tid = LLDB_INVALID_THREAD_ID;
36074a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
36174a628f7SDimitry Andric if (bkpt_sp) {
36214f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
36374a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
36474a628f7SDimitry Andric tid = bkpt_sp->GetThreadID();
365f034231aSEd Maste }
366f034231aSEd Maste
367f034231aSEd Maste return tid;
368f034231aSEd Maste }
369f034231aSEd Maste
SetThreadIndex(uint32_t index)37014f1b3e8SDimitry Andric void SBBreakpoint::SetThreadIndex(uint32_t index) {
3716f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, index);
3725f29bb8aSDimitry Andric
37374a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
37474a628f7SDimitry Andric if (bkpt_sp) {
37514f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
37674a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
377344a3780SDimitry Andric bkpt_sp->GetOptions().GetThreadSpec()->SetIndex(index);
378f034231aSEd Maste }
379f034231aSEd Maste }
380f034231aSEd Maste
GetThreadIndex() const38114f1b3e8SDimitry Andric uint32_t SBBreakpoint::GetThreadIndex() const {
3826f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
3835f29bb8aSDimitry Andric
384f034231aSEd Maste uint32_t thread_idx = UINT32_MAX;
38574a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
38674a628f7SDimitry Andric if (bkpt_sp) {
38714f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
38874a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
38914f1b3e8SDimitry Andric const ThreadSpec *thread_spec =
390344a3780SDimitry Andric bkpt_sp->GetOptions().GetThreadSpecNoCreate();
391e81d9d49SDimitry Andric if (thread_spec != nullptr)
392f034231aSEd Maste thread_idx = thread_spec->GetIndex();
393f034231aSEd Maste }
394f034231aSEd Maste
395f034231aSEd Maste return thread_idx;
396f034231aSEd Maste }
397f034231aSEd Maste
SetThreadName(const char * thread_name)39814f1b3e8SDimitry Andric void SBBreakpoint::SetThreadName(const char *thread_name) {
3996f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, thread_name);
4005f29bb8aSDimitry Andric
40174a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
402f034231aSEd Maste
40374a628f7SDimitry Andric if (bkpt_sp) {
40414f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
40574a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
406344a3780SDimitry Andric bkpt_sp->GetOptions().GetThreadSpec()->SetName(thread_name);
407f034231aSEd Maste }
408f034231aSEd Maste }
409f034231aSEd Maste
GetThreadName() const41014f1b3e8SDimitry Andric const char *SBBreakpoint::GetThreadName() const {
4116f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
4125f29bb8aSDimitry Andric
41374a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
4147fa27ce4SDimitry Andric if (!bkpt_sp)
4157fa27ce4SDimitry Andric return nullptr;
4167fa27ce4SDimitry Andric
41714f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
41874a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
4197fa27ce4SDimitry Andric if (const ThreadSpec *thread_spec =
4207fa27ce4SDimitry Andric bkpt_sp->GetOptions().GetThreadSpecNoCreate())
4217fa27ce4SDimitry Andric return ConstString(thread_spec->GetName()).GetCString();
422f034231aSEd Maste
4237fa27ce4SDimitry Andric return nullptr;
424f034231aSEd Maste }
425f034231aSEd Maste
SetQueueName(const char * queue_name)42614f1b3e8SDimitry Andric void SBBreakpoint::SetQueueName(const char *queue_name) {
4276f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, queue_name);
4285f29bb8aSDimitry Andric
4295f29bb8aSDimitry Andric BreakpointSP bkpt_sp = GetSP();
43074a628f7SDimitry Andric if (bkpt_sp) {
43114f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
43274a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
433344a3780SDimitry Andric bkpt_sp->GetOptions().GetThreadSpec()->SetQueueName(queue_name);
434f034231aSEd Maste }
435f034231aSEd Maste }
436f034231aSEd Maste
GetQueueName() const43714f1b3e8SDimitry Andric const char *SBBreakpoint::GetQueueName() const {
4386f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
4395f29bb8aSDimitry Andric
44074a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
4417fa27ce4SDimitry Andric if (!bkpt_sp)
4427fa27ce4SDimitry Andric return nullptr;
4437fa27ce4SDimitry Andric
44414f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
44574a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
4467fa27ce4SDimitry Andric if (const ThreadSpec *thread_spec =
4477fa27ce4SDimitry Andric bkpt_sp->GetOptions().GetThreadSpecNoCreate())
4487fa27ce4SDimitry Andric return ConstString(thread_spec->GetQueueName()).GetCString();
449f034231aSEd Maste
4507fa27ce4SDimitry Andric return nullptr;
451f034231aSEd Maste }
452f034231aSEd Maste
GetNumResolvedLocations() const45314f1b3e8SDimitry Andric size_t SBBreakpoint::GetNumResolvedLocations() const {
4546f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
4555f29bb8aSDimitry Andric
456f034231aSEd Maste size_t num_resolved = 0;
45774a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
45874a628f7SDimitry Andric if (bkpt_sp) {
45914f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
46074a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
46174a628f7SDimitry Andric num_resolved = bkpt_sp->GetNumResolvedLocations();
462f034231aSEd Maste }
463f034231aSEd Maste return num_resolved;
464f034231aSEd Maste }
465f034231aSEd Maste
GetNumLocations() const46614f1b3e8SDimitry Andric size_t SBBreakpoint::GetNumLocations() const {
4676f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
4685f29bb8aSDimitry Andric
46974a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
470f034231aSEd Maste size_t num_locs = 0;
47174a628f7SDimitry Andric if (bkpt_sp) {
47214f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
47374a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
47474a628f7SDimitry Andric num_locs = bkpt_sp->GetNumLocations();
475f034231aSEd Maste }
476f034231aSEd Maste return num_locs;
477f034231aSEd Maste }
478f034231aSEd Maste
SetCommandLineCommands(SBStringList & commands)47914f1b3e8SDimitry Andric void SBBreakpoint::SetCommandLineCommands(SBStringList &commands) {
4806f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, commands);
4815f29bb8aSDimitry Andric
48274a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
48374a628f7SDimitry Andric if (!bkpt_sp)
48414f1b3e8SDimitry Andric return;
48514f1b3e8SDimitry Andric if (commands.GetSize() == 0)
48614f1b3e8SDimitry Andric return;
48714f1b3e8SDimitry Andric
48814f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
48974a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
49014f1b3e8SDimitry Andric std::unique_ptr<BreakpointOptions::CommandData> cmd_data_up(
49114f1b3e8SDimitry Andric new BreakpointOptions::CommandData(*commands, eScriptLanguageNone));
49214f1b3e8SDimitry Andric
493344a3780SDimitry Andric bkpt_sp->GetOptions().SetCommandDataCallback(cmd_data_up);
49414f1b3e8SDimitry Andric }
49514f1b3e8SDimitry Andric
GetCommandLineCommands(SBStringList & commands)49614f1b3e8SDimitry Andric bool SBBreakpoint::GetCommandLineCommands(SBStringList &commands) {
4976f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, commands);
4985f29bb8aSDimitry Andric
49974a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
50074a628f7SDimitry Andric if (!bkpt_sp)
50114f1b3e8SDimitry Andric return false;
50214f1b3e8SDimitry Andric StringList command_list;
50314f1b3e8SDimitry Andric bool has_commands =
504344a3780SDimitry Andric bkpt_sp->GetOptions().GetCommandLineCallbacks(command_list);
50514f1b3e8SDimitry Andric if (has_commands)
50614f1b3e8SDimitry Andric commands.AppendList(command_list);
50714f1b3e8SDimitry Andric return has_commands;
50814f1b3e8SDimitry Andric }
50914f1b3e8SDimitry Andric
GetDescription(SBStream & s)51014f1b3e8SDimitry Andric bool SBBreakpoint::GetDescription(SBStream &s) {
5116f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, s);
5125f29bb8aSDimitry Andric
51314f1b3e8SDimitry Andric return GetDescription(s, true);
51414f1b3e8SDimitry Andric }
51514f1b3e8SDimitry Andric
GetDescription(SBStream & s,bool include_locations)51614f1b3e8SDimitry Andric bool SBBreakpoint::GetDescription(SBStream &s, bool include_locations) {
5176f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, s, include_locations);
5185f29bb8aSDimitry Andric
51974a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
52074a628f7SDimitry Andric if (bkpt_sp) {
52114f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
52274a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
52374a628f7SDimitry Andric s.Printf("SBBreakpoint: id = %i, ", bkpt_sp->GetID());
52474a628f7SDimitry Andric bkpt_sp->GetResolverDescription(s.get());
52574a628f7SDimitry Andric bkpt_sp->GetFilterDescription(s.get());
52614f1b3e8SDimitry Andric if (include_locations) {
52774a628f7SDimitry Andric const size_t num_locations = bkpt_sp->GetNumLocations();
528f034231aSEd Maste s.Printf(", locations = %" PRIu64, (uint64_t)num_locations);
52914f1b3e8SDimitry Andric }
530f034231aSEd Maste return true;
531f034231aSEd Maste }
532f034231aSEd Maste s.Printf("No value");
533f034231aSEd Maste return false;
534f034231aSEd Maste }
535f034231aSEd Maste
AddLocation(SBAddress & address)5365f29bb8aSDimitry Andric SBError SBBreakpoint::AddLocation(SBAddress &address) {
5376f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, address);
5385f29bb8aSDimitry Andric
53994994d37SDimitry Andric BreakpointSP bkpt_sp = GetSP();
54094994d37SDimitry Andric SBError error;
54194994d37SDimitry Andric
54294994d37SDimitry Andric if (!address.IsValid()) {
54394994d37SDimitry Andric error.SetErrorString("Can't add an invalid address.");
5446f8fc217SDimitry Andric return error;
54594994d37SDimitry Andric }
54694994d37SDimitry Andric
54794994d37SDimitry Andric if (!bkpt_sp) {
54894994d37SDimitry Andric error.SetErrorString("No breakpoint to add a location to.");
5496f8fc217SDimitry Andric return error;
55094994d37SDimitry Andric }
55194994d37SDimitry Andric
55294994d37SDimitry Andric if (!llvm::isa<BreakpointResolverScripted>(bkpt_sp->GetResolver().get())) {
55394994d37SDimitry Andric error.SetErrorString("Only a scripted resolver can add locations.");
5546f8fc217SDimitry Andric return error;
55594994d37SDimitry Andric }
55694994d37SDimitry Andric
55794994d37SDimitry Andric if (bkpt_sp->GetSearchFilter()->AddressPasses(address.ref()))
55894994d37SDimitry Andric bkpt_sp->AddLocation(address.ref());
5595f29bb8aSDimitry Andric else {
56094994d37SDimitry Andric StreamString s;
56194994d37SDimitry Andric address.get()->Dump(&s, &bkpt_sp->GetTarget(),
56294994d37SDimitry Andric Address::DumpStyleModuleWithFileAddress);
56394994d37SDimitry Andric error.SetErrorStringWithFormat("Address: %s didn't pass the filter.",
56494994d37SDimitry Andric s.GetData());
56594994d37SDimitry Andric }
5666f8fc217SDimitry Andric return error;
56794994d37SDimitry Andric }
56894994d37SDimitry Andric
SerializeToStructuredData()569b60736ecSDimitry Andric SBStructuredData SBBreakpoint::SerializeToStructuredData() {
5706f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
571b60736ecSDimitry Andric
572b60736ecSDimitry Andric SBStructuredData data;
573b60736ecSDimitry Andric BreakpointSP bkpt_sp = GetSP();
574b60736ecSDimitry Andric
575b60736ecSDimitry Andric if (!bkpt_sp)
5766f8fc217SDimitry Andric return data;
577b60736ecSDimitry Andric
578b60736ecSDimitry Andric StructuredData::ObjectSP bkpt_dict = bkpt_sp->SerializeToStructuredData();
579b60736ecSDimitry Andric data.m_impl_up->SetObjectSP(bkpt_dict);
5806f8fc217SDimitry Andric return data;
581b60736ecSDimitry Andric }
582b60736ecSDimitry Andric
SetCallback(SBBreakpointHitCallback callback,void * baton)5835f29bb8aSDimitry Andric void SBBreakpoint::SetCallback(SBBreakpointHitCallback callback, void *baton) {
5846f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, callback, baton);
58594994d37SDimitry Andric
58674a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
587f034231aSEd Maste
58874a628f7SDimitry Andric if (bkpt_sp) {
58914f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
59074a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
591f034231aSEd Maste BatonSP baton_sp(new SBBreakpointCallbackBaton(callback, baton));
592ef5d0b5eSDimitry Andric bkpt_sp->SetCallback(SBBreakpointCallbackBaton
593ef5d0b5eSDimitry Andric ::PrivateBreakpointHitCallback, baton_sp,
59474a628f7SDimitry Andric false);
595f034231aSEd Maste }
596f034231aSEd Maste }
597f034231aSEd Maste
SetScriptCallbackFunction(const char * callback_function_name)59814f1b3e8SDimitry Andric void SBBreakpoint::SetScriptCallbackFunction(
59914f1b3e8SDimitry Andric const char *callback_function_name) {
6006f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, callback_function_name);
601706b4fc4SDimitry Andric SBStructuredData empty_args;
602706b4fc4SDimitry Andric SetScriptCallbackFunction(callback_function_name, empty_args);
603706b4fc4SDimitry Andric }
6045f29bb8aSDimitry Andric
SetScriptCallbackFunction(const char * callback_function_name,SBStructuredData & extra_args)605706b4fc4SDimitry Andric SBError SBBreakpoint::SetScriptCallbackFunction(
606706b4fc4SDimitry Andric const char *callback_function_name,
607706b4fc4SDimitry Andric SBStructuredData &extra_args) {
6086f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, callback_function_name, extra_args);
609706b4fc4SDimitry Andric SBError sb_error;
61074a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
6110cac4ca3SEd Maste
61274a628f7SDimitry Andric if (bkpt_sp) {
613706b4fc4SDimitry Andric Status error;
61414f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
61574a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
616344a3780SDimitry Andric BreakpointOptions &bp_options = bkpt_sp->GetOptions();
617706b4fc4SDimitry Andric error = bkpt_sp->GetTarget()
61814f1b3e8SDimitry Andric .GetDebugger()
61914f1b3e8SDimitry Andric .GetScriptInterpreter()
62014f1b3e8SDimitry Andric ->SetBreakpointCommandCallbackFunction(bp_options,
621706b4fc4SDimitry Andric callback_function_name,
622706b4fc4SDimitry Andric extra_args.m_impl_up
623706b4fc4SDimitry Andric ->GetObjectSP());
624706b4fc4SDimitry Andric sb_error.SetError(error);
625706b4fc4SDimitry Andric } else
626706b4fc4SDimitry Andric sb_error.SetErrorString("invalid breakpoint");
627706b4fc4SDimitry Andric
6286f8fc217SDimitry Andric return sb_error;
6290cac4ca3SEd Maste }
6300cac4ca3SEd Maste
SetScriptCallbackBody(const char * callback_body_text)63114f1b3e8SDimitry Andric SBError SBBreakpoint::SetScriptCallbackBody(const char *callback_body_text) {
6326f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, callback_body_text);
6335f29bb8aSDimitry Andric
63474a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
6350cac4ca3SEd Maste
6360cac4ca3SEd Maste SBError sb_error;
63774a628f7SDimitry Andric if (bkpt_sp) {
63814f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
63974a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
640344a3780SDimitry Andric BreakpointOptions &bp_options = bkpt_sp->GetOptions();
641b76161e4SDimitry Andric Status error =
64274a628f7SDimitry Andric bkpt_sp->GetTarget()
64314f1b3e8SDimitry Andric .GetDebugger()
64414f1b3e8SDimitry Andric .GetScriptInterpreter()
6457fa27ce4SDimitry Andric ->SetBreakpointCommandCallback(bp_options, callback_body_text,
6467fa27ce4SDimitry Andric /*is_callback=*/false);
6470cac4ca3SEd Maste sb_error.SetError(error);
64814f1b3e8SDimitry Andric } else
6490cac4ca3SEd Maste sb_error.SetErrorString("invalid breakpoint");
6500cac4ca3SEd Maste
6516f8fc217SDimitry Andric return sb_error;
6520cac4ca3SEd Maste }
653f034231aSEd Maste
AddName(const char * new_name)65414f1b3e8SDimitry Andric bool SBBreakpoint::AddName(const char *new_name) {
6556f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, new_name);
6565f29bb8aSDimitry Andric
657cfca06d7SDimitry Andric SBError status = AddNameWithErrorHandling(new_name);
658cfca06d7SDimitry Andric return status.Success();
659cfca06d7SDimitry Andric }
660cfca06d7SDimitry Andric
AddNameWithErrorHandling(const char * new_name)661cfca06d7SDimitry Andric SBError SBBreakpoint::AddNameWithErrorHandling(const char *new_name) {
6626f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, new_name);
663cfca06d7SDimitry Andric
66474a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
665205afe67SEd Maste
666cfca06d7SDimitry Andric SBError status;
66774a628f7SDimitry Andric if (bkpt_sp) {
66814f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
66974a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
670cfca06d7SDimitry Andric Status error;
671ef5d0b5eSDimitry Andric bkpt_sp->GetTarget().AddNameToBreakpoint(bkpt_sp, new_name, error);
672cfca06d7SDimitry Andric status.SetError(error);
673cfca06d7SDimitry Andric } else {
674cfca06d7SDimitry Andric status.SetErrorString("invalid breakpoint");
675ef5d0b5eSDimitry Andric }
676205afe67SEd Maste
6776f8fc217SDimitry Andric return status;
678205afe67SEd Maste }
679205afe67SEd Maste
RemoveName(const char * name_to_remove)68014f1b3e8SDimitry Andric void SBBreakpoint::RemoveName(const char *name_to_remove) {
6816f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, name_to_remove);
6825f29bb8aSDimitry Andric
68374a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
684205afe67SEd Maste
68574a628f7SDimitry Andric if (bkpt_sp) {
68614f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
68774a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
688ef5d0b5eSDimitry Andric bkpt_sp->GetTarget().RemoveNameFromBreakpoint(bkpt_sp,
689ef5d0b5eSDimitry Andric ConstString(name_to_remove));
690205afe67SEd Maste }
691205afe67SEd Maste }
692205afe67SEd Maste
MatchesName(const char * name)69314f1b3e8SDimitry Andric bool SBBreakpoint::MatchesName(const char *name) {
6946f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, name);
6955f29bb8aSDimitry Andric
69674a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
697205afe67SEd Maste
69874a628f7SDimitry Andric if (bkpt_sp) {
69914f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
70074a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
70174a628f7SDimitry Andric return bkpt_sp->MatchesName(name);
702205afe67SEd Maste }
703205afe67SEd Maste
704205afe67SEd Maste return false;
705205afe67SEd Maste }
706205afe67SEd Maste
GetNames(SBStringList & names)70714f1b3e8SDimitry Andric void SBBreakpoint::GetNames(SBStringList &names) {
7086f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, names);
7095f29bb8aSDimitry Andric
71074a628f7SDimitry Andric BreakpointSP bkpt_sp = GetSP();
711205afe67SEd Maste
71274a628f7SDimitry Andric if (bkpt_sp) {
71314f1b3e8SDimitry Andric std::lock_guard<std::recursive_mutex> guard(
71474a628f7SDimitry Andric bkpt_sp->GetTarget().GetAPIMutex());
715205afe67SEd Maste std::vector<std::string> names_vec;
71674a628f7SDimitry Andric bkpt_sp->GetNames(names_vec);
717ac9a064cSDimitry Andric for (const std::string &name : names_vec) {
718205afe67SEd Maste names.AppendString(name.c_str());
719205afe67SEd Maste }
720205afe67SEd Maste }
721205afe67SEd Maste }
722205afe67SEd Maste
EventIsBreakpointEvent(const lldb::SBEvent & event)72314f1b3e8SDimitry Andric bool SBBreakpoint::EventIsBreakpointEvent(const lldb::SBEvent &event) {
7246f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(event);
7255f29bb8aSDimitry Andric
72614f1b3e8SDimitry Andric return Breakpoint::BreakpointEventData::GetEventDataFromEvent(event.get()) !=
72714f1b3e8SDimitry Andric nullptr;
728f034231aSEd Maste }
729f034231aSEd Maste
730f034231aSEd Maste BreakpointEventType
GetBreakpointEventTypeFromEvent(const SBEvent & event)73114f1b3e8SDimitry Andric SBBreakpoint::GetBreakpointEventTypeFromEvent(const SBEvent &event) {
7326f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(event);
7335f29bb8aSDimitry Andric
734f034231aSEd Maste if (event.IsValid())
73514f1b3e8SDimitry Andric return Breakpoint::BreakpointEventData::GetBreakpointEventTypeFromEvent(
73614f1b3e8SDimitry Andric event.GetSP());
737f034231aSEd Maste return eBreakpointEventTypeInvalidType;
738f034231aSEd Maste }
739f034231aSEd Maste
GetBreakpointFromEvent(const lldb::SBEvent & event)74014f1b3e8SDimitry Andric SBBreakpoint SBBreakpoint::GetBreakpointFromEvent(const lldb::SBEvent &event) {
7416f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(event);
7425f29bb8aSDimitry Andric
743f034231aSEd Maste if (event.IsValid())
7446f8fc217SDimitry Andric return SBBreakpoint(
7456f8fc217SDimitry Andric Breakpoint::BreakpointEventData::GetBreakpointFromEvent(event.GetSP()));
7466f8fc217SDimitry Andric return SBBreakpoint();
747f034231aSEd Maste }
748f034231aSEd Maste
749f034231aSEd Maste SBBreakpointLocation
GetBreakpointLocationAtIndexFromEvent(const lldb::SBEvent & event,uint32_t loc_idx)75014f1b3e8SDimitry Andric SBBreakpoint::GetBreakpointLocationAtIndexFromEvent(const lldb::SBEvent &event,
75114f1b3e8SDimitry Andric uint32_t loc_idx) {
7526f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(event, loc_idx);
7535f29bb8aSDimitry Andric
754f034231aSEd Maste SBBreakpointLocation sb_breakpoint_loc;
755f034231aSEd Maste if (event.IsValid())
75614f1b3e8SDimitry Andric sb_breakpoint_loc.SetLocation(
75714f1b3e8SDimitry Andric Breakpoint::BreakpointEventData::GetBreakpointLocationAtIndexFromEvent(
75814f1b3e8SDimitry Andric event.GetSP(), loc_idx));
7596f8fc217SDimitry Andric return sb_breakpoint_loc;
760f034231aSEd Maste }
761f034231aSEd Maste
762f034231aSEd Maste uint32_t
GetNumBreakpointLocationsFromEvent(const lldb::SBEvent & event)76314f1b3e8SDimitry Andric SBBreakpoint::GetNumBreakpointLocationsFromEvent(const lldb::SBEvent &event) {
7646f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(event);
7655f29bb8aSDimitry Andric
766f034231aSEd Maste uint32_t num_locations = 0;
767f034231aSEd Maste if (event.IsValid())
76814f1b3e8SDimitry Andric num_locations =
76914f1b3e8SDimitry Andric (Breakpoint::BreakpointEventData::GetNumBreakpointLocationsFromEvent(
77014f1b3e8SDimitry Andric event.GetSP()));
771f034231aSEd Maste return num_locations;
772f034231aSEd Maste }
77314f1b3e8SDimitry Andric
IsHardware() const77494994d37SDimitry Andric bool SBBreakpoint::IsHardware() const {
7756f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
7765f29bb8aSDimitry Andric
77794994d37SDimitry Andric BreakpointSP bkpt_sp = GetSP();
77894994d37SDimitry Andric if (bkpt_sp)
77994994d37SDimitry Andric return bkpt_sp->IsHardware();
78094994d37SDimitry Andric return false;
78194994d37SDimitry Andric }
78294994d37SDimitry Andric
GetSP() const78374a628f7SDimitry Andric BreakpointSP SBBreakpoint::GetSP() const { return m_opaque_wp.lock(); }
78474a628f7SDimitry Andric
78514f1b3e8SDimitry Andric // This is simple collection of breakpoint id's and their target.
78614f1b3e8SDimitry Andric class SBBreakpointListImpl {
78714f1b3e8SDimitry Andric public:
SBBreakpointListImpl(lldb::TargetSP target_sp)7886f8fc217SDimitry Andric SBBreakpointListImpl(lldb::TargetSP target_sp) {
78914f1b3e8SDimitry Andric if (target_sp && target_sp->IsValid())
79014f1b3e8SDimitry Andric m_target_wp = target_sp;
79114f1b3e8SDimitry Andric }
79214f1b3e8SDimitry Andric
79314f1b3e8SDimitry Andric ~SBBreakpointListImpl() = default;
79414f1b3e8SDimitry Andric
GetSize()79514f1b3e8SDimitry Andric size_t GetSize() { return m_break_ids.size(); }
79614f1b3e8SDimitry Andric
GetBreakpointAtIndex(size_t idx)79714f1b3e8SDimitry Andric BreakpointSP GetBreakpointAtIndex(size_t idx) {
79814f1b3e8SDimitry Andric if (idx >= m_break_ids.size())
79914f1b3e8SDimitry Andric return BreakpointSP();
80014f1b3e8SDimitry Andric TargetSP target_sp = m_target_wp.lock();
80114f1b3e8SDimitry Andric if (!target_sp)
80214f1b3e8SDimitry Andric return BreakpointSP();
80314f1b3e8SDimitry Andric lldb::break_id_t bp_id = m_break_ids[idx];
80414f1b3e8SDimitry Andric return target_sp->GetBreakpointList().FindBreakpointByID(bp_id);
80514f1b3e8SDimitry Andric }
80614f1b3e8SDimitry Andric
FindBreakpointByID(lldb::break_id_t desired_id)80714f1b3e8SDimitry Andric BreakpointSP FindBreakpointByID(lldb::break_id_t desired_id) {
80814f1b3e8SDimitry Andric TargetSP target_sp = m_target_wp.lock();
80914f1b3e8SDimitry Andric if (!target_sp)
81014f1b3e8SDimitry Andric return BreakpointSP();
81114f1b3e8SDimitry Andric
81214f1b3e8SDimitry Andric for (lldb::break_id_t &break_id : m_break_ids) {
81314f1b3e8SDimitry Andric if (break_id == desired_id)
81414f1b3e8SDimitry Andric return target_sp->GetBreakpointList().FindBreakpointByID(break_id);
81514f1b3e8SDimitry Andric }
81614f1b3e8SDimitry Andric return BreakpointSP();
81714f1b3e8SDimitry Andric }
81814f1b3e8SDimitry Andric
Append(BreakpointSP bkpt)81974a628f7SDimitry Andric bool Append(BreakpointSP bkpt) {
82014f1b3e8SDimitry Andric TargetSP target_sp = m_target_wp.lock();
82174a628f7SDimitry Andric if (!target_sp || !bkpt)
82214f1b3e8SDimitry Andric return false;
82374a628f7SDimitry Andric if (bkpt->GetTargetSP() != target_sp)
82414f1b3e8SDimitry Andric return false;
82574a628f7SDimitry Andric m_break_ids.push_back(bkpt->GetID());
82614f1b3e8SDimitry Andric return true;
82714f1b3e8SDimitry Andric }
82814f1b3e8SDimitry Andric
AppendIfUnique(BreakpointSP bkpt)82974a628f7SDimitry Andric bool AppendIfUnique(BreakpointSP bkpt) {
83014f1b3e8SDimitry Andric TargetSP target_sp = m_target_wp.lock();
83174a628f7SDimitry Andric if (!target_sp || !bkpt)
83214f1b3e8SDimitry Andric return false;
83374a628f7SDimitry Andric if (bkpt->GetTargetSP() != target_sp)
83414f1b3e8SDimitry Andric return false;
83574a628f7SDimitry Andric lldb::break_id_t bp_id = bkpt->GetID();
8364b4fe385SDimitry Andric if (!llvm::is_contained(m_break_ids, bp_id))
83714f1b3e8SDimitry Andric return false;
83814f1b3e8SDimitry Andric
83974a628f7SDimitry Andric m_break_ids.push_back(bkpt->GetID());
84014f1b3e8SDimitry Andric return true;
84114f1b3e8SDimitry Andric }
84214f1b3e8SDimitry Andric
AppendByID(lldb::break_id_t id)84314f1b3e8SDimitry Andric bool AppendByID(lldb::break_id_t id) {
84414f1b3e8SDimitry Andric TargetSP target_sp = m_target_wp.lock();
84514f1b3e8SDimitry Andric if (!target_sp)
84614f1b3e8SDimitry Andric return false;
84714f1b3e8SDimitry Andric if (id == LLDB_INVALID_BREAK_ID)
84814f1b3e8SDimitry Andric return false;
84914f1b3e8SDimitry Andric m_break_ids.push_back(id);
85014f1b3e8SDimitry Andric return true;
85114f1b3e8SDimitry Andric }
85214f1b3e8SDimitry Andric
Clear()85314f1b3e8SDimitry Andric void Clear() { m_break_ids.clear(); }
85414f1b3e8SDimitry Andric
CopyToBreakpointIDList(lldb_private::BreakpointIDList & bp_list)85514f1b3e8SDimitry Andric void CopyToBreakpointIDList(lldb_private::BreakpointIDList &bp_list) {
85614f1b3e8SDimitry Andric for (lldb::break_id_t id : m_break_ids) {
85714f1b3e8SDimitry Andric bp_list.AddBreakpointID(BreakpointID(id));
85814f1b3e8SDimitry Andric }
85914f1b3e8SDimitry Andric }
86014f1b3e8SDimitry Andric
GetTarget()86114f1b3e8SDimitry Andric TargetSP GetTarget() { return m_target_wp.lock(); }
86214f1b3e8SDimitry Andric
86314f1b3e8SDimitry Andric private:
86414f1b3e8SDimitry Andric std::vector<lldb::break_id_t> m_break_ids;
86514f1b3e8SDimitry Andric TargetWP m_target_wp;
86614f1b3e8SDimitry Andric };
86714f1b3e8SDimitry Andric
SBBreakpointList(SBTarget & target)86814f1b3e8SDimitry Andric SBBreakpointList::SBBreakpointList(SBTarget &target)
8695f29bb8aSDimitry Andric : m_opaque_sp(new SBBreakpointListImpl(target.GetSP())) {
8706f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, target);
8715f29bb8aSDimitry Andric }
87214f1b3e8SDimitry Andric
873cfca06d7SDimitry Andric SBBreakpointList::~SBBreakpointList() = default;
87414f1b3e8SDimitry Andric
GetSize() const87514f1b3e8SDimitry Andric size_t SBBreakpointList::GetSize() const {
8766f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
8775f29bb8aSDimitry Andric
87814f1b3e8SDimitry Andric if (!m_opaque_sp)
87914f1b3e8SDimitry Andric return 0;
88014f1b3e8SDimitry Andric else
88114f1b3e8SDimitry Andric return m_opaque_sp->GetSize();
88214f1b3e8SDimitry Andric }
88314f1b3e8SDimitry Andric
GetBreakpointAtIndex(size_t idx)88414f1b3e8SDimitry Andric SBBreakpoint SBBreakpointList::GetBreakpointAtIndex(size_t idx) {
8856f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, idx);
8865f29bb8aSDimitry Andric
88714f1b3e8SDimitry Andric if (!m_opaque_sp)
8886f8fc217SDimitry Andric return SBBreakpoint();
88914f1b3e8SDimitry Andric
89014f1b3e8SDimitry Andric BreakpointSP bkpt_sp = m_opaque_sp->GetBreakpointAtIndex(idx);
8916f8fc217SDimitry Andric return SBBreakpoint(bkpt_sp);
89214f1b3e8SDimitry Andric }
89314f1b3e8SDimitry Andric
FindBreakpointByID(lldb::break_id_t id)89414f1b3e8SDimitry Andric SBBreakpoint SBBreakpointList::FindBreakpointByID(lldb::break_id_t id) {
8956f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, id);
8965f29bb8aSDimitry Andric
89714f1b3e8SDimitry Andric if (!m_opaque_sp)
8986f8fc217SDimitry Andric return SBBreakpoint();
89914f1b3e8SDimitry Andric BreakpointSP bkpt_sp = m_opaque_sp->FindBreakpointByID(id);
9006f8fc217SDimitry Andric return SBBreakpoint(bkpt_sp);
90114f1b3e8SDimitry Andric }
90214f1b3e8SDimitry Andric
Append(const SBBreakpoint & sb_bkpt)90314f1b3e8SDimitry Andric void SBBreakpointList::Append(const SBBreakpoint &sb_bkpt) {
9046f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, sb_bkpt);
9055f29bb8aSDimitry Andric
90614f1b3e8SDimitry Andric if (!sb_bkpt.IsValid())
90714f1b3e8SDimitry Andric return;
90814f1b3e8SDimitry Andric if (!m_opaque_sp)
90914f1b3e8SDimitry Andric return;
91074a628f7SDimitry Andric m_opaque_sp->Append(sb_bkpt.m_opaque_wp.lock());
91114f1b3e8SDimitry Andric }
91214f1b3e8SDimitry Andric
AppendByID(lldb::break_id_t id)91314f1b3e8SDimitry Andric void SBBreakpointList::AppendByID(lldb::break_id_t id) {
9146f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, id);
9155f29bb8aSDimitry Andric
91614f1b3e8SDimitry Andric if (!m_opaque_sp)
91714f1b3e8SDimitry Andric return;
91814f1b3e8SDimitry Andric m_opaque_sp->AppendByID(id);
91914f1b3e8SDimitry Andric }
92014f1b3e8SDimitry Andric
AppendIfUnique(const SBBreakpoint & sb_bkpt)92114f1b3e8SDimitry Andric bool SBBreakpointList::AppendIfUnique(const SBBreakpoint &sb_bkpt) {
9226f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this, sb_bkpt);
9235f29bb8aSDimitry Andric
92414f1b3e8SDimitry Andric if (!sb_bkpt.IsValid())
92514f1b3e8SDimitry Andric return false;
92614f1b3e8SDimitry Andric if (!m_opaque_sp)
92714f1b3e8SDimitry Andric return false;
92874a628f7SDimitry Andric return m_opaque_sp->AppendIfUnique(sb_bkpt.GetSP());
92914f1b3e8SDimitry Andric }
93014f1b3e8SDimitry Andric
Clear()93114f1b3e8SDimitry Andric void SBBreakpointList::Clear() {
9326f8fc217SDimitry Andric LLDB_INSTRUMENT_VA(this);
9335f29bb8aSDimitry Andric
93414f1b3e8SDimitry Andric if (m_opaque_sp)
93514f1b3e8SDimitry Andric m_opaque_sp->Clear();
93614f1b3e8SDimitry Andric }
93714f1b3e8SDimitry Andric
CopyToBreakpointIDList(lldb_private::BreakpointIDList & bp_id_list)93814f1b3e8SDimitry Andric void SBBreakpointList::CopyToBreakpointIDList(
93914f1b3e8SDimitry Andric lldb_private::BreakpointIDList &bp_id_list) {
94014f1b3e8SDimitry Andric if (m_opaque_sp)
94114f1b3e8SDimitry Andric m_opaque_sp->CopyToBreakpointIDList(bp_id_list);
94214f1b3e8SDimitry Andric }
943