kkcode0 updated this revision to Diff 555574.
kkcode0 marked an inline comment as done.
kkcode0 added a comment.

formatting


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D143698/new/

https://reviews.llvm.org/D143698

Files:
  lldb/include/lldb/Host/common/NativeRegisterContext.h
  lldb/include/lldb/Target/RegisterContext.h
  lldb/include/lldb/Utility/StringExtractorGDBRemote.h
  lldb/source/Host/common/NativeRegisterContext.cpp
  lldb/source/Plugins/DynamicLoader/POSIX-DYLD/DynamicLoaderPOSIXDYLD.cpp
  lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux.cpp
  lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux.h
  lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux_x86_64.cpp
  lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux_x86_64.h
  lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.cpp
  lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.h
  lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp
  lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.h
  lldb/source/Plugins/Process/gdb-remote/GDBRemoteRegisterContext.cpp
  lldb/source/Plugins/Process/gdb-remote/GDBRemoteRegisterContext.h
  lldb/source/Target/RegisterContext.cpp
  lldb/source/Target/Thread.cpp
  lldb/source/Utility/StringExtractorGDBRemote.cpp
  lldb/test/API/lang/c/tls_globals/TestTlsGlobals.py

Index: lldb/test/API/lang/c/tls_globals/TestTlsGlobals.py
===================================================================
--- lldb/test/API/lang/c/tls_globals/TestTlsGlobals.py
+++ lldb/test/API/lang/c/tls_globals/TestTlsGlobals.py
@@ -37,11 +37,7 @@
 
     # TLS works differently on Windows, this would need to be implemented
     # separately.
-    @skipIfWindows
-    @expectedFailureAll(
-        bugnumber="llvm.org/pr28392",
-        oslist=no_match(lldbplatformutil.getDarwinOSTriples()),
-    )
+    @skipIf(archs=no_match(['x86_64']), oslist=no_match(['linux']))
     def test(self):
         """Test thread-local storage."""
         self.build()
Index: lldb/source/Utility/StringExtractorGDBRemote.cpp
===================================================================
--- lldb/source/Utility/StringExtractorGDBRemote.cpp
+++ lldb/source/Utility/StringExtractorGDBRemote.cpp
@@ -210,6 +210,8 @@
         return eServerPacketType_qGetProfileData;
       if (PACKET_MATCHES("qGDBServerVersion"))
         return eServerPacketType_qGDBServerVersion;
+      if (PACKET_STARTS_WITH("qGetTLSAddr"))
+	      return eServerPacketType_qGetTLSAddr;
       break;
 
     case 'H':
Index: lldb/source/Target/Thread.cpp
===================================================================
--- lldb/source/Target/Thread.cpp
+++ lldb/source/Target/Thread.cpp
@@ -1623,7 +1623,11 @@
 
 void Thread::SettingsTerminate() {}
 
