Threads now store their "temporary" resume state, so we know whether they were suspended in the most
recent step, and if they weren't allowed to run, don't ask questions about their state unless explicitly
requested to do so.
git-svn-id: https://llvm.org/svn/llvm-project/lldb/trunk@149443 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/source/Target/Thread.cpp b/source/Target/Thread.cpp
index 2a675e5..1c13b3d 100644
--- a/source/Target/Thread.cpp
+++ b/source/Target/Thread.cpp
@@ -58,6 +58,7 @@
m_prev_frames_sp (),
m_resume_signal (LLDB_INVALID_SIGNAL_NUMBER),
m_resume_state (eStateRunning),
+ m_temporary_resume_state (eStateRunning),
m_unwinder_ap (),
m_destroy_called (false),
m_thread_stop_reason_stop_id (0)
@@ -227,9 +228,20 @@
m_completed_plan_stack.clear();
m_discarded_plan_stack.clear();
- StopInfo *stop_info = GetPrivateStopReason().get();
- if (stop_info)
- stop_info->WillResume (resume_state);
+ SetTemporaryResumeState(resume_state);
+
+ // This is a little dubious, but we are trying to limit how often we actually fetch stop info from
+ // the target, 'cause that slows down single stepping. So assume that if we got to the point where
+ // we're about to resume, and we haven't yet had to fetch the stop reason, then it doesn't need to know
+ // about the fact that we are resuming...
+ const uint32_t process_stop_id = GetProcess().GetStopID();
+ if (m_thread_stop_reason_stop_id == process_stop_id &&
+ (m_actual_stop_info_sp && m_actual_stop_info_sp->IsValid()))
+ {
+ StopInfo *stop_info = GetPrivateStopReason().get();
+ if (stop_info)
+ stop_info->WillResume (resume_state);
+ }
// Tell all the plans that we are about to resume in case they need to clear any state.
// We distinguish between the plan on the top of the stack and the lower
@@ -260,8 +272,49 @@
bool should_stop = true;
LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_STEP));
+
+ if (GetResumeState () == eStateSuspended)
+ {
+ if (log)
+ log->Printf ("Thread::%s for tid = 0x%4.4llx, should_stop = 0 (ignore since thread was suspended)",
+ __FUNCTION__,
+ GetID ());
+// log->Printf ("Thread::%s for tid = 0x%4.4llx, pc = 0x%16.16llx, should_stop = 0 (ignore since thread was suspended)",
+// __FUNCTION__,
+// GetID (),
+// GetRegisterContext()->GetPC());
+ return false;
+ }
+
+ if (GetTemporaryResumeState () == eStateSuspended)
+ {
+ if (log)
+ log->Printf ("Thread::%s for tid = 0x%4.4llx, should_stop = 0 (ignore since thread was suspended)",
+ __FUNCTION__,
+ GetID ());
+// log->Printf ("Thread::%s for tid = 0x%4.4llx, pc = 0x%16.16llx, should_stop = 0 (ignore since thread was suspended)",
+// __FUNCTION__,
+// GetID (),
+// GetRegisterContext()->GetPC());
+ return false;
+ }
+
+ if (ThreadStoppedForAReason() == false)
+ {
+ if (log)
+ log->Printf ("Thread::%s for tid = 0x%4.4llx, pc = 0x%16.16llx, should_stop = 0 (ignore since no stop reason)",
+ __FUNCTION__,
+ GetID (),
+ GetRegisterContext()->GetPC());
+ return false;
+ }
+
if (log)
{
+ log->Printf ("Thread::%s for tid = 0x%4.4llx, pc = 0x%16.16llx",
+ __FUNCTION__,
+ GetID (),
+ GetRegisterContext()->GetPC());
log->Printf ("^^^^^^^^ Thread::ShouldStop Begin ^^^^^^^^");
StreamString s;
s.IndentMore();
@@ -401,6 +454,8 @@
Thread::ShouldReportStop (Event* event_ptr)
{
StateType thread_state = GetResumeState ();
+ StateType temp_thread_state = GetTemporaryResumeState();
+
LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_STEP));
if (thread_state == eStateSuspended || thread_state == eStateInvalid)
@@ -410,6 +465,20 @@
return eVoteNoOpinion;
}
+ if (temp_thread_state == eStateSuspended || temp_thread_state == eStateInvalid)
+ {
+ if (log)
+ log->Printf ("Thread::ShouldReportStop() tid = 0x%4.4llx: returning vote %i (temporary state was suspended or invalid)\n", GetID(), eVoteNoOpinion);
+ return eVoteNoOpinion;
+ }
+
+ if (!ThreadStoppedForAReason())
+ {
+ if (log)
+ log->Printf ("Thread::ShouldReportStop() tid = 0x%4.4llx: returning vote %i (thread didn't stop for a reason.)\n", GetID(), eVoteNoOpinion);
+ return eVoteNoOpinion;
+ }
+
if (m_completed_plan_stack.size() > 0)
{
// Don't use GetCompletedPlan here, since that suppresses private plans.