LLDB mainline
SBBreakpointName.cpp
Go to the documentation of this file.
1//===-- SBBreakpointName.cpp ----------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
10#include "lldb/API/SBDebugger.h"
11#include "lldb/API/SBError.h"
12#include "lldb/API/SBStream.h"
15#include "lldb/API/SBTarget.h"
17
20#include "lldb/Core/Debugger.h"
24#include "lldb/Target/Target.h"
26#include "lldb/Utility/Stream.h"
27
29
30using namespace lldb;
31using namespace lldb_private;
32
33namespace lldb
34{
36public:
37 SBBreakpointNameImpl(TargetSP target_sp, const char *name) {
38 if (!name || name[0] == '\0')
39 return;
40 m_name.assign(name);
41
42 if (!target_sp)
43 return;
44
45 m_target_wp = target_sp;
46 }
47
48 SBBreakpointNameImpl(SBTarget &sb_target, const char *name);
49 bool operator==(const SBBreakpointNameImpl &rhs);
50 bool operator!=(const SBBreakpointNameImpl &rhs);
51
52 // For now we take a simple approach and only keep the name, and relook up
53 // the location when we need it.
54
56 return m_target_wp.lock();
57 }
58
59 const char *GetName() const {
60 return m_name.c_str();
61 }
62
63 bool IsValid() const {
64 return !m_name.empty() && m_target_wp.lock();
65 }
66
68
69private:
71 std::string m_name;
72};
73
75 const char *name) {
76 if (!name || name[0] == '\0')
77 return;
78 m_name.assign(name);
79
80 if (!sb_target.IsValid())
81 return;
82
83 TargetSP target_sp = sb_target.GetSP();
84 if (!target_sp)
85 return;
86
87 m_target_wp = target_sp;
88}
89
91 return m_name == rhs.m_name && m_target_wp.lock() == rhs.m_target_wp.lock();
92}
93
95 return m_name != rhs.m_name || m_target_wp.lock() != rhs.m_target_wp.lock();
96}
97
99 if (!IsValid())
100 return nullptr;
101 TargetSP target_sp = GetTarget();
102 if (!target_sp)
103 return nullptr;
105 return target_sp->FindBreakpointName(m_name, true, error);
106}
107
108} // namespace lldb
109
111
112SBBreakpointName::SBBreakpointName(SBTarget &sb_target, const char *name) {
113 LLDB_INSTRUMENT_VA(this, sb_target, name);
114
115 m_impl_up = std::make_unique<SBBreakpointNameImpl>(sb_target, name);
116 // Call FindBreakpointName here to make sure the name is valid, reset if not:
118 if (!bp_name)
119 m_impl_up.reset();
120}
121
123 LLDB_INSTRUMENT_VA(this, sb_bkpt, name);
124
125 if (!sb_bkpt.IsValid()) {
126 m_impl_up.reset();
127 return;
128 }
129 BreakpointSP bkpt_sp = sb_bkpt.GetSP();
130 Target &target = bkpt_sp->GetTarget();
131
132 m_impl_up =
133 std::make_unique<SBBreakpointNameImpl>(target.shared_from_this(), name);
134
135 // Call FindBreakpointName here to make sure the name is valid, reset if not:
137 if (!bp_name) {
138 m_impl_up.reset();
139 return;
140 }
141
142 // Now copy over the breakpoint's options:
143 target.ConfigureBreakpointName(*bp_name, bkpt_sp->GetOptions(),
145}
146
148 LLDB_INSTRUMENT_VA(this, rhs);
149
150 if (!rhs.m_impl_up)
151 return;
152 else
153 m_impl_up = std::make_unique<SBBreakpointNameImpl>(
154 rhs.m_impl_up->GetTarget(), rhs.m_impl_up->GetName());
155}
156
158
160operator=(const SBBreakpointName &rhs) {
161 LLDB_INSTRUMENT_VA(this, rhs);
162
163 if (!rhs.m_impl_up) {
164 m_impl_up.reset();
165 return *this;
166 }
167
168 m_impl_up = std::make_unique<SBBreakpointNameImpl>(rhs.m_impl_up->GetTarget(),
169 rhs.m_impl_up->GetName());
170 return *this;
171}
172
174 LLDB_INSTRUMENT_VA(this, rhs);
175
176 return *m_impl_up == *rhs.m_impl_up;
177}
178
180 LLDB_INSTRUMENT_VA(this, rhs);
181
182 return *m_impl_up != *rhs.m_impl_up;
183}
184
186 LLDB_INSTRUMENT_VA(this);
187 return this->operator bool();
188}
189SBBreakpointName::operator bool() const {
190 LLDB_INSTRUMENT_VA(this);
191
192 if (!m_impl_up)
193 return false;
194 return m_impl_up->IsValid();
195}
196
197const char *SBBreakpointName::GetName() const {
198 LLDB_INSTRUMENT_VA(this);
199
200 if (!m_impl_up)
201 return "<Invalid Breakpoint Name Object>";
202 return ConstString(m_impl_up->GetName()).GetCString();
203}
204
206 LLDB_INSTRUMENT_VA(this, enable);
207
209 if (!bp_name)
210 return;
211
212 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
213 std::lock_guard<TargetAPIMutex> guard(api_lock);
214
215 bp_name->GetOptions().SetEnabled(enable);
216 UpdateName(*bp_name);
217}
218
220 if (!IsValid())
221 return;
222
223 TargetSP target_sp = m_impl_up->GetTarget();
224 if (!target_sp)
225 return;
226 target_sp->ApplyNameToBreakpoints(bp_name);
227
228}
229
231 LLDB_INSTRUMENT_VA(this);
232
234 if (!bp_name)
235 return false;
236
237 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
238 std::lock_guard<TargetAPIMutex> guard(api_lock);
239
240 return bp_name->GetOptions().IsEnabled();
241}
242
243void SBBreakpointName::SetOneShot(bool one_shot) {
244 LLDB_INSTRUMENT_VA(this, one_shot);
245
247 if (!bp_name)
248 return;
249
250 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
251 std::lock_guard<TargetAPIMutex> guard(api_lock);
252
253 bp_name->GetOptions().SetOneShot(one_shot);
254 UpdateName(*bp_name);
255}
256
258 LLDB_INSTRUMENT_VA(this);
259
260 const BreakpointName *bp_name = GetBreakpointName();
261 if (!bp_name)
262 return false;
263
264 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
265 std::lock_guard<TargetAPIMutex> guard(api_lock);
266
267 return bp_name->GetOptions().IsOneShot();
268}
269
271 LLDB_INSTRUMENT_VA(this, count);
272
274 if (!bp_name)
275 return;
276
277 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
278 std::lock_guard<TargetAPIMutex> guard(api_lock);
279
280 bp_name->GetOptions().SetIgnoreCount(count);
281 UpdateName(*bp_name);
282}
283
285 LLDB_INSTRUMENT_VA(this);
286
288 if (!bp_name)
289 return false;
290
291 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
292 std::lock_guard<TargetAPIMutex> guard(api_lock);
293
294 return bp_name->GetOptions().GetIgnoreCount();
295}
296
297void SBBreakpointName::SetCondition(const char *condition) {
298 LLDB_INSTRUMENT_VA(this, condition);
299
301 if (!bp_name)
302 return;
303
304 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
305 std::lock_guard<TargetAPIMutex> guard(api_lock);
306
307 bp_name->GetOptions().SetCondition(StopCondition(condition));
308 UpdateName(*bp_name);
309}
310
312 LLDB_INSTRUMENT_VA(this);
313
315 if (!bp_name)
316 return nullptr;
317
318 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
319 std::lock_guard<TargetAPIMutex> guard(api_lock);
320
321 return ConstString(bp_name->GetOptions().GetCondition().GetText())
322 .GetCString();
323}
324
325void SBBreakpointName::SetAutoContinue(bool auto_continue) {
326 LLDB_INSTRUMENT_VA(this, auto_continue);
327
329 if (!bp_name)
330 return;
331
332 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
333 std::lock_guard<TargetAPIMutex> guard(api_lock);
334
335 bp_name->GetOptions().SetAutoContinue(auto_continue);
336 UpdateName(*bp_name);
337}
338
340 LLDB_INSTRUMENT_VA(this);
341
343 if (!bp_name)
344 return false;
345
346 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
347 std::lock_guard<TargetAPIMutex> guard(api_lock);
348
349 return bp_name->GetOptions().IsAutoContinue();
350}
351
353 LLDB_INSTRUMENT_VA(this, tid);
354
356 if (!bp_name)
357 return;
358
359 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
360 std::lock_guard<TargetAPIMutex> guard(api_lock);
361
362 bp_name->GetOptions().SetThreadID(tid);
363 UpdateName(*bp_name);
364}
365
367 LLDB_INSTRUMENT_VA(this);
368
370 if (!bp_name)
372
373 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
374 std::lock_guard<TargetAPIMutex> guard(api_lock);
375
376 return bp_name->GetOptions().GetThreadSpec()->GetTID();
377}
378
380 LLDB_INSTRUMENT_VA(this, index);
381
383 if (!bp_name)
384 return;
385
386 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
387 std::lock_guard<TargetAPIMutex> guard(api_lock);
388
389 bp_name->GetOptions().GetThreadSpec()->SetIndex(index);
390 UpdateName(*bp_name);
391}
392
394 LLDB_INSTRUMENT_VA(this);
395
397 if (!bp_name)
399
400 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
401 std::lock_guard<TargetAPIMutex> guard(api_lock);
402
403 return bp_name->GetOptions().GetThreadSpec()->GetIndex();
404}
405
406void SBBreakpointName::SetThreadName(const char *thread_name) {
407 LLDB_INSTRUMENT_VA(this, thread_name);
408
410 if (!bp_name)
411 return;
412
413 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
414 std::lock_guard<TargetAPIMutex> guard(api_lock);
415
416 bp_name->GetOptions().GetThreadSpec()->SetName(thread_name);
417 UpdateName(*bp_name);
418}
419
421 LLDB_INSTRUMENT_VA(this);
422
424 if (!bp_name)
425 return nullptr;
426
427 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
428 std::lock_guard<TargetAPIMutex> guard(api_lock);
429
430 return ConstString(bp_name->GetOptions().GetThreadSpec()->GetName())
431 .GetCString();
432}
433
434void SBBreakpointName::SetQueueName(const char *queue_name) {
435 LLDB_INSTRUMENT_VA(this, queue_name);
436
438 if (!bp_name)
439 return;
440
441 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
442 std::lock_guard<TargetAPIMutex> guard(api_lock);
443
444 bp_name->GetOptions().GetThreadSpec()->SetQueueName(queue_name);
445 UpdateName(*bp_name);
446}
447
449 LLDB_INSTRUMENT_VA(this);
450
452 if (!bp_name)
453 return nullptr;
454
455 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
456 std::lock_guard<TargetAPIMutex> guard(api_lock);
457
458 return ConstString(bp_name->GetOptions().GetThreadSpec()->GetQueueName())
459 .GetCString();
460}
461
463 LLDB_INSTRUMENT_VA(this, commands);
464
466 if (!bp_name)
467 return;
468 if (commands.GetSize() == 0)
469 return;
470
471 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
472 std::lock_guard<TargetAPIMutex> guard(api_lock);
473 std::unique_ptr<BreakpointOptions::CommandData> cmd_data_up(
475
476 bp_name->GetOptions().SetCommandDataCallback(cmd_data_up);
477 UpdateName(*bp_name);
478}
479
481 LLDB_INSTRUMENT_VA(this, commands);
482
484 if (!bp_name)
485 return false;
486
487 StringList command_list;
488 bool has_commands =
489 bp_name->GetOptions().GetCommandLineCallbacks(command_list);
490 if (has_commands)
491 commands.AppendList(command_list);
492 return has_commands;
493}
494
496 LLDB_INSTRUMENT_VA(this);
497
499 if (!bp_name)
500 return "";
501
502 return ConstString(bp_name->GetHelp()).GetCString();
503}
504
505void SBBreakpointName::SetHelpString(const char *help_string) {
506 LLDB_INSTRUMENT_VA(this, help_string);
507
509 if (!bp_name)
510 return;
511
512 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
513 std::lock_guard<TargetAPIMutex> guard(api_lock);
514 bp_name->SetHelp(help_string);
515}
516
518 LLDB_INSTRUMENT_VA(this, s);
519
521 if (!bp_name)
522 {
523 s.Printf("No value");
524 return false;
525 }
526
527 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
528 std::lock_guard<TargetAPIMutex> guard(api_lock);
530 return true;
531}
532
534 void *baton) {
535 LLDB_INSTRUMENT_VA(this, callback, baton);
536
538 if (!bp_name)
539 return;
540 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
541 std::lock_guard<TargetAPIMutex> guard(api_lock);
542
543 BatonSP baton_sp(new SBBreakpointCallbackBaton(callback, baton));
545 ::PrivateBreakpointHitCallback,
546 baton_sp,
547 false);
548 UpdateName(*bp_name);
549}
550
552 const char *callback_function_name) {
553 LLDB_INSTRUMENT_VA(this, callback_function_name);
554 SBStructuredData empty_args;
555 SetScriptCallbackFunction(callback_function_name, empty_args);
556}
557
559 const char *callback_function_name,
560 SBStructuredData &extra_args) {
561 LLDB_INSTRUMENT_VA(this, callback_function_name, extra_args);
562 SBError sb_error;
564 if (!bp_name) {
565 sb_error = Status::FromErrorString("unrecognized breakpoint name");
566 return sb_error;
567 }
568
569 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
570 std::lock_guard<TargetAPIMutex> guard(api_lock);
571
572 BreakpointOptions &bp_options = bp_name->GetOptions();
573 Status error = m_impl_up->GetTarget()
574 ->GetDebugger()
575 .GetScriptInterpreter()
576 ->SetBreakpointCommandCallbackFunction(
577 bp_options, callback_function_name,
578 extra_args.m_impl_up->GetObjectSP());
579 sb_error.SetError(std::move(error));
580 UpdateName(*bp_name);
581 return sb_error;
582}
583
585SBBreakpointName::SetScriptCallbackBody(const char *callback_body_text) {
586 LLDB_INSTRUMENT_VA(this, callback_body_text);
587
588 SBError sb_error;
590 if (!bp_name)
591 return sb_error;
592
593 TargetAPIMutex api_lock = m_impl_up->GetTarget()->GetAPIMutex();
594 std::lock_guard<TargetAPIMutex> guard(api_lock);
595
596 BreakpointOptions &bp_options = bp_name->GetOptions();
597 Status error = m_impl_up->GetTarget()
598 ->GetDebugger()
599 .GetScriptInterpreter()
600 ->SetBreakpointCommandCallback(
601 bp_options, callback_body_text, /*is_callback=*/false);
602 sb_error.SetError(std::move(error));
603 if (!sb_error.Fail())
604 UpdateName(*bp_name);
605
606 return sb_error;
607}
608
610 LLDB_INSTRUMENT_VA(this);
611
613 if (!bp_name)
614 return false;
615 return bp_name->GetPermissions().GetAllowList();
616}
617
619 LLDB_INSTRUMENT_VA(this, value);
620
622 if (!bp_name)
623 return;
624 bp_name->GetPermissions().SetAllowList(value);
625}
626
628 LLDB_INSTRUMENT_VA(this);
629
631 if (!bp_name)
632 return false;
633 return bp_name->GetPermissions().GetAllowDelete();
634}
635
637 LLDB_INSTRUMENT_VA(this, value);
638
640 if (!bp_name)
641 return;
642 bp_name->GetPermissions().SetAllowDelete(value);
643}
644
646 LLDB_INSTRUMENT_VA(this);
647
649 if (!bp_name)
650 return false;
651 return bp_name->GetPermissions().GetAllowDisable();
652}
653
655 LLDB_INSTRUMENT_VA(this, value);
656
658 if (!bp_name)
659 return;
660 bp_name->GetPermissions().SetAllowDisable(value);
661}
662
664{
665 if (!IsValid())
666 return nullptr;
667 return m_impl_up->GetBreakpointName();
668}
static llvm::raw_ostream & error(Stream &strm)
#define LLDB_INSTRUMENT_VA(...)
bool operator==(const SBBreakpointNameImpl &rhs)
bool operator!=(const SBBreakpointNameImpl &rhs)
lldb_private::BreakpointName * GetBreakpointName() const
SBBreakpointNameImpl(TargetSP target_sp, const char *name)
const char * GetName() const
void SetCommandLineCommands(lldb::SBStringList &commands)
const char * GetName() const
void SetQueueName(const char *queue_name)
const char * GetQueueName() const
void SetThreadIndex(uint32_t index)
void SetAutoContinue(bool auto_continue)
bool operator!=(const lldb::SBBreakpointName &rhs)
void SetCondition(const char *condition)
bool GetDescription(lldb::SBStream &description)
const char * GetThreadName() const
void SetThreadName(const char *thread_name)
void SetAllowDisable(bool value)
void SetEnabled(bool enable)
void SetIgnoreCount(uint32_t count)
bool operator==(const lldb::SBBreakpointName &rhs)
std::unique_ptr< SBBreakpointNameImpl > m_impl_up
void SetAllowDelete(bool value)
void SetCallback(SBBreakpointHitCallback callback, void *baton)
SBError SetScriptCallbackBody(const char *script_body_text)
void SetAllowList(bool value)
lldb_private::BreakpointName * GetBreakpointName() const
void SetOneShot(bool one_shot)
uint32_t GetIgnoreCount() const
uint32_t GetThreadIndex() const
void SetHelpString(const char *help_string)
const char * GetHelpString() const
void SetThreadID(lldb::tid_t sb_thread_id)
void UpdateName(lldb_private::BreakpointName &bp_name)
void SetScriptCallbackFunction(const char *callback_function_name)
const lldb::SBBreakpointName & operator=(const lldb::SBBreakpointName &rhs)
bool GetCommandLineCommands(lldb::SBStringList &commands)
lldb::BreakpointSP GetSP() const
void SetError(uint32_t err, lldb::ErrorType type)
Definition SBError.cpp:124
bool Fail() const
Definition SBError.cpp:70
lldb_private::Stream * get()
Definition SBStream.cpp:177
uint32_t GetSize() const
void AppendList(const char **strv, int strc)
StructuredDataImplUP m_impl_up
bool IsValid() const
Definition SBTarget.cpp:168
lldb::TargetSP GetSP() const
Definition SBTarget.cpp:600
bool GetDescription(Stream *s, lldb::DescriptionLevel level)
void SetHelp(const char *description)
BreakpointOptions & GetOptions()
"lldb/Breakpoint/BreakpointOptions.h" Class that manages the options on a breakpoint or breakpoint lo...
void SetIgnoreCount(uint32_t n)
Set the breakpoint to ignore the next count breakpoint hits.
void SetCondition(StopCondition condition)
Set the breakpoint stop condition.
void SetEnabled(bool enabled)
If enable is true, enable the breakpoint, if false disable it.
const StopCondition & GetCondition() const
Return the breakpoint condition.
bool GetCommandLineCallbacks(StringList &command_list)
Returns the command line commands for the callback on this breakpoint.
bool IsOneShot() const
Check the One-shot state.
bool IsEnabled() const
Check the Enable/Disable state.
uint32_t GetIgnoreCount() const
Return the current Ignore Count.
bool IsAutoContinue() const
Check the auto-continue state.
ThreadSpec * GetThreadSpec()
Returns a pointer to the ThreadSpec for this option, creating it.
void SetOneShot(bool one_shot)
If enable is true, enable the breakpoint, if false disable it.
void SetAutoContinue(bool auto_continue)
Set the auto-continue state.
void SetThreadID(lldb::tid_t thread_id)
void SetCommandDataCallback(std::unique_ptr< CommandData > &cmd_data)
Set a callback based on BreakpointOptions::CommandData.
void SetCallback(BreakpointHitCallback callback, const lldb::BatonSP &baton_sp, bool synchronous=false)
Adds a callback to the breakpoint option set.
A uniqued constant string class.
Definition ConstString.h:40
const char * GetCString() const
Get the string value as a C string.
An error handling class.
Definition Status.h:118
static Status FromErrorString(const char *str)
Definition Status.h:141
llvm::StringRef GetText() const
A Lockable handle over a Target's API mutex, returned by Target::GetAPIMutex() and backing the public...
void ConfigureBreakpointName(BreakpointName &bp_name, const BreakpointOptions &options, const BreakpointName::Permissions &permissions)
Definition Target.cpp:922
void SetIndex(uint32_t index)
Definition ThreadSpec.h:47
void SetName(llvm::StringRef name)
Definition ThreadSpec.h:51
uint32_t GetIndex() const
Definition ThreadSpec.h:57
const char * GetName() const
void SetQueueName(llvm::StringRef queue_name)
Definition ThreadSpec.h:53
const char * GetQueueName() const
lldb::tid_t GetTID() const
Definition ThreadSpec.h:59
#define LLDB_INVALID_THREAD_ID
A class that represents a running process on the host machine.
@ eScriptLanguageNone
@ eDescriptionLevelFull
class LLDB_API SBBreakpointNameImpl
Definition SBDefines.h:54
std::shared_ptr< lldb_private::Breakpoint > BreakpointSP
std::shared_ptr< lldb_private::Baton > BatonSP
bool(* SBBreakpointHitCallback)(void *baton, lldb::SBProcess &process, lldb::SBThread &thread, lldb::SBBreakpointLocation &location)
Definition SBDefines.h:143
std::weak_ptr< lldb_private::Target > TargetWP
std::shared_ptr< lldb_private::Target > TargetSP
uint64_t tid_t
Definition lldb-types.h:85