-lldb::addr_t Thread::GetThreadPointer() { return LLDB_INVALID_ADDRESS; }
+lldb::addr_t Thread::GetThreadPointer() {
+  RegisterContext *reg_ctx = this->GetRegisterContext().get();
+  auto tp = reg_ctx->GetThreadPointer();
+  return tp;
+}
 
 addr_t Thread::GetThreadLocalData(const ModuleSP module,
                                   lldb::addr_t tls_file_addr) {
Index: lldb/source/Target/RegisterContext.cpp
===================================================================
--- lldb/source/Target/RegisterContext.cpp
+++ lldb/source/Target/RegisterContext.cpp
@@ -29,6 +29,10 @@
 
 RegisterContext::~RegisterContext() = default;
 
+uint64_t RegisterContext::GetThreadPointer() {
+  return UINT64_MAX;
+}
+
 void RegisterContext::InvalidateIfNeeded(bool force) {
   ProcessSP process_sp(m_thread.GetProcess());
   bool invalidate = force;
Index: lldb/source/Plugins/Process/gdb-remote/GDBRemoteRegisterContext.h
===================================================================
--- lldb/source/Plugins/Process/gdb-remote/GDBRemoteRegisterContext.h
+++ lldb/source/Plugins/Process/gdb-remote/GDBRemoteRegisterContext.h
@@ -55,6 +55,8 @@
 
   const RegisterInfo *GetRegisterInfoAtIndex(size_t reg) override;
 
+  uint64_t GetThreadPointer() override;
+
   size_t GetRegisterSetCount() override;
 
   const RegisterSet *GetRegisterSet(size_t reg_set) override;
Index: lldb/source/Plugins/Process/gdb-remote/GDBRemoteRegisterContext.cpp
===================================================================
--- lldb/source/Plugins/Process/gdb-remote/GDBRemoteRegisterContext.cpp
+++ lldb/source/Plugins/Process/gdb-remote/GDBRemoteRegisterContext.cpp
@@ -80,6 +80,19 @@
   return m_reg_info_sp->GetRegisterSet(reg_set);
 }
 
+uint64_t GDBRemoteRegisterContext::GetThreadPointer() {
+  ExecutionContext exe_ctx(CalculateThread());
+  Process *process = exe_ctx.GetProcessPtr();
+  Thread *thread = exe_ctx.GetThreadPtr();
+  if (process == nullptr || thread == nullptr)
+    return LLDB_INVALID_ADDRESS;
+  GDBRemoteCommunicationClient &gdb_comm(
+      ((ProcessGDBRemote *)process)->GetGDBRemote());
+  uint64_t tid = thread->GetProtocolID();
+  // Return thread pointer here, offset and link_map will be filled by GetThreadLocalData in DYLD
+  return gdb_comm.GetQGetTLSAddr(tid, LLDB_INVALID_ADDRESS /* offset */, LLDB_INVALID_ADDRESS /* lm */);
+}
+
 bool GDBRemoteRegisterContext::ReadRegister(const RegisterInfo *reg_info,
                                             RegisterValue &value) {
   // Read the register
Index: lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.h
===================================================================
--- lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.h
+++ lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.h
@@ -185,6 +185,8 @@
 
   PacketResult Handle_qsThreadInfo(StringExtractorGDBRemote &packet);
 
+  PacketResult Handle_qGetTLSAddr(StringExtractorGDBRemote &packet);
+  
   PacketResult Handle_p(StringExtractorGDBRemote &packet);
 
   PacketResult Handle_P(StringExtractorGDBRemote &packet);
Index: lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp
===================================================================
--- lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp
+++ lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp
@@ -148,6 +148,9 @@
   RegisterMemberFunctionHandler(
       StringExtractorGDBRemote::eServerPacketType_qsThreadInfo,
       &GDBRemoteCommunicationServerLLGS::Handle_qsThreadInfo);
+  RegisterMemberFunctionHandler(
+      StringExtractorGDBRemote::eServerPacketType_qGetTLSAddr,
+      &GDBRemoteCommunicationServerLLGS::Handle_qGetTLSAddr);
   RegisterMemberFunctionHandler(
       StringExtractorGDBRemote::eServerPacketType_qThreadStopInfo,
       &GDBRemoteCommunicationServerLLGS::Handle_qThreadStopInfo);
@@ -2108,6 +2111,30 @@
   return SendPacketNoLock("l");
 }
 
+GDBRemoteCommunication::PacketResult
+GDBRemoteCommunicationServerLLGS::Handle_qGetTLSAddr(
+    StringExtractorGDBRemote &packet) {
+  llvm::StringRef s = packet.GetStringRef();
+  if (!s.consume_front("qGetTLSAddr:"))
+    return SendErrorResponse(8);
+  llvm::SmallVector<llvm::StringRef, 16> argv;
+  s.split(argv, ',');
+  lldb::tid_t tid =  StringExtractor(argv[0]).GetU64(LLDB_INVALID_ADDRESS, 16);
+  lldb::addr_t offset = StringExtractor(argv[1]).GetU64(LLDB_INVALID_ADDRESS, 16);
+  lldb::addr_t lm = StringExtractor(argv[2]).GetU64(LLDB_INVALID_ADDRESS, 16);
+  (void) offset;
+  (void) lm;
+  NativeThreadProtocol *ntp = m_current_process->GetThreadByID(tid);
+  NativeRegisterContext &reg_ctx = ntp->GetRegisterContext();
+  lldb::addr_t tp = LLDB_INVALID_ADDRESS;
+  StreamGDBRemote response;
+  if(!reg_ctx.ReadThreadPointer(tp).Fail()) {
+    response.PutHex64(tp, lldb::eByteOrderBig);
+    return SendPacketNoLock(response.GetString());
+  } else
+    return SendErrorResponse(8);
+}
+
 GDBRemoteCommunication::PacketResult
 GDBRemoteCommunicationServerLLGS::Handle_g(StringExtractorGDBRemote &packet) {
   Log *log = GetLog(LLDBLog::Thread);
Index: lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.h
===================================================================
--- lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.h
+++ lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.h
@@ -443,6 +443,8 @@
   /// one value in the offsets field.
   std::optional<QOffsets> GetQOffsets();
 
+  lldb::addr_t GetQGetTLSAddr(lldb::tid_t tid, lldb::addr_t offset, lldb::addr_t lms);
+  
   bool GetModuleInfo(const FileSpec &module_file_spec,
                      const ArchSpec &arch_spec, ModuleSpec &module_spec);
 
Index: lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.cpp
===================================================================
--- lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.cpp
+++ lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.cpp
@@ -3752,6 +3752,28 @@
   return std::nullopt;
 }
 
+lldb::addr_t GDBRemoteCommunicationClient::GetQGetTLSAddr(lldb::tid_t tid, lldb::addr_t offset, lldb::addr_t lm) {
+  StreamString packet;
+  packet.PutCString("qGetTLSAddr:");
+  packet.PutHex64(tid, lldb::eByteOrderBig);
+  packet.PutCString(",");
+  packet.PutHex64(offset, lldb::eByteOrderBig);
+  packet.PutCString(",");
+  packet.PutHex64(lm, lldb::eByteOrderBig);
+  StringExtractorGDBRemote response;
+  if (SendPacketAndWaitForResponse(packet.GetString(), response) !=
+      PacketResult::Success)
+    return LLDB_INVALID_ADDRESS;
+  if (response.IsErrorResponse())
+    return LLDB_INVALID_ADDRESS;
+  if (response.IsUnsupportedResponse())
+    return LLDB_INVALID_ADDRESS;
+  llvm::StringRef ref = response.GetStringRef();
+  uint64_t addr = LLDB_INVALID_ADDRESS;
+  ref.consumeInteger(16, addr);
+  return addr;
+}
+
 bool GDBRemoteCommunicationClient::GetModuleInfo(
     const FileSpec &module_file_spec, const lldb_private::ArchSpec &arch_spec,
     ModuleSpec &module_spec) {
Index: lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux_x86_64.h
===================================================================
--- lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux_x86_64.h
+++ lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux_x86_64.h
@@ -37,6 +37,8 @@
 
   uint32_t GetUserRegisterCount() const override;
 
+  Status ReadThreadPointer(uint64_t &tp) override;
+
   Status ReadRegister(const RegisterInfo *reg_info,
                       RegisterValue &reg_value) override;
 
Index: lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux_x86_64.cpp
===================================================================
--- lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux_x86_64.cpp
+++ lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux_x86_64.cpp
@@ -13,6 +13,7 @@
 #include "Plugins/Process/Utility/RegisterContextLinux_i386.h"
 #include "Plugins/Process/Utility/RegisterContextLinux_x86_64.h"
 #include "lldb/Host/HostInfo.h"
+#include "lldb/Host/linux/Ptrace.h"
 #include "lldb/Utility/DataBufferHeap.h"
 #include "lldb/Utility/Log.h"
 #include "lldb/Utility/RegisterValue.h"
@@ -373,6 +374,16 @@
   m_fctrl_offset_in_userarea = reg_info_fctrl->byte_offset;
 }
 
+Status NativeRegisterContextLinux_x86_64::ReadThreadPointer(uint64_t& tp) {
+  Status error;
+  errno = 0;
+  auto ret= ptrace(static_cast<__ptrace_request>(PTRACE_ARCH_PRCTL), m_thread.GetID(),
+                   &tp, (void *)ARCH_GET_FS, 0);
+  if (ret == -1)
+    error.SetErrorToErrno();
+    return error;
+}
+
 // CONSIDER after local and llgs debugging are merged, register set support can
 // be moved into a base x86-64 class with IsRegisterSetAvailable made virtual.
 uint32_t NativeRegisterContextLinux_x86_64::GetRegisterSetCount() const {
Index: lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux.h
===================================================================
--- lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux.h
+++ lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux.h
@@ -82,6 +82,8 @@
         "Architecture does not support memory tagging");
   }
 
