From 02fd7e24721844aaa8f9a20d38ea6e8e5e9ed08d Mon Sep 17 00:00:00 2001 From: Richard Henderson Date: Tue, 22 Jan 2019 15:32:08 -0500 Subject: [PATCH] target/arm: Decode PAuth within system hint space Backports commit 7c94c8343c6a0eea1633a65ed27987b6a71b9089 from qemu --- qemu/target/arm/translate-a64.c | 94 ++++++++++++++++++++++++++++----- 1 file changed, 82 insertions(+), 12 deletions(-) diff --git a/qemu/target/arm/translate-a64.c b/qemu/target/arm/translate-a64.c index 255bd6e0..687ce47c 100644 --- a/qemu/target/arm/translate-a64.c +++ b/qemu/target/arm/translate-a64.c @@ -1538,6 +1538,7 @@ static void disas_cond_b_imm(DisasContext *s, uint32_t insn) static void handle_hint(DisasContext *s, uint32_t insn, unsigned int op1, unsigned int op2, unsigned int crm) { + TCGContext *tcg_ctx = s->uc->tcg_ctx; unsigned int selector = crm << 3 | op2; if (op1 != 3) { @@ -1546,28 +1547,97 @@ static void handle_hint(DisasContext *s, uint32_t insn, } switch (selector) { - case 0: /* NOP */ - return; - case 3: /* WFI */ + case 0b00000: /* NOP */ + break; + case 0b00011: /* WFI */ s->base.is_jmp = DISAS_WFI; - return; - case 1: /* YIELD */ + break; + case 0b00001: /* YIELD */ if (!s->uc->parallel_cpus) { s->base.is_jmp = DISAS_YIELD; } - return; - case 2: /* WFE */ + break; + case 0b00010: /* WFE */ if (!s->uc->parallel_cpus) { s->base.is_jmp = DISAS_WFE; } - return; - case 4: /* SEV */ - case 5: /* SEVL */ + break; + case 0b00100: /* SEV */ + case 0b00101: /* SEVL */ /* we treat all as NOP at least for now */ - return; + break; + case 0b00111: /* XPACLRI */ + if (s->pauth_active) { + gen_helper_xpaci(tcg_ctx, tcg_ctx->cpu_X[30], tcg_ctx->cpu_env, tcg_ctx->cpu_X[30]); + } + break; + case 0b01000: /* PACIA1716 */ + if (s->pauth_active) { + gen_helper_pacia(tcg_ctx, tcg_ctx->cpu_X[17], tcg_ctx->cpu_env, tcg_ctx->cpu_X[17], tcg_ctx->cpu_X[16]); + } + break; + case 0b01010: /* PACIB1716 */ + if (s->pauth_active) { + gen_helper_pacib(tcg_ctx, tcg_ctx->cpu_X[17], tcg_ctx->cpu_env, tcg_ctx->cpu_X[17], tcg_ctx->cpu_X[16]); + } + break; + case 0b01100: /* AUTIA1716 */ + if (s->pauth_active) { + gen_helper_autia(tcg_ctx, tcg_ctx->cpu_X[17], tcg_ctx->cpu_env, tcg_ctx->cpu_X[17], tcg_ctx->cpu_X[16]); + } + break; + case 0b01110: /* AUTIB1716 */ + if (s->pauth_active) { + gen_helper_autib(tcg_ctx, tcg_ctx->cpu_X[17], tcg_ctx->cpu_env, tcg_ctx->cpu_X[17], tcg_ctx->cpu_X[16]); + } + break; + case 0b11000: /* PACIAZ */ + if (s->pauth_active) { + gen_helper_pacia(tcg_ctx, tcg_ctx->cpu_X[30], tcg_ctx->cpu_env, tcg_ctx->cpu_X[30], + new_tmp_a64_zero(s)); + } + break; + case 0b11001: /* PACIASP */ + if (s->pauth_active) { + gen_helper_pacia(tcg_ctx, tcg_ctx->cpu_X[30], tcg_ctx->cpu_env, tcg_ctx->cpu_X[30], tcg_ctx->cpu_X[31]); + } + break; + case 0b11010: /* PACIBZ */ + if (s->pauth_active) { + gen_helper_pacib(tcg_ctx, tcg_ctx->cpu_X[30], tcg_ctx->cpu_env, tcg_ctx->cpu_X[30], + new_tmp_a64_zero(s)); + } + break; + case 0b11011: /* PACIBSP */ + if (s->pauth_active) { + gen_helper_pacib(tcg_ctx, tcg_ctx->cpu_X[30], tcg_ctx->cpu_env, tcg_ctx->cpu_X[30], tcg_ctx->cpu_X[31]); + } + break; + case 0b11100: /* AUTIAZ */ + if (s->pauth_active) { + gen_helper_autia(tcg_ctx, tcg_ctx->cpu_X[30], tcg_ctx->cpu_env, tcg_ctx->cpu_X[30], + new_tmp_a64_zero(s)); + } + break; + case 0b11101: /* AUTIASP */ + if (s->pauth_active) { + gen_helper_autia(tcg_ctx, tcg_ctx->cpu_X[30], tcg_ctx->cpu_env, tcg_ctx->cpu_X[30], tcg_ctx->cpu_X[31]); + } + break; + case 0b11110: /* AUTIBZ */ + if (s->pauth_active) { + gen_helper_autib(tcg_ctx, tcg_ctx->cpu_X[30], tcg_ctx->cpu_env, tcg_ctx->cpu_X[30], + new_tmp_a64_zero(s)); + } + break; + case 0b11111: /* AUTIBSP */ + if (s->pauth_active) { + gen_helper_autib(tcg_ctx, tcg_ctx->cpu_X[30], tcg_ctx->cpu_env, tcg_ctx->cpu_X[30], tcg_ctx->cpu_X[31]); + } + break; default: /* default specified as NOP equivalent */ - return; + break; } }