xref: /llvm-project/lldb/source/Commands/CommandObjectThread.cpp (revision 7a88ec9ac05c4f9e4cc03bd9e84af9e6da73c8b9)
1 //===-- CommandObjectThread.cpp ---------------------------------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 #include "lldb/lldb-python.h"
11 
12 #include "CommandObjectThread.h"
13 
14 // C Includes
15 // C++ Includes
16 // Other libraries and framework includes
17 // Project includes
18 #include "lldb/lldb-private.h"
19 #include "lldb/Core/State.h"
20 #include "lldb/Core/SourceManager.h"
21 #include "lldb/Host/Host.h"
22 #include "lldb/Interpreter/CommandInterpreter.h"
23 #include "lldb/Interpreter/CommandReturnObject.h"
24 #include "lldb/Interpreter/Options.h"
25 #include "lldb/Symbol/CompileUnit.h"
26 #include "lldb/Symbol/Function.h"
27 #include "lldb/Symbol/LineTable.h"
28 #include "lldb/Symbol/LineEntry.h"
29 #include "lldb/Target/Process.h"
30 #include "lldb/Target/RegisterContext.h"
31 #include "lldb/Target/SystemRuntime.h"
32 #include "lldb/Target/Target.h"
33 #include "lldb/Target/Thread.h"
34 #include "lldb/Target/ThreadPlan.h"
35 #include "lldb/Target/ThreadPlanStepInstruction.h"
36 #include "lldb/Target/ThreadPlanStepOut.h"
37 #include "lldb/Target/ThreadPlanStepRange.h"
38 #include "lldb/Target/ThreadPlanStepInRange.h"
39 
40 
41 using namespace lldb;
42 using namespace lldb_private;
43 
44 
45 //-------------------------------------------------------------------------
46 // CommandObjectThreadBacktrace
47 //-------------------------------------------------------------------------
48 
49 class CommandObjectThreadBacktrace : public CommandObjectParsed
50 {
51 public:
52 
53     class CommandOptions : public Options
54     {
55     public:
56 
57         CommandOptions (CommandInterpreter &interpreter) :
58             Options(interpreter)
59         {
60             // Keep default values of all options in one place: OptionParsingStarting ()
61             OptionParsingStarting ();
62         }
63 
64         virtual
65         ~CommandOptions ()
66         {
67         }
68 
69         virtual Error
70         SetOptionValue (uint32_t option_idx, const char *option_arg)
71         {
72             Error error;
73             const int short_option = m_getopt_table[option_idx].val;
74 
75             switch (short_option)
76             {
77                 case 'c':
78                 {
79                     bool success;
80                     int32_t input_count =  Args::StringToSInt32 (option_arg, -1, 0, &success);
81                     if (!success)
82                         error.SetErrorStringWithFormat("invalid integer value for option '%c'", short_option);
83                     if (input_count < -1)
84                         m_count = UINT32_MAX;
85                     else
86                         m_count = input_count;
87                 }
88                 break;
89                 case 's':
90                 {
91                     bool success;
92                     m_start =  Args::StringToUInt32 (option_arg, 0, 0, &success);
93                     if (!success)
94                         error.SetErrorStringWithFormat("invalid integer value for option '%c'", short_option);
95                 }
96                 case 'e':
97                 {
98                     bool success;
99                     m_extended_backtrace =  Args::StringToBoolean (option_arg, false, &success);
100                     if (!success)
101                         error.SetErrorStringWithFormat("invalid boolean value for option '%c'", short_option);
102                 }
103                 break;
104                 default:
105                     error.SetErrorStringWithFormat("invalid short option character '%c'", short_option);
106                     break;
107 
108             }
109             return error;
110         }
111 
112         void
113         OptionParsingStarting ()
114         {
115             m_count = UINT32_MAX;
116             m_start = 0;
117             m_extended_backtrace = false;
118         }
119 
120         const OptionDefinition*
121         GetDefinitions ()
122         {
123             return g_option_table;
124         }
125 
126         // Options table: Required for subclasses of Options.
127 
128         static OptionDefinition g_option_table[];
129 
130         // Instance variables to hold the values for command options.
131         uint32_t m_count;
132         uint32_t m_start;
133         bool     m_extended_backtrace;
134     };
135 
136     CommandObjectThreadBacktrace (CommandInterpreter &interpreter) :
137         CommandObjectParsed (interpreter,
138                              "thread backtrace",
139                              "Show the stack for one or more threads.  If no threads are specified, show the currently selected thread.  Use the thread-index \"all\" to see all threads.",
140                              NULL,
141                              eFlagRequiresProcess       |
142                              eFlagRequiresThread        |
143                              eFlagTryTargetAPILock      |
144                              eFlagProcessMustBeLaunched |
145                              eFlagProcessMustBePaused   ),
146         m_options(interpreter)
147     {
148         CommandArgumentEntry arg;
149         CommandArgumentData thread_idx_arg;
150 
151         // Define the first (and only) variant of this arg.
152         thread_idx_arg.arg_type = eArgTypeThreadIndex;
153         thread_idx_arg.arg_repetition = eArgRepeatStar;
154 
155         // There is only one variant this argument could be; put it into the argument entry.
156         arg.push_back (thread_idx_arg);
157 
158         // Push the data for the first argument into the m_arguments vector.
159         m_arguments.push_back (arg);
160     }
161 
162     ~CommandObjectThreadBacktrace()
163     {
164     }
165 
166     virtual Options *
167     GetOptions ()
168     {
169         return &m_options;
170     }
171 
172 protected:
173     void
174     DoExtendedBacktrace (Thread *thread, CommandReturnObject &result)
175     {
176         SystemRuntime *runtime = thread->GetProcess()->GetSystemRuntime();
177         if (runtime)
178         {
179             Stream &strm = result.GetOutputStream();
180             const std::vector<ConstString> &types = runtime->GetExtendedBacktraceTypes();
181             for (auto type : types)
182             {
183                 ThreadSP ext_thread_sp = runtime->GetExtendedBacktraceThread (thread->shared_from_this(), type);
184                 if (ext_thread_sp && ext_thread_sp->IsValid ())
185                 {
186                     const uint32_t num_frames_with_source = 0;
187                     if (ext_thread_sp->GetStatus (strm,
188                         m_options.m_start,
189                         m_options.m_count,
190                         num_frames_with_source))
191                     {
192                         DoExtendedBacktrace (ext_thread_sp.get(), result);
193                     }
194                 }
195             }
196         }
197     }
198 
199     virtual bool
200     DoExecute (Args& command, CommandReturnObject &result)
201     {
202         result.SetStatus (eReturnStatusSuccessFinishResult);
203         Stream &strm = result.GetOutputStream();
204 
205         // Don't show source context when doing backtraces.
206         const uint32_t num_frames_with_source = 0;
207         if (command.GetArgumentCount() == 0)
208         {
209             Thread *thread = m_exe_ctx.GetThreadPtr();
210             // Thread::GetStatus() returns the number of frames shown.
211             if (thread->GetStatus (strm,
212                                    m_options.m_start,
213                                    m_options.m_count,
214                                    num_frames_with_source))
215             {
216                 result.SetStatus (eReturnStatusSuccessFinishResult);
217                 if (m_options.m_extended_backtrace)
218                 {
219                     DoExtendedBacktrace (thread, result);
220                 }
221             }
222         }
223         else if (command.GetArgumentCount() == 1 && ::strcmp (command.GetArgumentAtIndex(0), "all") == 0)
224         {
225             Process *process = m_exe_ctx.GetProcessPtr();
226             uint32_t idx = 0;
227             for (ThreadSP thread_sp : process->Threads())
228             {
229                 if (idx != 0)
230                     result.AppendMessage("");
231 
232                 if (!thread_sp->GetStatus (strm,
233                                            m_options.m_start,
234                                            m_options.m_count,
235                                            num_frames_with_source))
236                 {
237                     result.AppendErrorWithFormat ("error displaying backtrace for thread: \"0x%4.4x\"\n", idx);
238                     result.SetStatus (eReturnStatusFailed);
239                     return false;
240                 }
241                 if (m_options.m_extended_backtrace)
242                 {
243                     DoExtendedBacktrace (thread_sp.get(), result);
244                 }
245 
246                 ++idx;
247             }
248         }
249         else
250         {
251             const size_t num_args = command.GetArgumentCount();
252             Process *process = m_exe_ctx.GetProcessPtr();
253             Mutex::Locker locker (process->GetThreadList().GetMutex());
254             std::vector<ThreadSP> thread_sps;
255 
256             for (size_t i = 0; i < num_args; i++)
257             {
258                 bool success;
259 
260                 uint32_t thread_idx = Args::StringToUInt32(command.GetArgumentAtIndex(i), 0, 0, &success);
261                 if (!success)
262                 {
263                     result.AppendErrorWithFormat ("invalid thread specification: \"%s\"\n", command.GetArgumentAtIndex(i));
264                     result.SetStatus (eReturnStatusFailed);
265                     return false;
266                 }
267 
268                 thread_sps.push_back(process->GetThreadList().FindThreadByIndexID(thread_idx));
269 
270                 if (!thread_sps[i])
271                 {
272                     result.AppendErrorWithFormat ("no thread with index: \"%s\"\n", command.GetArgumentAtIndex(i));
273                     result.SetStatus (eReturnStatusFailed);
274                     return false;
275                 }
276 
277             }
278 
279             for (uint32_t i = 0; i < num_args; i++)
280             {
281                 if (!thread_sps[i]->GetStatus (strm,
282                                                m_options.m_start,
283                                                m_options.m_count,
284                                                num_frames_with_source))
285                 {
286                     result.AppendErrorWithFormat ("error displaying backtrace for thread: \"%s\"\n", command.GetArgumentAtIndex(i));
287                     result.SetStatus (eReturnStatusFailed);
288                     return false;
289                 }
290                 if (m_options.m_extended_backtrace)
291                 {
292                     DoExtendedBacktrace (thread_sps[i].get(), result);
293                 }
294 
295                 if (i < num_args - 1)
296                     result.AppendMessage("");
297             }
298         }
299         return result.Succeeded();
300     }
301 
302     CommandOptions m_options;
303 };
304 
305 OptionDefinition
306 CommandObjectThreadBacktrace::CommandOptions::g_option_table[] =
307 {
308 { LLDB_OPT_SET_1, false, "count", 'c', OptionParser::eRequiredArgument, NULL, 0, eArgTypeCount, "How many frames to display (-1 for all)"},
309 { LLDB_OPT_SET_1, false, "start", 's', OptionParser::eRequiredArgument, NULL, 0, eArgTypeFrameIndex, "Frame in which to start the backtrace"},
310 { LLDB_OPT_SET_1, false, "extended", 'e', OptionParser::eRequiredArgument, NULL, 0, eArgTypeBoolean, "Show the extended backtrace, if available"},
311 { 0, false, NULL, 0, 0, NULL, 0, eArgTypeNone, NULL }
312 };
313 
314 enum StepScope
315 {
316     eStepScopeSource,
317     eStepScopeInstruction
318 };
319 
320 class CommandObjectThreadStepWithTypeAndScope : public CommandObjectParsed
321 {
322 public:
323 
324     class CommandOptions : public Options
325     {
326     public:
327 
328         CommandOptions (CommandInterpreter &interpreter) :
329             Options (interpreter)
330         {
331             // Keep default values of all options in one place: OptionParsingStarting ()
332             OptionParsingStarting ();
333         }
334 
335         virtual
336         ~CommandOptions ()
337         {
338         }
339 
340         virtual Error
341         SetOptionValue (uint32_t option_idx, const char *option_arg)
342         {
343             Error error;
344             const int short_option = m_getopt_table[option_idx].val;
345 
346             switch (short_option)
347             {
348             case 'a':
349                 {
350                     bool success;
351                     bool avoid_no_debug =  Args::StringToBoolean (option_arg, true, &success);
352                     if (!success)
353                         error.SetErrorStringWithFormat("invalid boolean value for option '%c'", short_option);
354                     else
355                     {
356                         m_step_in_avoid_no_debug = avoid_no_debug ? eLazyBoolYes : eLazyBoolNo;
357                     }
358                 }
359                 break;
360 
361             case 'A':
362                 {
363                     bool success;
364                     bool avoid_no_debug =  Args::StringToBoolean (option_arg, true, &success);
365                     if (!success)
366                         error.SetErrorStringWithFormat("invalid boolean value for option '%c'", short_option);
367                     else
368                     {
369                         m_step_out_avoid_no_debug = avoid_no_debug ? eLazyBoolYes : eLazyBoolNo;
370                     }
371                 }
372                 break;
373 
374             case 'c':
375                 {
376                     m_step_count = Args::StringToUInt32(option_arg, UINT32_MAX, 0);
377                     if (m_step_count == UINT32_MAX)
378                        error.SetErrorStringWithFormat ("invalid ignore count '%s'", option_arg);
379                     break;
380                 }
381                 break;
382             case 'm':
383                 {
384                     OptionEnumValueElement *enum_values = g_option_table[option_idx].enum_values;
385                     m_run_mode = (lldb::RunMode) Args::StringToOptionEnum(option_arg, enum_values, eOnlyDuringStepping, error);
386                 }
387                 break;
388 
389             case 'r':
390                 {
391                     m_avoid_regexp.clear();
392                     m_avoid_regexp.assign(option_arg);
393                 }
394                 break;
395 
396             case 't':
397                 {
398                     m_step_in_target.clear();
399                     m_step_in_target.assign(option_arg);
400 
401                 }
402                 break;
403             default:
404                 error.SetErrorStringWithFormat("invalid short option character '%c'", short_option);
405                 break;
406 
407             }
408             return error;
409         }
410 
411         void
412         OptionParsingStarting ()
413         {
414             m_step_in_avoid_no_debug = eLazyBoolCalculate;
415             m_step_out_avoid_no_debug = eLazyBoolCalculate;
416             m_run_mode = eOnlyDuringStepping;
417             m_avoid_regexp.clear();
418             m_step_in_target.clear();
419             m_step_count = 1;
420         }
421 
422         const OptionDefinition*
423         GetDefinitions ()
424         {
425             return g_option_table;
426         }
427 
428         // Options table: Required for subclasses of Options.
429 
430         static OptionDefinition g_option_table[];
431 
432         // Instance variables to hold the values for command options.
433         LazyBool m_step_in_avoid_no_debug;
434         LazyBool m_step_out_avoid_no_debug;
435         RunMode m_run_mode;
436         std::string m_avoid_regexp;
437         std::string m_step_in_target;
438         int32_t m_step_count;
439     };
440 
441     CommandObjectThreadStepWithTypeAndScope (CommandInterpreter &interpreter,
442                                              const char *name,
443                                              const char *help,
444                                              const char *syntax,
445                                              StepType step_type,
446                                              StepScope step_scope) :
447         CommandObjectParsed (interpreter, name, help, syntax,
448                              eFlagRequiresProcess       |
449                              eFlagRequiresThread        |
450                              eFlagTryTargetAPILock      |
451                              eFlagProcessMustBeLaunched |
452                              eFlagProcessMustBePaused   ),
453         m_step_type (step_type),
454         m_step_scope (step_scope),
455         m_options (interpreter)
456     {
457         CommandArgumentEntry arg;
458         CommandArgumentData thread_id_arg;
459 
460         // Define the first (and only) variant of this arg.
461         thread_id_arg.arg_type = eArgTypeThreadID;
462         thread_id_arg.arg_repetition = eArgRepeatOptional;
463 
464         // There is only one variant this argument could be; put it into the argument entry.
465         arg.push_back (thread_id_arg);
466 
467         // Push the data for the first argument into the m_arguments vector.
468         m_arguments.push_back (arg);
469     }
470 
471     virtual
472     ~CommandObjectThreadStepWithTypeAndScope ()
473     {
474     }
475 
476     virtual
477     Options *
478     GetOptions ()
479     {
480         return &m_options;
481     }
482 
483 protected:
484     virtual bool
485     DoExecute (Args& command, CommandReturnObject &result)
486     {
487         Process *process = m_exe_ctx.GetProcessPtr();
488         bool synchronous_execution = m_interpreter.GetSynchronous();
489 
490         const uint32_t num_threads = process->GetThreadList().GetSize();
491         Thread *thread = NULL;
492 
493         if (command.GetArgumentCount() == 0)
494         {
495             thread = process->GetThreadList().GetSelectedThread().get();
496             if (thread == NULL)
497             {
498                 result.AppendError ("no selected thread in process");
499                 result.SetStatus (eReturnStatusFailed);
500                 return false;
501             }
502         }
503         else
504         {
505             const char *thread_idx_cstr = command.GetArgumentAtIndex(0);
506             uint32_t step_thread_idx = Args::StringToUInt32 (thread_idx_cstr, LLDB_INVALID_INDEX32);
507             if (step_thread_idx == LLDB_INVALID_INDEX32)
508             {
509                 result.AppendErrorWithFormat ("invalid thread index '%s'.\n", thread_idx_cstr);
510                 result.SetStatus (eReturnStatusFailed);
511                 return false;
512             }
513             thread = process->GetThreadList().FindThreadByIndexID(step_thread_idx).get();
514             if (thread == NULL)
515             {
516                 result.AppendErrorWithFormat ("Thread index %u is out of range (valid values are 0 - %u).\n",
517                                               step_thread_idx, num_threads);
518                 result.SetStatus (eReturnStatusFailed);
519                 return false;
520             }
521         }
522 
523         const bool abort_other_plans = false;
524         const lldb::RunMode stop_other_threads = m_options.m_run_mode;
525 
526         // This is a bit unfortunate, but not all the commands in this command object support
527         // only while stepping, so I use the bool for them.
528         bool bool_stop_other_threads;
529         if (m_options.m_run_mode == eAllThreads)
530             bool_stop_other_threads = false;
531         else if (m_options.m_run_mode == eOnlyDuringStepping)
532         {
533             if (m_step_type == eStepTypeOut)
534                 bool_stop_other_threads = false;
535             else
536                 bool_stop_other_threads = true;
537         }
538         else
539             bool_stop_other_threads = true;
540 
541         ThreadPlanSP new_plan_sp;
542 
543         if (m_step_type == eStepTypeInto)
544         {
545             StackFrame *frame = thread->GetStackFrameAtIndex(0).get();
546 
547             if (frame->HasDebugInformation ())
548             {
549                 new_plan_sp = thread->QueueThreadPlanForStepInRange (abort_other_plans,
550                                                                 frame->GetSymbolContext(eSymbolContextEverything).line_entry.range,
551                                                                 frame->GetSymbolContext(eSymbolContextEverything),
552                                                                 m_options.m_step_in_target.c_str(),
553                                                                 stop_other_threads,
554                                                                 m_options.m_step_in_avoid_no_debug,
555                                                                 m_options.m_step_out_avoid_no_debug);
556 
557                 if (new_plan_sp && !m_options.m_avoid_regexp.empty())
558                 {
559                     ThreadPlanStepInRange *step_in_range_plan = static_cast<ThreadPlanStepInRange *> (new_plan_sp.get());
560                     step_in_range_plan->SetAvoidRegexp(m_options.m_avoid_regexp.c_str());
561                 }
562             }
563             else
564                 new_plan_sp = thread->QueueThreadPlanForStepSingleInstruction (false, abort_other_plans, bool_stop_other_threads);
565 
566         }
567         else if (m_step_type == eStepTypeOver)
568         {
569             StackFrame *frame = thread->GetStackFrameAtIndex(0).get();
570 
571             if (frame->HasDebugInformation())
572                 new_plan_sp = thread->QueueThreadPlanForStepOverRange (abort_other_plans,
573                                                                     frame->GetSymbolContext(eSymbolContextEverything).line_entry.range,
574                                                                     frame->GetSymbolContext(eSymbolContextEverything),
575                                                                     stop_other_threads,
576                                                                     m_options.m_step_out_avoid_no_debug);
577             else
578                 new_plan_sp = thread->QueueThreadPlanForStepSingleInstruction (true,
579                                                                             abort_other_plans,
580                                                                             bool_stop_other_threads);
581 
582         }
583         else if (m_step_type == eStepTypeTrace)
584         {
585             new_plan_sp = thread->QueueThreadPlanForStepSingleInstruction (false, abort_other_plans, bool_stop_other_threads);
586         }
587         else if (m_step_type == eStepTypeTraceOver)
588         {
589             new_plan_sp = thread->QueueThreadPlanForStepSingleInstruction (true, abort_other_plans, bool_stop_other_threads);
590         }
591         else if (m_step_type == eStepTypeOut)
592         {
593             new_plan_sp = thread->QueueThreadPlanForStepOut (abort_other_plans,
594                                                           NULL,
595                                                           false,
596                                                           bool_stop_other_threads,
597                                                           eVoteYes,
598                                                           eVoteNoOpinion,
599                                                           thread->GetSelectedFrameIndex(),
600                                                           m_options.m_step_out_avoid_no_debug);
601         }
602         else
603         {
604             result.AppendError ("step type is not supported");
605             result.SetStatus (eReturnStatusFailed);
606             return false;
607         }
608 
609         // If we got a new plan, then set it to be a master plan (User level Plans should be master plans
610         // so that they can be interruptible).  Then resume the process.
611 
612         if (new_plan_sp)
613         {
614             new_plan_sp->SetIsMasterPlan (true);
615             new_plan_sp->SetOkayToDiscard (false);
616 
617             if (m_options.m_step_count > 1)
618             {
619                 if (new_plan_sp->SetIterationCount(m_options.m_step_count) != m_options.m_step_count)
620                 {
621                     result.AppendWarning ("step operation does not support iteration count.");
622                 }
623             }
624 
625             process->GetThreadList().SetSelectedThreadByID (thread->GetID());
626             process->Resume ();
627 
628 
629             if (synchronous_execution)
630             {
631                 StateType state = process->WaitForProcessToStop (NULL);
632 
633                 //EventSP event_sp;
634                 //StateType state = process->WaitForStateChangedEvents (NULL, event_sp);
635                 //while (! StateIsStoppedState (state))
636                 //  {
637                 //    state = process->WaitForStateChangedEvents (NULL, event_sp);
638                 //  }
639                 process->GetThreadList().SetSelectedThreadByID (thread->GetID());
640                 result.SetDidChangeProcessState (true);
641                 result.AppendMessageWithFormat ("Process %" PRIu64 " %s\n", process->GetID(), StateAsCString (state));
642                 result.SetStatus (eReturnStatusSuccessFinishNoResult);
643             }
644             else
645             {
646                 result.SetStatus (eReturnStatusSuccessContinuingNoResult);
647             }
648         }
649         else
650         {
651             result.AppendError ("Couldn't find thread plan to implement step type.");
652             result.SetStatus (eReturnStatusFailed);
653         }
654         return result.Succeeded();
655     }
656 
657 protected:
658     StepType m_step_type;
659     StepScope m_step_scope;
660     CommandOptions m_options;
661 };
662 
663 static OptionEnumValueElement
664 g_tri_running_mode[] =
665 {
666 { eOnlyThisThread,     "this-thread",    "Run only this thread"},
667 { eAllThreads,         "all-threads",    "Run all threads"},
668 { eOnlyDuringStepping, "while-stepping", "Run only this thread while stepping"},
669 { 0, NULL, NULL }
670 };
671 
672 static OptionEnumValueElement
673 g_duo_running_mode[] =
674 {
675 { eOnlyThisThread,     "this-thread",    "Run only this thread"},
676 { eAllThreads,         "all-threads",    "Run all threads"},
677 { 0, NULL, NULL }
678 };
679 
680 OptionDefinition
681 CommandObjectThreadStepWithTypeAndScope::CommandOptions::g_option_table[] =
682 {
683 { LLDB_OPT_SET_1, false, "step-in-avoids-no-debug",   'a', OptionParser::eRequiredArgument, NULL,               0, eArgTypeBoolean,     "A boolean value that sets whether stepping into functions will step over functions with no debug information."},
684 { LLDB_OPT_SET_1, false, "step-out-avoids-no-debug",  'A', OptionParser::eRequiredArgument, NULL,               0, eArgTypeBoolean,     "A boolean value, if true stepping out of functions will continue to step out till it hits a function with debug information."},
685 { LLDB_OPT_SET_1, false, "count",           'c', OptionParser::eRequiredArgument, NULL,               1, eArgTypeCount,     "How many times to perform the stepping operation - currently only supported for step-inst and next-inst."},
686 { LLDB_OPT_SET_1, false, "run-mode",        'm', OptionParser::eRequiredArgument, g_tri_running_mode, 0, eArgTypeRunMode, "Determine how to run other threads while stepping the current thread."},
687 { LLDB_OPT_SET_1, false, "step-over-regexp",'r', OptionParser::eRequiredArgument, NULL,               0, eArgTypeRegularExpression,   "A regular expression that defines function names to not to stop at when stepping in."},
688 { LLDB_OPT_SET_1, false, "step-in-target",  't', OptionParser::eRequiredArgument, NULL,               0, eArgTypeFunctionName,   "The name of the directly called function step in should stop at when stepping into."},
689 { 0, false, NULL, 0, 0, NULL, 0, eArgTypeNone, NULL }
690 };
691 
692 
693 //-------------------------------------------------------------------------
694 // CommandObjectThreadContinue
695 //-------------------------------------------------------------------------
696 
697 class CommandObjectThreadContinue : public CommandObjectParsed
698 {
699 public:
700 
701     CommandObjectThreadContinue (CommandInterpreter &interpreter) :
702         CommandObjectParsed (interpreter,
703                              "thread continue",
704                              "Continue execution of one or more threads in an active process.",
705                              NULL,
706                              eFlagRequiresThread        |
707                              eFlagTryTargetAPILock      |
708                              eFlagProcessMustBeLaunched |
709                              eFlagProcessMustBePaused)
710     {
711         CommandArgumentEntry arg;
712         CommandArgumentData thread_idx_arg;
713 
714         // Define the first (and only) variant of this arg.
715         thread_idx_arg.arg_type = eArgTypeThreadIndex;
716         thread_idx_arg.arg_repetition = eArgRepeatPlus;
717 
718         // There is only one variant this argument could be; put it into the argument entry.
719         arg.push_back (thread_idx_arg);
720 
721         // Push the data for the first argument into the m_arguments vector.
722         m_arguments.push_back (arg);
723     }
724 
725 
726     virtual
727     ~CommandObjectThreadContinue ()
728     {
729     }
730 
731     virtual bool
732     DoExecute (Args& command, CommandReturnObject &result)
733     {
734         bool synchronous_execution = m_interpreter.GetSynchronous ();
735 
736         if (!m_interpreter.GetDebugger().GetSelectedTarget().get())
737         {
738             result.AppendError ("invalid target, create a debug target using the 'target create' command");
739             result.SetStatus (eReturnStatusFailed);
740             return false;
741         }
742 
743         Process *process = m_exe_ctx.GetProcessPtr();
744         if (process == NULL)
745         {
746             result.AppendError ("no process exists. Cannot continue");
747             result.SetStatus (eReturnStatusFailed);
748             return false;
749         }
750 
751         StateType state = process->GetState();
752         if ((state == eStateCrashed) || (state == eStateStopped) || (state == eStateSuspended))
753         {
754             const size_t argc = command.GetArgumentCount();
755             if (argc > 0)
756             {
757                 // These two lines appear at the beginning of both blocks in
758                 // this if..else, but that is because we need to release the
759                 // lock before calling process->Resume below.
760                 Mutex::Locker locker (process->GetThreadList().GetMutex());
761                 const uint32_t num_threads = process->GetThreadList().GetSize();
762                 std::vector<Thread *> resume_threads;
763                 for (uint32_t i=0; i<argc; ++i)
764                 {
765                     bool success;
766                     const int base = 0;
767                     uint32_t thread_idx = Args::StringToUInt32 (command.GetArgumentAtIndex(i), LLDB_INVALID_INDEX32, base, &success);
768                     if (success)
769                     {
770                         Thread *thread = process->GetThreadList().FindThreadByIndexID(thread_idx).get();
771 
772                         if (thread)
773                         {
774                             resume_threads.push_back(thread);
775                         }
776                         else
777                         {
778                             result.AppendErrorWithFormat("invalid thread index %u.\n", thread_idx);
779                             result.SetStatus (eReturnStatusFailed);
780                             return false;
781                         }
782                     }
783                     else
784                     {
785                         result.AppendErrorWithFormat ("invalid thread index argument: \"%s\".\n", command.GetArgumentAtIndex(i));
786                         result.SetStatus (eReturnStatusFailed);
787                         return false;
788                     }
789                 }
790 
791                 if (resume_threads.empty())
792                 {
793                     result.AppendError ("no valid thread indexes were specified");
794                     result.SetStatus (eReturnStatusFailed);
795                     return false;
796                 }
797                 else
798                 {
799                     if (resume_threads.size() == 1)
800                         result.AppendMessageWithFormat ("Resuming thread: ");
801                     else
802                         result.AppendMessageWithFormat ("Resuming threads: ");
803 
804                     for (uint32_t idx=0; idx<num_threads; ++idx)
805                     {
806                         Thread *thread = process->GetThreadList().GetThreadAtIndex(idx).get();
807                         std::vector<Thread *>::iterator this_thread_pos = find(resume_threads.begin(), resume_threads.end(), thread);
808 
809                         if (this_thread_pos != resume_threads.end())
810                         {
811                             resume_threads.erase(this_thread_pos);
812                             if (resume_threads.size() > 0)
813                                 result.AppendMessageWithFormat ("%u, ", thread->GetIndexID());
814                             else
815                                 result.AppendMessageWithFormat ("%u ", thread->GetIndexID());
816 
817                             const bool override_suspend = true;
818                             thread->SetResumeState (eStateRunning, override_suspend);
819                         }
820                         else
821                         {
822                             thread->SetResumeState (eStateSuspended);
823                         }
824                     }
825                     result.AppendMessageWithFormat ("in process %" PRIu64 "\n", process->GetID());
826                 }
827             }
828             else
829             {
830                 // These two lines appear at the beginning of both blocks in
831                 // this if..else, but that is because we need to release the
832                 // lock before calling process->Resume below.
833                 Mutex::Locker locker (process->GetThreadList().GetMutex());
834                 const uint32_t num_threads = process->GetThreadList().GetSize();
835                 Thread *current_thread = process->GetThreadList().GetSelectedThread().get();
836                 if (current_thread == NULL)
837                 {
838                     result.AppendError ("the process doesn't have a current thread");
839                     result.SetStatus (eReturnStatusFailed);
840                     return false;
841                 }
842                 // Set the actions that the threads should each take when resuming
843                 for (uint32_t idx=0; idx<num_threads; ++idx)
844                 {
845                     Thread *thread = process->GetThreadList().GetThreadAtIndex(idx).get();
846                     if (thread == current_thread)
847                     {
848                         result.AppendMessageWithFormat ("Resuming thread 0x%4.4" PRIx64 " in process %" PRIu64 "\n", thread->GetID(), process->GetID());
849                         const bool override_suspend = true;
850                         thread->SetResumeState (eStateRunning, override_suspend);
851                     }
852                     else
853                     {
854                         thread->SetResumeState (eStateSuspended);
855                     }
856                 }
857             }
858 
859             // We should not be holding the thread list lock when we do this.
860             Error error (process->Resume());
861             if (error.Success())
862             {
863                 result.AppendMessageWithFormat ("Process %" PRIu64 " resuming\n", process->GetID());
864                 if (synchronous_execution)
865                 {
866                     state = process->WaitForProcessToStop (NULL);
867 
868                     result.SetDidChangeProcessState (true);
869                     result.AppendMessageWithFormat ("Process %" PRIu64 " %s\n", process->GetID(), StateAsCString (state));
870                     result.SetStatus (eReturnStatusSuccessFinishNoResult);
871                 }
872                 else
873                 {
874                     result.SetStatus (eReturnStatusSuccessContinuingNoResult);
875                 }
876             }
877             else
878             {
879                 result.AppendErrorWithFormat("Failed to resume process: %s\n", error.AsCString());
880                 result.SetStatus (eReturnStatusFailed);
881             }
882         }
883         else
884         {
885             result.AppendErrorWithFormat ("Process cannot be continued from its current state (%s).\n",
886                                           StateAsCString(state));
887             result.SetStatus (eReturnStatusFailed);
888         }
889 
890         return result.Succeeded();
891     }
892 
893 };
894 
895 //-------------------------------------------------------------------------
896 // CommandObjectThreadUntil
897 //-------------------------------------------------------------------------
898 
899 class CommandObjectThreadUntil : public CommandObjectParsed
900 {
901 public:
902 
903     class CommandOptions : public Options
904     {
905     public:
906         uint32_t m_thread_idx;
907         uint32_t m_frame_idx;
908 
909         CommandOptions (CommandInterpreter &interpreter) :
910             Options (interpreter),
911             m_thread_idx(LLDB_INVALID_THREAD_ID),
912             m_frame_idx(LLDB_INVALID_FRAME_ID)
913         {
914             // Keep default values of all options in one place: OptionParsingStarting ()
915             OptionParsingStarting ();
916         }
917 
918         virtual
919         ~CommandOptions ()
920         {
921         }
922 
923         virtual Error
924         SetOptionValue (uint32_t option_idx, const char *option_arg)
925         {
926             Error error;
927             const int short_option = m_getopt_table[option_idx].val;
928 
929             switch (short_option)
930             {
931                 case 't':
932                 {
933                     m_thread_idx = Args::StringToUInt32 (option_arg, LLDB_INVALID_INDEX32);
934                     if (m_thread_idx == LLDB_INVALID_INDEX32)
935                     {
936                         error.SetErrorStringWithFormat ("invalid thread index '%s'", option_arg);
937                     }
938                 }
939                 break;
940                 case 'f':
941                 {
942                     m_frame_idx = Args::StringToUInt32 (option_arg, LLDB_INVALID_FRAME_ID);
943                     if (m_frame_idx == LLDB_INVALID_FRAME_ID)
944                     {
945                         error.SetErrorStringWithFormat ("invalid frame index '%s'", option_arg);
946                     }
947                 }
948                 break;
949                 case 'm':
950                 {
951                     OptionEnumValueElement *enum_values = g_option_table[option_idx].enum_values;
952                     lldb::RunMode run_mode = (lldb::RunMode) Args::StringToOptionEnum(option_arg, enum_values, eOnlyDuringStepping, error);
953 
954                     if (error.Success())
955                     {
956                         if (run_mode == eAllThreads)
957                             m_stop_others = false;
958                         else
959                             m_stop_others = true;
960                     }
961                 }
962                 break;
963                 default:
964                     error.SetErrorStringWithFormat("invalid short option character '%c'", short_option);
965                     break;
966 
967             }
968             return error;
969         }
970 
971         void
972         OptionParsingStarting ()
973         {
974             m_thread_idx = LLDB_INVALID_THREAD_ID;
975             m_frame_idx = 0;
976             m_stop_others = false;
977         }
978 
979         const OptionDefinition*
980         GetDefinitions ()
981         {
982             return g_option_table;
983         }
984 
985         uint32_t m_step_thread_idx;
986         bool m_stop_others;
987 
988         // Options table: Required for subclasses of Options.
989 
990         static OptionDefinition g_option_table[];
991 
992         // Instance variables to hold the values for command options.
993     };
994 
995     CommandObjectThreadUntil (CommandInterpreter &interpreter) :
996         CommandObjectParsed (interpreter,
997                              "thread until",
998                              "Run the current or specified thread until it reaches a given line number or leaves the current function.",
999                              NULL,
1000                              eFlagRequiresThread        |
1001                              eFlagTryTargetAPILock      |
1002                              eFlagProcessMustBeLaunched |
1003                              eFlagProcessMustBePaused   ),
1004         m_options (interpreter)
1005     {
1006         CommandArgumentEntry arg;
1007         CommandArgumentData line_num_arg;
1008 
1009         // Define the first (and only) variant of this arg.
1010         line_num_arg.arg_type = eArgTypeLineNum;
1011         line_num_arg.arg_repetition = eArgRepeatPlain;
1012 
1013         // There is only one variant this argument could be; put it into the argument entry.
1014         arg.push_back (line_num_arg);
1015 
1016         // Push the data for the first argument into the m_arguments vector.
1017         m_arguments.push_back (arg);
1018     }
1019 
1020 
1021     virtual
1022     ~CommandObjectThreadUntil ()
1023     {
1024     }
1025 
1026     virtual
1027     Options *
1028     GetOptions ()
1029     {
1030         return &m_options;
1031     }
1032 
1033 protected:
1034     virtual bool
1035     DoExecute (Args& command, CommandReturnObject &result)
1036     {
1037         bool synchronous_execution = m_interpreter.GetSynchronous ();
1038 
1039         Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
1040         if (target == NULL)
1041         {
1042             result.AppendError ("invalid target, create a debug target using the 'target create' command");
1043             result.SetStatus (eReturnStatusFailed);
1044             return false;
1045         }
1046 
1047         Process *process = m_exe_ctx.GetProcessPtr();
1048         if (process == NULL)
1049         {
1050             result.AppendError ("need a valid process to step");
1051             result.SetStatus (eReturnStatusFailed);
1052 
1053         }
1054         else
1055         {
1056             Thread *thread = NULL;
1057             uint32_t line_number;
1058 
1059             if (command.GetArgumentCount() != 1)
1060             {
1061                 result.AppendErrorWithFormat ("No line number provided:\n%s", GetSyntax());
1062                 result.SetStatus (eReturnStatusFailed);
1063                 return false;
1064             }
1065 
1066             line_number = Args::StringToUInt32 (command.GetArgumentAtIndex(0), UINT32_MAX);
1067             if (line_number == UINT32_MAX)
1068             {
1069                 result.AppendErrorWithFormat ("invalid line number: '%s'.\n", command.GetArgumentAtIndex(0));
1070                 result.SetStatus (eReturnStatusFailed);
1071                 return false;
1072             }
1073 
1074             if (m_options.m_thread_idx == LLDB_INVALID_THREAD_ID)
1075             {
1076                 thread = process->GetThreadList().GetSelectedThread().get();
1077             }
1078             else
1079             {
1080                 thread = process->GetThreadList().FindThreadByIndexID(m_options.m_thread_idx).get();
1081             }
1082 
1083             if (thread == NULL)
1084             {
1085                 const uint32_t num_threads = process->GetThreadList().GetSize();
1086                 result.AppendErrorWithFormat ("Thread index %u is out of range (valid values are 0 - %u).\n",
1087                                               m_options.m_thread_idx,
1088                                               num_threads);
1089                 result.SetStatus (eReturnStatusFailed);
1090                 return false;
1091             }
1092 
1093             const bool abort_other_plans = false;
1094 
1095             StackFrame *frame = thread->GetStackFrameAtIndex(m_options.m_frame_idx).get();
1096             if (frame == NULL)
1097             {
1098 
1099                 result.AppendErrorWithFormat ("Frame index %u is out of range for thread %u.\n",
1100                                               m_options.m_frame_idx,
1101                                               m_options.m_thread_idx);
1102                 result.SetStatus (eReturnStatusFailed);
1103                 return false;
1104             }
1105 
1106             ThreadPlanSP new_plan_sp;
1107 
1108             if (frame->HasDebugInformation ())
1109             {
1110                 // Finally we got here...  Translate the given line number to a bunch of addresses:
1111                 SymbolContext sc(frame->GetSymbolContext (eSymbolContextCompUnit));
1112                 LineTable *line_table = NULL;
1113                 if (sc.comp_unit)
1114                     line_table = sc.comp_unit->GetLineTable();
1115 
1116                 if (line_table == NULL)
1117                 {
1118                     result.AppendErrorWithFormat ("Failed to resolve the line table for frame %u of thread index %u.\n",
1119                                                  m_options.m_frame_idx, m_options.m_thread_idx);
1120                     result.SetStatus (eReturnStatusFailed);
1121                     return false;
1122                 }
1123 
1124                 LineEntry function_start;
1125                 uint32_t index_ptr = 0, end_ptr;
1126                 std::vector<addr_t> address_list;
1127 
1128                 // Find the beginning & end index of the
1129                 AddressRange fun_addr_range = sc.function->GetAddressRange();
1130                 Address fun_start_addr = fun_addr_range.GetBaseAddress();
1131                 line_table->FindLineEntryByAddress (fun_start_addr, function_start, &index_ptr);
1132 
1133                 Address fun_end_addr(fun_start_addr.GetSection(),
1134                                      fun_start_addr.GetOffset() + fun_addr_range.GetByteSize());
1135                 line_table->FindLineEntryByAddress (fun_end_addr, function_start, &end_ptr);
1136 
1137                 bool all_in_function = true;
1138 
1139                 while (index_ptr <= end_ptr)
1140                 {
1141                     LineEntry line_entry;
1142                     const bool exact = false;
1143                     index_ptr = sc.comp_unit->FindLineEntry(index_ptr, line_number, sc.comp_unit, exact, &line_entry);
1144                     if (index_ptr == UINT32_MAX)
1145                         break;
1146 
1147                     addr_t address = line_entry.range.GetBaseAddress().GetLoadAddress(target);
1148                     if (address != LLDB_INVALID_ADDRESS)
1149                     {
1150                         if (fun_addr_range.ContainsLoadAddress (address, target))
1151                             address_list.push_back (address);
1152                         else
1153                             all_in_function = false;
1154                     }
1155                     index_ptr++;
1156                 }
1157 
1158                 if (address_list.size() == 0)
1159                 {
1160                     if (all_in_function)
1161                         result.AppendErrorWithFormat ("No line entries matching until target.\n");
1162                     else
1163                         result.AppendErrorWithFormat ("Until target outside of the current function.\n");
1164 
1165                     result.SetStatus (eReturnStatusFailed);
1166                     return false;
1167                 }
1168 
1169                 new_plan_sp = thread->QueueThreadPlanForStepUntil (abort_other_plans,
1170                                                                 &address_list.front(),
1171                                                                 address_list.size(),
1172                                                                 m_options.m_stop_others,
1173                                                                 m_options.m_frame_idx);
1174                 // User level plans should be master plans so they can be interrupted (e.g. by hitting a breakpoint)
1175                 // and other plans executed by the user (stepping around the breakpoint) and then a "continue"
1176                 // will resume the original plan.
1177                 new_plan_sp->SetIsMasterPlan (true);
1178                 new_plan_sp->SetOkayToDiscard(false);
1179             }
1180             else
1181             {
1182                 result.AppendErrorWithFormat ("Frame index %u of thread %u has no debug information.\n",
1183                                               m_options.m_frame_idx,
1184                                               m_options.m_thread_idx);
1185                 result.SetStatus (eReturnStatusFailed);
1186                 return false;
1187 
1188             }
1189 
1190             process->GetThreadList().SetSelectedThreadByID (m_options.m_thread_idx);
1191             Error error (process->Resume ());
1192             if (error.Success())
1193             {
1194                 result.AppendMessageWithFormat ("Process %" PRIu64 " resuming\n", process->GetID());
1195                 if (synchronous_execution)
1196                 {
1197                     StateType state = process->WaitForProcessToStop (NULL);
1198 
1199                     result.SetDidChangeProcessState (true);
1200                     result.AppendMessageWithFormat ("Process %" PRIu64 " %s\n", process->GetID(), StateAsCString (state));
1201                     result.SetStatus (eReturnStatusSuccessFinishNoResult);
1202                 }
1203                 else
1204                 {
1205                     result.SetStatus (eReturnStatusSuccessContinuingNoResult);
1206                 }
1207             }
1208             else
1209             {
1210                 result.AppendErrorWithFormat("Failed to resume process: %s.\n", error.AsCString());
1211                 result.SetStatus (eReturnStatusFailed);
1212             }
1213 
1214         }
1215         return result.Succeeded();
1216     }
1217 
1218     CommandOptions m_options;
1219 
1220 };
1221 
1222 OptionDefinition
1223 CommandObjectThreadUntil::CommandOptions::g_option_table[] =
1224 {
1225 { LLDB_OPT_SET_1, false, "frame",   'f', OptionParser::eRequiredArgument, NULL,               0, eArgTypeFrameIndex,   "Frame index for until operation - defaults to 0"},
1226 { LLDB_OPT_SET_1, false, "thread",  't', OptionParser::eRequiredArgument, NULL,               0, eArgTypeThreadIndex,  "Thread index for the thread for until operation"},
1227 { LLDB_OPT_SET_1, false, "run-mode",'m', OptionParser::eRequiredArgument, g_duo_running_mode, 0, eArgTypeRunMode,"Determine how to run other threads while stepping this one"},
1228 { 0, false, NULL, 0, 0, NULL, 0, eArgTypeNone, NULL }
1229 };
1230 
1231 
1232 //-------------------------------------------------------------------------
1233 // CommandObjectThreadSelect
1234 //-------------------------------------------------------------------------
1235 
1236 class CommandObjectThreadSelect : public CommandObjectParsed
1237 {
1238 public:
1239 
1240     CommandObjectThreadSelect (CommandInterpreter &interpreter) :
1241         CommandObjectParsed (interpreter,
1242                              "thread select",
1243                              "Select a thread as the currently active thread.",
1244                              NULL,
1245                              eFlagRequiresProcess       |
1246                              eFlagTryTargetAPILock      |
1247                              eFlagProcessMustBeLaunched |
1248                              eFlagProcessMustBePaused   )
1249     {
1250         CommandArgumentEntry arg;
1251         CommandArgumentData thread_idx_arg;
1252 
1253         // Define the first (and only) variant of this arg.
1254         thread_idx_arg.arg_type = eArgTypeThreadIndex;
1255         thread_idx_arg.arg_repetition = eArgRepeatPlain;
1256 
1257         // There is only one variant this argument could be; put it into the argument entry.
1258         arg.push_back (thread_idx_arg);
1259 
1260         // Push the data for the first argument into the m_arguments vector.
1261         m_arguments.push_back (arg);
1262     }
1263 
1264 
1265     virtual
1266     ~CommandObjectThreadSelect ()
1267     {
1268     }
1269 
1270 protected:
1271     virtual bool
1272     DoExecute (Args& command, CommandReturnObject &result)
1273     {
1274         Process *process = m_exe_ctx.GetProcessPtr();
1275         if (process == NULL)
1276         {
1277             result.AppendError ("no process");
1278             result.SetStatus (eReturnStatusFailed);
1279             return false;
1280         }
1281         else if (command.GetArgumentCount() != 1)
1282         {
1283             result.AppendErrorWithFormat("'%s' takes exactly one thread index argument:\nUsage: %s\n", m_cmd_name.c_str(), m_cmd_syntax.c_str());
1284             result.SetStatus (eReturnStatusFailed);
1285             return false;
1286         }
1287 
1288         uint32_t index_id = Args::StringToUInt32(command.GetArgumentAtIndex(0), 0, 0);
1289 
1290         Thread *new_thread = process->GetThreadList().FindThreadByIndexID(index_id).get();
1291         if (new_thread == NULL)
1292         {
1293             result.AppendErrorWithFormat ("invalid thread #%s.\n", command.GetArgumentAtIndex(0));
1294             result.SetStatus (eReturnStatusFailed);
1295             return false;
1296         }
1297 
1298         process->GetThreadList().SetSelectedThreadByID(new_thread->GetID(), true);
1299         result.SetStatus (eReturnStatusSuccessFinishNoResult);
1300 
1301         return result.Succeeded();
1302     }
1303 
1304 };
1305 
1306 
1307 //-------------------------------------------------------------------------
1308 // CommandObjectThreadList
1309 //-------------------------------------------------------------------------
1310 
1311 class CommandObjectThreadList : public CommandObjectParsed
1312 {
1313 public:
1314 
1315 
1316     CommandObjectThreadList (CommandInterpreter &interpreter):
1317         CommandObjectParsed (interpreter,
1318                              "thread list",
1319                              "Show a summary of all current threads in a process.",
1320                              "thread list",
1321                              eFlagRequiresProcess       |
1322                              eFlagTryTargetAPILock      |
1323                              eFlagProcessMustBeLaunched |
1324                              eFlagProcessMustBePaused   )
1325     {
1326     }
1327 
1328     ~CommandObjectThreadList()
1329     {
1330     }
1331 
1332 protected:
1333     bool
1334     DoExecute (Args& command, CommandReturnObject &result)
1335     {
1336         Stream &strm = result.GetOutputStream();
1337         result.SetStatus (eReturnStatusSuccessFinishNoResult);
1338         Process *process = m_exe_ctx.GetProcessPtr();
1339         const bool only_threads_with_stop_reason = false;
1340         const uint32_t start_frame = 0;
1341         const uint32_t num_frames = 0;
1342         const uint32_t num_frames_with_source = 0;
1343         process->GetStatus(strm);
1344         process->GetThreadStatus (strm,
1345                                   only_threads_with_stop_reason,
1346                                   start_frame,
1347                                   num_frames,
1348                                   num_frames_with_source);
1349         return result.Succeeded();
1350     }
1351 };
1352 
1353 //-------------------------------------------------------------------------
1354 // CommandObjectThreadInfo
1355 //-------------------------------------------------------------------------
1356 
1357 class CommandObjectThreadInfo : public CommandObjectParsed
1358 {
1359 public:
1360 
1361     CommandObjectThreadInfo (CommandInterpreter &interpreter) :
1362         CommandObjectParsed (interpreter,
1363                              "thread info",
1364                              "Show an extended summary of information about thread(s) in a process.",
1365                              "thread info",
1366                              eFlagRequiresProcess       |
1367                              eFlagTryTargetAPILock      |
1368                              eFlagProcessMustBeLaunched |
1369                              eFlagProcessMustBePaused),
1370         m_options (interpreter)
1371     {
1372         CommandArgumentEntry arg;
1373         CommandArgumentData thread_idx_arg;
1374 
1375         thread_idx_arg.arg_type = eArgTypeThreadIndex;
1376         thread_idx_arg.arg_repetition = eArgRepeatStar;
1377 
1378         // There is only one variant this argument could be; put it into the argument entry.
1379         arg.push_back (thread_idx_arg);
1380 
1381         // Push the data for the first argument into the m_arguments vector.
1382         m_arguments.push_back (arg);
1383     }
1384 
1385     class CommandOptions : public Options
1386     {
1387     public:
1388 
1389         CommandOptions (CommandInterpreter &interpreter) :
1390             Options (interpreter)
1391         {
1392             OptionParsingStarting ();
1393         }
1394 
1395         void
1396         OptionParsingStarting ()
1397         {
1398             m_json = false;
1399         }
1400 
1401         virtual
1402         ~CommandOptions ()
1403         {
1404         }
1405 
1406         virtual Error
1407         SetOptionValue (uint32_t option_idx, const char *option_arg)
1408         {
1409             const int short_option = m_getopt_table[option_idx].val;
1410             Error error;
1411 
1412             switch (short_option)
1413             {
1414                 case 'j':
1415                     m_json = true;
1416                     break;
1417 
1418                  default:
1419                     return Error("invalid short option character '%c'", short_option);
1420 
1421             }
1422             return error;
1423         }
1424 
1425         const OptionDefinition*
1426         GetDefinitions ()
1427         {
1428             return g_option_table;
1429         }
1430 
1431         bool m_json;
1432 
1433         static OptionDefinition g_option_table[];
1434     };
1435 
1436     virtual
1437     Options *
1438     GetOptions ()
1439     {
1440         return &m_options;
1441     }
1442 
1443 
1444     virtual
1445     ~CommandObjectThreadInfo ()
1446     {
1447     }
1448 
1449     virtual bool
1450     DoExecute (Args& command, CommandReturnObject &result)
1451     {
1452         result.SetStatus (eReturnStatusSuccessFinishResult);
1453         Stream &strm = result.GetOutputStream();
1454 
1455         if (command.GetArgumentCount() == 0)
1456         {
1457             Thread *thread = m_exe_ctx.GetThreadPtr();
1458             if (thread->GetDescription (strm, eDescriptionLevelFull, m_options.m_json))
1459             {
1460                 result.SetStatus (eReturnStatusSuccessFinishResult);
1461             }
1462         }
1463         else if (command.GetArgumentCount() == 1 && ::strcmp (command.GetArgumentAtIndex(0), "all") == 0)
1464         {
1465             Process *process = m_exe_ctx.GetProcessPtr();
1466             uint32_t idx = 0;
1467             for (ThreadSP thread_sp : process->Threads())
1468             {
1469                 if (idx != 0)
1470                     result.AppendMessage("");
1471                 if (!thread_sp->GetDescription (strm, eDescriptionLevelFull, m_options.m_json))
1472                 {
1473                     result.AppendErrorWithFormat ("error displaying info for thread: \"0x%4.4x\"\n", idx);
1474                     result.SetStatus (eReturnStatusFailed);
1475                     return false;
1476                 }
1477                 ++idx;
1478             }
1479         }
1480         else
1481         {
1482             const size_t num_args = command.GetArgumentCount();
1483             Process *process = m_exe_ctx.GetProcessPtr();
1484             Mutex::Locker locker (process->GetThreadList().GetMutex());
1485             std::vector<ThreadSP> thread_sps;
1486 
1487             for (size_t i = 0; i < num_args; i++)
1488             {
1489                 bool success;
1490 
1491                 uint32_t thread_idx = Args::StringToUInt32(command.GetArgumentAtIndex(i), 0, 0, &success);
1492                 if (!success)
1493                 {
1494                     result.AppendErrorWithFormat ("invalid thread specification: \"%s\"\n", command.GetArgumentAtIndex(i));
1495                     result.SetStatus (eReturnStatusFailed);
1496                     return false;
1497                 }
1498 
1499                 thread_sps.push_back(process->GetThreadList().FindThreadByIndexID(thread_idx));
1500 
1501                 if (!thread_sps[i])
1502                 {
1503                     result.AppendErrorWithFormat ("no thread with index: \"%s\"\n", command.GetArgumentAtIndex(i));
1504                     result.SetStatus (eReturnStatusFailed);
1505                     return false;
1506                 }
1507 
1508             }
1509 
1510             for (uint32_t i = 0; i < num_args; i++)
1511             {
1512                 if (!thread_sps[i]->GetDescription (strm, eDescriptionLevelFull, m_options.m_json))
1513                 {
1514                     result.AppendErrorWithFormat ("error displaying info for thread: \"%s\"\n", command.GetArgumentAtIndex(i));
1515                     result.SetStatus (eReturnStatusFailed);
1516                     return false;
1517                 }
1518 
1519                 if (i < num_args - 1)
1520                     result.AppendMessage("");
1521             }
1522 
1523         }
1524         return result.Succeeded();
1525     }
1526 
1527     CommandOptions m_options;
1528 
1529 };
1530 
1531 OptionDefinition
1532 CommandObjectThreadInfo::CommandOptions::g_option_table[] =
1533 {
1534     { LLDB_OPT_SET_ALL, false, "json",'j', OptionParser::eNoArgument, NULL, 0, eArgTypeNone, "Display the thread info in JSON format."},
1535 
1536     { 0, false, NULL, 0, 0, NULL, 0, eArgTypeNone, NULL }
1537 };
1538 
1539 
1540 //-------------------------------------------------------------------------
1541 // CommandObjectThreadReturn
1542 //-------------------------------------------------------------------------
1543 
1544 class CommandObjectThreadReturn : public CommandObjectRaw
1545 {
1546 public:
1547     class CommandOptions : public Options
1548     {
1549     public:
1550 
1551         CommandOptions (CommandInterpreter &interpreter) :
1552             Options (interpreter),
1553             m_from_expression (false)
1554         {
1555             // Keep default values of all options in one place: OptionParsingStarting ()
1556             OptionParsingStarting ();
1557         }
1558 
1559         virtual
1560         ~CommandOptions ()
1561         {
1562         }
1563 
1564         virtual Error
1565         SetOptionValue (uint32_t option_idx, const char *option_arg)
1566         {
1567             Error error;
1568             const int short_option = m_getopt_table[option_idx].val;
1569 
1570             switch (short_option)
1571             {
1572                 case 'x':
1573                 {
1574                     bool success;
1575                     bool tmp_value = Args::StringToBoolean (option_arg, false, &success);
1576                     if (success)
1577                         m_from_expression = tmp_value;
1578                     else
1579                     {
1580                         error.SetErrorStringWithFormat ("invalid boolean value '%s' for 'x' option", option_arg);
1581                     }
1582                 }
1583                 break;
1584                 default:
1585                     error.SetErrorStringWithFormat("invalid short option character '%c'", short_option);
1586                     break;
1587 
1588             }
1589             return error;
1590         }
1591 
1592         void
1593         OptionParsingStarting ()
1594         {
1595             m_from_expression = false;
1596         }
1597 
1598         const OptionDefinition*
1599         GetDefinitions ()
1600         {
1601             return g_option_table;
1602         }
1603 
1604         bool m_from_expression;
1605 
1606         // Options table: Required for subclasses of Options.
1607 
1608         static OptionDefinition g_option_table[];
1609 
1610         // Instance variables to hold the values for command options.
1611     };
1612 
1613     virtual
1614     Options *
1615     GetOptions ()
1616     {
1617         return &m_options;
1618     }
1619 
1620     CommandObjectThreadReturn (CommandInterpreter &interpreter) :
1621         CommandObjectRaw (interpreter,
1622                           "thread return",
1623                           "Return from the currently selected frame, short-circuiting execution of the frames below it, with an optional return value,"
1624                           " or with the -x option from the innermost function evaluation.",
1625                           "thread return",
1626                           eFlagRequiresFrame         |
1627                           eFlagTryTargetAPILock      |
1628                           eFlagProcessMustBeLaunched |
1629                           eFlagProcessMustBePaused   ),
1630         m_options (interpreter)
1631     {
1632         CommandArgumentEntry arg;
1633         CommandArgumentData expression_arg;
1634 
1635         // Define the first (and only) variant of this arg.
1636         expression_arg.arg_type = eArgTypeExpression;
1637         expression_arg.arg_repetition = eArgRepeatOptional;
1638 
1639         // There is only one variant this argument could be; put it into the argument entry.
1640         arg.push_back (expression_arg);
1641 
1642         // Push the data for the first argument into the m_arguments vector.
1643         m_arguments.push_back (arg);
1644 
1645 
1646     }
1647 
1648     ~CommandObjectThreadReturn()
1649     {
1650     }
1651 
1652 protected:
1653 
1654     bool DoExecute
1655     (
1656         const char *command,
1657         CommandReturnObject &result
1658     )
1659     {
1660         // I am going to handle this by hand, because I don't want you to have to say:
1661         // "thread return -- -5".
1662         if (command[0] == '-' && command[1] == 'x')
1663         {
1664             if (command && command[2] != '\0')
1665                 result.AppendWarning("Return values ignored when returning from user called expressions");
1666 
1667             Thread *thread = m_exe_ctx.GetThreadPtr();
1668             Error error;
1669             error = thread->UnwindInnermostExpression();
1670             if (!error.Success())
1671             {
1672                 result.AppendErrorWithFormat ("Unwinding expression failed - %s.", error.AsCString());
1673                 result.SetStatus (eReturnStatusFailed);
1674             }
1675             else
1676             {
1677                 bool success = thread->SetSelectedFrameByIndexNoisily (0, result.GetOutputStream());
1678                 if (success)
1679                 {
1680                     m_exe_ctx.SetFrameSP(thread->GetSelectedFrame ());
1681                     result.SetStatus (eReturnStatusSuccessFinishResult);
1682                 }
1683                 else
1684                 {
1685                     result.AppendErrorWithFormat ("Could not select 0th frame after unwinding expression.");
1686                     result.SetStatus (eReturnStatusFailed);
1687                 }
1688             }
1689             return result.Succeeded();
1690         }
1691 
1692         ValueObjectSP return_valobj_sp;
1693 
1694         StackFrameSP frame_sp = m_exe_ctx.GetFrameSP();
1695         uint32_t frame_idx = frame_sp->GetFrameIndex();
1696 
1697         if (frame_sp->IsInlined())
1698         {
1699             result.AppendError("Don't know how to return from inlined frames.");
1700             result.SetStatus (eReturnStatusFailed);
1701             return false;
1702         }
1703 
1704         if (command && command[0] != '\0')
1705         {
1706             Target *target = m_exe_ctx.GetTargetPtr();
1707             EvaluateExpressionOptions options;
1708 
1709             options.SetUnwindOnError(true);
1710             options.SetUseDynamic(eNoDynamicValues);
1711 
1712             ExpressionResults exe_results = eExpressionSetupError;
1713             exe_results = target->EvaluateExpression (command,
1714                                                       frame_sp.get(),
1715                                                       return_valobj_sp,
1716                                                       options);
1717             if (exe_results != eExpressionCompleted)
1718             {
1719                 if (return_valobj_sp)
1720                     result.AppendErrorWithFormat("Error evaluating result expression: %s", return_valobj_sp->GetError().AsCString());
1721                 else
1722                     result.AppendErrorWithFormat("Unknown error evaluating result expression.");
1723                 result.SetStatus (eReturnStatusFailed);
1724                 return false;
1725 
1726             }
1727         }
1728 
1729         Error error;
1730         ThreadSP thread_sp = m_exe_ctx.GetThreadSP();
1731         const bool broadcast = true;
1732         error = thread_sp->ReturnFromFrame (frame_sp, return_valobj_sp, broadcast);
1733         if (!error.Success())
1734         {
1735             result.AppendErrorWithFormat("Error returning from frame %d of thread %d: %s.", frame_idx, thread_sp->GetIndexID(), error.AsCString());
1736             result.SetStatus (eReturnStatusFailed);
1737             return false;
1738         }
1739 
1740         result.SetStatus (eReturnStatusSuccessFinishResult);
1741         return true;
1742     }
1743 
1744     CommandOptions m_options;
1745 
1746 };
1747 OptionDefinition
1748 CommandObjectThreadReturn::CommandOptions::g_option_table[] =
1749 {
1750 { LLDB_OPT_SET_ALL, false, "from-expression",  'x', OptionParser::eNoArgument, NULL,               0, eArgTypeNone,     "Return from the innermost expression evaluation."},
1751 { 0, false, NULL, 0, 0, NULL, 0, eArgTypeNone, NULL }
1752 };
1753 
1754 //-------------------------------------------------------------------------
1755 // CommandObjectThreadJump
1756 //-------------------------------------------------------------------------
1757 
1758 class CommandObjectThreadJump : public CommandObjectParsed
1759 {
1760 public:
1761     class CommandOptions : public Options
1762     {
1763     public:
1764 
1765         CommandOptions (CommandInterpreter &interpreter) :
1766             Options (interpreter)
1767         {
1768             OptionParsingStarting ();
1769         }
1770 
1771         void
1772         OptionParsingStarting ()
1773         {
1774             m_filenames.Clear();
1775             m_line_num = 0;
1776             m_line_offset = 0;
1777             m_load_addr = LLDB_INVALID_ADDRESS;
1778             m_force = false;
1779         }
1780 
1781         virtual
1782         ~CommandOptions ()
1783         {
1784         }
1785 
1786         virtual Error
1787         SetOptionValue (uint32_t option_idx, const char *option_arg)
1788         {
1789             bool success;
1790             const int short_option = m_getopt_table[option_idx].val;
1791             Error error;
1792 
1793             switch (short_option)
1794             {
1795                 case 'f':
1796                     m_filenames.AppendIfUnique (FileSpec(option_arg, false));
1797                     if (m_filenames.GetSize() > 1)
1798                         return Error("only one source file expected.");
1799                     break;
1800                 case 'l':
1801                     m_line_num = Args::StringToUInt32 (option_arg, 0, 0, &success);
1802                     if (!success || m_line_num == 0)
1803                         return Error("invalid line number: '%s'.", option_arg);
1804                     break;
1805                 case 'b':
1806                     m_line_offset = Args::StringToSInt32 (option_arg, 0, 0, &success);
1807                     if (!success)
1808                         return Error("invalid line offset: '%s'.", option_arg);
1809                     break;
1810                 case 'a':
1811                     {
1812                         ExecutionContext exe_ctx (m_interpreter.GetExecutionContext());
1813                         m_load_addr = Args::StringToAddress(&exe_ctx, option_arg, LLDB_INVALID_ADDRESS, &error);
1814                     }
1815                     break;
1816                 case 'r':
1817                     m_force = true;
1818                     break;
1819 
1820                  default:
1821                     return Error("invalid short option character '%c'", short_option);
1822 
1823             }
1824             return error;
1825         }
1826 
1827         const OptionDefinition*
1828         GetDefinitions ()
1829         {
1830             return g_option_table;
1831         }
1832 
1833         FileSpecList m_filenames;
1834         uint32_t m_line_num;
1835         int32_t m_line_offset;
1836         lldb::addr_t m_load_addr;
1837         bool m_force;
1838 
1839         static OptionDefinition g_option_table[];
1840     };
1841 
1842     virtual
1843     Options *
1844     GetOptions ()
1845     {
1846         return &m_options;
1847     }
1848 
1849     CommandObjectThreadJump (CommandInterpreter &interpreter) :
1850         CommandObjectParsed (interpreter,
1851                           "thread jump",
1852                           "Sets the program counter to a new address.",
1853                           "thread jump",
1854                           eFlagRequiresFrame         |
1855                           eFlagTryTargetAPILock      |
1856                           eFlagProcessMustBeLaunched |
1857                           eFlagProcessMustBePaused   ),
1858         m_options (interpreter)
1859     {
1860     }
1861 
1862     ~CommandObjectThreadJump()
1863     {
1864     }
1865 
1866 protected:
1867 
1868     bool DoExecute (Args& args, CommandReturnObject &result)
1869     {
1870         RegisterContext *reg_ctx = m_exe_ctx.GetRegisterContext();
1871         StackFrame *frame = m_exe_ctx.GetFramePtr();
1872         Thread *thread = m_exe_ctx.GetThreadPtr();
1873         Target *target = m_exe_ctx.GetTargetPtr();
1874         const SymbolContext &sym_ctx = frame->GetSymbolContext (eSymbolContextLineEntry);
1875 
1876         if (m_options.m_load_addr != LLDB_INVALID_ADDRESS)
1877         {
1878             // Use this address directly.
1879             Address dest = Address(m_options.m_load_addr);
1880 
1881             lldb::addr_t callAddr = dest.GetCallableLoadAddress (target);
1882             if (callAddr == LLDB_INVALID_ADDRESS)
1883             {
1884                 result.AppendErrorWithFormat ("Invalid destination address.");
1885                 result.SetStatus (eReturnStatusFailed);
1886                 return false;
1887             }
1888 
1889             if (!reg_ctx->SetPC (callAddr))
1890             {
1891                 result.AppendErrorWithFormat ("Error changing PC value for thread %d.", thread->GetIndexID());
1892                 result.SetStatus (eReturnStatusFailed);
1893                 return false;
1894             }
1895         }
1896         else
1897         {
1898             // Pick either the absolute line, or work out a relative one.
1899             int32_t line = (int32_t)m_options.m_line_num;
1900             if (line == 0)
1901                 line = sym_ctx.line_entry.line + m_options.m_line_offset;
1902 
1903             // Try the current file, but override if asked.
1904             FileSpec file = sym_ctx.line_entry.file;
1905             if (m_options.m_filenames.GetSize() == 1)
1906                 file = m_options.m_filenames.GetFileSpecAtIndex(0);
1907 
1908             if (!file)
1909             {
1910                 result.AppendErrorWithFormat ("No source file available for the current location.");
1911                 result.SetStatus (eReturnStatusFailed);
1912                 return false;
1913             }
1914 
1915             std::string warnings;
1916             Error err = thread->JumpToLine (file, line, m_options.m_force, &warnings);
1917 
1918             if (err.Fail())
1919             {
1920                 result.SetError (err);
1921                 return false;
1922             }
1923 
1924             if (!warnings.empty())
1925                 result.AppendWarning (warnings.c_str());
1926         }
1927 
1928         result.SetStatus (eReturnStatusSuccessFinishResult);
1929         return true;
1930     }
1931 
1932     CommandOptions m_options;
1933 };
1934 OptionDefinition
1935 CommandObjectThreadJump::CommandOptions::g_option_table[] =
1936 {
1937     { LLDB_OPT_SET_1, false, "file", 'f', OptionParser::eRequiredArgument, NULL, CommandCompletions::eSourceFileCompletion, eArgTypeFilename,
1938         "Specifies the source file to jump to."},
1939 
1940     { LLDB_OPT_SET_1, true, "line", 'l', OptionParser::eRequiredArgument, NULL, 0, eArgTypeLineNum,
1941         "Specifies the line number to jump to."},
1942 
1943     { LLDB_OPT_SET_2, true, "by", 'b', OptionParser::eRequiredArgument, NULL, 0, eArgTypeOffset,
1944         "Jumps by a relative line offset from the current line."},
1945 
1946     { LLDB_OPT_SET_3, true, "address", 'a', OptionParser::eRequiredArgument, NULL, 0, eArgTypeAddressOrExpression,
1947         "Jumps to a specific address."},
1948 
1949     { LLDB_OPT_SET_1|
1950       LLDB_OPT_SET_2|
1951       LLDB_OPT_SET_3, false, "force",'r', OptionParser::eNoArgument, NULL, 0, eArgTypeNone,"Allows the PC to leave the current function."},
1952 
1953     { 0, false, NULL, 0, 0, NULL, 0, eArgTypeNone, NULL }
1954 };
1955 
1956 //-------------------------------------------------------------------------
1957 // CommandObjectMultiwordThread
1958 //-------------------------------------------------------------------------
1959 
1960 CommandObjectMultiwordThread::CommandObjectMultiwordThread (CommandInterpreter &interpreter) :
1961     CommandObjectMultiword (interpreter,
1962                             "thread",
1963                             "A set of commands for operating on one or more threads within a running process.",
1964                             "thread <subcommand> [<subcommand-options>]")
1965 {
1966     LoadSubCommand ("backtrace",  CommandObjectSP (new CommandObjectThreadBacktrace (interpreter)));
1967     LoadSubCommand ("continue",   CommandObjectSP (new CommandObjectThreadContinue (interpreter)));
1968     LoadSubCommand ("list",       CommandObjectSP (new CommandObjectThreadList (interpreter)));
1969     LoadSubCommand ("return",     CommandObjectSP (new CommandObjectThreadReturn (interpreter)));
1970     LoadSubCommand ("jump",       CommandObjectSP (new CommandObjectThreadJump (interpreter)));
1971     LoadSubCommand ("select",     CommandObjectSP (new CommandObjectThreadSelect (interpreter)));
1972     LoadSubCommand ("until",      CommandObjectSP (new CommandObjectThreadUntil (interpreter)));
1973     LoadSubCommand ("info",       CommandObjectSP (new CommandObjectThreadInfo (interpreter)));
1974     LoadSubCommand ("step-in",    CommandObjectSP (new CommandObjectThreadStepWithTypeAndScope (
1975                                                     interpreter,
1976                                                     "thread step-in",
1977                                                     "Source level single step in specified thread (current thread, if none specified).",
1978                                                     NULL,
1979                                                     eStepTypeInto,
1980                                                     eStepScopeSource)));
1981 
1982     LoadSubCommand ("step-out",   CommandObjectSP (new CommandObjectThreadStepWithTypeAndScope (
1983                                                     interpreter,
1984                                                     "thread step-out",
1985                                                     "Finish executing the function of the currently selected frame and return to its call site in specified thread (current thread, if none specified).",
1986                                                     NULL,
1987                                                     eStepTypeOut,
1988                                                     eStepScopeSource)));
1989 
1990     LoadSubCommand ("step-over",   CommandObjectSP (new CommandObjectThreadStepWithTypeAndScope (
1991                                                     interpreter,
1992                                                     "thread step-over",
1993                                                     "Source level single step in specified thread (current thread, if none specified), stepping over calls.",
1994                                                     NULL,
1995                                                     eStepTypeOver,
1996                                                     eStepScopeSource)));
1997 
1998     LoadSubCommand ("step-inst",   CommandObjectSP (new CommandObjectThreadStepWithTypeAndScope (
1999                                                     interpreter,
2000                                                     "thread step-inst",
2001                                                     "Single step one instruction in specified thread (current thread, if none specified).",
2002                                                     NULL,
2003                                                     eStepTypeTrace,
2004                                                     eStepScopeInstruction)));
2005 
2006     LoadSubCommand ("step-inst-over", CommandObjectSP (new CommandObjectThreadStepWithTypeAndScope (
2007                                                     interpreter,
2008                                                     "thread step-inst-over",
2009                                                     "Single step one instruction in specified thread (current thread, if none specified), stepping over calls.",
2010                                                     NULL,
2011                                                     eStepTypeTraceOver,
2012                                                     eStepScopeInstruction)));
2013 }
2014 
2015 CommandObjectMultiwordThread::~CommandObjectMultiwordThread ()
2016 {
2017 }
2018 
2019 
2020