[Lldb-commits] [lldb] [lldb][debugserver] Read/write SME registers on arm64 (PR #119171)

David Spickett via lldb-commits lldb-commits at lists.llvm.org
Mon Dec 9 07:01:02 PST 2024


================
@@ -2106,29 +2345,220 @@ const DNBRegisterInfo DNBArchMachARM64::g_exc_registers[] = {
 // Number of registers in each register set
 const size_t DNBArchMachARM64::k_num_gpr_registers =
     sizeof(g_gpr_registers) / sizeof(DNBRegisterInfo);
-const size_t DNBArchMachARM64::k_num_vfp_registers =
-    sizeof(g_vfp_registers) / sizeof(DNBRegisterInfo);
 const size_t DNBArchMachARM64::k_num_exc_registers =
     sizeof(g_exc_registers) / sizeof(DNBRegisterInfo);
-const size_t DNBArchMachARM64::k_num_all_registers =
-    k_num_gpr_registers + k_num_vfp_registers + k_num_exc_registers;
-
-// Register set definitions. The first definitions at register set index
-// of zero is for all registers, followed by other registers sets. The
-// register information for the all register set need not be filled in.
-const DNBRegisterSetInfo DNBArchMachARM64::g_reg_sets[] = {
-    {"ARM64 Registers", NULL, k_num_all_registers},
-    {"General Purpose Registers", g_gpr_registers, k_num_gpr_registers},
-    {"Floating Point Registers", g_vfp_registers, k_num_vfp_registers},
-    {"Exception State Registers", g_exc_registers, k_num_exc_registers}};
-// Total number of register sets for this architecture
-const size_t DNBArchMachARM64::k_num_register_sets =
-    sizeof(g_reg_sets) / sizeof(DNBRegisterSetInfo);
 
+static std::vector<DNBRegisterInfo> g_sve_registers;
+static void initialize_sve_registers() {
+  static const char *g_z_regnames[32] = {
+      "z0",  "z1",  "z2",  "z3",  "z4",  "z5",  "z6",  "z7",
+      "z8",  "z9",  "z10", "z11", "z12", "z13", "z14", "z15",
+      "z16", "z17", "z18", "z19", "z20", "z21", "z22", "z23",
+      "z24", "z25", "z26", "z27", "z28", "z29", "z30", "z31"};
+  static const char *g_p_regnames[16] = {
+      "p0", "p1", "p2",  "p3",  "p4",  "p5",  "p6",  "p7",
+      "p8", "p9", "p10", "p11", "p12", "p13", "p14", "p15"};
+
+  if (DNBArchMachARM64::CPUHasSME()) {
+    uint32_t svl_bytes = DNBArchMachARM64::GetSMEMaxSVL();
+    for (uint32_t i = 0; i < 32; i++) {
+      g_sve_registers.push_back(
+          {DNBArchMachARM64::e_regSetSVE, (uint32_t)sve_z0 + i, g_z_regnames[i],
+           NULL, Vector, VectorOfUInt8, svl_bytes,
+           static_cast<uint32_t>(SVE_OFFSET_Z_IDX(i)), INVALID_NUB_REGNUM,
+           INVALID_NUB_REGNUM, INVALID_NUB_REGNUM,
+           (uint32_t)debugserver_sve_z0 + i, NULL, g_invalidate_z[i]});
+    }
+    for (uint32_t i = 0; i < 16; i++) {
+      g_sve_registers.push_back(
+          {DNBArchMachARM64::e_regSetSVE, (uint32_t)sve_p0 + i, g_p_regnames[i],
+           NULL, Vector, VectorOfUInt8, svl_bytes / 8,
+           (uint32_t)SVE_OFFSET_P_IDX(i), INVALID_NUB_REGNUM,
+           INVALID_NUB_REGNUM, INVALID_NUB_REGNUM,
+           (uint32_t)debugserver_sve_p0 + i, NULL, NULL});
+    }
+  }
+}
+
+static std::vector<DNBRegisterInfo> g_vfp_registers;
+static void initialize_vfp_registers() {
+  static const char *g_v_regnames[32] = {
+      "v0",  "v1",  "v2",  "v3",  "v4",  "v5",  "v6",  "v7",
+      "v8",  "v9",  "v10", "v11", "v12", "v13", "v14", "v15",
+      "v16", "v17", "v18", "v19", "v20", "v21", "v22", "v23",
+      "v24", "v25", "v26", "v27", "v28", "v29", "v30", "v31"};
+  static const char *g_q_regnames[32] = {
+      "q0",  "q1",  "q2",  "q3",  "q4",  "q5",  "q6",  "q7",
+      "q8",  "q9",  "q10", "q11", "q12", "q13", "q14", "q15",
+      "q16", "q17", "q18", "q19", "q20", "q21", "q22", "q23",
+      "q24", "q25", "q26", "q27", "q28", "q29", "q30", "q31"};
+
+  static const char *g_d_regnames[32] = {
+      "d0",  "d1",  "d2",  "d3",  "d4",  "d5",  "d6",  "d7",
+      "d8",  "d9",  "d10", "d11", "d12", "d13", "d14", "d15",
+      "d16", "d17", "d18", "d19", "d20", "d21", "d22", "d23",
+      "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31"};
+
+  static const char *g_s_regnames[32] = {
+      "s0",  "s1",  "s2",  "s3",  "s4",  "s5",  "s6",  "s7",
+      "s8",  "s9",  "s10", "s11", "s12", "s13", "s14", "s15",
+      "s16", "s17", "s18", "s19", "s20", "s21", "s22", "s23",
+      "s24", "s25", "s26", "s27", "s28", "s29", "s30", "s31"};
+
+  for (uint32_t i = 0; i < 32; i++)
+    if (DNBArchMachARM64::CPUHasSME())
+      g_vfp_registers.push_back(
+          {DNBArchMachARM64::e_regSetVFP, (uint32_t)vfp_v0 + i, g_v_regnames[i],
+           g_q_regnames[i], Vector, VectorOfUInt8, 16,
+           static_cast<uint32_t>(VFP_V_OFFSET_IDX(i)), INVALID_NUB_REGNUM,
+           (uint32_t)dwarf_v0 + i, INVALID_NUB_REGNUM,
+           (uint32_t)debugserver_vfp_v0 + i, NULL, g_invalidate_z[i]});
+    else
+      g_vfp_registers.push_back(
+          {DNBArchMachARM64::e_regSetVFP, (uint32_t)vfp_v0 + i, g_v_regnames[i],
+           g_q_regnames[i], Vector, VectorOfUInt8, 16,
+           static_cast<uint32_t>(VFP_V_OFFSET_IDX(i)), INVALID_NUB_REGNUM,
+           (uint32_t)dwarf_v0 + i, INVALID_NUB_REGNUM,
+           (uint32_t)debugserver_vfp_v0 + i, NULL, g_invalidate_v[i]});
+
+  g_vfp_registers.push_back(
+      {DNBArchMachARM64::e_regSetVFP, vfp_fpsr, "fpsr", NULL, Uint, Hex, 4,
+       VFP_V_OFFSET_IDX(32) + 0, INVALID_NUB_REGNUM, INVALID_NUB_REGNUM,
+       INVALID_NUB_REGNUM, INVALID_NUB_REGNUM, NULL, NULL});
+  g_vfp_registers.push_back(
+      {DNBArchMachARM64::e_regSetVFP, vfp_fpcr, "fpcr", NULL, Uint, Hex, 4,
+       VFP_V_OFFSET_IDX(32) + 4, INVALID_NUB_REGNUM, INVALID_NUB_REGNUM,
+       INVALID_NUB_REGNUM, INVALID_NUB_REGNUM, NULL, NULL});
+
+  for (uint32_t i = 0; i < 32; i++)
+    if (DNBArchMachARM64::CPUHasSME())
+      g_vfp_registers.push_back(
+          {DNBArchMachARM64::e_regSetVFP, (uint32_t)vfp_d0 + i, g_d_regnames[i],
+           NULL, IEEE754, Float, 8, 0, INVALID_NUB_REGNUM, INVALID_NUB_REGNUM,
+           INVALID_NUB_REGNUM, INVALID_NUB_REGNUM, NULL, g_invalidate_z[i]});
+    else
+      g_vfp_registers.push_back(
+          {DNBArchMachARM64::e_regSetVFP, (uint32_t)vfp_d0 + i, g_d_regnames[i],
+           NULL, IEEE754, Float, 8, 0, INVALID_NUB_REGNUM, INVALID_NUB_REGNUM,
+           INVALID_NUB_REGNUM, INVALID_NUB_REGNUM, NULL, g_invalidate_v[i]});
----------------
DavidSpickett wrote:

You could set a pointer `const T *invalidates = CPUHasSME() ? x : y;` and use that. Removes a large if/else.

https://github.com/llvm/llvm-project/pull/119171


More information about the lldb-commits mailing list