diff options
author | John Baldwin <jhb@FreeBSD.org> | 2022-08-10 12:14:16 -0700 |
---|---|---|
committer | John Baldwin <jhb@FreeBSD.org> | 2022-09-01 16:47:42 -0700 |
commit | 36d1b3bff14b48cb2166e0bc27cf74c9c3bc3c25 (patch) | |
tree | 1898cd45c0d8be4e705c450373e0f938b0a94232 | |
parent | cabfc6253d9d61d97cd3c6b0c4cae949dd36187b (diff) | |
download | binutils-gdb-36d1b3bff14b48cb2166e0bc27cf74c9c3bc3c25.tar.gz |
Write memory capabilities atomically.
Use target_write_capability to write a capability atomically in
put_frame_register.
-rw-r--r-- | gdb/frame.c | 14 |
1 files changed, 10 insertions, 4 deletions
diff --git a/gdb/frame.c b/gdb/frame.c index 44b3bd09463..bc3189e3dac 100644 --- a/gdb/frame.c +++ b/gdb/frame.c @@ -1399,15 +1399,21 @@ put_frame_register (struct frame_info *frame, int regnum, { case lval_memory: { - write_memory (addr, buf, register_size (gdbarch, regnum)); - /* If this value is a capability, we need to handle the capability tag - as well. */ + as an atomic write. */ if ((val_type->code () == TYPE_CODE_CAPABILITY || (val_type->code () == TYPE_CODE_PTR && TYPE_CAPABILITY (val_type))) && value_tagged (fromval)) - gdbarch_set_cap_tag_from_address (gdbarch, addr, value_tag (fromval)); + { + gdb::byte_vector cap (register_size (gdbarch, regnum) + 1); + + cap[0] = value_tag (fromval) ? 1 : 0; + memcpy (cap.data () + 1, buf, register_size (gdbarch, regnum)); + if (target_write_capability (addr, cap)) + break; + } + write_memory (addr, buf, register_size (gdbarch, regnum)); break; } case lval_register: |