[Lldb-commits] [lldb] r242997 - Add jstopinfo support to llgs

Pavel Labath labath at google.com
Thu Jul 23 02:09:50 PDT 2015


Author: labath
Date: Thu Jul 23 04:09:29 2015
New Revision: 242997

URL: http://llvm.org/viewvc/llvm-project?rev=242997&view=rev
Log:
Add jstopinfo support to llgs

Summary:
This adds support for jstopinfo field of stop-reply packets. This field enables us to avoid
querying full thread stop data on most stops  (see r242593 for more details).

Reviewers: ovyalov, clayborg

Subscribers: lldb-commits

Differential Revision: http://reviews.llvm.org/D11415

Modified:
    lldb/trunk/source/Plugins/Process/Linux/NativeProcessLinux.cpp
    lldb/trunk/source/Plugins/Process/Linux/NativeThreadLinux.cpp
    lldb/trunk/source/Plugins/Process/Linux/NativeThreadLinux.h
    lldb/trunk/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp

Modified: lldb/trunk/source/Plugins/Process/Linux/NativeProcessLinux.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/Process/Linux/NativeProcessLinux.cpp?rev=242997&r1=242996&r2=242997&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/Process/Linux/NativeProcessLinux.cpp (original)
+++ lldb/trunk/source/Plugins/Process/Linux/NativeProcessLinux.cpp Thu Jul 23 04:09:29 2015
@@ -1492,7 +1492,7 @@ NativeProcessLinux::MonitorSignal(const
                 if (m_pending_notification_up && m_pending_notification_up->triggering_tid == pid)
                     linux_thread_sp->SetStoppedBySignal(SIGSTOP, info);
                 else
-                    linux_thread_sp->SetStoppedBySignal(0);
+                    linux_thread_sp->SetStoppedWithNoReason();
 
                 SetCurrentThreadID (thread_sp->GetID ());
                 ThreadDidStop (thread_sp->GetID (), true);

Modified: lldb/trunk/source/Plugins/Process/Linux/NativeThreadLinux.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/Process/Linux/NativeThreadLinux.cpp?rev=242997&r1=242996&r2=242997&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/Process/Linux/NativeThreadLinux.cpp (original)
+++ lldb/trunk/source/Plugins/Process/Linux/NativeThreadLinux.cpp Thu Jul 23 04:09:29 2015
@@ -362,14 +362,14 @@ NativeThreadLinux::SetStoppedByTrace ()
 }
 
 void
-NativeThreadLinux::SetSuspended ()
+NativeThreadLinux::SetStoppedWithNoReason ()
 {
-    const StateType new_state = StateType::eStateSuspended;
+    const StateType new_state = StateType::eStateStopped;
     MaybeLogStateChange (new_state);
     m_state = new_state;
 
-    // FIXME what makes sense here? Do we need a suspended StopReason?
     m_stop_info.reason = StopReason::eStopReasonNone;
+    m_stop_info.details.signal.signo = 0;
 }
 
 void