+  virtual Status ReadThreadPointer(uint64_t &tp) override;
+
 protected:
   // NB: This constructor is here only because gcc<=6.5 requires a virtual base
   // class initializer on abstract class (even though it is never used). It can
@@ -105,7 +107,6 @@
   virtual Status ReadGPR();
 
   virtual Status WriteGPR();
-
   virtual Status ReadFPR();
 
   virtual Status WriteFPR();
Index: lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux.cpp
===================================================================
--- lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux.cpp
+++ lldb/source/Plugins/Process/Linux/NativeRegisterContextLinux.cpp
@@ -112,6 +112,12 @@
                                            GetFPRSize());
 }
 
+Status NativeRegisterContextLinux::ReadThreadPointer(uint64_t &tp) {
+  tp = LLDB_INVALID_ADDRESS;
+  Status error;
+  return error;
+}
+
 Status NativeRegisterContextLinux::WriteFPR() {
   return NativeProcessLinux::PtraceWrapper(PTRACE_SETFPREGS, m_thread.GetID(),
                                            nullptr, GetFPRBuffer(),
Index: lldb/source/Plugins/DynamicLoader/POSIX-DYLD/DynamicLoaderPOSIXDYLD.cpp
===================================================================
--- lldb/source/Plugins/DynamicLoader/POSIX-DYLD/DynamicLoaderPOSIXDYLD.cpp
+++ lldb/source/Plugins/DynamicLoader/POSIX-DYLD/DynamicLoaderPOSIXDYLD.cpp
@@ -183,14 +183,7 @@
 
     LLDB_LOGF(log, "DynamicLoaderPOSIXDYLD::%s about to call ProbeEntry()",
               __FUNCTION__);
-
-    if (!SetRendezvousBreakpoint()) {
-      // If we cannot establish rendezvous breakpoint right now we'll try again
-      // at entry point.
-      ProbeEntry();
-    }
-
-    LoadVDSO();
+    ProbeEntry();
     m_process->GetTarget().ModulesDidLoad(module_list);
   }
 }
