From patchwork Mon Aug 20 15:30:15 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 959822 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=nongnu.org (client-ip=2001:4830:134:3::11; helo=lists.gnu.org; envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=fail (p=none dis=none) header.from=linaro.org Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 41vHtj5Z9Tz9s8T for ; Tue, 21 Aug 2018 01:35:09 +1000 (AEST) Received: from localhost ([::1]:47764 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frmCx-0008Kl-Hy for incoming@patchwork.ozlabs.org; Mon, 20 Aug 2018 11:35:07 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:46282) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frm8X-0005dE-H5 for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:36 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1frm8W-0004DE-V6 for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:33 -0400 Received: from orth.archaic.org.uk ([2001:8b0:1d0::2]:44712) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1frm8U-00044t-Vj; Mon, 20 Aug 2018 11:30:31 -0400 Received: from pm215 by orth.archaic.org.uk with local (Exim 4.89) (envelope-from ) id 1frm8N-0003Xq-PG; Mon, 20 Aug 2018 16:30:23 +0100 From: Peter Maydell To: qemu-arm@nongnu.org, qemu-devel@nongnu.org Date: Mon, 20 Aug 2018 16:30:15 +0100 Message-Id: <20180820153020.21478-2-peter.maydell@linaro.org> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180820153020.21478-1-peter.maydell@linaro.org> References: <20180820153020.21478-1-peter.maydell@linaro.org> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2001:8b0:1d0::2 Subject: [Qemu-devel] [PATCH v2 1/6] target/arm: Implement RAZ/WI HACTLR2 X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: "Edgar E . Iglesias" , Luc Michel , patches@linaro.org Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" The v8 AArch32 HACTLR2 register maps to bits [63:32] of ACTLR_EL2. We implement ACTLR_EL2 as RAZ/WI, so make HACTLR2 also RAZ/WI. (We put the regdef next to ACTLR_EL2 as a reminder in case we ever make ACTLR_EL2 something other than RAZ/WI). Signed-off-by: Peter Maydell --- changes from v1: only define in ARMv8, not v7 --- target/arm/helper.c | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/target/arm/helper.c b/target/arm/helper.c index c9bce1efcb2..22547d8e739 100644 --- a/target/arm/helper.c +++ b/target/arm/helper.c @@ -5459,6 +5459,16 @@ void register_cp_regs_for_features(ARMCPU *cpu) REGINFO_SENTINEL }; define_arm_cp_regs(cpu, auxcr_reginfo); + if (arm_feature(env, ARM_FEATURE_V8)) { + /* HACTLR2 maps to ACTLR_EL2[63:32] and is not in ARMv7 */ + ARMCPRegInfo hactlr2_reginfo = { + .name = "HACTLR2", .state = ARM_CP_STATE_AA32, + .cp = 15, .opc1 = 4, .crn = 1, .crm = 0, .opc2 = 3, + .access = PL2_RW, .type = ARM_CP_CONST, + .resetvalue = 0 + }; + define_one_arm_cp_reg(cpu, &hactlr2_reginfo); + } } if (arm_feature(env, ARM_FEATURE_CBAR)) { From patchwork Mon Aug 20 15:30:16 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 959821 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=nongnu.org (client-ip=2001:4830:134:3::11; helo=lists.gnu.org; envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=fail (p=none dis=none) header.from=linaro.org Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 41vHtP35FRz9s4v for ; Tue, 21 Aug 2018 01:34:51 +1000 (AEST) Received: from localhost ([::1]:47761 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frmCe-00084e-Mn for incoming@patchwork.ozlabs.org; Mon, 20 Aug 2018 11:34:48 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:46187) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frm8T-0005WA-8R for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:30 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1frm8S-00046I-CH for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:29 -0400 Received: from orth.archaic.org.uk ([2001:8b0:1d0::2]:44694) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1frm8Q-00041d-63; Mon, 20 Aug 2018 11:30:26 -0400 Received: from pm215 by orth.archaic.org.uk with local (Exim 4.89) (envelope-from ) id 1frm8O-0003YA-Mk; Mon, 20 Aug 2018 16:30:24 +0100 From: Peter Maydell To: qemu-arm@nongnu.org, qemu-devel@nongnu.org Date: Mon, 20 Aug 2018 16:30:16 +0100 Message-Id: <20180820153020.21478-3-peter.maydell@linaro.org> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180820153020.21478-1-peter.maydell@linaro.org> References: <20180820153020.21478-1-peter.maydell@linaro.org> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2001:8b0:1d0::2 Subject: [Qemu-devel] [PATCH v2 2/6] target/arm: Implement AArch32 HCR and HCR2 X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: "Edgar E . Iglesias" , Luc Michel , patches@linaro.org Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" The AArch32 HCR and HCR2 registers alias HCR_EL2 bits [31:0] and [63:32]; implement them. Since HCR2 exists in ARMv8 but not ARMv7, we need new regdef arrays for "we have EL3, not EL2, we're ARMv8" and "we have EL2, we're ARMv8" to hold the definitions. Signed-off-by: Peter Maydell --- Changes from v1: moved HCR2 definition to new regdef arrays so we don't define it for ARMv7 CPUs --- target/arm/helper.c | 54 +++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 50 insertions(+), 4 deletions(-) diff --git a/target/arm/helper.c b/target/arm/helper.c index 22547d8e739..9ff6778b3ae 100644 --- a/target/arm/helper.c +++ b/target/arm/helper.c @@ -3754,11 +3754,11 @@ static const ARMCPRegInfo el3_no_el2_cp_reginfo[] = { .opc0 = 3, .opc1 = 4, .crn = 12, .crm = 0, .opc2 = 0, .access = PL2_RW, .readfn = arm_cp_read_zero, .writefn = arm_cp_write_ignore }, - { .name = "HCR_EL2", .state = ARM_CP_STATE_AA64, + { .name = "HCR_EL2", .state = ARM_CP_STATE_BOTH, .type = ARM_CP_NO_RAW, .opc0 = 3, .opc1 = 4, .crn = 1, .crm = 1, .opc2 = 0, .access = PL2_RW, - .readfn = arm_cp_read_zero, .writefn = arm_cp_write_ignore }, + .type = ARM_CP_CONST, .resetvalue = 0 }, { .name = "ESR_EL2", .state = ARM_CP_STATE_BOTH, .opc0 = 3, .opc1 = 4, .crn = 5, .crm = 2, .opc2 = 0, .access = PL2_RW, @@ -3857,6 +3857,15 @@ static const ARMCPRegInfo el3_no_el2_cp_reginfo[] = { REGINFO_SENTINEL }; +/* Ditto, but for registers which exist in ARMv8 but not v7 */ +static const ARMCPRegInfo el3_no_el2_v8_cp_reginfo[] = { + { .name = "HCR2", .state = ARM_CP_STATE_AA32, + .cp = 15, .opc1 = 4, .crn = 1, .crm = 1, .opc2 = 4, + .access = PL2_RW, + .type = ARM_CP_CONST, .resetvalue = 0 }, + REGINFO_SENTINEL +}; + static void hcr_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value) { ARMCPU *cpu = arm_env_get_cpu(env); @@ -3883,10 +3892,26 @@ static void hcr_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value) * HCR_PTW forbids certain page-table setups * HCR_DC Disables stage1 and enables stage2 translation */ - if ((raw_read(env, ri) ^ value) & (HCR_VM | HCR_PTW | HCR_DC)) { + if ((env->cp15.hcr_el2 ^ value) & (HCR_VM | HCR_PTW | HCR_DC)) { tlb_flush(CPU(cpu)); } - raw_write(env, ri, value); + env->cp15.hcr_el2 = value; +} + +static void hcr_writehigh(CPUARMState *env, const ARMCPRegInfo *ri, + uint64_t value) +{ + /* Handle HCR2 write, i.e. write to high half of HCR_EL2 */ + value = deposit64(env->cp15.hcr_el2, 32, 32, value); + hcr_write(env, NULL, value); +} + +static void hcr_writelow(CPUARMState *env, const ARMCPRegInfo *ri, + uint64_t value) +{ + /* Handle HCR write, i.e. write to low half of HCR_EL2 */ + value = deposit64(env->cp15.hcr_el2, 0, 32, value); + hcr_write(env, NULL, value); } static const ARMCPRegInfo el2_cp_reginfo[] = { @@ -3894,6 +3919,11 @@ static const ARMCPRegInfo el2_cp_reginfo[] = { .opc0 = 3, .opc1 = 4, .crn = 1, .crm = 1, .opc2 = 0, .access = PL2_RW, .fieldoffset = offsetof(CPUARMState, cp15.hcr_el2), .writefn = hcr_write }, + { .name = "HCR", .state = ARM_CP_STATE_AA32, + .type = ARM_CP_ALIAS, + .cp = 15, .opc1 = 4, .crn = 1, .crm = 1, .opc2 = 0, + .access = PL2_RW, .fieldoffset = offsetof(CPUARMState, cp15.hcr_el2), + .writefn = hcr_writelow }, { .name = "ELR_EL2", .state = ARM_CP_STATE_AA64, .type = ARM_CP_ALIAS, .opc0 = 3, .opc1 = 4, .crn = 4, .crm = 0, .opc2 = 1, @@ -4128,6 +4158,16 @@ static const ARMCPRegInfo el2_cp_reginfo[] = { REGINFO_SENTINEL }; +static const ARMCPRegInfo el2_v8_cp_reginfo[] = { + { .name = "HCR2", .state = ARM_CP_STATE_AA32, + .type = ARM_CP_ALIAS, + .cp = 15, .opc1 = 4, .crn = 1, .crm = 1, .opc2 = 4, + .access = PL2_RW, + .fieldoffset = offsetofhigh32(CPUARMState, cp15.hcr_el2), + .writefn = hcr_writehigh }, + REGINFO_SENTINEL +}; + static CPAccessResult nsacr_access(CPUARMState *env, const ARMCPRegInfo *ri, bool isread) { @@ -5179,6 +5219,9 @@ void register_cp_regs_for_features(ARMCPU *cpu) }; define_arm_cp_regs(cpu, vpidr_regs); define_arm_cp_regs(cpu, el2_cp_reginfo); + if (arm_feature(env, ARM_FEATURE_V8)) { + define_arm_cp_regs(cpu, el2_v8_cp_reginfo); + } /* RVBAR_EL2 is only implemented if EL2 is the highest EL */ if (!arm_feature(env, ARM_FEATURE_EL3)) { ARMCPRegInfo rvbar = { @@ -5211,6 +5254,9 @@ void register_cp_regs_for_features(ARMCPU *cpu) }; define_arm_cp_regs(cpu, vpidr_regs); define_arm_cp_regs(cpu, el3_no_el2_cp_reginfo); + if (arm_feature(env, ARM_FEATURE_V8)) { + define_arm_cp_regs(cpu, el3_no_el2_v8_cp_reginfo); + } } } if (arm_feature(env, ARM_FEATURE_EL3)) { From patchwork Mon Aug 20 15:30:17 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 959818 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=nongnu.org (client-ip=2001:4830:134:3::11; helo=lists.gnu.org; envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=fail (p=none dis=none) header.from=linaro.org Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 41vHpb1y61z9s4v for ; Tue, 21 Aug 2018 01:31:35 +1000 (AEST) Received: from localhost ([::1]:47748 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frm9U-0005qf-RF for incoming@patchwork.ozlabs.org; Mon, 20 Aug 2018 11:31:32 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:46189) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frm8T-0005Wb-Bq for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:30 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1frm8S-00046b-Ji for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:29 -0400 Received: from orth.archaic.org.uk ([2001:8b0:1d0::2]:44704) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1frm8Q-00042m-K9; Mon, 20 Aug 2018 11:30:26 -0400 Received: from pm215 by orth.archaic.org.uk with local (Exim 4.89) (envelope-from ) id 1frm8P-0003Yj-LK; Mon, 20 Aug 2018 16:30:25 +0100 From: Peter Maydell To: qemu-arm@nongnu.org, qemu-devel@nongnu.org Date: Mon, 20 Aug 2018 16:30:17 +0100 Message-Id: <20180820153020.21478-4-peter.maydell@linaro.org> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180820153020.21478-1-peter.maydell@linaro.org> References: <20180820153020.21478-1-peter.maydell@linaro.org> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2001:8b0:1d0::2 Subject: [Qemu-devel] [PATCH v2 3/6] target/arm: Factor out code for taking an AArch32 exception X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: "Edgar E . Iglesias" , Luc Michel , patches@linaro.org Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" Factor out the code which changes the CPU state so as to actually take an exception to AArch32. We're going to want to use this for handling exception entry to Hyp mode. Signed-off-by: Peter Maydell --- target/arm/helper.c | 64 +++++++++++++++++++++++++++++---------------- 1 file changed, 41 insertions(+), 23 deletions(-) diff --git a/target/arm/helper.c b/target/arm/helper.c index 9ff6778b3ae..a4ddda5a1bd 100644 --- a/target/arm/helper.c +++ b/target/arm/helper.c @@ -8033,6 +8033,46 @@ void aarch64_sync_64_to_32(CPUARMState *env) env->regs[15] = env->pc; } +static void take_aarch32_exception(CPUARMState *env, int new_mode, + uint32_t mask, uint32_t offset, + uint32_t newpc) +{ + /* Change the CPU state so as to actually take the exception. */ + switch_mode(env, new_mode); + /* + * For exceptions taken to AArch32 we must clear the SS bit in both + * PSTATE and in the old-state value we save to SPSR_, so zero it now. + */ + env->uncached_cpsr &= ~PSTATE_SS; + env->spsr = cpsr_read(env); + /* Clear IT bits. */ + env->condexec_bits = 0; + /* Switch to the new mode, and to the correct instruction set. */ + env->uncached_cpsr = (env->uncached_cpsr & ~CPSR_M) | new_mode; + /* Set new mode endianness */ + env->uncached_cpsr &= ~CPSR_E; + if (env->cp15.sctlr_el[arm_current_el(env)] & SCTLR_EE) { + env->uncached_cpsr |= CPSR_E; + } + env->daif |= mask; + + if (new_mode == ARM_CPU_MODE_HYP) { + env->thumb = (env->cp15.sctlr_el[2] & SCTLR_TE) != 0; + env->elr_el[2] = env->regs[15]; + } else { + /* + * this is a lie, as there was no c1_sys on V4T/V5, but who cares + * and we should just guard the thumb mode on V4 + */ + if (arm_feature(env, ARM_FEATURE_V4T)) { + env->thumb = + (A32_BANKED_CURRENT_REG_GET(env, sctlr) & SCTLR_TE) != 0; + } + env->regs[14] = env->regs[15] + offset; + } + env->regs[15] = newpc; +} + static void arm_cpu_do_interrupt_aarch32(CPUState *cs) { ARMCPU *cpu = ARM_CPU(cs); @@ -8175,29 +8215,7 @@ static void arm_cpu_do_interrupt_aarch32(CPUState *cs) env->cp15.scr_el3 &= ~SCR_NS; } - switch_mode (env, new_mode); - /* For exceptions taken to AArch32 we must clear the SS bit in both - * PSTATE and in the old-state value we save to SPSR_, so zero it now. - */ - env->uncached_cpsr &= ~PSTATE_SS; - env->spsr = cpsr_read(env); - /* Clear IT bits. */ - env->condexec_bits = 0; - /* Switch to the new mode, and to the correct instruction set. */ - env->uncached_cpsr = (env->uncached_cpsr & ~CPSR_M) | new_mode; - /* Set new mode endianness */ - env->uncached_cpsr &= ~CPSR_E; - if (env->cp15.sctlr_el[arm_current_el(env)] & SCTLR_EE) { - env->uncached_cpsr |= CPSR_E; - } - env->daif |= mask; - /* this is a lie, as the was no c1_sys on V4T/V5, but who cares - * and we should just guard the thumb mode on V4 */ - if (arm_feature(env, ARM_FEATURE_V4T)) { - env->thumb = (A32_BANKED_CURRENT_REG_GET(env, sctlr) & SCTLR_TE) != 0; - } - env->regs[14] = env->regs[15] + offset; - env->regs[15] = addr; + take_aarch32_exception(env, new_mode, mask, offset, addr); } /* Handle exception entry to a target EL which is using AArch64 */ From patchwork Mon Aug 20 15:30:18 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 959820 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=nongnu.org (client-ip=2001:4830:134:3::11; helo=lists.gnu.org; envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=fail (p=none dis=none) header.from=linaro.org Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 41vHqH38KPz9s8T for ; Tue, 21 Aug 2018 01:32:11 +1000 (AEST) Received: from localhost ([::1]:47753 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frmA4-0006F2-Nc for incoming@patchwork.ozlabs.org; Mon, 20 Aug 2018 11:32:08 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:46267) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frm8W-0005cB-Tj for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:34 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1frm8W-0004Ca-3e for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:32 -0400 Received: from orth.archaic.org.uk ([2001:8b0:1d0::2]:44712) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1frm8T-00044t-KX; Mon, 20 Aug 2018 11:30:29 -0400 Received: from pm215 by orth.archaic.org.uk with local (Exim 4.89) (envelope-from ) id 1frm8Q-0003Z3-Kf; Mon, 20 Aug 2018 16:30:26 +0100 From: Peter Maydell To: qemu-arm@nongnu.org, qemu-devel@nongnu.org Date: Mon, 20 Aug 2018 16:30:18 +0100 Message-Id: <20180820153020.21478-5-peter.maydell@linaro.org> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180820153020.21478-1-peter.maydell@linaro.org> References: <20180820153020.21478-1-peter.maydell@linaro.org> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2001:8b0:1d0::2 Subject: [Qemu-devel] [PATCH v2 4/6] target/arm: Implement support for taking exceptions to Hyp mode X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: "Edgar E . Iglesias" , Luc Michel , patches@linaro.org Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" Implement the necessary support code for taking exceptions to Hyp mode in AArch32. Signed-off-by: Peter Maydell --- target/arm/helper.c | 82 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 82 insertions(+) diff --git a/target/arm/helper.c b/target/arm/helper.c index a4ddda5a1bd..21a2d438944 100644 --- a/target/arm/helper.c +++ b/target/arm/helper.c @@ -8073,6 +8073,83 @@ static void take_aarch32_exception(CPUARMState *env, int new_mode, env->regs[15] = newpc; } +static void arm_cpu_do_interrupt_aarch32_hyp(CPUState *cs) +{ + /* + * Handle exception entry to Hyp mode; this is sufficiently + * different to entry to other AArch32 modes that we handle it + * separately here. + * + * The vector table entry used is always the 0x14 Hyp mode entry point, + * unless this is an UNDEF/HVC/abort taken from Hyp to Hyp. + * The offset applied to the preferred return address is always zero + * (see DDI0487C.a section G1.12.3). + * PSTATE A/I/F masks are set based only on the SCR.EA/IRQ/FIQ values. + */ + uint32_t addr, mask; + ARMCPU *cpu = ARM_CPU(cs); + CPUARMState *env = &cpu->env; + + switch (cs->exception_index) { + case EXCP_UDEF: + addr = 0x04; + break; + case EXCP_SWI: + addr = 0x14; + break; + case EXCP_BKPT: + /* Fall through to prefetch abort. */ + case EXCP_PREFETCH_ABORT: + env->cp15.ifar_s = env->exception.vaddress; + qemu_log_mask(CPU_LOG_INT, "...with HIFAR 0x%x\n", + (uint32_t)env->exception.vaddress); + addr = 0x0c; + break; + case EXCP_DATA_ABORT: + env->cp15.dfar_s = env->exception.vaddress; + qemu_log_mask(CPU_LOG_INT, "...with HDFAR 0x%x\n", + (uint32_t)env->exception.vaddress); + addr = 0x10; + break; + case EXCP_IRQ: + addr = 0x18; + break; + case EXCP_FIQ: + addr = 0x1c; + break; + case EXCP_HVC: + addr = 0x08; + break; + case EXCP_HYP_TRAP: + addr = 0x14; + default: + cpu_abort(cs, "Unhandled exception 0x%x\n", cs->exception_index); + } + + if (cs->exception_index != EXCP_IRQ && cs->exception_index != EXCP_FIQ) { + env->cp15.esr_el[2] = env->exception.syndrome; + } + + if (arm_current_el(env) != 2 && addr < 0x14) { + addr = 0x14; + } + + mask = 0; + if (!(env->cp15.scr_el3 & SCR_EA)) { + mask |= CPSR_A; + } + if (!(env->cp15.scr_el3 & SCR_IRQ)) { + mask |= CPSR_I; + } + if (!(env->cp15.scr_el3 & SCR_FIQ)) { + mask |= CPSR_F; + } + + addr += env->cp15.hvbar; + + take_aarch32_exception(env, ARM_CPU_MODE_HYP, mask, 0, addr); +} + static void arm_cpu_do_interrupt_aarch32(CPUState *cs) { ARMCPU *cpu = ARM_CPU(cs); @@ -8108,6 +8185,11 @@ static void arm_cpu_do_interrupt_aarch32(CPUState *cs) env->cp15.mdscr_el1 = deposit64(env->cp15.mdscr_el1, 2, 4, moe); } + if (env->exception.target_el == 2) { + arm_cpu_do_interrupt_aarch32_hyp(cs); + return; + } + /* TODO: Vectored interrupt controller. */ switch (cs->exception_index) { case EXCP_UDEF: From patchwork Mon Aug 20 15:30:19 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 959823 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=nongnu.org (client-ip=2001:4830:134:3::11; helo=lists.gnu.org; envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=fail (p=none dis=none) header.from=linaro.org Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 41vHwn3b73z9s4v for ; Tue, 21 Aug 2018 01:36:57 +1000 (AEST) Received: from localhost ([::1]:47775 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frmEh-0001u5-5l for incoming@patchwork.ozlabs.org; Mon, 20 Aug 2018 11:36:55 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:46226) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frm8U-0005a1-Uv for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:31 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1frm8U-0004AF-9B for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:30 -0400 Received: from orth.archaic.org.uk ([2001:8b0:1d0::2]:44712) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1frm8S-00044t-IG; Mon, 20 Aug 2018 11:30:28 -0400 Received: from pm215 by orth.archaic.org.uk with local (Exim 4.89) (envelope-from ) id 1frm8R-0003aL-KN; Mon, 20 Aug 2018 16:30:27 +0100 From: Peter Maydell To: qemu-arm@nongnu.org, qemu-devel@nongnu.org Date: Mon, 20 Aug 2018 16:30:19 +0100 Message-Id: <20180820153020.21478-6-peter.maydell@linaro.org> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180820153020.21478-1-peter.maydell@linaro.org> References: <20180820153020.21478-1-peter.maydell@linaro.org> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2001:8b0:1d0::2 Subject: [Qemu-devel] [PATCH v2 5/6] target/arm: Clear CPSR.IL and CPSR.J on 32-bit exception entry X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: "Edgar E . Iglesias" , Luc Michel , patches@linaro.org Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" On 32-bit exception entry, CPSR.J must always be set to 0 (see v7A Arm ARM DDI0406C.c B1.8.5). CPSR.IL must also be cleared on 32-bit exception entry (see v8A Arm ARM DDI0487C.a G1.10). Clear these bits. (This fixes a bug which will never be noticed by non-buggy guests.) Signed-off-by: Peter Maydell --- Not strictly required for Hyp mode, but a minor nit we can cross off the todo list, and it fits better here after the refactoring of the exception-exit function. --- target/arm/helper.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/target/arm/helper.c b/target/arm/helper.c index 21a2d438944..f548ba17697 100644 --- a/target/arm/helper.c +++ b/target/arm/helper.c @@ -8054,6 +8054,8 @@ static void take_aarch32_exception(CPUARMState *env, int new_mode, if (env->cp15.sctlr_el[arm_current_el(env)] & SCTLR_EE) { env->uncached_cpsr |= CPSR_E; } + /* J and IL must always be cleared for exception entry */ + env->uncached_cpsr &= ~(CPSR_IL | CPSR_J); env->daif |= mask; if (new_mode == ARM_CPU_MODE_HYP) { From patchwork Mon Aug 20 15:30:20 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 959819 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=nongnu.org (client-ip=2001:4830:134:3::11; helo=lists.gnu.org; envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=fail (p=none dis=none) header.from=linaro.org Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 41vHqF6z06z9s8T for ; Tue, 21 Aug 2018 01:32:09 +1000 (AEST) Received: from localhost ([::1]:47752 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frmA3-0006Cr-Jy for incoming@patchwork.ozlabs.org; Mon, 20 Aug 2018 11:32:07 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:46265) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1frm8W-0005c6-PI for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:33 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1frm8W-0004CM-0x for qemu-devel@nongnu.org; Mon, 20 Aug 2018 11:30:32 -0400 Received: from orth.archaic.org.uk ([2001:8b0:1d0::2]:44720) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1frm8T-00048Z-PS; Mon, 20 Aug 2018 11:30:30 -0400 Received: from pm215 by orth.archaic.org.uk with local (Exim 4.89) (envelope-from ) id 1frm8S-0003ab-RS; Mon, 20 Aug 2018 16:30:28 +0100 From: Peter Maydell To: qemu-arm@nongnu.org, qemu-devel@nongnu.org Date: Mon, 20 Aug 2018 16:30:20 +0100 Message-Id: <20180820153020.21478-7-peter.maydell@linaro.org> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180820153020.21478-1-peter.maydell@linaro.org> References: <20180820153020.21478-1-peter.maydell@linaro.org> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2001:8b0:1d0::2 Subject: [Qemu-devel] [PATCH v2 6/6] hw/arm/boot: AArch32 kernels should be started in Hyp mode if available X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: "Edgar E . Iglesias" , Luc Michel , patches@linaro.org Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" The kernel booting specification for an AArch32 kernel requires that it is booted in Hyp mode if available; otherwise the kernel can't enable KVM. We were incorrectly leaving the kernel in SVC mode. If we're booting an AArch32 kernel in the Nonsecure state and Hyp mode is available, start in it. Signed-off-by: Peter Maydell --- hw/arm/boot.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/hw/arm/boot.c b/hw/arm/boot.c index ca9467e583f..20c71d7d961 100644 --- a/hw/arm/boot.c +++ b/hw/arm/boot.c @@ -736,6 +736,17 @@ static void do_cpu_reset(void *opaque) } } + if (!env->aarch64 && !info->secure_boot && + arm_feature(env, ARM_FEATURE_EL2)) { + /* + * This is an AArch32 boot not to Secure state, and + * we have Hyp mode available, so boot the kernel into + * Hyp mode. This is not how the CPU comes out of reset, + * so we need to manually put it there. + */ + cpsr_write(env, ARM_CPU_MODE_HYP, CPSR_M, CPSRWriteRaw); + } + if (cs == first_cpu) { AddressSpace *as = arm_boot_address_space(cpu, info);