Modified: lldb/trunk/source/Plugins/Process/Linux/NativeThreadLinux.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/Process/Linux/NativeThreadLinux.h?rev=242997&r1=242996&r2=242997&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/Process/Linux/NativeThreadLinux.h (original)
+++ lldb/trunk/source/Plugins/Process/Linux/NativeThreadLinux.h Thu Jul 23 04:09:29 2015
@@ -87,10 +87,7 @@ namespace process_linux {
         SetStoppedByTrace ();
 
         void
-        SetCrashedWithException (const siginfo_t& info);
-
-        void
-        SetSuspended ();
+        SetStoppedWithNoReason ();
 
         void
         SetExited ();

Modified: lldb/trunk/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp?rev=242997&r1=242996&r2=242997&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp (original)
+++ lldb/trunk/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp Thu Jul 23 04:09:29 2015
@@ -537,6 +537,86 @@ GetStopReasonString(StopReason stop_reas
     return nullptr;
 }
 
+static JSONArray::SP
+GetJSONThreadsInfo(NativeProcessProtocol &process, bool threads_with_valid_stop_info_only)
+{
+    Log *log (GetLogIfAnyCategoriesSet (LIBLLDB_LOG_PROCESS | LIBLLDB_LOG_THREAD));
+
+    JSONArray::SP threads_array_sp = std::make_shared<JSONArray>();
+
+    // Ensure we can get info on the given thread.
+    uint32_t thread_idx = 0;
+    for ( NativeThreadProtocolSP thread_sp;
+          (thread_sp = process.GetThreadAtIndex(thread_idx)) != nullptr;
+          ++thread_idx)
+    {
+
+        lldb::tid_t tid = thread_sp->GetID();
+
+        // Grab the reason this thread stopped.
+        struct ThreadStopInfo tid_stop_info;
+        std::string description;
+        if (!thread_sp->GetStopReason (tid_stop_info, description))
+            return nullptr;
+
+        const int signum = tid_stop_info.details.signal.signo;
+        if (log)
+        {
+            log->Printf ("GDBRemoteCommunicationServerLLGS::%s pid %" PRIu64 " tid %" PRIu64 " got signal signo = %d, reason = %d, exc_type = %" PRIu64,
+                    __FUNCTION__,
+                    process.GetID (),
+                    tid,
+                    signum,
+                    tid_stop_info.reason,
+                    tid_stop_info.details.exception.type);
+        }
+
+        if (threads_with_valid_stop_info_only && tid_stop_info.reason == eStopReasonNone)
+            continue; // No stop reason, skip this thread completely.
+
+        JSONObject::SP thread_obj_sp = std::make_shared<JSONObject>();
+        threads_array_sp->AppendObject(thread_obj_sp);
+
+        thread_obj_sp->SetObject("tid", std::make_shared<JSONNumber>(tid));
+        if (signum != 0)
+            thread_obj_sp->SetObject("signal", std::make_shared<JSONNumber>(uint64_t(signum)));
+
+        const std::string thread_name = thread_sp->GetName ();
+        if (! thread_name.empty())
+            thread_obj_sp->SetObject("name", std::make_shared<JSONString>(thread_name));
+
+        if (const char *stop_reason_str = GetStopReasonString(tid_stop_info.reason))
+            thread_obj_sp->SetObject("reason", std::make_shared<JSONString>(stop_reason_str));
+
+        if (! description.empty())
+            thread_obj_sp->SetObject("description", std::make_shared<JSONString>(description));
+
+        if ((tid_stop_info.reason == eStopReasonException) && tid_stop_info.details.exception.type)
+        {
+            thread_obj_sp->SetObject("metype",
+                    std::make_shared<JSONNumber>(tid_stop_info.details.exception.type));
+
+            JSONArray::SP medata_array_sp = std::make_shared<JSONArray>();
+            for (uint32_t i = 0; i < tid_stop_info.details.exception.data_count; ++i)
+            {
+                medata_array_sp->AppendObject(std::make_shared<JSONNumber>(
+                            tid_stop_info.details.exception.data[i]));
+            }
+            thread_obj_sp->SetObject("medata", medata_array_sp);
+        }
+
+        if (threads_with_valid_stop_info_only)
+            continue; // Only send the abridged stop info.
+
+        if (JSONObject::SP registers_sp = GetRegistersAsJSON(*thread_sp))
+            thread_obj_sp->SetObject("registers", registers_sp);
+
+        // TODO: Expedite interesting regions of inferior memory
+    }
+
+    return threads_array_sp;
+}
+
 GDBRemoteCommunication::PacketResult
 GDBRemoteCommunicationServerLLGS::SendStopReplyPacketForThread (lldb::tid_t tid)
 {
@@ -630,6 +710,31 @@ GDBRemoteCommunicationServerLLGS::SendSt
             response.Printf ("%" PRIx64, listed_thread_sp->GetID ());
         }
         response.PutChar (';');
+
+        // Include JSON info that describes the stop reason for any threads
+        // that actually have stop reasons. We use the new "jstopinfo" key
+        // whose values is hex ascii JSON that contains the thread IDs
+        // thread stop info only for threads that have stop reasons. Only send
+        // this if we have more than one thread otherwise this packet has all
+        // the info it needs.
+        if (thread_index > 0)
+        {
+            const bool threads_with_valid_stop_info_only = true;
+            JSONArray::SP threads_info_sp = GetJSONThreadsInfo(*m_debugged_process_sp,
+                                                               threads_with_valid_stop_info_only);
+            if (threads_info_sp)
+            {
+                response.PutCString("jstopinfo:");
+                StreamString unescaped_response;
+                threads_info_sp->Write(unescaped_response);
+                response.PutCStringAsRawHex8(unescaped_response.GetData());
+                response.PutChar(';');
+            }
+            else if (log)
+                log->Printf ("GDBRemoteCommunicationServerLLGS::%s failed to prepare a jstopinfo field for pid %" PRIu64,
+                        __FUNCTION__, m_debugged_process_sp->GetID());
+
+        }
     }
 
     //
