[Lldb-commits] [PATCH] D110020: [lldb] [gdb-remote] Remove unused arg from GDBRemoteRegisterContext::ReadRegisterBytes()

2021-09-18 Thread Michał Górny via Phabricator via lldb-commits
mgorny created this revision.
mgorny added reviewers: labath, krytarowski, emaste.
mgorny requested review of this revision.

https://reviews.llvm.org/D110020

Files:
  lldb/source/Plugins/Process/gdb-remote/GDBRemoteRegisterContext.cpp
  lldb/source/Plugins/Process/gdb-remote/GDBRemoteRegisterContext.h


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
@@ -87,7 +87,7 @@
 protected:
   friend class ThreadGDBRemote;
 
-  bool ReadRegisterBytes(const RegisterInfo *reg_info, DataExtractor &data);
+  bool ReadRegisterBytes(const RegisterInfo *reg_info);
 
   bool WriteRegisterBytes(const RegisterInfo *reg_info, DataExtractor &data,
   uint32_t data_offset);
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
@@ -90,7 +90,7 @@
 bool GDBRemoteRegisterContext::ReadRegister(const RegisterInfo *reg_info,
 RegisterValue &value) {
   // Read the register
-  if (ReadRegisterBytes(reg_info, m_reg_data)) {
+  if (ReadRegisterBytes(reg_info)) {
 const uint32_t reg = reg_info->kinds[eRegisterKindLLDB];
 if (m_reg_valid[reg] == false)
   return false;
@@ -184,8 +184,7 @@
   return false;
 }
 
-bool GDBRemoteRegisterContext::ReadRegisterBytes(const RegisterInfo *reg_info,
- DataExtractor &data) {
+bool GDBRemoteRegisterContext::ReadRegisterBytes(const RegisterInfo *reg_info) 
{
   ExecutionContext exe_ctx(CalculateThread());
 
   Process *process = exe_ctx.GetProcessPtr();
@@ -279,22 +278,6 @@
   return false;
   }
 
-  if (&data != &m_reg_data) {
-assert(m_reg_data.GetByteSize() >=
-   reg_info->byte_offset + reg_info->byte_size);
-// If our register context and our register info disagree, which should
-// never happen, don't read past the end of the buffer.
-if (m_reg_data.GetByteSize() < reg_info->byte_offset + reg_info->byte_size)
-  return false;
-
-// If we aren't extracting into our own buffer (which only happens when
-// this function is called from ReadRegisterValue(uint32_t, Scalar&)) then
-// we transfer bytes from our buffer into the data buffer that was passed
-// in
-
-data.SetByteOrder(m_reg_data.GetByteOrder());
-data.SetData(m_reg_data, reg_info->byte_offset, reg_info->byte_size);
-  }
   return true;
 }
 
@@ -526,7 +509,7 @@
   if (reg_info
   ->value_regs) // skip registers that are slices of real registers
 continue;
-  ReadRegisterBytes(reg_info, m_reg_data);
+  ReadRegisterBytes(reg_info);
   // ReadRegisterBytes saves the contents of the register in to the
   // m_reg_data buffer
 }


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
@@ -87,7 +87,7 @@
 protected:
   friend class ThreadGDBRemote;
 
-  bool ReadRegisterBytes(const RegisterInfo *reg_info, DataExtractor &data);
+  bool ReadRegisterBytes(const RegisterInfo *reg_info);
 
   bool WriteRegisterBytes(const RegisterInfo *reg_info, DataExtractor &data,
   uint32_t data_offset);
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
@@ -90,7 +90,7 @@
 bool GDBRemoteRegisterContext::ReadRegister(const RegisterInfo *reg_info,
 RegisterValue &value) {
   // Read the register
-  if (ReadRegisterBytes(reg_info, m_reg_data)) {
+  if (ReadRegisterBytes(reg_info)) {
 const uint32_t reg = reg_info->kinds[eRegisterKindLLDB];
 if (m_reg_valid[reg] == false)
   return false;
@@ -184,8 +184,7 @@
   return false;
 }
 
-bool GDBRemoteRegisterContext::ReadRegisterBytes(const RegisterInfo *reg_info,
- DataExtractor &data) {
+bool GDBRemoteRegisterContext::ReadRegisterBytes(const RegisterInfo *reg_info) {
   ExecutionContext exe_ctx(CalculateThread());
 
   Process *process = exe_ctx.GetProcessPtr();
@@ -279,22 +278,6 @@
   return false;
   }
 
-  if (&data != &m_reg_data) {
-assert(m_reg_data.GetByteSize() >=
-   reg_info->byte_offset + reg_info->byte_size);
-// If our register cont

[Lldb-commits] [PATCH] D109906: [lldb] [test] Add unittest for DynamicRegisterInfo::Finalize()

2021-09-18 Thread Michał Górny via Phabricator via lldb-commits
mgorny updated this revision to Diff 373410.
mgorny added a comment.

Add a helper function. Test the weird invalidate_regs expansion logic.


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

https://reviews.llvm.org/D109906

Files:
  lldb/unittests/Process/Utility/CMakeLists.txt
  lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp

Index: lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
===
--- /dev/null
+++ lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
@@ -0,0 +1,98 @@
+//===-- DynamicRegisterInfoTest.cpp ---===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===--===//
+
+#include "gmock/gmock.h"
+#include "gtest/gtest.h"
+
+#include "Plugins/Process/Utility/DynamicRegisterInfo.h"
+
+#include "lldb/Utility/ArchSpec.h"
+
+using namespace lldb_private;
+
+static uint32_t AddRegister(DynamicRegisterInfo &info, const char *name,
+uint32_t byte_size,
+std::vector value_regs = {},
+std::vector invalidate_regs = {}) {
+  ConstString group{"group"};
+  static uint32_t regnum = 0;
+
+  struct RegisterInfo new_reg {
+name, nullptr, byte_size, LLDB_INVALID_INDEX32, lldb::eEncodingUint,
+lldb::eFormatUnsigned,
+{LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, regnum,
+ regnum},
+nullptr, nullptr, nullptr, 0
+  };
+
+  if (!value_regs.empty()) {
+value_regs.push_back(LLDB_INVALID_REGNUM);
+new_reg.value_regs = value_regs.data();
+  }
+  if (!invalidate_regs.empty()) {
+invalidate_regs.push_back(LLDB_INVALID_REGNUM);
+new_reg.invalidate_regs = invalidate_regs.data();
+  }
+
+  info.AddRegister(new_reg, group);
+  return regnum++;
+}
+
+TEST(DynamicRegisterInfoTest, finalize_regs) {
+  DynamicRegisterInfo info;
+
+  // Add regular registers
+  uint32_t b1 = AddRegister(info, "b1", 8);
+  uint32_t b2 = AddRegister(info, "b2", 8);
+
+  // Add a few sub-registers
+  uint32_t s1 = AddRegister(info, "s1", 4, {b1});
+  uint32_t s2 = AddRegister(info, "s2", 4, {b2});
+
+  // Add a register with invalidate_regs
+  uint32_t i1 = AddRegister(info, "i1", 8, {}, {b1});
+
+  // Add a register with indirect invalidate regs to be expanded
+  // TODO: why is it done conditionally to value_regs?
+  uint32_t i2 = AddRegister(info, "i2", 4, {b2}, {i1});
+
+  info.Finalize(lldb_private::ArchSpec());
+
+  const RegisterInfo *added_reg = info.GetRegisterInfoAtIndex(0);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 0U);
+
+  added_reg = info.GetRegisterInfoAtIndex(1);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 8U);
+
+  added_reg = info.GetRegisterInfoAtIndex(2);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 0U);
+  EXPECT_EQ(added_reg->value_regs[0], b1);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(3);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 8U);
+  EXPECT_EQ(added_reg->value_regs[0], b2);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(4);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 16U);
+  EXPECT_EQ(added_reg->invalidate_regs[0], b1);
+  EXPECT_EQ(added_reg->invalidate_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(5);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 8U);
+  EXPECT_EQ(added_reg->invalidate_regs[0], b1);
+  EXPECT_EQ(added_reg->invalidate_regs[1], i1);
+  EXPECT_EQ(added_reg->invalidate_regs[2], LLDB_INVALID_REGNUM);
+}
Index: lldb/unittests/Process/Utility/CMakeLists.txt
===
--- lldb/unittests/Process/Utility/CMakeLists.txt
+++ lldb/unittests/Process/Utility/CMakeLists.txt
@@ -15,9 +15,10 @@
   ${NETBSD_SOURCES})
 
 add_lldb_unittest(ProcessUtilityTests
-  RegisterContextTest.cpp
+  DynamicRegisterInfoTest.cpp
   LinuxProcMapsTest.cpp
   MemoryTagManagerAArch64MTETest.cpp
+  RegisterContextTest.cpp
   ${PLATFORM_SOURCES}
 
   LINK_LIBS
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [PATCH] D109906: [lldb] [test] Add unittest for DynamicRegisterInfo::Finalize()

2021-09-18 Thread Michał Górny via Phabricator via lldb-commits
mgorny updated this revision to Diff 373411.
mgorny added a comment.

Eliminate unused vars.


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

https://reviews.llvm.org/D109906

Files:
  lldb/unittests/Process/Utility/CMakeLists.txt
  lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp

Index: lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
===
--- /dev/null
+++ lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
@@ -0,0 +1,98 @@
+//===-- DynamicRegisterInfoTest.cpp ---===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===--===//
+
+#include "gmock/gmock.h"
+#include "gtest/gtest.h"
+
+#include "Plugins/Process/Utility/DynamicRegisterInfo.h"
+
+#include "lldb/Utility/ArchSpec.h"
+
+using namespace lldb_private;
+
+static uint32_t AddRegister(DynamicRegisterInfo &info, const char *name,
+uint32_t byte_size,
+std::vector value_regs = {},
+std::vector invalidate_regs = {}) {
+  ConstString group{"group"};
+  static uint32_t regnum = 0;
+
+  struct RegisterInfo new_reg {
+name, nullptr, byte_size, LLDB_INVALID_INDEX32, lldb::eEncodingUint,
+lldb::eFormatUnsigned,
+{LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, regnum,
+ regnum},
+nullptr, nullptr, nullptr, 0
+  };
+
+  if (!value_regs.empty()) {
+value_regs.push_back(LLDB_INVALID_REGNUM);
+new_reg.value_regs = value_regs.data();
+  }
+  if (!invalidate_regs.empty()) {
+invalidate_regs.push_back(LLDB_INVALID_REGNUM);
+new_reg.invalidate_regs = invalidate_regs.data();
+  }
+
+  info.AddRegister(new_reg, group);
+  return regnum++;
+}
+
+TEST(DynamicRegisterInfoTest, finalize_regs) {
+  DynamicRegisterInfo info;
+
+  // Add regular registers
+  uint32_t b1 = AddRegister(info, "b1", 8);
+  uint32_t b2 = AddRegister(info, "b2", 8);
+
+  // Add a few sub-registers
+  AddRegister(info, "s1", 4, {b1});
+  AddRegister(info, "s2", 4, {b2});
+
+  // Add a register with invalidate_regs
+  uint32_t i1 = AddRegister(info, "i1", 8, {}, {b1});
+
+  // Add a register with indirect invalidate regs to be expanded
+  // TODO: why is it done conditionally to value_regs?
+  AddRegister(info, "i2", 4, {b2}, {i1});
+
+  info.Finalize(lldb_private::ArchSpec());
+
+  const RegisterInfo *added_reg = info.GetRegisterInfoAtIndex(0);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 0U);
+
+  added_reg = info.GetRegisterInfoAtIndex(1);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 8U);
+
+  added_reg = info.GetRegisterInfoAtIndex(2);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 0U);
+  EXPECT_EQ(added_reg->value_regs[0], b1);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(3);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 8U);
+  EXPECT_EQ(added_reg->value_regs[0], b2);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(4);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 16U);
+  EXPECT_EQ(added_reg->invalidate_regs[0], b1);
+  EXPECT_EQ(added_reg->invalidate_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(5);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->byte_offset, 8U);
+  EXPECT_EQ(added_reg->invalidate_regs[0], b1);
+  EXPECT_EQ(added_reg->invalidate_regs[1], i1);
+  EXPECT_EQ(added_reg->invalidate_regs[2], LLDB_INVALID_REGNUM);
+}
Index: lldb/unittests/Process/Utility/CMakeLists.txt
===
--- lldb/unittests/Process/Utility/CMakeLists.txt
+++ lldb/unittests/Process/Utility/CMakeLists.txt
@@ -15,9 +15,10 @@
   ${NETBSD_SOURCES})
 
 add_lldb_unittest(ProcessUtilityTests
-  RegisterContextTest.cpp
+  DynamicRegisterInfoTest.cpp
   LinuxProcMapsTest.cpp
   MemoryTagManagerAArch64MTETest.cpp
+  RegisterContextTest.cpp
   ${PLATFORM_SOURCES}
 
   LINK_LIBS
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [PATCH] D109879: [lldb] [DynamicRegisterInfo] Replace value_regs/invalidate_regs in AddRegister()

2021-09-18 Thread Michał Górny via Phabricator via lldb-commits
mgorny updated this revision to Diff 373412.
mgorny retitled this revision from "[lldb] [DynamicRegisterInfo] Update 
RegisterInfo with copy of value_regs/invalidate_regs" to "[lldb] 
[DynamicRegisterInfo] Replace value_regs/invalidate_regs in AddRegister()".
mgorny edited the summary of this revision.
mgorny added a comment.
Herald added a subscriber: mgrang.

Revive. Move sorting & making unique into `AddRegister()`. Add a unittest.


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

https://reviews.llvm.org/D109879

Files:
  lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
  lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.h
  lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp

Index: lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
===
--- lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
+++ lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
@@ -43,6 +43,44 @@
   return regnum++;
 }
 
