kernel can potentially be tagged addresses. */
struct gdbarch *gdbarch = thread_architecture (inferior_ptid);
const CORE_ADDR addr_trap
- = gdbarch_remove_non_address_bits (gdbarch, (CORE_ADDR) siginfo.si_addr);
+ = aarch64_remove_non_address_bits (gdbarch, (CORE_ADDR) siginfo.si_addr);
/* Check if the address matches any watched address. */
state = aarch64_get_debug_reg_state (inferior_ptid.pid ());
aarch64_linux_tagged_address_p (struct gdbarch *gdbarch, CORE_ADDR address)
{
/* Remove the top byte for the memory range check. */
- address = gdbarch_remove_non_address_bits (gdbarch, address);
+ address = aarch64_remove_non_address_bits (gdbarch, address);
/* Check if the page that contains ADDRESS is mapped with PROT_MTE. */
if (!linux_address_in_memtag_page (address))
uiout->text ("\n");
std::optional<CORE_ADDR> atag
- = aarch64_mte_get_atag (gdbarch_remove_non_address_bits (gdbarch,
- fault_addr));
+ = aarch64_mte_get_atag (
+ aarch64_remove_non_address_bits (gdbarch, fault_addr));
+
gdb_byte ltag = aarch64_mte_get_ltag (fault_addr);
if (!atag.has_value ())
/* Fetch the allocation tag for ADDRESS. */
std::optional<CORE_ADDR> atag
- = aarch64_mte_get_atag (gdbarch_remove_non_address_bits (gdbarch, addr));
+ = aarch64_mte_get_atag (aarch64_remove_non_address_bits (gdbarch, addr));
if (!atag.has_value ())
return true;
else
{
/* Remove the top byte. */
- addr = gdbarch_remove_non_address_bits (gdbarch, addr);
+ addr = aarch64_remove_non_address_bits (gdbarch, addr);
/* With G being the number of tag granules and N the number of tags
passed in, we can have the following cases:
else
{
/* Remove the top byte. */
- addr = gdbarch_remove_non_address_bits (gdbarch, addr);
+ addr = aarch64_remove_non_address_bits (gdbarch, addr);
std::optional<CORE_ADDR> atag = aarch64_mte_get_atag (addr);
if (!atag.has_value ())
return string_printf ("0x%s", phex_nz (tag, sizeof (tag)));
}
-/* AArch64 implementation of the remove_non_address_bits gdbarch hook. Remove
- non address bits from a pointer value. */
+/* See aarch64-tdep.h. */
-static CORE_ADDR
+CORE_ADDR
aarch64_remove_non_address_bits (struct gdbarch *gdbarch, CORE_ADDR pointer)
{
/* By default, we assume TBI and discard the top 8 bits plus the VA range
tdep->ra_sign_state_regnum = ra_sign_state_offset + num_regs;
/* Architecture hook to remove bits of a pointer that are not part of the
- address, like memory tags (MTE) and pointer authentication signatures. */
- set_gdbarch_remove_non_address_bits (gdbarch,
- aarch64_remove_non_address_bits);
+ address, like memory tags (MTE) and pointer authentication signatures.
+ Configure address adjustment for watchpoints, breakpoints and memory
+ transfer. */
+ set_gdbarch_remove_non_address_bits_watchpoint
+ (gdbarch, aarch64_remove_non_address_bits);
+ set_gdbarch_remove_non_address_bits_breakpoint
+ (gdbarch, aarch64_remove_non_address_bits);
+ set_gdbarch_remove_non_address_bits_memory
+ (gdbarch, aarch64_remove_non_address_bits);
/* SME pseudo-registers. */
if (tdep->has_sme ())
std::optional<CORE_ADDR> aarch64_mte_get_atag (CORE_ADDR address);
+/* AArch64 implementation of the remove_non_address_bits gdbarch hooks.
+ Remove non address bits from a pointer value. */
+
+CORE_ADDR aarch64_remove_non_address_bits (struct gdbarch *gdbarch,
+ CORE_ADDR pointer);
+
#endif /* aarch64-tdep.h */
loc->gdbarch = v->type ()->arch ();
loc->pspace = wp_pspace;
loc->address
- = gdbarch_remove_non_address_bits (loc->gdbarch, addr);
+ = gdbarch_remove_non_address_bits_watchpoint (loc->gdbarch,
+ addr);
b->add_location (*loc);
if (bitsize != 0)
}
adjusted_bpaddr
- = gdbarch_remove_non_address_bits (gdbarch, adjusted_bpaddr);
+ = gdbarch_remove_non_address_bits_breakpoint (gdbarch, adjusted_bpaddr);
/* An adjusted breakpoint address can significantly alter
a user's expectations. Print a warning if an adjustment
int frame_red_zone_size = 0;
gdbarch_convert_from_func_ptr_addr_ftype *convert_from_func_ptr_addr = convert_from_func_ptr_addr_identity;
gdbarch_addr_bits_remove_ftype *addr_bits_remove = core_addr_identity;
- gdbarch_remove_non_address_bits_ftype *remove_non_address_bits = default_remove_non_address_bits;
+ gdbarch_remove_non_address_bits_watchpoint_ftype *remove_non_address_bits_watchpoint = default_remove_non_address_bits;
+ gdbarch_remove_non_address_bits_breakpoint_ftype *remove_non_address_bits_breakpoint = default_remove_non_address_bits;
+ gdbarch_remove_non_address_bits_memory_ftype *remove_non_address_bits_memory = default_remove_non_address_bits;
gdbarch_memtag_to_string_ftype *memtag_to_string = default_memtag_to_string;
gdbarch_tagged_address_p_ftype *tagged_address_p = default_tagged_address_p;
gdbarch_memtag_matches_p_ftype *memtag_matches_p = default_memtag_matches_p;
/* Skip verify of frame_red_zone_size, invalid_p == 0. */
/* Skip verify of convert_from_func_ptr_addr, invalid_p == 0. */
/* Skip verify of addr_bits_remove, invalid_p == 0. */
- /* Skip verify of remove_non_address_bits, invalid_p == 0. */
+ /* Skip verify of remove_non_address_bits_watchpoint, invalid_p == 0. */
+ /* Skip verify of remove_non_address_bits_breakpoint, invalid_p == 0. */
+ /* Skip verify of remove_non_address_bits_memory, invalid_p == 0. */
/* Skip verify of memtag_to_string, invalid_p == 0. */
/* Skip verify of tagged_address_p, invalid_p == 0. */
/* Skip verify of memtag_matches_p, invalid_p == 0. */
"gdbarch_dump: addr_bits_remove = <%s>\n",
host_address_to_string (gdbarch->addr_bits_remove));
gdb_printf (file,
- "gdbarch_dump: remove_non_address_bits = <%s>\n",
- host_address_to_string (gdbarch->remove_non_address_bits));
+ "gdbarch_dump: remove_non_address_bits_watchpoint = <%s>\n",
+ host_address_to_string (gdbarch->remove_non_address_bits_watchpoint));
+ gdb_printf (file,
+ "gdbarch_dump: remove_non_address_bits_breakpoint = <%s>\n",
+ host_address_to_string (gdbarch->remove_non_address_bits_breakpoint));
+ gdb_printf (file,
+ "gdbarch_dump: remove_non_address_bits_memory = <%s>\n",
+ host_address_to_string (gdbarch->remove_non_address_bits_memory));
gdb_printf (file,
"gdbarch_dump: memtag_to_string = <%s>\n",
host_address_to_string (gdbarch->memtag_to_string));
}
CORE_ADDR
-gdbarch_remove_non_address_bits (struct gdbarch *gdbarch, CORE_ADDR pointer)
+gdbarch_remove_non_address_bits_watchpoint (struct gdbarch *gdbarch, CORE_ADDR pointer)
+{
+ gdb_assert (gdbarch != NULL);
+ gdb_assert (gdbarch->remove_non_address_bits_watchpoint != NULL);
+ if (gdbarch_debug >= 2)
+ gdb_printf (gdb_stdlog, "gdbarch_remove_non_address_bits_watchpoint called\n");
+ return gdbarch->remove_non_address_bits_watchpoint (gdbarch, pointer);
+}
+
+void
+set_gdbarch_remove_non_address_bits_watchpoint (struct gdbarch *gdbarch,
+ gdbarch_remove_non_address_bits_watchpoint_ftype remove_non_address_bits_watchpoint)
+{
+ gdbarch->remove_non_address_bits_watchpoint = remove_non_address_bits_watchpoint;
+}
+
+CORE_ADDR
+gdbarch_remove_non_address_bits_breakpoint (struct gdbarch *gdbarch, CORE_ADDR pointer)
+{
+ gdb_assert (gdbarch != NULL);
+ gdb_assert (gdbarch->remove_non_address_bits_breakpoint != NULL);
+ if (gdbarch_debug >= 2)
+ gdb_printf (gdb_stdlog, "gdbarch_remove_non_address_bits_breakpoint called\n");
+ return gdbarch->remove_non_address_bits_breakpoint (gdbarch, pointer);
+}
+
+void
+set_gdbarch_remove_non_address_bits_breakpoint (struct gdbarch *gdbarch,
+ gdbarch_remove_non_address_bits_breakpoint_ftype remove_non_address_bits_breakpoint)
+{
+ gdbarch->remove_non_address_bits_breakpoint = remove_non_address_bits_breakpoint;
+}
+
+CORE_ADDR
+gdbarch_remove_non_address_bits_memory (struct gdbarch *gdbarch, CORE_ADDR pointer)
{
gdb_assert (gdbarch != NULL);
- gdb_assert (gdbarch->remove_non_address_bits != NULL);
+ gdb_assert (gdbarch->remove_non_address_bits_memory != NULL);
if (gdbarch_debug >= 2)
- gdb_printf (gdb_stdlog, "gdbarch_remove_non_address_bits called\n");
- return gdbarch->remove_non_address_bits (gdbarch, pointer);
+ gdb_printf (gdb_stdlog, "gdbarch_remove_non_address_bits_memory called\n");
+ return gdbarch->remove_non_address_bits_memory (gdbarch, pointer);
}
void
-set_gdbarch_remove_non_address_bits (struct gdbarch *gdbarch,
- gdbarch_remove_non_address_bits_ftype remove_non_address_bits)
+set_gdbarch_remove_non_address_bits_memory (struct gdbarch *gdbarch,
+ gdbarch_remove_non_address_bits_memory_ftype remove_non_address_bits_memory)
{
- gdbarch->remove_non_address_bits = remove_non_address_bits;
+ gdbarch->remove_non_address_bits_memory = remove_non_address_bits_memory;
}
std::string
extern void set_gdbarch_addr_bits_remove (struct gdbarch *gdbarch, gdbarch_addr_bits_remove_ftype *addr_bits_remove);
/* On some architectures, not all bits of a pointer are significant.
- On AArch64, for example, the top bits of a pointer may carry a "tag", which
- can be ignored by the kernel and the hardware. The "tag" can be regarded as
- additional data associated with the pointer, but it is not part of the address.
+ On AArch64 and amd64, for example, the top bits of a pointer may carry a
+ "tag", which can be ignored by the kernel and the hardware. The "tag" can be
+ regarded as additional data associated with the pointer, but it is not part
+ of the address.
Given a pointer for the architecture, this hook removes all the
- non-significant bits and sign-extends things as needed. It gets used to remove
- non-address bits from data pointers (for example, removing the AArch64 MTE tag
- bits from a pointer) and from code pointers (removing the AArch64 PAC signature
- from a pointer containing the return address). */
-
-typedef CORE_ADDR (gdbarch_remove_non_address_bits_ftype) (struct gdbarch *gdbarch, CORE_ADDR pointer);
-extern CORE_ADDR gdbarch_remove_non_address_bits (struct gdbarch *gdbarch, CORE_ADDR pointer);
-extern void set_gdbarch_remove_non_address_bits (struct gdbarch *gdbarch, gdbarch_remove_non_address_bits_ftype *remove_non_address_bits);
+ non-significant bits and sign-extends things as needed. It gets used to
+ remove non-address bits from pointers used for watchpoints. */
+
+typedef CORE_ADDR (gdbarch_remove_non_address_bits_watchpoint_ftype) (struct gdbarch *gdbarch, CORE_ADDR pointer);
+extern CORE_ADDR gdbarch_remove_non_address_bits_watchpoint (struct gdbarch *gdbarch, CORE_ADDR pointer);
+extern void set_gdbarch_remove_non_address_bits_watchpoint (struct gdbarch *gdbarch, gdbarch_remove_non_address_bits_watchpoint_ftype *remove_non_address_bits_watchpoint);
+
+/* On some architectures, not all bits of a pointer are significant.
+ On AArch64 and amd64, for example, the top bits of a pointer may carry a
+ "tag", which can be ignored by the kernel and the hardware. The "tag" can be
+ regarded as additional data associated with the pointer, but it is not part
+ of the address.
+
+ Given a pointer for the architecture, this hook removes all the
+ non-significant bits and sign-extends things as needed. It gets used to
+ remove non-address bits from pointers used for breakpoints. */
+
+typedef CORE_ADDR (gdbarch_remove_non_address_bits_breakpoint_ftype) (struct gdbarch *gdbarch, CORE_ADDR pointer);
+extern CORE_ADDR gdbarch_remove_non_address_bits_breakpoint (struct gdbarch *gdbarch, CORE_ADDR pointer);
+extern void set_gdbarch_remove_non_address_bits_breakpoint (struct gdbarch *gdbarch, gdbarch_remove_non_address_bits_breakpoint_ftype *remove_non_address_bits_breakpoint);
+
+/* On some architectures, not all bits of a pointer are significant.
+ On AArch64 and amd64, for example, the top bits of a pointer may carry a
+ "tag", which can be ignored by the kernel and the hardware. The "tag" can be
+ regarded as additional data associated with the pointer, but it is not part
+ of the address.
+
+ Given a pointer for the architecture, this hook removes all the
+ non-significant bits and sign-extends things as needed. It gets used to
+ remove non-address bits from any pointer used to access memory. */
+
+typedef CORE_ADDR (gdbarch_remove_non_address_bits_memory_ftype) (struct gdbarch *gdbarch, CORE_ADDR pointer);
+extern CORE_ADDR gdbarch_remove_non_address_bits_memory (struct gdbarch *gdbarch, CORE_ADDR pointer);
+extern void set_gdbarch_remove_non_address_bits_memory (struct gdbarch *gdbarch, gdbarch_remove_non_address_bits_memory_ftype *remove_non_address_bits_memory);
/* Return a string representation of the memory tag TAG. */
Method(
comment="""
On some architectures, not all bits of a pointer are significant.
-On AArch64, for example, the top bits of a pointer may carry a "tag", which
-can be ignored by the kernel and the hardware. The "tag" can be regarded as
-additional data associated with the pointer, but it is not part of the address.
+On AArch64 and amd64, for example, the top bits of a pointer may carry a
+"tag", which can be ignored by the kernel and the hardware. The "tag" can be
+regarded as additional data associated with the pointer, but it is not part
+of the address.
Given a pointer for the architecture, this hook removes all the
-non-significant bits and sign-extends things as needed. It gets used to remove
-non-address bits from data pointers (for example, removing the AArch64 MTE tag
-bits from a pointer) and from code pointers (removing the AArch64 PAC signature
-from a pointer containing the return address).
+non-significant bits and sign-extends things as needed. It gets used to
+remove non-address bits from pointers used for watchpoints.
""",
type="CORE_ADDR",
- name="remove_non_address_bits",
+ name="remove_non_address_bits_watchpoint",
+ params=[("CORE_ADDR", "pointer")],
+ predefault="default_remove_non_address_bits",
+ invalid=False,
+)
+
+Method(
+ comment="""
+On some architectures, not all bits of a pointer are significant.
+On AArch64 and amd64, for example, the top bits of a pointer may carry a
+"tag", which can be ignored by the kernel and the hardware. The "tag" can be
+regarded as additional data associated with the pointer, but it is not part
+of the address.
+
+Given a pointer for the architecture, this hook removes all the
+non-significant bits and sign-extends things as needed. It gets used to
+remove non-address bits from pointers used for breakpoints.
+""",
+ type="CORE_ADDR",
+ name="remove_non_address_bits_breakpoint",
+ params=[("CORE_ADDR", "pointer")],
+ predefault="default_remove_non_address_bits",
+ invalid=False,
+)
+
+Method(
+ comment="""
+On some architectures, not all bits of a pointer are significant.
+On AArch64 and amd64, for example, the top bits of a pointer may carry a
+"tag", which can be ignored by the kernel and the hardware. The "tag" can be
+regarded as additional data associated with the pointer, but it is not part
+of the address.
+
+Given a pointer for the architecture, this hook removes all the
+non-significant bits and sign-extends things as needed. It gets used to
+remove non-address bits from any pointer used to access memory.
+""",
+ type="CORE_ADDR",
+ name="remove_non_address_bits_memory",
params=[("CORE_ADDR", "pointer")],
predefault="default_remove_non_address_bits",
invalid=False,
if (len == 0)
return TARGET_XFER_EOF;
- memaddr = gdbarch_remove_non_address_bits (current_inferior ()->arch (),
+ memaddr
+ = gdbarch_remove_non_address_bits_memory (current_inferior ()->arch (),
memaddr);
/* Fill in READBUF with breakpoint shadows, or WRITEBUF with