From patchwork Tue Aug 19 18:09:31 2014 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 35660 Return-Path: X-Original-To: linaro@patches.linaro.org Delivered-To: linaro@patches.linaro.org Received: from mail-ob0-f197.google.com (mail-ob0-f197.google.com [209.85.214.197]) by ip-10-151-82-157.ec2.internal (Postfix) with ESMTPS id 28AB02034C for ; Tue, 19 Aug 2014 18:18:29 +0000 (UTC) Received: by mail-ob0-f197.google.com with SMTP id vb8sf44223977obc.4 for ; Tue, 19 Aug 2014 11:18:28 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20130820; h=x-gm-message-state:mime-version:delivered-to:from:to:date :message-id:in-reply-to:references:subject:precedence:list-id :list-unsubscribe:list-archive:list-post:list-help:list-subscribe :errors-to:sender:x-original-sender :x-original-authentication-results:mailing-list; bh=WQNMEDnQKoihAkiHxcaEV3B+euMBnNSWFzbHV0MJF/8=; b=TLWCtFRdnTBU63y+TO5GpeV6xLZ6b6tLqaa1Hfzi3vHFmDgJTzOvuHussCJZtO0IcQ R8KW0A4CW5PCewPgsQX/amAL1CHS+Ts6B7ynTpL6mxOR7orpAjIOL3nZZqNV7Wokf8G3 +TvyCcLbJi0ARaOBs7DFrB21dka3LSNaMGxRjY8FWPY7C3lhAfVk8VkTXYVV2bf5ROH1 gYZ25I8l1gi9i2j6M8LZTRrN6HXrkspOvOx08+CeIGSzx6inzADg45Q94RwJFqsst1xJ Ub8CZyvvMSVUjpk2/2jyR9WOl54t5+AsUtWGz65S5/iddAo3vOsyNSEbdD13V96kn8DP oFLw== X-Gm-Message-State: ALoCoQkhbo3OfHHIojq+AQopb+PPtP4Lkg+DZjDa9yPpBEbpbsg+o1ZyYRKOhF1MxaUEONZIYyqm X-Received: by 10.50.66.236 with SMTP id i12mr3968821igt.5.1408472308775; Tue, 19 Aug 2014 11:18:28 -0700 (PDT) MIME-Version: 1.0 X-BeenThere: patchwork-forward@linaro.org Received: by 10.140.84.176 with SMTP id l45ls2828732qgd.81.gmail; Tue, 19 Aug 2014 11:18:28 -0700 (PDT) X-Received: by 10.220.189.3 with SMTP id dc3mr1753947vcb.64.1408472308638; Tue, 19 Aug 2014 11:18:28 -0700 (PDT) Received: from mail-vc0-f174.google.com (mail-vc0-f174.google.com [209.85.220.174]) by mx.google.com with ESMTPS id n20si9294453vcq.104.2014.08.19.11.18.28 for (version=TLSv1 cipher=ECDHE-RSA-RC4-SHA bits=128/128); Tue, 19 Aug 2014 11:18:28 -0700 (PDT) Received-SPF: pass (google.com: domain of patch+caf_=patchwork-forward=linaro.org@linaro.org designates 209.85.220.174 as permitted sender) client-ip=209.85.220.174; Received: by mail-vc0-f174.google.com with SMTP id la4so7864981vcb.19 for ; Tue, 19 Aug 2014 11:18:28 -0700 (PDT) X-Received: by 10.52.129.200 with SMTP id ny8mr2347107vdb.27.1408472308547; Tue, 19 Aug 2014 11:18:28 -0700 (PDT) X-Forwarded-To: patchwork-forward@linaro.org X-Forwarded-For: patch@linaro.org patchwork-forward@linaro.org Delivered-To: patch@linaro.org Received: by 10.221.37.5 with SMTP id tc5csp260554vcb; Tue, 19 Aug 2014 11:18:28 -0700 (PDT) X-Received: by 10.224.54.205 with SMTP id r13mr70287267qag.59.1408472307881; Tue, 19 Aug 2014 11:18:27 -0700 (PDT) Received: from lists.gnu.org (lists.gnu.org. [2001:4830:134:3::11]) by mx.google.com with ESMTPS id c77si30161005qge.0.2014.08.19.11.18.27 for (version=TLSv1 cipher=RC4-SHA bits=128/128); Tue, 19 Aug 2014 11:18:27 -0700 (PDT) Received-SPF: pass (google.com: domain of qemu-devel-bounces+patch=linaro.org@nongnu.org designates 2001:4830:134:3::11 as permitted sender) client-ip=2001:4830:134:3::11; Received: from localhost ([::1]:52489 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1XJnzG-0004NZ-U0 for patch@linaro.org; Tue, 19 Aug 2014 14:18:26 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:50669) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1XJnsB-0001Cr-N7 for qemu-devel@nongnu.org; Tue, 19 Aug 2014 14:11:22 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1XJns3-00048O-4t for qemu-devel@nongnu.org; Tue, 19 Aug 2014 14:11:07 -0400 Received: from mnementh.archaic.org.uk ([81.2.115.146]:42051) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1XJns2-0003wv-US for qemu-devel@nongnu.org; Tue, 19 Aug 2014 14:10:59 -0400 Received: from pm215 by mnementh.archaic.org.uk with local (Exim 4.80) (envelope-from ) id 1XJnqq-0000hi-Ff for qemu-devel@nongnu.org; Tue, 19 Aug 2014 19:09:44 +0100 From: Peter Maydell To: qemu-devel@nongnu.org Date: Tue, 19 Aug 2014 19:09:31 +0100 Message-Id: <1408471784-2652-7-git-send-email-peter.maydell@linaro.org> X-Mailer: git-send-email 1.7.10.4 In-Reply-To: <1408471784-2652-1-git-send-email-peter.maydell@linaro.org> References: <1408471784-2652-1-git-send-email-peter.maydell@linaro.org> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 3.x X-Received-From: 81.2.115.146 Subject: [Qemu-devel] [PULL 06/19] target-arm: Don't allow AArch32 to access RES0 CPSR bits X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: , List-Help: , List-Subscribe: , Errors-To: qemu-devel-bounces+patch=linaro.org@nongnu.org Sender: qemu-devel-bounces+patch=linaro.org@nongnu.org X-Removed-Original-Auth: Dkim didn't pass. X-Original-Sender: peter.maydell@linaro.org X-Original-Authentication-Results: mx.google.com; spf=pass (google.com: domain of patch+caf_=patchwork-forward=linaro.org@linaro.org designates 209.85.220.174 as permitted sender) smtp.mail=patch+caf_=patchwork-forward=linaro.org@linaro.org Mailing-list: list patchwork-forward@linaro.org; contact patchwork-forward+owners@linaro.org X-Google-Group-Id: 836684582541 The CPSR has a new-in-v8 execution state bit (IL), and also some state which has effects in AArch32 but appears only in the SPSR format (SS) but is RES0 in the CPSR. Add the IL bit to CPSR_EXEC, and enforce that guest direct reads and writes to CPSR can't read or write the RES0 bits, so the guest can't get at the SS bit which we store in uncached_cpsr. This includes not permitting exception returns to copy reserved bits from an SPSR into CPSR. Signed-off-by: Peter Maydell Reviewed-by: Edgar E. Iglesias --- target-arm/cpu.h | 12 ++++++++++-- target-arm/op_helper.c | 2 +- target-arm/translate.c | 13 +++++++------ 3 files changed, 18 insertions(+), 9 deletions(-) diff --git a/target-arm/cpu.h b/target-arm/cpu.h index 79205ba..8380c13 100644 --- a/target-arm/cpu.h +++ b/target-arm/cpu.h @@ -411,7 +411,13 @@ int arm_cpu_handle_mmu_fault(CPUState *cpu, vaddr address, int rw, #define CPSR_E (1U << 9) #define CPSR_IT_2_7 (0xfc00U) #define CPSR_GE (0xfU << 16) -#define CPSR_RESERVED (0xfU << 20) +#define CPSR_IL (1U << 20) +/* Note that the RESERVED bits include bit 21, which is PSTATE_SS in + * an AArch64 SPSR but RES0 in AArch32 SPSR and CPSR. In QEMU we use + * env->uncached_cpsr bit 21 to store PSTATE.SS when executing in AArch32, + * where it is live state but not accessible to the AArch32 code. + */ +#define CPSR_RESERVED (0x7U << 21) #define CPSR_J (1U << 24) #define CPSR_IT_0_1 (3U << 25) #define CPSR_Q (1U << 27) @@ -428,7 +434,9 @@ int arm_cpu_handle_mmu_fault(CPUState *cpu, vaddr address, int rw, /* Bits writable in user mode. */ #define CPSR_USER (CPSR_NZCV | CPSR_Q | CPSR_GE) /* Execution state bits. MRS read as zero, MSR writes ignored. */ -#define CPSR_EXEC (CPSR_T | CPSR_IT | CPSR_J) +#define CPSR_EXEC (CPSR_T | CPSR_IT | CPSR_J | CPSR_IL) +/* Mask of bits which may be set by exception return copying them from SPSR */ +#define CPSR_ERET_MASK (~CPSR_RESERVED) #define TTBCR_N (7U << 0) /* TTBCR.EAE==0 */ #define TTBCR_T0SZ (7U << 0) /* TTBCR.EAE==1 */ diff --git a/target-arm/op_helper.c b/target-arm/op_helper.c index 25ad902..180a4a0 100644 --- a/target-arm/op_helper.c +++ b/target-arm/op_helper.c @@ -258,7 +258,7 @@ void HELPER(exception_with_syndrome)(CPUARMState *env, uint32_t excp, uint32_t HELPER(cpsr_read)(CPUARMState *env) { - return cpsr_read(env) & ~CPSR_EXEC; + return cpsr_read(env) & ~(CPSR_EXEC | CPSR_RESERVED); } void HELPER(cpsr_write)(CPUARMState *env, uint32_t val, uint32_t mask) diff --git a/target-arm/translate.c b/target-arm/translate.c index 4012185..4cde309 100644 --- a/target-arm/translate.c +++ b/target-arm/translate.c @@ -3908,9 +3908,10 @@ static uint32_t msr_mask(CPUARMState *env, DisasContext *s, int flags, int spsr) mask &= ~(CPSR_E | CPSR_GE); if (!arm_feature(env, ARM_FEATURE_THUMB2)) mask &= ~CPSR_IT; - /* Mask out execution state bits. */ - if (!spsr) - mask &= ~CPSR_EXEC; + /* Mask out execution state and reserved bits. */ + if (!spsr) { + mask &= ~(CPSR_EXEC | CPSR_RESERVED); + } /* Mask out privileged bits. */ if (IS_USER(s)) mask &= CPSR_USER; @@ -3954,7 +3955,7 @@ static void gen_exception_return(DisasContext *s, TCGv_i32 pc) TCGv_i32 tmp; store_reg(s, 15, pc); tmp = load_cpu_field(spsr); - gen_set_cpsr(tmp, 0xffffffff); + gen_set_cpsr(tmp, CPSR_ERET_MASK); tcg_temp_free_i32(tmp); s->is_jmp = DISAS_UPDATE; } @@ -3962,7 +3963,7 @@ static void gen_exception_return(DisasContext *s, TCGv_i32 pc) /* Generate a v6 exception return. Marks both values as dead. */ static void gen_rfe(DisasContext *s, TCGv_i32 pc, TCGv_i32 cpsr) { - gen_set_cpsr(cpsr, 0xffffffff); + gen_set_cpsr(cpsr, CPSR_ERET_MASK); tcg_temp_free_i32(cpsr); store_reg(s, 15, pc); s->is_jmp = DISAS_UPDATE; @@ -8836,7 +8837,7 @@ static void disas_arm_insn(CPUARMState * env, DisasContext *s) if ((insn & (1 << 22)) && !user) { /* Restore CPSR from SPSR. */ tmp = load_cpu_field(spsr); - gen_set_cpsr(tmp, 0xffffffff); + gen_set_cpsr(tmp, CPSR_ERET_MASK); tcg_temp_free_i32(tmp); s->is_jmp = DISAS_UPDATE; }