@@ -2719,74 +2824,20 @@ GDBRemoteCommunicationServerLLGS::Handle
         log->Printf ("GDBRemoteCommunicationServerLLGS::%s preparing packet for pid %" PRIu64,
                 __FUNCTION__, m_debugged_process_sp->GetID());
 
-    JSONArray threads_array;
 
-    // Ensure we can get info on the given thread.
-    uint32_t thread_idx = 0;
-    for ( NativeThreadProtocolSP thread_sp;
-          (thread_sp = m_debugged_process_sp->GetThreadAtIndex(thread_idx)) != nullptr;
-          ++thread_idx)
+    StreamString response;
+    const bool threads_with_valid_stop_info_only = false;
+    JSONArray::SP threads_array_sp = GetJSONThreadsInfo(*m_debugged_process_sp,
+                                                        threads_with_valid_stop_info_only);
+    if (! threads_array_sp)
     {
-
-        JSONObject::SP thread_obj_sp = std::make_shared<JSONObject>();
-
-        lldb::tid_t tid = thread_sp->GetID();
-
-        // Grab the reason this thread stopped.
-        struct ThreadStopInfo tid_stop_info;
-        std::string description;
-        if (!thread_sp->GetStopReason (tid_stop_info, description))
-            return SendErrorResponse (52);
-
-        const int signum = tid_stop_info.details.signal.signo;
         if (log)
-        {
-            log->Printf ("GDBRemoteCommunicationServerLLGS::%s pid %" PRIu64 " tid %" PRIu64 " got signal signo = %d, reason = %d, exc_type = %" PRIu64,
-                    __FUNCTION__,
-                    m_debugged_process_sp->GetID (),
-                    tid,
-                    signum,
-                    tid_stop_info.reason,
-                    tid_stop_info.details.exception.type);
-        }
-
-        thread_obj_sp->SetObject("tid", std::make_shared<JSONNumber>(tid));
-        if (signum != LLDB_INVALID_SIGNAL_NUMBER)
-            thread_obj_sp->SetObject("signal", std::make_shared<JSONNumber>(uint64_t(signum)));
-
-        const std::string thread_name = thread_sp->GetName ();
-        if (! thread_name.empty())
-            thread_obj_sp->SetObject("name", std::make_shared<JSONString>(thread_name));
-
-        if (JSONObject::SP registers_sp = GetRegistersAsJSON(*thread_sp))
-            thread_obj_sp->SetObject("registers", registers_sp);
-
-        if (const char *stop_reason_str = GetStopReasonString(tid_stop_info.reason))
-            thread_obj_sp->SetObject("reason", std::make_shared<JSONString>(stop_reason_str));
-
-        if (! description.empty())
-            thread_obj_sp->SetObject("description", std::make_shared<JSONString>(description));
-
-        if ((tid_stop_info.reason == eStopReasonException) && tid_stop_info.details.exception.type)
-        {
-            thread_obj_sp->SetObject("metype",
-                    std::make_shared<JSONNumber>(tid_stop_info.details.exception.type));
-
-            JSONArray::SP medata_array_sp = std::make_shared<JSONArray>();
-            for (uint32_t i = 0; i < tid_stop_info.details.exception.data_count; ++i)
-            {
-                medata_array_sp->AppendObject(std::make_shared<JSONNumber>(
-                            tid_stop_info.details.exception.data[i]));
-            }
-            thread_obj_sp->SetObject("medata", medata_array_sp);
-        }
-
-        threads_array.AppendObject(thread_obj_sp);
+            log->Printf ("GDBRemoteCommunicationServerLLGS::%s failed to prepare a packet for pid %" PRIu64,
+                    __FUNCTION__, m_debugged_process_sp->GetID());
+        return SendErrorResponse(52);
     }
-    // TODO: Expedite interesting regions of inferior memory
 
-    StreamString response;
-    threads_array.Write(response);
+    threads_array_sp->Write(response);
     StreamGDBRemote escaped_response;
     escaped_response.PutEscapedBytes(response.GetData(), response.GetSize());
     return SendPacketNoLock (escaped_response.GetData(), escaped_response.GetSize());





More information about the lldb-commits mailing list