+TEST(DynamicRegisterInfoTest, add_regs) {
+  DynamicRegisterInfo info;
+
+  // Add regular registers
+  uint32_t b1 = AddRegister(info, "b1", 8);
+  uint32_t b2 = AddRegister(info, "b2", 8);
+
+  // Add a few sub-registers
+  AddRegister(info, "s1", 4, {b1});
+  AddRegister(info, "s2", 4, {b2});
+
+  // Add a register with invalidate_regs
+  uint32_t i1 = AddRegister(info, "i1", 8, {}, {b1});
+
+  // Add a register with indirect invalidate regs to be expanded
+  AddRegister(info, "i2", 4, {b2}, {i1});
+
+  const RegisterInfo *added_reg = info.GetRegisterInfoAtIndex(2);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], b1);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(3);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], b2);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(4);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], b1);
+  EXPECT_EQ(added_reg->invalidate_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(5);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], i1);
+  EXPECT_EQ(added_reg->invalidate_regs[1], LLDB_INVALID_REGNUM);
+}
+
 TEST(DynamicRegisterInfoTest, finalize_regs) {
   DynamicRegisterInfo info;
 
Index: lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.h
===
--- lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.h
+++ lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.h
@@ -35,7 +35,7 @@
   size_t SetRegisterInfo(const lldb_private::StructuredData::Dictionary &dict,
  const lldb_private::ArchSpec &arch);
 
-  void AddRegister(lldb_private::RegisterInfo ®_info,
+  void AddRegister(lldb_private::RegisterInfo reg_info,
lldb_private::ConstString &set_name);
 
   void Finalize(const lldb_private::ArchSpec &arch);
Index: lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
===
--- lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
+++ lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
@@ -395,20 +395,58 @@
   return m_regs.size();
 }
 
-void DynamicRegisterInfo::AddRegister(RegisterInfo ®_info,
+void DynamicRegisterInfo::AddRegister(RegisterInfo reg_info,
   ConstString &set_name) {
   assert(!m_finalized);
   const uint32_t reg_num = m_regs.size();
   assert(reg_info.name);
   uint32_t i;
   if (reg_info.value_regs) {
-for (i = 0; reg_info.value_regs[i] != LLDB_INVALID_REGNUM; ++i)
-  m_value_regs_map[reg_num].push_back(reg_info.value_regs[i]);
+reg_num_collection &value_regs = m_value_regs_map[reg_num];
+
+// copy value_regs into the collection
+for (i = 0;; ++i) {
+  value_regs.push_back(reg_info.value_regs[i]);
+  if (reg_info.value_regs[i] == LLDB_INVALID_REGNUM)
+break;
+}
+
+// sort and unique them
+if (value_regs.size() > 1) {
+  llvm::sort(value_regs.begin(), value_regs.end());
+  reg_num_collection::iterator unique_end =
+  std::unique(value_regs.begin(), value_regs.end());
+  if (unique_end != value_regs.end())
+value_regs.erase(unique_end, value_regs.end());
+}
+assert(!value_regs.empty());
+
+reg_info.value_regs = value_regs.data();
   }
+
   if (reg_info.invalidate_regs) {
-for (i = 0; reg_info.invalidate_regs[i] != LLDB_INVALID_REGNUM; ++i)
-  m_invalidate_regs_map[reg_num].push_back(reg_info.invalidate_regs[i]);
+reg_num_collection &invalidate_regs = m_invalidate_regs_map[reg_num];
+
+// copy invalidate regs into the collection
+for (i = 0;; ++i) {
+  invalidate_regs.push_back(reg_info.invalidate_regs[i]);
+  if (reg_info.invalidate_regs[i] == LLDB_INVALID_

[Lldb-commits] [PATCH] D110023: [lldb] [DynamicRegisterInfo] Add a convenience method to add suppl. registers

2021-09-18 Thread Michał Górny via Phabricator via lldb-commits
mgorny created this revision.
mgorny added reviewers: labath, krytarowski, emaste.
mgorny requested review of this revision.

Add a convenience method to add supplementary registers that takes care
of adding invalidate_regs to all (potentially) overlapping registers.


https://reviews.llvm.org/D110023

Files:
  lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
  lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.h
  lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp

Index: lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
===
--- lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
+++ lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
@@ -134,3 +134,104 @@
   EXPECT_EQ(added_reg->invalidate_regs[1], i1);
   EXPECT_EQ(added_reg->invalidate_regs[2], LLDB_INVALID_REGNUM);
 }
+
+TEST(DynamicRegisterInfoTest, add_supplementary_register) {
+  DynamicRegisterInfo info;
+
+  // Add a base register
+  uint32_t rax = AddRegister(info, "rax", 8);
+
+  // Register numbers
+  uint32_t eax = 1;
+  uint32_t ax = 2;
+  uint32_t ah = 3;
+  uint32_t al = 4;
+
+  ConstString group{"supplementary registers"};
+  uint32_t value_regs[2] = {rax, LLDB_INVALID_REGNUM};
+  struct RegisterInfo eax_reg {
+"eax", nullptr, 4, LLDB_INVALID_INDEX32, lldb::eEncodingUint,
+lldb::eFormatUnsigned,
+{LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, eax,
+ eax},
+value_regs, nullptr, nullptr, 0
+  };
+  info.AddSupplementaryRegister(eax_reg, group);
+
+  struct RegisterInfo ax_reg {
+"ax", nullptr, 2, LLDB_INVALID_INDEX32, lldb::eEncodingUint,
+lldb::eFormatUnsigned,
+{LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, ax, ax},
+value_regs, nullptr, nullptr, 0
+  };
+  info.AddSupplementaryRegister(ax_reg, group);
+
+  struct RegisterInfo ah_reg {
+"ah", nullptr, 1, LLDB_INVALID_INDEX32, lldb::eEncodingUint,
+lldb::eFormatUnsigned,
+{LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, ah, ah},
+value_regs, nullptr, nullptr, 0
+  };
+  info.AddSupplementaryRegister(ah_reg, group);
+
+  struct RegisterInfo al_reg {
+"al", nullptr, 1, LLDB_INVALID_INDEX32, lldb::eEncodingUint,
+lldb::eFormatUnsigned,
+{LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, al, al},
+value_regs, nullptr, nullptr, 0
+  };
+  info.AddSupplementaryRegister(al_reg, group);
+
+  const RegisterInfo *added_reg = info.GetRegisterInfoAtIndex(0);
+  ASSERT_NE(added_reg, nullptr);
+  ASSERT_NE(added_reg->invalidate_regs, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], eax);
+  EXPECT_EQ(added_reg->invalidate_regs[1], ax);
+  EXPECT_EQ(added_reg->invalidate_regs[2], ah);
+  EXPECT_EQ(added_reg->invalidate_regs[3], al);
+  EXPECT_EQ(added_reg->invalidate_regs[4], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(1);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], rax);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+  ASSERT_NE(added_reg->invalidate_regs, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], rax);
+  EXPECT_EQ(added_reg->invalidate_regs[1], ax);
+  EXPECT_EQ(added_reg->invalidate_regs[2], ah);
+  EXPECT_EQ(added_reg->invalidate_regs[3], al);
+  EXPECT_EQ(added_reg->invalidate_regs[4], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(2);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], rax);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+  ASSERT_NE(added_reg->invalidate_regs, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], rax);
+  EXPECT_EQ(added_reg->invalidate_regs[1], eax);
+  EXPECT_EQ(added_reg->invalidate_regs[2], ah);
+  EXPECT_EQ(added_reg->invalidate_regs[3], al);
+  EXPECT_EQ(added_reg->invalidate_regs[4], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(3);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], rax);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+  ASSERT_NE(added_reg->invalidate_regs, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], rax);
+  EXPECT_EQ(added_reg->invalidate_regs[1], eax);
+  EXPECT_EQ(added_reg->invalidate_regs[2], ax);
+  EXPECT_EQ(added_reg->invalidate_regs[3], al);
+  EXPECT_EQ(added_reg->invalidate_regs[4], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(4);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], rax);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+  ASSERT_NE(added_reg->invalidate_regs, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], rax);
+  EXPECT_EQ(added_reg->invalidate_regs[1], eax);
+  EXPECT_EQ(added_reg->invalidate_regs[2], ax);
+  EXPECT_EQ(added_reg->invalidate_regs[3], ah);
+  EXPECT_EQ(added_reg->invalidate_regs[4], LLDB_INVALID_REGNUM);
+}
Index: lldb/source/Plugins/Process/U

