From 38a6bce5396b1a2bdf21db7bd3cde3c75cec65ca Mon Sep 17 00:00:00 2001 From: Lucas Prates Date: Thu, 8 Feb 2024 09:59:00 +0000 Subject: [PATCH 1/2] [aadwarf64] Add DWARF support for unwinding with FEAT_PAuth_LR enabled This introduces DWARF support to enable unwinders to authenticate return addresses signed using FEAT_PAuth_LR, where the value of PC is used as an extra diversifier. To achieve that, this proposes the following changes to the aadwarf64 document: * Expanding usage of the `RA_SIGN_STATE` pseudo-register, allocating it's bit[1] to indicate wether the value of PC has been used for return address signing. * Introducing a new vendor call frame instruction, `DW_CFA_AARCH64_negate_ra_state_with_pc`, which negates both bit[0] and bit[1] of `RA_SIGN_STATE` and instructs the unwinder to capture the current code location to be used when authenticating the return address. Co-authored-by: Oliver Stannard --- aadwarf64/aadwarf64.rst | 48 +++++++++++++++++++++++++++-------------- 1 file changed, 32 insertions(+), 16 deletions(-) diff --git a/aadwarf64/aadwarf64.rst b/aadwarf64/aadwarf64.rst index 4aca883..4670c21 100644 --- a/aadwarf64/aadwarf64.rst +++ b/aadwarf64/aadwarf64.rst @@ -470,11 +470,19 @@ integers. .. _Note 8: 8. The RA_SIGN_STATE pseudo-register records whether the return address has - been signed with a PAC. This information can be used when unwinding. It - is an unsigned integer with the same size as a general register. Only - bit[0] is meaningful and is initialized to zero. A value of 0 indicates - the return address has not been signed. A value of 1 indicates the return - address has been signed. + been signed with a PAC, and whether the value of PC has been used as a + diversifier for the return address signing. This information can be used + when unwinding. It is an unsigned integer with the same size as a general + register. Only bit[0] and bit[1] are meaningful and are initialized to zero. + + Bit[0] indicates whether the return address has been signed. A value of 0 + indicates the return address has not been signed. A value of 1 indicates + the return address has been signed. + + Bit[1] indicates whether the value of PC has been used as a diversifier for + signing the return address. A value of 0 indicates the value of PC has not + been used for return address signing. A value of 1 indicates the value of PC + has been used for return address signing. .. _Note 9: @@ -574,25 +582,33 @@ a CIE augmentation string. Call frame instructions ----------------------- -This ABI defines one vendor call frame instruction -``DW_CFA_AARCH64_negate_ra_state``. +This ABI defines two vendor call frame instructions: +``DW_CFA_AARCH64_negate_ra_state`` and ``DW_CFA_AARCH64_negate_ra_state_with_pc``. .. class:: aadwarf64-vendor-cfa-operations .. table:: AArch64 vendor CFA operations - +------------------------------------+-------------+------------+-----------+-----------+ - | Instruction | High 2 bits | Low 6 bits | Operand 1 | Operand 2 | - +====================================+=============+============+===========+===========+ - | ``DW_CFA_AARCH64_negate_ra_state`` | 0 | ``0x2D`` | \- | \- | - +------------------------------------+-------------+------------+-----------+-----------+ + +--------------------------------------------+-------------+------------+-----------+-----------+ + | Instruction | High 2 bits | Low 6 bits | Operand 1 | Operand 2 | + +============================================+=============+============+===========+===========+ + | ``DW_CFA_AARCH64_negate_ra_state`` | 0 | ``0x2D`` | \- | \- | + +--------------------------------------------+-------------+------------+-----------+-----------+ + | ``DW_CFA_AARCH64_negate_ra_state_with_pc`` | 0 | ``0x2C`` | \- | \- | + +--------------------------------------------+-------------+------------+-----------+-----------+ The ``DW_CFA_AARCH64_negate_ra_state`` operation negates bit[0] of the RA_SIGN_STATE pseudo-register. It does not take any operands. -The ``DW_CFA_AARCH64_negate_ra_state`` must not be mixed with other DWARF -Register Rule Instructions (GDWARF_, §6.4.2.3) on the RA_SIGN_STATE -pseudo-register in one Common Information Entry (CIE) and Frame Descriptor -Entry (FDE) program sequence. + +The ``DW_CFA_AARCH64_negate_ra_state_with_pc`` operation negates bit[0] and +bit[1] of the RA_SIGN_STATE pseudo-register, and instructs the unwinder capture +the current code location. The code location information can be used for +authenticating the return address. + +The ``DW_CFA_AARCH64_negate_ra_state`` and ``DW_CFA_AARCH64_negate_ra_state_with_pc`` +instructions must not be mixed with other DWARF Register Rule Instructions +(GDWARF_, §6.4.2.3) on the RA_SIGN_STATE pseudo-register in one Common +Information Entry (CIE) and Frame Descriptor Entry (FDE) program sequence. .. _DWARF expression operations: From 06242c5086ec21554a94177887bccc5b29a29dde Mon Sep 17 00:00:00 2001 From: Lucas Prates Date: Mon, 26 Feb 2024 16:02:36 +0000 Subject: [PATCH 2/2] fixup! [aadwarf64] Add DWARF support for unwinding with FEAT_PAuth_LR enabled --- aadwarf64/aadwarf64.rst | 24 ++++++++++++++++++++---- 1 file changed, 20 insertions(+), 4 deletions(-) diff --git a/aadwarf64/aadwarf64.rst b/aadwarf64/aadwarf64.rst index 4670c21..cf82aeb 100644 --- a/aadwarf64/aadwarf64.rst +++ b/aadwarf64/aadwarf64.rst @@ -484,6 +484,18 @@ integers. been used for return address signing. A value of 1 indicates the value of PC has been used for return address signing. + +--------+--------+----------------------------------+ + | Bit[1] | Bit[0] | State | + +========+========+==================================+ + | 0 | 0 | Return address not signed | + +--------+--------+----------------------------------+ + | 0 | 1 | Return address signed with SP | + +--------+--------+----------------------------------+ + | 1 | 1 | Return address signed with SP+PC | + +--------+--------+----------------------------------+ + | 1 | 0 | Invalid state | + +--------+--------+----------------------------------+ + .. _Note 9: 9. Normally, the program counter is restored from the return address, however @@ -582,7 +594,7 @@ a CIE augmentation string. Call frame instructions ----------------------- -This ABI defines two vendor call frame instructions: +This ABI defines the following vendor call frame instructions: ``DW_CFA_AARCH64_negate_ra_state`` and ``DW_CFA_AARCH64_negate_ra_state_with_pc``. .. class:: aadwarf64-vendor-cfa-operations @@ -601,9 +613,13 @@ The ``DW_CFA_AARCH64_negate_ra_state`` operation negates bit[0] of the RA_SIGN_STATE pseudo-register. It does not take any operands. The ``DW_CFA_AARCH64_negate_ra_state_with_pc`` operation negates bit[0] and -bit[1] of the RA_SIGN_STATE pseudo-register, and instructs the unwinder capture -the current code location. The code location information can be used for -authenticating the return address. +bit[1] of the RA_SIGN_STATE pseudo-register, and instructs the unwinder to +capture the current code location. The code location information can be used +for authenticating the return address. + +The ``DW_CFA_AARCH64_negate_ra_state_with_pc`` instruction must be placed within +the debug frame in a position that refers to the exact code location of the +signing/authenticating PAC instructions. The ``DW_CFA_AARCH64_negate_ra_state`` and ``DW_CFA_AARCH64_negate_ra_state_with_pc`` instructions must not be mixed with other DWARF Register Rule Instructions