Author: jingham Date: Tue Jul 8 14:28:57 2014 New Revision: 212559 URL: http://llvm.org/viewvc/llvm-project?rev=212559&view=rev Log: Add the ability to provide a "count" option to the various "thread step-*" operations. Only step-inst and step-inst are currently supported, the rest just warn that they are not supported if you try to provide a count.
Modified: lldb/trunk/include/lldb/Target/ThreadPlan.h lldb/trunk/include/lldb/Target/ThreadPlanStepInstruction.h lldb/trunk/source/Commands/CommandObjectThread.cpp lldb/trunk/source/Target/ThreadPlanStepInstruction.cpp Modified: lldb/trunk/include/lldb/Target/ThreadPlan.h URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Target/ThreadPlan.h?rev=212559&r1=212558&r2=212559&view=diff ============================================================================== --- lldb/trunk/include/lldb/Target/ThreadPlan.h (original) +++ lldb/trunk/include/lldb/Target/ThreadPlan.h Tue Jul 8 14:28:57 2014 @@ -539,6 +539,27 @@ public: return false; } + virtual bool + SetIterationCount (size_t count) + { + if (m_takes_iteration_count) + { + // Don't tell me to do something 0 times... + if (count == 0) + return false; + m_iteration_count = count; + } + return m_takes_iteration_count; + } + + virtual size_t + GetIterationCount () + { + if (!m_takes_iteration_count) + return 0; + else + return m_iteration_count; + } protected: //------------------------------------------------------------------ // Classes that inherit from ThreadPlan can see and modify these @@ -593,6 +614,8 @@ protected: Thread &m_thread; Vote m_stop_vote; Vote m_run_vote; + bool m_takes_iteration_count = false; + int32_t m_iteration_count = 1; private: //------------------------------------------------------------------ Modified: lldb/trunk/include/lldb/Target/ThreadPlanStepInstruction.h URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Target/ThreadPlanStepInstruction.h?rev=212559&r1=212558&r2=212559&view=diff ============================================================================== --- lldb/trunk/include/lldb/Target/ThreadPlanStepInstruction.h (original) +++ lldb/trunk/include/lldb/Target/ThreadPlanStepInstruction.h Tue Jul 8 14:28:57 2014 @@ -32,6 +32,7 @@ public: virtual lldb::StateType GetPlanRunState (); virtual bool WillStop (); virtual bool MischiefManaged (); + virtual bool IsPlanStale (); protected: virtual bool DoPlanExplainsStop (Event *event_ptr); @@ -41,6 +42,7 @@ protected: bool stop_others, Vote stop_vote, Vote run_vote); + void SetUpState (); private: friend lldb::ThreadPlanSP Modified: lldb/trunk/source/Commands/CommandObjectThread.cpp URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Commands/CommandObjectThread.cpp?rev=212559&r1=212558&r2=212559&view=diff ============================================================================== --- lldb/trunk/source/Commands/CommandObjectThread.cpp (original) +++ lldb/trunk/source/Commands/CommandObjectThread.cpp Tue Jul 8 14:28:57 2014 @@ -371,6 +371,14 @@ public: } break; + case 'c': + { + m_step_count = Args::StringToUInt32(option_arg, UINT32_MAX, 0); + if (m_step_count == UINT32_MAX) + error.SetErrorStringWithFormat ("invalid ignore count '%s'", option_arg); + break; + } + break; case 'm': { OptionEnumValueElement *enum_values = g_option_table[option_idx].enum_values; @@ -408,6 +416,7 @@ public: m_run_mode = eOnlyDuringStepping; m_avoid_regexp.clear(); m_step_in_target.clear(); + m_step_count = 1; } const OptionDefinition* @@ -426,6 +435,7 @@ public: RunMode m_run_mode; std::string m_avoid_regexp; std::string m_step_in_target; + int32_t m_step_count; }; CommandObjectThreadStepWithTypeAndScope (CommandInterpreter &interpreter, @@ -603,6 +613,14 @@ protected: { new_plan_sp->SetIsMasterPlan (true); new_plan_sp->SetOkayToDiscard (false); + + if (m_options.m_step_count > 1) + { + if (new_plan_sp->SetIterationCount(m_options.m_step_count) != m_options.m_step_count) + { + result.AppendWarning ("step operation does not support iteration count."); + } + } process->GetThreadList().SetSelectedThreadByID (thread->GetID()); process->Resume (); @@ -664,6 +682,7 @@ CommandObjectThreadStepWithTypeAndScope: { { 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."}, { 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."}, +{ 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."}, { 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."}, { 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."}, { 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."}, Modified: lldb/trunk/source/Target/ThreadPlanStepInstruction.cpp URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Target/ThreadPlanStepInstruction.cpp?rev=212559&r1=212558&r2=212559&view=diff ============================================================================== --- lldb/trunk/source/Target/ThreadPlanStepInstruction.cpp (original) +++ lldb/trunk/source/Target/ThreadPlanStepInstruction.cpp Tue Jul 8 14:28:57 2014 @@ -43,21 +43,28 @@ ThreadPlanStepInstruction::ThreadPlanSte m_stop_other_threads (stop_other_threads), m_step_over (step_over) { + m_takes_iteration_count = true; + SetUpState(); +} + +ThreadPlanStepInstruction::~ThreadPlanStepInstruction () +{ +} + +void +ThreadPlanStepInstruction::SetUpState() +{ m_instruction_addr = m_thread.GetRegisterContext()->GetPC(0); - StackFrameSP m_start_frame_sp(m_thread.GetStackFrameAtIndex(0)); - m_stack_id = m_start_frame_sp->GetStackID(); + StackFrameSP start_frame_sp(m_thread.GetStackFrameAtIndex(0)); + m_stack_id = start_frame_sp->GetStackID(); - m_start_has_symbol = m_start_frame_sp->GetSymbolContext(eSymbolContextSymbol).symbol != NULL; + m_start_has_symbol = start_frame_sp->GetSymbolContext(eSymbolContextSymbol).symbol != NULL; StackFrameSP parent_frame_sp = m_thread.GetStackFrameAtIndex(1); if (parent_frame_sp) m_parent_frame_id = parent_frame_sp->GetStackID(); } -ThreadPlanStepInstruction::~ThreadPlanStepInstruction () -{ -} - void ThreadPlanStepInstruction::GetDescription (Stream *s, lldb::DescriptionLevel level) { @@ -106,6 +113,37 @@ ThreadPlanStepInstruction::DoPlanExplain } bool +ThreadPlanStepInstruction::IsPlanStale () +{ + Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_STEP)); + StackID cur_frame_id = m_thread.GetStackFrameAtIndex(0)->GetStackID(); + if (cur_frame_id == m_stack_id) + { + if (m_thread.GetRegisterContext()->GetPC(0) != m_instruction_addr) + return true; + else + return false; + } + else if (cur_frame_id < m_stack_id) + { + // If the current frame is younger than the start frame and we are stepping over, then we need to continue, + // but if we are doing just one step, we're done. + if (m_step_over) + return false; + else + return true; + } + else + { + if (log) + { + log->Printf ("ThreadPlanStepInstruction::IsPlanStale - Current frame is older than start frame, plan is stale."); + } + return true; + } +} + +bool ThreadPlanStepInstruction::ShouldStop (Event *event_ptr) { if (m_step_over) @@ -118,8 +156,18 @@ ThreadPlanStepInstruction::ShouldStop (E { if (m_thread.GetRegisterContext()->GetPC(0) != m_instruction_addr) { - SetPlanComplete(); - return true; + if (--m_iteration_count <= 0) + { + SetPlanComplete(); + return true; + } + else + { + // We are still stepping, reset the start pc, and in case we've stepped out, + // reset the current stack id. + SetUpState(); + return false; + } } else return false; @@ -182,8 +230,18 @@ ThreadPlanStepInstruction::ShouldStop (E { if (m_thread.GetRegisterContext()->GetPC(0) != m_instruction_addr) { - SetPlanComplete(); - return true; + if (--m_iteration_count <= 0) + { + SetPlanComplete(); + return true; + } + else + { + // We are still stepping, reset the start pc, and in case we've stepped in or out, + // reset the current stack id. + SetUpState(); + return false; + } } else return false; _______________________________________________ lldb-commits mailing list lldb-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/lldb-commits