[Lldb-commits] [PATCH] D110023: [lldb] [DynamicRegisterInfo] Add a convenience method to add suppl. registers

2021-09-18 Thread Michał Górny via Phabricator via lldb-commits
mgorny added a comment.

Currently it's still using process plugin regnums in 
value_regs/invalidate_regs; I'm going to try changing that next.


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

https://reviews.llvm.org/D110023

___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [PATCH] D110025: [lldb] [gdb-remote] Refactor getting remote regs to use local vector [WIP]

2021-09-18 Thread Michał Górny via Phabricator via lldb-commits
mgorny created this revision.
mgorny added reviewers: labath, krytarowski, emaste.
mgorny requested review of this revision.

Refactor ProcessGDBRemote::GetGDBServerRegisterInfo() and helper
routines to collect remote registers into a local std::vector rather
than adding them straight into DynamicRegisterInfo.  The purpose of this
change is to lay groundwork for switching value_regs and invalidate_regs
to use local LLDB register numbers rather than remote numbers.


https://reviews.llvm.org/D110025

Files:
  lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
  lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h

Index: lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h
===
--- lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h
+++ lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h
@@ -44,6 +44,8 @@
 }
 namespace process_gdb_remote {
 
+struct RemoteRegisterInfo;
+
 class ThreadGDBRemote;
 
 class ProcessGDBRemote : public Process,
@@ -396,8 +398,7 @@
 
   bool GetGDBServerRegisterInfoXMLAndProcess(ArchSpec &arch_to_use,
  std::string xml_filename,
- uint32_t &cur_reg_remote,
- uint32_t &cur_reg_local);
+ std::vector ®isters);
 
   // Query remote GDBServer for register information
   bool GetGDBServerRegisterInfo(ArchSpec &arch);
