1 //===-- SBThread.cpp --------------------------------------------*- C++ -*-===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 #include "lldb/API/SBThread.h"
12 #include "lldb/API/SBFileSpec.h"
13 #include "lldb/API/SBStream.h"
14 #include "lldb/API/SBSymbolContext.h"
15 #include "lldb/Breakpoint/BreakpointLocation.h"
16 #include "lldb/Core/Debugger.h"
17 #include "lldb/Core/State.h"
18 #include "lldb/Core/StreamFile.h"
19 #include "lldb/Core/ValueObject.h"
20 #include "lldb/Interpreter/CommandInterpreter.h"
21 #include "lldb/Symbol/CompileUnit.h"
22 #include "lldb/Symbol/SymbolContext.h"
23 #include "lldb/Target/Process.h"
24 #include "lldb/Target/Queue.h"
25 #include "lldb/Target/StopInfo.h"
26 #include "lldb/Target/SystemRuntime.h"
27 #include "lldb/Target/Target.h"
28 #include "lldb/Target/Thread.h"
29 #include "lldb/Target/ThreadPlan.h"
30 #include "lldb/Target/ThreadPlanStepInRange.h"
31 #include "lldb/Target/ThreadPlanStepInstruction.h"
32 #include "lldb/Target/ThreadPlanStepOut.h"
33 #include "lldb/Target/ThreadPlanStepRange.h"
34 #include "lldb/Target/UnixSignals.h"
35 #include "lldb/Utility/Stream.h"
36 #include "lldb/Utility/StructuredData.h"
38 #include "lldb/API/SBAddress.h"
39 #include "lldb/API/SBDebugger.h"
40 #include "lldb/API/SBEvent.h"
41 #include "lldb/API/SBFrame.h"
42 #include "lldb/API/SBProcess.h"
43 #include "lldb/API/SBThreadCollection.h"
44 #include "lldb/API/SBThreadPlan.h"
45 #include "lldb/API/SBValue.h"
46 #include "lldb/lldb-enumerations.h"
49 using namespace lldb_private;
51 const char *SBThread::GetBroadcasterClassName() {
52 return Thread::GetStaticBroadcasterClass().AsCString();
55 //----------------------------------------------------------------------
57 //----------------------------------------------------------------------
58 SBThread::SBThread() : m_opaque_sp(new ExecutionContextRef()) {}
60 SBThread::SBThread(const ThreadSP &lldb_object_sp)
61 : m_opaque_sp(new ExecutionContextRef(lldb_object_sp)) {}
63 SBThread::SBThread(const SBThread &rhs)
64 : m_opaque_sp(new ExecutionContextRef(*rhs.m_opaque_sp)) {}
66 //----------------------------------------------------------------------
67 // Assignment operator
68 //----------------------------------------------------------------------
70 const lldb::SBThread &SBThread::operator=(const SBThread &rhs) {
72 *m_opaque_sp = *rhs.m_opaque_sp;
76 //----------------------------------------------------------------------
78 //----------------------------------------------------------------------
79 SBThread::~SBThread() {}
81 lldb::SBQueue SBThread::GetQueue() const {
84 std::unique_lock<std::recursive_mutex> lock;
85 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
87 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
88 if (exe_ctx.HasThreadScope()) {
89 Process::StopLocker stop_locker;
90 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
91 queue_sp = exe_ctx.GetThreadPtr()->GetQueue();
93 sb_queue.SetQueue(queue_sp);
97 log->Printf("SBThread(%p)::GetQueue() => error: process is running",
98 static_cast<void *>(exe_ctx.GetThreadPtr()));
103 log->Printf("SBThread(%p)::GetQueue () => SBQueue(%p)",
104 static_cast<void *>(exe_ctx.GetThreadPtr()),
105 static_cast<void *>(queue_sp.get()));
110 bool SBThread::IsValid() const {
111 std::unique_lock<std::recursive_mutex> lock;
112 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
114 Target *target = exe_ctx.GetTargetPtr();
115 Process *process = exe_ctx.GetProcessPtr();
116 if (target && process) {
117 Process::StopLocker stop_locker;
118 if (stop_locker.TryLock(&process->GetRunLock()))
119 return m_opaque_sp->GetThreadSP().get() != NULL;
121 // Without a valid target & process, this thread can't be valid.
125 void SBThread::Clear() { m_opaque_sp->Clear(); }
127 StopReason SBThread::GetStopReason() {
128 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
130 StopReason reason = eStopReasonInvalid;
131 std::unique_lock<std::recursive_mutex> lock;
132 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
134 if (exe_ctx.HasThreadScope()) {
135 Process::StopLocker stop_locker;
136 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
137 return exe_ctx.GetThreadPtr()->GetStopReason();
141 "SBThread(%p)::GetStopReason() => error: process is running",
142 static_cast<void *>(exe_ctx.GetThreadPtr()));
147 log->Printf("SBThread(%p)::GetStopReason () => %s",
148 static_cast<void *>(exe_ctx.GetThreadPtr()),
149 Thread::StopReasonAsCString(reason));
154 size_t SBThread::GetStopReasonDataCount() {
155 std::unique_lock<std::recursive_mutex> lock;
156 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
158 if (exe_ctx.HasThreadScope()) {
159 Process::StopLocker stop_locker;
160 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
161 StopInfoSP stop_info_sp = exe_ctx.GetThreadPtr()->GetStopInfo();
163 StopReason reason = stop_info_sp->GetStopReason();
165 case eStopReasonInvalid:
166 case eStopReasonNone:
167 case eStopReasonTrace:
168 case eStopReasonExec:
169 case eStopReasonPlanComplete:
170 case eStopReasonThreadExiting:
171 case eStopReasonInstrumentation:
172 // There is no data for these stop reasons.
175 case eStopReasonBreakpoint: {
176 break_id_t site_id = stop_info_sp->GetValue();
177 lldb::BreakpointSiteSP bp_site_sp(
178 exe_ctx.GetProcessPtr()->GetBreakpointSiteList().FindByID(
181 return bp_site_sp->GetNumberOfOwners() * 2;
183 return 0; // Breakpoint must have cleared itself...
186 case eStopReasonWatchpoint:
189 case eStopReasonSignal:
192 case eStopReasonException:
197 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
199 log->Printf("SBThread(%p)::GetStopReasonDataCount() => error: process "
201 static_cast<void *>(exe_ctx.GetThreadPtr()));
207 uint64_t SBThread::GetStopReasonDataAtIndex(uint32_t idx) {
208 std::unique_lock<std::recursive_mutex> lock;
209 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
211 if (exe_ctx.HasThreadScope()) {
212 Process::StopLocker stop_locker;
213 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
214 Thread *thread = exe_ctx.GetThreadPtr();
215 StopInfoSP stop_info_sp = thread->GetStopInfo();
217 StopReason reason = stop_info_sp->GetStopReason();
219 case eStopReasonInvalid:
220 case eStopReasonNone:
221 case eStopReasonTrace:
222 case eStopReasonExec:
223 case eStopReasonPlanComplete:
224 case eStopReasonThreadExiting:
225 case eStopReasonInstrumentation:
226 // There is no data for these stop reasons.
229 case eStopReasonBreakpoint: {
230 break_id_t site_id = stop_info_sp->GetValue();
231 lldb::BreakpointSiteSP bp_site_sp(
232 exe_ctx.GetProcessPtr()->GetBreakpointSiteList().FindByID(
235 uint32_t bp_index = idx / 2;
236 BreakpointLocationSP bp_loc_sp(
237 bp_site_sp->GetOwnerAtIndex(bp_index));
240 // Odd idx, return the breakpoint location ID
241 return bp_loc_sp->GetID();
243 // Even idx, return the breakpoint ID
244 return bp_loc_sp->GetBreakpoint().GetID();
248 return LLDB_INVALID_BREAK_ID;
251 case eStopReasonWatchpoint:
252 return stop_info_sp->GetValue();
254 case eStopReasonSignal:
255 return stop_info_sp->GetValue();
257 case eStopReasonException:
258 return stop_info_sp->GetValue();
262 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
264 log->Printf("SBThread(%p)::GetStopReasonDataAtIndex() => error: "
265 "process is running",
266 static_cast<void *>(exe_ctx.GetThreadPtr()));
272 bool SBThread::GetStopReasonExtendedInfoAsJSON(lldb::SBStream &stream) {
273 Stream &strm = stream.ref();
275 std::unique_lock<std::recursive_mutex> lock;
276 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
278 if (!exe_ctx.HasThreadScope())
281 StopInfoSP stop_info = exe_ctx.GetThreadPtr()->GetStopInfo();
282 StructuredData::ObjectSP info = stop_info->GetExtendedInfo();
292 SBThread::GetStopReasonExtendedBacktraces(InstrumentationRuntimeType type) {
293 ThreadCollectionSP threads;
294 threads.reset(new ThreadCollection());
296 std::unique_lock<std::recursive_mutex> lock;
297 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
299 if (!exe_ctx.HasThreadScope())
302 ProcessSP process_sp = exe_ctx.GetProcessSP();
304 StopInfoSP stop_info = exe_ctx.GetThreadPtr()->GetStopInfo();
305 StructuredData::ObjectSP info = stop_info->GetExtendedInfo();
309 return process_sp->GetInstrumentationRuntime(type)
310 ->GetBacktracesFromExtendedStopInfo(info);
313 size_t SBThread::GetStopDescription(char *dst, size_t dst_len) {
314 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
316 std::unique_lock<std::recursive_mutex> lock;
317 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
319 if (exe_ctx.HasThreadScope()) {
320 Process::StopLocker stop_locker;
321 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
323 StopInfoSP stop_info_sp = exe_ctx.GetThreadPtr()->GetStopInfo();
325 const char *stop_desc = stop_info_sp->GetDescription();
329 "SBThread(%p)::GetStopDescription (dst, dst_len) => \"%s\"",
330 static_cast<void *>(exe_ctx.GetThreadPtr()), stop_desc);
332 return ::snprintf(dst, dst_len, "%s", stop_desc);
334 // NULL dst passed in, return the length needed to contain the
336 return ::strlen(stop_desc) + 1; // Include the NULL byte for size
339 size_t stop_desc_len = 0;
340 switch (stop_info_sp->GetStopReason()) {
341 case eStopReasonTrace:
342 case eStopReasonPlanComplete: {
343 static char trace_desc[] = "step";
344 stop_desc = trace_desc;
346 sizeof(trace_desc); // Include the NULL byte for size
349 case eStopReasonBreakpoint: {
350 static char bp_desc[] = "breakpoint hit";
352 stop_desc_len = sizeof(bp_desc); // Include the NULL byte for size
355 case eStopReasonWatchpoint: {
356 static char wp_desc[] = "watchpoint hit";
358 stop_desc_len = sizeof(wp_desc); // Include the NULL byte for size
361 case eStopReasonSignal: {
363 exe_ctx.GetProcessPtr()->GetUnixSignals()->GetSignalAsCString(
364 stop_info_sp->GetValue());
365 if (stop_desc == NULL || stop_desc[0] == '\0') {
366 static char signal_desc[] = "signal";
367 stop_desc = signal_desc;
369 sizeof(signal_desc); // Include the NULL byte for size
373 case eStopReasonException: {
374 char exc_desc[] = "exception";
375 stop_desc = exc_desc;
376 stop_desc_len = sizeof(exc_desc); // Include the NULL byte for size
379 case eStopReasonExec: {
380 char exc_desc[] = "exec";
381 stop_desc = exc_desc;
382 stop_desc_len = sizeof(exc_desc); // Include the NULL byte for size
385 case eStopReasonThreadExiting: {
386 char limbo_desc[] = "thread exiting";
387 stop_desc = limbo_desc;
388 stop_desc_len = sizeof(limbo_desc);
394 if (stop_desc && stop_desc[0]) {
397 "SBThread(%p)::GetStopDescription (dst, dst_len) => '%s'",
398 static_cast<void *>(exe_ctx.GetThreadPtr()), stop_desc);
401 return ::snprintf(dst, dst_len, "%s", stop_desc) +
402 1; // Include the NULL byte
404 if (stop_desc_len == 0)
405 stop_desc_len = ::strlen(stop_desc) + 1; // Include the NULL byte
407 return stop_desc_len;
412 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
415 "SBThread(%p)::GetStopDescription() => error: process is running",
416 static_cast<void *>(exe_ctx.GetThreadPtr()));
424 SBValue SBThread::GetStopReturnValue() {
425 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
426 ValueObjectSP return_valobj_sp;
427 std::unique_lock<std::recursive_mutex> lock;
428 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
430 if (exe_ctx.HasThreadScope()) {
431 Process::StopLocker stop_locker;
432 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
433 StopInfoSP stop_info_sp = exe_ctx.GetThreadPtr()->GetStopInfo();
435 return_valobj_sp = StopInfo::GetReturnValueObject(stop_info_sp);
440 "SBThread(%p)::GetStopReturnValue() => error: process is running",
441 static_cast<void *>(exe_ctx.GetThreadPtr()));
446 log->Printf("SBThread(%p)::GetStopReturnValue () => %s",
447 static_cast<void *>(exe_ctx.GetThreadPtr()),
448 return_valobj_sp.get() ? return_valobj_sp->GetValueAsCString()
449 : "<no return value>");
451 return SBValue(return_valobj_sp);
454 void SBThread::SetThread(const ThreadSP &lldb_object_sp) {
455 m_opaque_sp->SetThreadSP(lldb_object_sp);
458 lldb::tid_t SBThread::GetThreadID() const {
459 ThreadSP thread_sp(m_opaque_sp->GetThreadSP());
461 return thread_sp->GetID();
462 return LLDB_INVALID_THREAD_ID;
465 uint32_t SBThread::GetIndexID() const {
466 ThreadSP thread_sp(m_opaque_sp->GetThreadSP());
468 return thread_sp->GetIndexID();
469 return LLDB_INVALID_INDEX32;
472 const char *SBThread::GetName() const {
473 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
474 const char *name = NULL;
475 std::unique_lock<std::recursive_mutex> lock;
476 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
478 if (exe_ctx.HasThreadScope()) {
479 Process::StopLocker stop_locker;
480 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
481 name = exe_ctx.GetThreadPtr()->GetName();
484 log->Printf("SBThread(%p)::GetName() => error: process is running",
485 static_cast<void *>(exe_ctx.GetThreadPtr()));
490 log->Printf("SBThread(%p)::GetName () => %s",
491 static_cast<void *>(exe_ctx.GetThreadPtr()),
492 name ? name : "NULL");
497 const char *SBThread::GetQueueName() const {
498 const char *name = NULL;
499 std::unique_lock<std::recursive_mutex> lock;
500 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
502 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
503 if (exe_ctx.HasThreadScope()) {
504 Process::StopLocker stop_locker;
505 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
506 name = exe_ctx.GetThreadPtr()->GetQueueName();
509 log->Printf("SBThread(%p)::GetQueueName() => error: process is running",
510 static_cast<void *>(exe_ctx.GetThreadPtr()));
515 log->Printf("SBThread(%p)::GetQueueName () => %s",
516 static_cast<void *>(exe_ctx.GetThreadPtr()),
517 name ? name : "NULL");
522 lldb::queue_id_t SBThread::GetQueueID() const {
523 queue_id_t id = LLDB_INVALID_QUEUE_ID;
524 std::unique_lock<std::recursive_mutex> lock;
525 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
527 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
528 if (exe_ctx.HasThreadScope()) {
529 Process::StopLocker stop_locker;
530 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
531 id = exe_ctx.GetThreadPtr()->GetQueueID();
534 log->Printf("SBThread(%p)::GetQueueID() => error: process is running",
535 static_cast<void *>(exe_ctx.GetThreadPtr()));
540 log->Printf("SBThread(%p)::GetQueueID () => 0x%" PRIx64,
541 static_cast<void *>(exe_ctx.GetThreadPtr()), id);
546 bool SBThread::GetInfoItemByPathAsString(const char *path, SBStream &strm) {
547 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
548 bool success = false;
549 std::unique_lock<std::recursive_mutex> lock;
550 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
552 if (exe_ctx.HasThreadScope()) {
553 Process::StopLocker stop_locker;
554 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
555 Thread *thread = exe_ctx.GetThreadPtr();
556 StructuredData::ObjectSP info_root_sp = thread->GetExtendedInfo();
558 StructuredData::ObjectSP node =
559 info_root_sp->GetObjectForDotSeparatedPath(path);
561 if (node->GetType() == eStructuredDataTypeString) {
562 strm.Printf("%s", node->GetAsString()->GetValue().str().c_str());
565 if (node->GetType() == eStructuredDataTypeInteger) {
566 strm.Printf("0x%" PRIx64, node->GetAsInteger()->GetValue());
569 if (node->GetType() == eStructuredDataTypeFloat) {
570 strm.Printf("0x%f", node->GetAsFloat()->GetValue());
573 if (node->GetType() == eStructuredDataTypeBoolean) {
574 if (node->GetAsBoolean()->GetValue() == true)
577 strm.Printf("false");
580 if (node->GetType() == eStructuredDataTypeNull) {
588 log->Printf("SBThread(%p)::GetInfoItemByPathAsString() => error: "
589 "process is running",
590 static_cast<void *>(exe_ctx.GetThreadPtr()));
595 log->Printf("SBThread(%p)::GetInfoItemByPathAsString (\"%s\") => \"%s\"",
596 static_cast<void *>(exe_ctx.GetThreadPtr()), path, strm.GetData());
601 SBError SBThread::ResumeNewPlan(ExecutionContext &exe_ctx,
602 ThreadPlan *new_plan) {
605 Process *process = exe_ctx.GetProcessPtr();
607 sb_error.SetErrorString("No process in SBThread::ResumeNewPlan");
611 Thread *thread = exe_ctx.GetThreadPtr();
613 sb_error.SetErrorString("No thread in SBThread::ResumeNewPlan");
617 // User level plans should be Master Plans so they can be interrupted, other
618 // plans executed, and then a "continue" will resume the plan.
619 if (new_plan != NULL) {
620 new_plan->SetIsMasterPlan(true);
621 new_plan->SetOkayToDiscard(false);
624 // Why do we need to set the current thread by ID here???
625 process->GetThreadList().SetSelectedThreadByID(thread->GetID());
627 if (process->GetTarget().GetDebugger().GetAsyncExecution())
628 sb_error.ref() = process->Resume();
630 sb_error.ref() = process->ResumeSynchronous(NULL);
635 void SBThread::StepOver(lldb::RunMode stop_other_threads) {
636 SBError error; // Ignored
637 StepOver(stop_other_threads, error);
640 void SBThread::StepOver(lldb::RunMode stop_other_threads, SBError &error) {
641 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
643 std::unique_lock<std::recursive_mutex> lock;
644 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
647 log->Printf("SBThread(%p)::StepOver (stop_other_threads='%s')",
648 static_cast<void *>(exe_ctx.GetThreadPtr()),
649 Thread::RunModeAsCString(stop_other_threads));
651 if (!exe_ctx.HasThreadScope()) {
652 error.SetErrorString("this SBThread object is invalid");
656 Thread *thread = exe_ctx.GetThreadPtr();
657 bool abort_other_plans = false;
658 StackFrameSP frame_sp(thread->GetStackFrameAtIndex(0));
660 ThreadPlanSP new_plan_sp;
662 if (frame_sp->HasDebugInformation()) {
663 const LazyBool avoid_no_debug = eLazyBoolCalculate;
664 SymbolContext sc(frame_sp->GetSymbolContext(eSymbolContextEverything));
665 new_plan_sp = thread->QueueThreadPlanForStepOverRange(
666 abort_other_plans, sc.line_entry, sc, stop_other_threads,
669 new_plan_sp = thread->QueueThreadPlanForStepSingleInstruction(
670 true, abort_other_plans, stop_other_threads);
673 error = ResumeNewPlan(exe_ctx, new_plan_sp.get());
676 void SBThread::StepInto(lldb::RunMode stop_other_threads) {
677 StepInto(NULL, stop_other_threads);
680 void SBThread::StepInto(const char *target_name,
681 lldb::RunMode stop_other_threads) {
682 SBError error; // Ignored
683 StepInto(target_name, LLDB_INVALID_LINE_NUMBER, error, stop_other_threads);
686 void SBThread::StepInto(const char *target_name, uint32_t end_line,
687 SBError &error, lldb::RunMode stop_other_threads) {
688 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
690 std::unique_lock<std::recursive_mutex> lock;
691 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
695 "SBThread(%p)::StepInto (target_name='%s', stop_other_threads='%s')",
696 static_cast<void *>(exe_ctx.GetThreadPtr()),
697 target_name ? target_name : "<NULL>",
698 Thread::RunModeAsCString(stop_other_threads));
700 if (!exe_ctx.HasThreadScope()) {
701 error.SetErrorString("this SBThread object is invalid");
705 bool abort_other_plans = false;
707 Thread *thread = exe_ctx.GetThreadPtr();
708 StackFrameSP frame_sp(thread->GetStackFrameAtIndex(0));
709 ThreadPlanSP new_plan_sp;
711 if (frame_sp && frame_sp->HasDebugInformation()) {
712 SymbolContext sc(frame_sp->GetSymbolContext(eSymbolContextEverything));
714 if (end_line == LLDB_INVALID_LINE_NUMBER)
715 range = sc.line_entry.range;
717 if (!sc.GetAddressRangeFromHereToEndLine(end_line, range, error.ref()))
721 const LazyBool step_out_avoids_code_without_debug_info =
723 const LazyBool step_in_avoids_code_without_debug_info =
725 new_plan_sp = thread->QueueThreadPlanForStepInRange(
726 abort_other_plans, range, sc, target_name, stop_other_threads,
727 step_in_avoids_code_without_debug_info,
728 step_out_avoids_code_without_debug_info);
730 new_plan_sp = thread->QueueThreadPlanForStepSingleInstruction(
731 false, abort_other_plans, stop_other_threads);
733 error = ResumeNewPlan(exe_ctx, new_plan_sp.get());
736 void SBThread::StepOut() {
737 SBError error; // Ignored
741 void SBThread::StepOut(SBError &error) {
742 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
744 std::unique_lock<std::recursive_mutex> lock;
745 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
748 log->Printf("SBThread(%p)::StepOut ()",
749 static_cast<void *>(exe_ctx.GetThreadPtr()));
751 if (!exe_ctx.HasThreadScope()) {
752 error.SetErrorString("this SBThread object is invalid");
756 bool abort_other_plans = false;
757 bool stop_other_threads = false;
759 Thread *thread = exe_ctx.GetThreadPtr();
761 const LazyBool avoid_no_debug = eLazyBoolCalculate;
762 ThreadPlanSP new_plan_sp(thread->QueueThreadPlanForStepOut(
763 abort_other_plans, NULL, false, stop_other_threads, eVoteYes,
764 eVoteNoOpinion, 0, avoid_no_debug));
766 error = ResumeNewPlan(exe_ctx, new_plan_sp.get());
769 void SBThread::StepOutOfFrame(SBFrame &sb_frame) {
770 SBError error; // Ignored
771 StepOutOfFrame(sb_frame, error);
774 void SBThread::StepOutOfFrame(SBFrame &sb_frame, SBError &error) {
775 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
777 std::unique_lock<std::recursive_mutex> lock;
778 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
780 if (!sb_frame.IsValid()) {
783 "SBThread(%p)::StepOutOfFrame passed an invalid frame, returning.",
784 static_cast<void *>(exe_ctx.GetThreadPtr()));
785 error.SetErrorString("passed invalid SBFrame object");
789 StackFrameSP frame_sp(sb_frame.GetFrameSP());
791 SBStream frame_desc_strm;
792 sb_frame.GetDescription(frame_desc_strm);
793 log->Printf("SBThread(%p)::StepOutOfFrame (frame = SBFrame(%p): %s)",
794 static_cast<void *>(exe_ctx.GetThreadPtr()),
795 static_cast<void *>(frame_sp.get()), frame_desc_strm.GetData());
798 if (!exe_ctx.HasThreadScope()) {
799 error.SetErrorString("this SBThread object is invalid");
803 bool abort_other_plans = false;
804 bool stop_other_threads = false;
805 Thread *thread = exe_ctx.GetThreadPtr();
806 if (sb_frame.GetThread().GetThreadID() != thread->GetID()) {
807 log->Printf("SBThread(%p)::StepOutOfFrame passed a frame from another "
808 "thread (0x%" PRIx64 " vrs. 0x%" PRIx64 ", returning.",
809 static_cast<void *>(exe_ctx.GetThreadPtr()),
810 sb_frame.GetThread().GetThreadID(), thread->GetID());
811 error.SetErrorString("passed a frame from another thread");
815 ThreadPlanSP new_plan_sp(thread->QueueThreadPlanForStepOut(
816 abort_other_plans, NULL, false, stop_other_threads, eVoteYes,
817 eVoteNoOpinion, frame_sp->GetFrameIndex()));
819 error = ResumeNewPlan(exe_ctx, new_plan_sp.get());
822 void SBThread::StepInstruction(bool step_over) {
823 SBError error; // Ignored
824 StepInstruction(step_over, error);
827 void SBThread::StepInstruction(bool step_over, SBError &error) {
828 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
830 std::unique_lock<std::recursive_mutex> lock;
831 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
834 log->Printf("SBThread(%p)::StepInstruction (step_over=%i)",
835 static_cast<void *>(exe_ctx.GetThreadPtr()), step_over);
837 if (!exe_ctx.HasThreadScope()) {
838 error.SetErrorString("this SBThread object is invalid");
842 Thread *thread = exe_ctx.GetThreadPtr();
843 ThreadPlanSP new_plan_sp(
844 thread->QueueThreadPlanForStepSingleInstruction(step_over, true, true));
846 error = ResumeNewPlan(exe_ctx, new_plan_sp.get());
849 void SBThread::RunToAddress(lldb::addr_t addr) {
850 SBError error; // Ignored
851 RunToAddress(addr, error);
854 void SBThread::RunToAddress(lldb::addr_t addr, SBError &error) {
855 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
857 std::unique_lock<std::recursive_mutex> lock;
858 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
861 log->Printf("SBThread(%p)::RunToAddress (addr=0x%" PRIx64 ")",
862 static_cast<void *>(exe_ctx.GetThreadPtr()), addr);
864 if (!exe_ctx.HasThreadScope()) {
865 error.SetErrorString("this SBThread object is invalid");
869 bool abort_other_plans = false;
870 bool stop_other_threads = true;
872 Address target_addr(addr);
874 Thread *thread = exe_ctx.GetThreadPtr();
876 ThreadPlanSP new_plan_sp(thread->QueueThreadPlanForRunToAddress(
877 abort_other_plans, target_addr, stop_other_threads));
879 error = ResumeNewPlan(exe_ctx, new_plan_sp.get());
882 SBError SBThread::StepOverUntil(lldb::SBFrame &sb_frame,
883 lldb::SBFileSpec &sb_file_spec, uint32_t line) {
885 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
888 std::unique_lock<std::recursive_mutex> lock;
889 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
891 StackFrameSP frame_sp(sb_frame.GetFrameSP());
894 SBStream frame_desc_strm;
895 sb_frame.GetDescription(frame_desc_strm);
896 sb_file_spec->GetPath(path, sizeof(path));
897 log->Printf("SBThread(%p)::StepOverUntil (frame = SBFrame(%p): %s, "
898 "file+line = %s:%u)",
899 static_cast<void *>(exe_ctx.GetThreadPtr()),
900 static_cast<void *>(frame_sp.get()), frame_desc_strm.GetData(),
904 if (exe_ctx.HasThreadScope()) {
905 Target *target = exe_ctx.GetTargetPtr();
906 Thread *thread = exe_ctx.GetThreadPtr();
909 sb_error.SetErrorString("invalid line argument");
914 frame_sp = thread->GetSelectedFrame();
916 frame_sp = thread->GetStackFrameAtIndex(0);
919 SymbolContext frame_sc;
921 sb_error.SetErrorString("no valid frames in thread to step");
925 // If we have a frame, get its line
926 frame_sc = frame_sp->GetSymbolContext(
927 eSymbolContextCompUnit | eSymbolContextFunction |
928 eSymbolContextLineEntry | eSymbolContextSymbol);
930 if (frame_sc.comp_unit == NULL) {
931 sb_error.SetErrorStringWithFormat(
932 "frame %u doesn't have debug information", frame_sp->GetFrameIndex());
936 FileSpec step_file_spec;
937 if (sb_file_spec.IsValid()) {
938 // The file spec passed in was valid, so use it
939 step_file_spec = sb_file_spec.ref();
941 if (frame_sc.line_entry.IsValid())
942 step_file_spec = frame_sc.line_entry.file;
944 sb_error.SetErrorString("invalid file argument or no file for frame");
949 // Grab the current function, then we will make sure the "until" address is
950 // within the function. We discard addresses that are out of the current
951 // function, and then if there are no addresses remaining, give an
952 // appropriate error message.
954 bool all_in_function = true;
955 AddressRange fun_range = frame_sc.function->GetAddressRange();
957 std::vector<addr_t> step_over_until_addrs;
958 const bool abort_other_plans = false;
959 const bool stop_other_threads = false;
960 const bool check_inlines = true;
961 const bool exact = false;
963 SymbolContextList sc_list;
964 const uint32_t num_matches = frame_sc.comp_unit->ResolveSymbolContext(
965 step_file_spec, line, check_inlines, exact, eSymbolContextLineEntry,
967 if (num_matches > 0) {
969 for (uint32_t i = 0; i < num_matches; ++i) {
970 if (sc_list.GetContextAtIndex(i, sc)) {
972 sc.line_entry.range.GetBaseAddress().GetLoadAddress(target);
973 if (step_addr != LLDB_INVALID_ADDRESS) {
974 if (fun_range.ContainsLoadAddress(step_addr, target))
975 step_over_until_addrs.push_back(step_addr);
977 all_in_function = false;
983 if (step_over_until_addrs.empty()) {
984 if (all_in_function) {
985 step_file_spec.GetPath(path, sizeof(path));
986 sb_error.SetErrorStringWithFormat("No line entries for %s:%u", path,
989 sb_error.SetErrorString("step until target not in current function");
991 ThreadPlanSP new_plan_sp(thread->QueueThreadPlanForStepUntil(
992 abort_other_plans, &step_over_until_addrs[0],
993 step_over_until_addrs.size(), stop_other_threads,
994 frame_sp->GetFrameIndex()));
996 sb_error = ResumeNewPlan(exe_ctx, new_plan_sp.get());
999 sb_error.SetErrorString("this SBThread object is invalid");
1004 SBError SBThread::StepUsingScriptedThreadPlan(const char *script_class_name) {
1005 return StepUsingScriptedThreadPlan(script_class_name, true);
1008 SBError SBThread::StepUsingScriptedThreadPlan(const char *script_class_name,
1009 bool resume_immediately) {
1010 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1013 std::unique_lock<std::recursive_mutex> lock;
1014 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1017 log->Printf("SBThread(%p)::StepUsingScriptedThreadPlan: class name: %s",
1018 static_cast<void *>(exe_ctx.GetThreadPtr()), script_class_name);
1021 if (!exe_ctx.HasThreadScope()) {
1022 sb_error.SetErrorString("this SBThread object is invalid");
1026 Thread *thread = exe_ctx.GetThreadPtr();
1027 ThreadPlanSP thread_plan_sp =
1028 thread->QueueThreadPlanForStepScripted(false, script_class_name, false);
1030 if (!thread_plan_sp) {
1031 sb_error.SetErrorStringWithFormat(
1032 "Error queueing thread plan for class: %s", script_class_name);
1036 if (!resume_immediately) {
1041 sb_error = ResumeNewPlan(exe_ctx, thread_plan_sp.get());
1043 sb_error.SetErrorStringWithFormat(
1044 "Error resuming thread plan for class: %s.", script_class_name);
1046 log->Printf("SBThread(%p)::StepUsingScriptedThreadPlan: Error queuing "
1047 "thread plan for class: %s",
1048 static_cast<void *>(exe_ctx.GetThreadPtr()),
1055 SBError SBThread::JumpToLine(lldb::SBFileSpec &file_spec, uint32_t line) {
1056 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1059 std::unique_lock<std::recursive_mutex> lock;
1060 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1063 log->Printf("SBThread(%p)::JumpToLine (file+line = %s:%u)",
1064 static_cast<void *>(exe_ctx.GetThreadPtr()),
1065 file_spec->GetPath().c_str(), line);
1067 if (!exe_ctx.HasThreadScope()) {
1068 sb_error.SetErrorString("this SBThread object is invalid");
1072 Thread *thread = exe_ctx.GetThreadPtr();
1074 Status err = thread->JumpToLine(file_spec.get(), line, true);
1075 sb_error.SetError(err);
1079 SBError SBThread::ReturnFromFrame(SBFrame &frame, SBValue &return_value) {
1082 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1084 std::unique_lock<std::recursive_mutex> lock;
1085 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1088 log->Printf("SBThread(%p)::ReturnFromFrame (frame=%d)",
1089 static_cast<void *>(exe_ctx.GetThreadPtr()),
1090 frame.GetFrameID());
1092 if (exe_ctx.HasThreadScope()) {
1093 Thread *thread = exe_ctx.GetThreadPtr();
1095 thread->ReturnFromFrame(frame.GetFrameSP(), return_value.GetSP()));
1101 SBError SBThread::UnwindInnermostExpression() {
1104 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1106 std::unique_lock<std::recursive_mutex> lock;
1107 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1110 log->Printf("SBThread(%p)::UnwindExpressionEvaluation",
1111 static_cast<void *>(exe_ctx.GetThreadPtr()));
1113 if (exe_ctx.HasThreadScope()) {
1114 Thread *thread = exe_ctx.GetThreadPtr();
1115 sb_error.SetError(thread->UnwindInnermostExpression());
1116 if (sb_error.Success())
1117 thread->SetSelectedFrameByIndex(0, false);
1123 bool SBThread::Suspend() {
1124 SBError error; // Ignored
1125 return Suspend(error);
1128 bool SBThread::Suspend(SBError &error) {
1129 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1130 std::unique_lock<std::recursive_mutex> lock;
1131 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1133 bool result = false;
1134 if (exe_ctx.HasThreadScope()) {
1135 Process::StopLocker stop_locker;
1136 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
1137 exe_ctx.GetThreadPtr()->SetResumeState(eStateSuspended);
1140 error.SetErrorString("process is running");
1142 log->Printf("SBThread(%p)::Suspend() => error: process is running",
1143 static_cast<void *>(exe_ctx.GetThreadPtr()));
1146 error.SetErrorString("this SBThread object is invalid");
1148 log->Printf("SBThread(%p)::Suspend() => %i",
1149 static_cast<void *>(exe_ctx.GetThreadPtr()), result);
1153 bool SBThread::Resume() {
1154 SBError error; // Ignored
1155 return Resume(error);
1158 bool SBThread::Resume(SBError &error) {
1159 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1160 std::unique_lock<std::recursive_mutex> lock;
1161 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1163 bool result = false;
1164 if (exe_ctx.HasThreadScope()) {
1165 Process::StopLocker stop_locker;
1166 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
1167 const bool override_suspend = true;
1168 exe_ctx.GetThreadPtr()->SetResumeState(eStateRunning, override_suspend);
1171 error.SetErrorString("process is running");
1173 log->Printf("SBThread(%p)::Resume() => error: process is running",
1174 static_cast<void *>(exe_ctx.GetThreadPtr()));
1177 error.SetErrorString("this SBThread object is invalid");
1179 log->Printf("SBThread(%p)::Resume() => %i",
1180 static_cast<void *>(exe_ctx.GetThreadPtr()), result);
1184 bool SBThread::IsSuspended() {
1185 std::unique_lock<std::recursive_mutex> lock;
1186 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1188 if (exe_ctx.HasThreadScope())
1189 return exe_ctx.GetThreadPtr()->GetResumeState() == eStateSuspended;
1193 bool SBThread::IsStopped() {
1194 std::unique_lock<std::recursive_mutex> lock;
1195 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1197 if (exe_ctx.HasThreadScope())
1198 return StateIsStoppedState(exe_ctx.GetThreadPtr()->GetState(), true);
1202 SBProcess SBThread::GetProcess() {
1203 SBProcess sb_process;
1204 std::unique_lock<std::recursive_mutex> lock;
1205 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1207 if (exe_ctx.HasThreadScope()) {
1208 // Have to go up to the target so we can get a shared pointer to our
1210 sb_process.SetSP(exe_ctx.GetProcessSP());
1213 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1215 SBStream frame_desc_strm;
1216 sb_process.GetDescription(frame_desc_strm);
1217 log->Printf("SBThread(%p)::GetProcess () => SBProcess(%p): %s",
1218 static_cast<void *>(exe_ctx.GetThreadPtr()),
1219 static_cast<void *>(sb_process.GetSP().get()),
1220 frame_desc_strm.GetData());
1226 uint32_t SBThread::GetNumFrames() {
1227 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1229 uint32_t num_frames = 0;
1230 std::unique_lock<std::recursive_mutex> lock;
1231 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1233 if (exe_ctx.HasThreadScope()) {
1234 Process::StopLocker stop_locker;
1235 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
1236 num_frames = exe_ctx.GetThreadPtr()->GetStackFrameCount();
1239 log->Printf("SBThread(%p)::GetNumFrames() => error: process is running",
1240 static_cast<void *>(exe_ctx.GetThreadPtr()));
1245 log->Printf("SBThread(%p)::GetNumFrames () => %u",
1246 static_cast<void *>(exe_ctx.GetThreadPtr()), num_frames);
1251 SBFrame SBThread::GetFrameAtIndex(uint32_t idx) {
1252 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1255 StackFrameSP frame_sp;
1256 std::unique_lock<std::recursive_mutex> lock;
1257 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1259 if (exe_ctx.HasThreadScope()) {
1260 Process::StopLocker stop_locker;
1261 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
1262 frame_sp = exe_ctx.GetThreadPtr()->GetStackFrameAtIndex(idx);
1263 sb_frame.SetFrameSP(frame_sp);
1267 "SBThread(%p)::GetFrameAtIndex() => error: process is running",
1268 static_cast<void *>(exe_ctx.GetThreadPtr()));
1273 SBStream frame_desc_strm;
1274 sb_frame.GetDescription(frame_desc_strm);
1275 log->Printf("SBThread(%p)::GetFrameAtIndex (idx=%d) => SBFrame(%p): %s",
1276 static_cast<void *>(exe_ctx.GetThreadPtr()), idx,
1277 static_cast<void *>(frame_sp.get()), frame_desc_strm.GetData());
1283 lldb::SBFrame SBThread::GetSelectedFrame() {
1284 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1287 StackFrameSP frame_sp;
1288 std::unique_lock<std::recursive_mutex> lock;
1289 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1291 if (exe_ctx.HasThreadScope()) {
1292 Process::StopLocker stop_locker;
1293 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
1294 frame_sp = exe_ctx.GetThreadPtr()->GetSelectedFrame();
1295 sb_frame.SetFrameSP(frame_sp);
1299 "SBThread(%p)::GetSelectedFrame() => error: process is running",
1300 static_cast<void *>(exe_ctx.GetThreadPtr()));
1305 SBStream frame_desc_strm;
1306 sb_frame.GetDescription(frame_desc_strm);
1307 log->Printf("SBThread(%p)::GetSelectedFrame () => SBFrame(%p): %s",
1308 static_cast<void *>(exe_ctx.GetThreadPtr()),
1309 static_cast<void *>(frame_sp.get()), frame_desc_strm.GetData());
1315 lldb::SBFrame SBThread::SetSelectedFrame(uint32_t idx) {
1316 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1319 StackFrameSP frame_sp;
1320 std::unique_lock<std::recursive_mutex> lock;
1321 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1323 if (exe_ctx.HasThreadScope()) {
1324 Process::StopLocker stop_locker;
1325 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
1326 Thread *thread = exe_ctx.GetThreadPtr();
1327 frame_sp = thread->GetStackFrameAtIndex(idx);
1329 thread->SetSelectedFrame(frame_sp.get());
1330 sb_frame.SetFrameSP(frame_sp);
1335 "SBThread(%p)::SetSelectedFrame() => error: process is running",
1336 static_cast<void *>(exe_ctx.GetThreadPtr()));
1341 SBStream frame_desc_strm;
1342 sb_frame.GetDescription(frame_desc_strm);
1343 log->Printf("SBThread(%p)::SetSelectedFrame (idx=%u) => SBFrame(%p): %s",
1344 static_cast<void *>(exe_ctx.GetThreadPtr()), idx,
1345 static_cast<void *>(frame_sp.get()), frame_desc_strm.GetData());
1350 bool SBThread::EventIsThreadEvent(const SBEvent &event) {
1351 return Thread::ThreadEventData::GetEventDataFromEvent(event.get()) != NULL;
1354 SBFrame SBThread::GetStackFrameFromEvent(const SBEvent &event) {
1355 return Thread::ThreadEventData::GetStackFrameFromEvent(event.get());
1358 SBThread SBThread::GetThreadFromEvent(const SBEvent &event) {
1359 return Thread::ThreadEventData::GetThreadFromEvent(event.get());
1362 bool SBThread::operator==(const SBThread &rhs) const {
1363 return m_opaque_sp->GetThreadSP().get() ==
1364 rhs.m_opaque_sp->GetThreadSP().get();
1367 bool SBThread::operator!=(const SBThread &rhs) const {
1368 return m_opaque_sp->GetThreadSP().get() !=
1369 rhs.m_opaque_sp->GetThreadSP().get();
1372 bool SBThread::GetStatus(SBStream &status) const {
1373 Stream &strm = status.ref();
1375 std::unique_lock<std::recursive_mutex> lock;
1376 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1378 if (exe_ctx.HasThreadScope()) {
1379 exe_ctx.GetThreadPtr()->GetStatus(strm, 0, 1, 1, true);
1381 strm.PutCString("No status");
1386 bool SBThread::GetDescription(SBStream &description) const {
1387 return GetDescription(description, false);
1390 bool SBThread::GetDescription(SBStream &description, bool stop_format) const {
1391 Stream &strm = description.ref();
1393 std::unique_lock<std::recursive_mutex> lock;
1394 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1396 if (exe_ctx.HasThreadScope()) {
1397 exe_ctx.GetThreadPtr()->DumpUsingSettingsFormat(strm,
1398 LLDB_INVALID_THREAD_ID,
1400 // strm.Printf("SBThread: tid = 0x%4.4" PRIx64,
1401 // exe_ctx.GetThreadPtr()->GetID());
1403 strm.PutCString("No value");
1408 SBThread SBThread::GetExtendedBacktraceThread(const char *type) {
1409 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_API));
1410 std::unique_lock<std::recursive_mutex> lock;
1411 ExecutionContext exe_ctx(m_opaque_sp.get(), lock);
1412 SBThread sb_origin_thread;
1414 if (exe_ctx.HasThreadScope()) {
1415 Process::StopLocker stop_locker;
1416 if (stop_locker.TryLock(&exe_ctx.GetProcessPtr()->GetRunLock())) {
1417 ThreadSP real_thread(exe_ctx.GetThreadSP());
1419 ConstString type_const(type);
1420 Process *process = exe_ctx.GetProcessPtr();
1422 SystemRuntime *runtime = process->GetSystemRuntime();
1424 ThreadSP new_thread_sp(
1425 runtime->GetExtendedBacktraceThread(real_thread, type_const));
1426 if (new_thread_sp) {
1427 // Save this in the Process' ExtendedThreadList so a strong
1428 // pointer retains the object.
1429 process->GetExtendedThreadList().AddThread(new_thread_sp);
1430 sb_origin_thread.SetThread(new_thread_sp);
1432 const char *queue_name = new_thread_sp->GetQueueName();
1433 if (queue_name == NULL)
1435 log->Printf("SBThread(%p)::GetExtendedBacktraceThread() => new "
1437 "created (%p) with queue_id 0x%" PRIx64
1439 static_cast<void *>(exe_ctx.GetThreadPtr()),
1440 static_cast<void *>(new_thread_sp.get()),
1441 new_thread_sp->GetQueueID(), queue_name);
1449 log->Printf("SBThread(%p)::GetExtendedBacktraceThread() => error: "
1450 "process is running",
1451 static_cast<void *>(exe_ctx.GetThreadPtr()));
1455 if (log && sb_origin_thread.IsValid() == false)
1456 log->Printf("SBThread(%p)::GetExtendedBacktraceThread() is not returning a "
1458 static_cast<void *>(exe_ctx.GetThreadPtr()));
1459 return sb_origin_thread;
1462 uint32_t SBThread::GetExtendedBacktraceOriginatingIndexID() {
1463 ThreadSP thread_sp(m_opaque_sp->GetThreadSP());
1465 return thread_sp->GetExtendedBacktraceOriginatingIndexID();
1466 return LLDB_INVALID_INDEX32;
1469 bool SBThread::SafeToCallFunctions() {
1470 ThreadSP thread_sp(m_opaque_sp->GetThreadSP());
1472 return thread_sp->SafeToCallFunctions();
1476 lldb_private::Thread *SBThread::operator->() {
1477 ThreadSP thread_sp(m_opaque_sp->GetThreadSP());
1479 return thread_sp.get();
1484 lldb_private::Thread *SBThread::get() {
1485 ThreadSP thread_sp(m_opaque_sp->GetThreadSP());
1487 return thread_sp.get();