diff --git a/gas/config/tc-aarch64.c b/gas/config/tc-aarch64.c index 0887d9a0736..f69b0b0c0e2 100644 --- a/gas/config/tc-aarch64.c +++ b/gas/config/tc-aarch64.c @@ -306,6 +306,8 @@ struct reloc_entry /* Typecheck: same, plus SVE registers. */ \ MULTI_REG_TYPE(SVE_BASE, REG_TYPE(R_64) | REG_TYPE(SP_64) \ | REG_TYPE(Z)) \ + /* Typecheck: x[0-30], w[0-30]. */ \ + MULTI_REG_TYPE(R, REG_TYPE(R_32) | REG_TYPE(R_64)) \ /* Typecheck: x[0-30], w[0-30] or [xw]zr. */ \ MULTI_REG_TYPE(R_ZR, REG_TYPE(R_32) | REG_TYPE(R_64) \ | REG_TYPE(ZR_32) | REG_TYPE(ZR_64)) \ @@ -6688,7 +6690,15 @@ parse_operands (char *str, const aarch64_opcode *opcode) case AARCH64_OPND_PAIRREG: case AARCH64_OPND_PAIRREG_OR_XZR: case AARCH64_OPND_SVE_Rm: - po_int_fp_reg_or_fail (REG_TYPE_R_ZR); + switch (opcode->iclass) + { + case ic_pauth_lr: + po_int_fp_reg_or_fail (REG_TYPE_R); + break; + default: + po_int_fp_reg_or_fail (REG_TYPE_R_ZR); + break; + } /* In LS64 load/store instructions Rt register number must be even and <=22. */ diff --git a/gas/testsuite/gas/aarch64/pauth_lr-bad.d b/gas/testsuite/gas/aarch64/pauth_lr-bad.d new file mode 100644 index 00000000000..4ee0bfcaf35 --- /dev/null +++ b/gas/testsuite/gas/aarch64/pauth_lr-bad.d @@ -0,0 +1,3 @@ +#source: pauth_lr-bad.s +#as: -march=armv9.4-a+pauth-lr +#error_output: pauth_lr-bad.l \ No newline at end of file diff --git a/gas/testsuite/gas/aarch64/pauth_lr-bad.l b/gas/testsuite/gas/aarch64/pauth_lr-bad.l new file mode 100644 index 00000000000..d0a629f216f --- /dev/null +++ b/gas/testsuite/gas/aarch64/pauth_lr-bad.l @@ -0,0 +1,11 @@ +.*: Assembler messages: +.*: Error: operand mismatch -- `autiasppcr w0' +.*: Info: did you mean this\? +.*: Info: autiasppcr x0 +.*: Error: unexpected register type at operand 1 -- `autiasppcr sp' +.*: Error: unexpected register type at operand 1 -- `autiasppcr xzr' +.*: Error: operand mismatch -- `retaasppcr w0' +.*: Info: did you mean this\? +.*: Info: retaasppcr x0 +.*: Error: unexpected register type at operand 1 -- `retaasppcr sp' +.*: Error: unexpected register type at operand 1 -- `retaasppcr xzr' \ No newline at end of file diff --git a/gas/testsuite/gas/aarch64/pauth_lr-bad.s b/gas/testsuite/gas/aarch64/pauth_lr-bad.s new file mode 100644 index 00000000000..98840d4c257 --- /dev/null +++ b/gas/testsuite/gas/aarch64/pauth_lr-bad.s @@ -0,0 +1,12 @@ + /* ARMv9.5 Pointer authentication instructions. */ + .text + +lr_signing: + + autiasppcr w0 // 32-bit registers not allowed + autiasppcr sp // stack pointer register not allowed + autiasppcr xzr // zero register not allowed + + retaasppcr w0 // 32-bit registers not allowed + retaasppcr sp // SP not allowed + retaasppcr xzr // zero register not allowed diff --git a/gas/testsuite/gas/aarch64/pauth_lr.d b/gas/testsuite/gas/aarch64/pauth_lr.d new file mode 100644 index 00000000000..ddd65b77fd1 --- /dev/null +++ b/gas/testsuite/gas/aarch64/pauth_lr.d @@ -0,0 +1,24 @@ +#source: pauth_lr.s +#as: -march=armv9.4-a+pauth-lr +#objdump: -dr + +.*: file .* + +Disassembly of section \.text: + +0+ <.*>: +.*: d50324ff pacm +.*: dac1a3fe paciasppc +.*: dac1a7fe pacibsppc +.*: dac18bfe pacia171615 +.*: dac18ffe pacib171615 +.*: dac183fe pacnbiasppc +.*: dac187fe pacnbibsppc +.*: dac1bbfe autia171615 +.*: dac1bffe autib171615 +.*: dac1901e autiasppcr x0 +.*: dac193de autiasppcr x30 +.*: dac1941e autibsppcr x0 +.*: d65f0be0 retaasppcr x0 +.*: d65f0bfe retaasppcr x30 +.*: d65f0fe0 retabsppcr x0 \ No newline at end of file diff --git a/gas/testsuite/gas/aarch64/pauth_lr.s b/gas/testsuite/gas/aarch64/pauth_lr.s new file mode 100644 index 00000000000..cdedd6e4588 --- /dev/null +++ b/gas/testsuite/gas/aarch64/pauth_lr.s @@ -0,0 +1,30 @@ + /* ARMv9.5 Pointer authentication instructions. */ + .text + + // only NOP-space instruction to enable ComputePAC2() with PAuth instructions. + pacm + + // Signing of LR using SP and PC as deversifiers. + paciasppc + pacibsppc + + pacia171615 + pacib171615 + + // When used along feature FEAT_BTI + pacnbiasppc + pacnbibsppc + + // Authenticating the PAC in the address in register LR + autia171615 + autib171615 + + // Variant with value of PC passed by register + autiasppcr x0 + autiasppcr x30 + autibsppcr x0 + + // Authentication + return + retaasppcr x0 + retaasppcr x30 + retabsppcr x0 diff --git a/include/opcode/aarch64.h b/include/opcode/aarch64.h index 2710730e72e..81c9b1f1220 100644 --- a/include/opcode/aarch64.h +++ b/include/opcode/aarch64.h @@ -1054,6 +1054,7 @@ enum aarch64_insn_class lse_atomic, lse128_atomic, movewide, + ic_pauth_lr, pcreladdr, ic_system, sme_fp_sd, diff --git a/opcodes/aarch64-tbl.h b/opcodes/aarch64-tbl.h index 3ba2c088be8..ef7b69e4970 100644 --- a/opcodes/aarch64-tbl.h +++ b/opcodes/aarch64-tbl.h @@ -1034,6 +1034,12 @@ QLF4(V_16B, V_16B, V_16B, imm_0_15), \ } +/* e.g. AUTISPPCR Xn */ +#define QL_PAUTH_REG \ +{ \ + QLF1(X), \ +} + /* e.g. . */ #define QL_V3SAMEHS \ { \ @@ -3888,6 +3894,8 @@ const struct aarch64_opcode aarch64_opcode_table[] = PAUTH_INSN ("retab", 0xd65f0fff, 0xffffffff, branch_reg, OP0 (), {}, 0), PAUTH_INSN ("eretaa", 0xd69f0bff, 0xffffffff, branch_reg, OP0 (), {}, 0), PAUTH_INSN ("eretab", 0xd69f0fff, 0xffffffff, branch_reg, OP0 (), {}, 0), + PAUTH_LR_INSN ("retaasppcr", 0xd65f0be0, 0xffffffe0, ic_pauth_lr, OP1 (Rd), QL_PAUTH_REG, 0), + PAUTH_LR_INSN ("retabsppcr", 0xd65f0fe0, 0xffffffe0, ic_pauth_lr, OP1 (Rd), QL_PAUTH_REG, 0), /* Compare & branch (immediate). */ CORE_INSN ("cbz", 0x34000000, 0x7f000000, compbranch, 0, OP2 (Rt, ADDR_PCREL19), QL_R_PCREL, F_SF), CORE_INSN ("cbnz", 0x35000000, 0x7f000000, compbranch, 0, OP2 (Rt, ADDR_PCREL19), QL_R_PCREL, F_SF), @@ -3939,10 +3947,20 @@ const struct aarch64_opcode aarch64_opcode_table[] = PAUTH_INSN ("pacib", 0xdac10400, 0xfffffc00, dp_1src, OP2 (Rd, Rn_SP), QL_I2SAMEX, 0), PAUTH_INSN ("pacda", 0xdac10800, 0xfffffc00, dp_1src, OP2 (Rd, Rn_SP), QL_I2SAMEX, 0), PAUTH_INSN ("pacdb", 0xdac10c00, 0xfffffc00, dp_1src, OP2 (Rd, Rn_SP), QL_I2SAMEX, 0), + PAUTH_LR_INSN ("paciasppc", 0xdac1a3fe, 0xffffffff, ic_system, OP0 (), {}, 0), + PAUTH_LR_INSN ("pacibsppc", 0xdac1a7fe, 0xffffffff, ic_system, OP0 (), {}, 0), + PAUTH_LR_INSN ("pacnbiasppc", 0xdac183fe, 0xffffffff, ic_system, OP0 (), {}, 0), + PAUTH_LR_INSN ("pacnbibsppc", 0xdac187fe, 0xffffffff, ic_system, OP0 (), {}, 0), + PAUTH_LR_INSN ("pacia171615", 0xdac18bfe, 0xffffffff, ic_system, OP0 (), {}, 0), + PAUTH_LR_INSN ("pacib171615", 0xdac18ffe, 0xffffffff, ic_system, OP0 (), {}, 0), PAUTH_INSN ("autia", 0xdac11000, 0xfffffc00, dp_1src, OP2 (Rd, Rn_SP), QL_I2SAMEX, 0), PAUTH_INSN ("autib", 0xdac11400, 0xfffffc00, dp_1src, OP2 (Rd, Rn_SP), QL_I2SAMEX, 0), PAUTH_INSN ("autda", 0xdac11800, 0xfffffc00, dp_1src, OP2 (Rd, Rn_SP), QL_I2SAMEX, 0), PAUTH_INSN ("autdb", 0xdac11c00, 0xfffffc00, dp_1src, OP2 (Rd, Rn_SP), QL_I2SAMEX, 0), + PAUTH_LR_INSN ("autiasppcr", 0xdac1901e, 0xfffffc1f, ic_pauth_lr, OP1 (Rn), QL_PAUTH_REG, 0), + PAUTH_LR_INSN ("autibsppcr", 0xdac1941e, 0xfffffc1f, ic_pauth_lr, OP1 (Rn), QL_PAUTH_REG, 0), + PAUTH_LR_INSN ("autia171615", 0xdac1bbfe, 0xffffffff, ic_system, OP0 (), {}, 0), + PAUTH_LR_INSN ("autib171615", 0xdac1bffe, 0xffffffff, ic_system, OP0 (), {}, 0), PAUTH_INSN ("paciza", 0xdac123e0, 0xffffffe0, dp_1src, OP1 (Rd), QL_I1X, 0), PAUTH_INSN ("pacizb", 0xdac127e0, 0xffffffe0, dp_1src, OP1 (Rd), QL_I1X, 0), PAUTH_INSN ("pacdza", 0xdac12be0, 0xffffffe0, dp_1src, OP1 (Rd), QL_I1X, 0),