Index: lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
===
--- lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
+++ lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
@@ -4365,6 +4365,29 @@
   return m_gdb_comm.GetMacCatalystVersion();
 }
 
+namespace lldb_private {
+namespace process_gdb_remote {
+
+struct RemoteRegisterInfo {
+  ConstString name;
+  ConstString alt_name;
+  ConstString set_name;
+  uint32_t byte_size = LLDB_INVALID_INDEX32;
+  uint32_t byte_offset = LLDB_INVALID_INDEX32;
+  lldb::Encoding encoding = eEncodingUint;
+  lldb::Format format = eFormatHex;
+  uint32_t regnum_dwarf = LLDB_INVALID_REGNUM;
+  uint32_t regnum_ehframe = LLDB_INVALID_REGNUM;
+  uint32_t regnum_generic = LLDB_INVALID_REGNUM;
+  uint32_t regnum_remote = LLDB_INVALID_REGNUM;
+  std::vector value_regs;
+  std::vector invalidate_regs;
+  std::vector dwarf_opcode_bytes;
+};
+
+}; // namespace process_gdb_remote
+}; // namespace lldb_private
+
 namespace {
 
 typedef std::vector stringVec;
@@ -4384,53 +4407,24 @@
 };
 
 bool ParseRegisters(XMLNode feature_node, GdbServerTargetInfo &target_info,
-GDBRemoteDynamicRegisterInfo &dyn_reg_info, ABISP abi_sp,
-uint32_t ®_num_remote, uint32_t ®_num_local) {
+std::vector ®isters) {
   if (!feature_node)
 return false;
 
-  uint32_t reg_offset = LLDB_INVALID_INDEX32;
   feature_node.ForEachChildElementWithName(
-  "reg", [&target_info, &dyn_reg_info, ®_num_remote, ®_num_local,
-  ®_offset, &abi_sp](const XMLNode ®_node) -> bool {
+  "reg", [&target_info, ®isters](const XMLNode ®_node) -> bool {
 std::string gdb_group;
 std::string gdb_type;
-ConstString reg_name;
-ConstString alt_name;
-ConstString set_name;
-std::vector value_regs;
-std::vector invalidate_regs;
-std::vector dwarf_opcode_bytes;
+RemoteRegisterInfo reg_info;
 bool encoding_set = false;
 bool format_set = false;
-RegisterInfo reg_info = {
-nullptr,   // Name
-nullptr,   // Alt name
-0, // byte size
-reg_offset,// offset
-eEncodingUint, // encoding
-eFormatHex,// format
-{
-LLDB_INVALID_REGNUM, // eh_frame reg num
-LLDB_INVALID_REGNUM, // DWARF reg num
-LLDB_INVALID_REGNUM, // generic reg num
-reg_num_remote,  // process plugin reg num
-reg_num_local// native register number
-},
-nullptr,
-nullptr,
-nullptr, // Dwarf Expression opcode bytes pointer
-0// Dwarf Expression opcode bytes length
-};
 
-reg_node.ForEachAttribute([&target_info, &gdb_group, &gdb_type,
-   ®_name, &alt_name, &set_name, &value_regs,
-   &invalidate_regs, &encoding_set, &format_set,
-   ®_info, ®_offset, &dwarf_opcode_bytes](
+reg_node.ForEachAttribute([&target_info, &gdb_group, &gdb_type, &encoding_set, &format_set,
+   ®_info](
   const llvm::StringRef &name,
   const llvm::StringRef &value) 

[Lldb-commits] [PATCH] D110025: [lldb] [gdb-remote] Refactor getting remote regs to use local vector [WIP]

2021-09-18 Thread Michał Górny via Phabricator via lldb-commits
mgorny added a comment.

@labath, please tell me if you like this design. If it's ok, I'm going to 
convert the other routine to it, then move the conversion to 
`DynamicRegisterInfo` into a common function.

(also I haven't reformatted the code yet)


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

https://reviews.llvm.org/D110025

___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [PATCH] D109879: [lldb] [DynamicRegisterInfo] Replace value_regs/invalidate_regs in AddRegister()

2021-09-18 Thread Michał Górny via Phabricator via lldb-commits
mgorny updated this revision to Diff 373426.
mgorny added a comment.

clang-format


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

https://reviews.llvm.org/D109879

Files:
  lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
  lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.h
  lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp

Index: lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
===
--- lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
+++ lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
@@ -43,6 +43,44 @@
   return regnum++;
 }
 
+TEST(DynamicRegisterInfoTest, add_regs) {
+  DynamicRegisterInfo info;
+
+  // Add regular registers
+  uint32_t b1 = AddRegister(info, "b1", 8);
+  uint32_t b2 = AddRegister(info, "b2", 8);
+
+  // Add a few sub-registers
+  AddRegister(info, "s1", 4, {b1});
+  AddRegister(info, "s2", 4, {b2});
+
+  // Add a register with invalidate_regs
+  uint32_t i1 = AddRegister(info, "i1", 8, {}, {b1});
+
+  // Add a register with indirect invalidate regs to be expanded
+  AddRegister(info, "i2", 4, {b2}, {i1});
+
+  const RegisterInfo *added_reg = info.GetRegisterInfoAtIndex(2);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], b1);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(3);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], b2);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(4);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], b1);
+  EXPECT_EQ(added_reg->invalidate_regs[1], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(5);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], i1);
+  EXPECT_EQ(added_reg->invalidate_regs[1], LLDB_INVALID_REGNUM);
+}
+
 TEST(DynamicRegisterInfoTest, finalize_regs) {
   DynamicRegisterInfo info;
 
Index: lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.h
===
--- lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.h
+++ lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.h
@@ -35,7 +35,7 @@
   size_t SetRegisterInfo(const lldb_private::StructuredData::Dictionary &dict,
  const lldb_private::ArchSpec &arch);
 
-  void AddRegister(lldb_private::RegisterInfo ®_info,
+  void AddRegister(lldb_private::RegisterInfo reg_info,
lldb_private::ConstString &set_name);
 
   void Finalize(const lldb_private::ArchSpec &arch);
Index: lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
===
--- lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
+++ lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
@@ -395,20 +395,58 @@
   return m_regs.size();
 }
 
-void DynamicRegisterInfo::AddRegister(RegisterInfo ®_info,
+void DynamicRegisterInfo::AddRegister(RegisterInfo reg_info,
   ConstString &set_name) {
   assert(!m_finalized);
   const uint32_t reg_num = m_regs.size();
   assert(reg_info.name);
   uint32_t i;
   if (reg_info.value_regs) {
-for (i = 0; reg_info.value_regs[i] != LLDB_INVALID_REGNUM; ++i)
-  m_value_regs_map[reg_num].push_back(reg_info.value_regs[i]);
+reg_num_collection &value_regs = m_value_regs_map[reg_num];
+
+// copy value_regs into the collection
+for (i = 0;; ++i) {
+  value_regs.push_back(reg_info.value_regs[i]);
+  if (reg_info.value_regs[i] == LLDB_INVALID_REGNUM)
+break;
+}
+
+// sort and unique them
+if (value_regs.size() > 1) {
+  llvm::sort(value_regs.begin(), value_regs.end());
+  reg_num_collection::iterator unique_end =
+  std::unique(value_regs.begin(), value_regs.end());
+  if (unique_end != value_regs.end())
+value_regs.erase(unique_end, value_regs.end());
+}
+assert(!value_regs.empty());
+
+reg_info.value_regs = value_regs.data();
   }
+
   if (reg_info.invalidate_regs) {
-for (i = 0; reg_info.invalidate_regs[i] != LLDB_INVALID_REGNUM; ++i)
-  m_invalidate_regs_map[reg_num].push_back(reg_info.invalidate_regs[i]);
+reg_num_collection &invalidate_regs = m_invalidate_regs_map[reg_num];
+
+// copy invalidate regs into the collection
+for (i = 0;; ++i) {
+  invalidate_regs.push_back(reg_info.invalidate_regs[i]);
+  if (reg_info.invalidate_regs[i] == LLDB_INVALID_REGNUM)
+break;
+}
+
+// sort and unique them
+if (invalidate_regs.size() > 1) {
+  llvm::sort(invalidate_regs.begin(), invalidate_regs.end());
+  reg_num_collection::iterator unique_end =
+  std::unique(invalidate_regs.begin(), invalidate_regs.end());
+  if (unique_end != invalidate_regs.end())
+invalidate

[Lldb-commits] [PATCH] D110023: [lldb] [DynamicRegisterInfo] Add a convenience method to add suppl. registers

2021-09-18 Thread Michał Górny via Phabricator via lldb-commits
mgorny updated this revision to Diff 373427.
mgorny added a comment.

clang-format


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

https://reviews.llvm.org/D110023

Files:
  lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
  lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.h
  lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp

Index: lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
===
--- lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
+++ lldb/unittests/Process/Utility/DynamicRegisterInfoTest.cpp
@@ -134,3 +134,104 @@
   EXPECT_EQ(added_reg->invalidate_regs[1], i1);
   EXPECT_EQ(added_reg->invalidate_regs[2], LLDB_INVALID_REGNUM);
 }
+
+TEST(DynamicRegisterInfoTest, add_supplementary_register) {
+  DynamicRegisterInfo info;
+
+  // Add a base register
+  uint32_t rax = AddRegister(info, "rax", 8);
+
+  // Register numbers
+  uint32_t eax = 1;
+  uint32_t ax = 2;
+  uint32_t ah = 3;
+  uint32_t al = 4;
+
+  ConstString group{"supplementary registers"};
+  uint32_t value_regs[2] = {rax, LLDB_INVALID_REGNUM};
+  struct RegisterInfo eax_reg {
+"eax", nullptr, 4, LLDB_INVALID_INDEX32, lldb::eEncodingUint,
+lldb::eFormatUnsigned,
+{LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, eax,
+ eax},
+value_regs, nullptr, nullptr, 0
+  };
+  info.AddSupplementaryRegister(eax_reg, group);
+
+  struct RegisterInfo ax_reg {
+"ax", nullptr, 2, LLDB_INVALID_INDEX32, lldb::eEncodingUint,
+lldb::eFormatUnsigned,
+{LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, ax, ax},
+value_regs, nullptr, nullptr, 0
+  };
+  info.AddSupplementaryRegister(ax_reg, group);
+
+  struct RegisterInfo ah_reg {
+"ah", nullptr, 1, LLDB_INVALID_INDEX32, lldb::eEncodingUint,
+lldb::eFormatUnsigned,
+{LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, ah, ah},
+value_regs, nullptr, nullptr, 0
+  };
+  info.AddSupplementaryRegister(ah_reg, group);
+
+  struct RegisterInfo al_reg {
+"al", nullptr, 1, LLDB_INVALID_INDEX32, lldb::eEncodingUint,
+lldb::eFormatUnsigned,
+{LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, LLDB_INVALID_REGNUM, al, al},
+value_regs, nullptr, nullptr, 0
+  };
+  info.AddSupplementaryRegister(al_reg, group);
+
+  const RegisterInfo *added_reg = info.GetRegisterInfoAtIndex(0);
+  ASSERT_NE(added_reg, nullptr);
+  ASSERT_NE(added_reg->invalidate_regs, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], eax);
+  EXPECT_EQ(added_reg->invalidate_regs[1], ax);
+  EXPECT_EQ(added_reg->invalidate_regs[2], ah);
+  EXPECT_EQ(added_reg->invalidate_regs[3], al);
+  EXPECT_EQ(added_reg->invalidate_regs[4], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(1);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], rax);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+  ASSERT_NE(added_reg->invalidate_regs, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], rax);
+  EXPECT_EQ(added_reg->invalidate_regs[1], ax);
+  EXPECT_EQ(added_reg->invalidate_regs[2], ah);
+  EXPECT_EQ(added_reg->invalidate_regs[3], al);
+  EXPECT_EQ(added_reg->invalidate_regs[4], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(2);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], rax);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+  ASSERT_NE(added_reg->invalidate_regs, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], rax);
+  EXPECT_EQ(added_reg->invalidate_regs[1], eax);
+  EXPECT_EQ(added_reg->invalidate_regs[2], ah);
+  EXPECT_EQ(added_reg->invalidate_regs[3], al);
+  EXPECT_EQ(added_reg->invalidate_regs[4], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(3);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], rax);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+  ASSERT_NE(added_reg->invalidate_regs, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], rax);
+  EXPECT_EQ(added_reg->invalidate_regs[1], eax);
+  EXPECT_EQ(added_reg->invalidate_regs[2], ax);
+  EXPECT_EQ(added_reg->invalidate_regs[3], al);
+  EXPECT_EQ(added_reg->invalidate_regs[4], LLDB_INVALID_REGNUM);
+
+  added_reg = info.GetRegisterInfoAtIndex(4);
+  ASSERT_NE(added_reg, nullptr);
+  EXPECT_EQ(added_reg->value_regs[0], rax);
+  EXPECT_EQ(added_reg->value_regs[1], LLDB_INVALID_REGNUM);
+  ASSERT_NE(added_reg->invalidate_regs, nullptr);
+  EXPECT_EQ(added_reg->invalidate_regs[0], rax);
+  EXPECT_EQ(added_reg->invalidate_regs[1], eax);
+  EXPECT_EQ(added_reg->invalidate_regs[2], ax);
+  EXPECT_EQ(added_reg->invalidate_regs[3], ah);
+  EXPECT_EQ(added_reg->invalidate_regs[4], LLDB_INVALID_REGNUM);
+}
Index: lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.h
===
--- lldb/source/Plugi