@@ -745,9 +738,10 @@
     return LLDB_INVALID_ADDRESS;
 
   // Find the module's modid.
+
   int modid_size = 4; // FIXME(spucci): This isn't right for big-endian 64-bit
   int64_t modid = ReadUnsignedIntWithSizeInBytes(
-      link_map + metadata.modid_offset, modid_size);
+                    link_map + metadata.modid_offset, modid_size);
   if (modid == -1)
     return LLDB_INVALID_ADDRESS;
 
Index: lldb/source/Host/common/NativeRegisterContext.cpp
===================================================================
--- lldb/source/Host/common/NativeRegisterContext.cpp
+++ lldb/source/Host/common/NativeRegisterContext.cpp
@@ -120,6 +120,12 @@
   return nullptr;
 }
 
+Status NativeRegisterContext::ReadThreadPointer(uint64_t& tp) {
+  tp = LLDB_INVALID_ADDRESS;
+  Status error;
+  return error;
+}
+
 lldb::addr_t NativeRegisterContext::GetPC(lldb::addr_t fail_value) {
   Log *log = GetLog(LLDBLog::Thread);
 
Index: lldb/include/lldb/Utility/StringExtractorGDBRemote.h
===================================================================
--- lldb/include/lldb/Utility/StringExtractorGDBRemote.h
+++ lldb/include/lldb/Utility/StringExtractorGDBRemote.h
@@ -109,6 +109,7 @@
     eServerPacketType_jThreadsInfo,
     eServerPacketType_qsThreadInfo,
     eServerPacketType_qfThreadInfo,
+    eServerPacketType_qGetTLSAddr,
     eServerPacketType_qGetPid,
     eServerPacketType_qGetProfileData,
     eServerPacketType_qGDBServerVersion,
Index: lldb/include/lldb/Target/RegisterContext.h
===================================================================
--- lldb/include/lldb/Target/RegisterContext.h
+++ lldb/include/lldb/Target/RegisterContext.h
@@ -37,6 +37,15 @@
 
   virtual lldb::ByteOrder GetByteOrder();
 
+  /// Retrieves the per-thread data area.
+  /// Most OSs maintain a per-thread pointer (e.g. the FS register on
+  /// x64), which we return the value of here.
+  ///
+  /// \return
+  ///     LLDB_INVALID_ADDRESS if not supported, otherwise the thread
+  ///     pointer value.
+  virtual uint64_t GetThreadPointer();
+
   virtual bool ReadRegister(const RegisterInfo *reg_info,
                             RegisterValue &reg_value) = 0;
 
Index: lldb/include/lldb/Host/common/NativeRegisterContext.h
===================================================================
--- lldb/include/lldb/Host/common/NativeRegisterContext.h
+++ lldb/include/lldb/Host/common/NativeRegisterContext.h
@@ -48,6 +48,8 @@
   virtual Status ReadRegister(const RegisterInfo *reg_info,
                               RegisterValue &reg_value) = 0;
 
+  virtual Status ReadThreadPointer(uint64_t &tp);
+
   virtual Status WriteRegister(const RegisterInfo *reg_info,
                                const RegisterValue &reg_value) = 0;
 
_______________________________________________
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits

Reply via email to