[Lldb-commits] [PATCH] D110027: [lldb] [gdb-remote] Use local regnos for value_regs/invalidate_regs

2021-09-18 Thread Michał Górny via Phabricator via lldb-commits
mgorny created this revision.
mgorny added reviewers: labath, krytarowski, emaste.
mgorny requested review of this revision.

Switch the gdb-remote client logic to use local (LLDB) register numbers
in value_regs/invalidate_regs rather than remote regnos.  This involves
translating regnos received from lldb-server.


https://reviews.llvm.org/D110027

Files:
  lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
  lldb/source/Plugins/Process/gdb-remote/GDBRemoteRegisterContext.cpp
  lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp


Index: lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
===
--- lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
+++ lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
@@ -4680,10 +4680,29 @@
 
 uint32_t local_regnum = 0;
 uint32_t remote_regnum = 0;
+std::map remote_to_local_map;
 for (RemoteRegisterInfo& remote_reg_info : registers) {
-  // Use remote regnum if available, previous remote regnum + 1 when not.
-  if (remote_reg_info.regnum_remote != LLDB_INVALID_REGNUM)
-remote_regnum = remote_reg_info.regnum_remote;
+  // Assign successive remote regnums if missing.
+  if (remote_reg_info.regnum_remote == LLDB_INVALID_REGNUM)
+remote_reg_info.regnum_remote = remote_regnum;
+
+  // Create a mapping from remote to local regnos.
+  remote_to_local_map[remote_reg_info.regnum_remote] = local_regnum++;
+
+  remote_regnum = remote_reg_info.regnum_remote + 1;
+}
+
+local_regnum = 0;
+for (RemoteRegisterInfo& remote_reg_info : registers) {
+  // Translate value_regs and invalidate_regs to local regnums
+  for (uint32_t &x : remote_reg_info.value_regs) {
+if (x != LLDB_INVALID_REGNUM)
+  x = remote_to_local_map[x];
+  }
+  for (uint32_t &x : remote_reg_info.invalidate_regs) {
+if (x != LLDB_INVALID_REGNUM)
+  x = remote_to_local_map[x];
+  }
 
   struct RegisterInfo reg_info{
   remote_reg_info.name.AsCString(),
@@ -4695,7 +4714,7 @@
   { remote_reg_info.regnum_ehframe,
 remote_reg_info.regnum_dwarf,
 remote_reg_info.regnum_generic,
-remote_regnum++,
+remote_reg_info.regnum_remote,
 local_regnum++ },
   remote_reg_info.value_regs.data(),
   remote_reg_info.invalidate_regs.data(),
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
@@ -254,7 +254,7 @@
 // We have a valid primordial register as our constituent. Grab the
 // corresponding register info.
 const RegisterInfo *prim_reg_info =
-GetRegisterInfo(eRegisterKindProcessPlugin, prim_reg);
+GetRegisterInfo(eRegisterKindLLDB, prim_reg);
 if (prim_reg_info == nullptr)
   success = false;
 else {
@@ -401,7 +401,7 @@
 // We have a valid primordial register as our constituent. Grab the
 // corresponding register info.
 const RegisterInfo *value_reg_info =
-GetRegisterInfo(eRegisterKindProcessPlugin, reg);
+GetRegisterInfo(eRegisterKindLLDB, reg);
 if (value_reg_info == nullptr)
   success = false;
 else
@@ -422,7 +422,7 @@
reg != LLDB_INVALID_REGNUM;
reg = reg_info->invalidate_regs[++idx])
 SetRegisterIsValid(ConvertRegisterKindToRegisterNumber(
-   eRegisterKindProcessPlugin, reg),
+   eRegisterKindLLDB, reg),
false);
 }
 
Index: lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
===
--- lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
+++ lldb/source/Plugins/Process/Utility/DynamicRegisterInfo.cpp
@@ -655,9 +655,7 @@
   if (reg.byte_offset == LLDB_INVALID_INDEX32) {
 uint32_t value_regnum = reg.value_regs[0];
 if (value_regnum != LLDB_INVALID_INDEX32)
-  reg.byte_offset =
-  GetRegisterInfoAtIndex(remote_to_local_regnum_map[value_regnum])
-  ->byte_offset;
+  reg.byte_offset = GetRegisterInfoAtIndex(value_regnum)->byte_offset;
   }
 }
 


Index: lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
===
--- lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
+++ lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
@@ -4680,10 +4680,29 @@
 
 uint32_t local_regnum = 0;
 uint32_t remote_regnum = 0;
+std::map remote_to_lo