From patchwork Sat Jul 9 03:22:25 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Benjamin Herrenschmidt X-Patchwork-Id: 646615 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.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 3rmcCW6vMnz9ssP for ; Sat, 9 Jul 2016 13:24:07 +1000 (AEST) Received: from localhost ([::1]:48776 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1bLis7-00006A-8T for incoming@patchwork.ozlabs.org; Fri, 08 Jul 2016 23:24:03 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:39177) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1bLirA-0007yT-JV for qemu-devel@nongnu.org; Fri, 08 Jul 2016 23:23:05 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1bLir8-00075l-8O for qemu-devel@nongnu.org; Fri, 08 Jul 2016 23:23:03 -0400 Received: from gate.crashing.org ([63.228.1.57]:42860) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1bLir1-000755-Di; Fri, 08 Jul 2016 23:22:55 -0400 Received: from localhost.localdomain (localhost.localdomain [127.0.0.1]) by gate.crashing.org (8.14.1/8.13.8) with ESMTP id u693MS83004425; Fri, 8 Jul 2016 22:22:30 -0500 Message-ID: <1468034545.20552.26.camel@kernel.crashing.org> From: Benjamin Herrenschmidt To: Mark Cave-Ayland , David Gibson , peter.maydell@linaro.org Date: Sat, 09 Jul 2016 13:22:25 +1000 In-Reply-To: <1468033695.20552.24.camel@kernel.crashing.org> References: <1467355319-28406-1-git-send-email-david@gibson.dropbear.id.au> <1467355319-28406-6-git-send-email-david@gibson.dropbear.id.au> <1468032411.20552.21.camel@kernel.crashing.org> <1468032757.20552.22.camel@au1.ibm.com> <1468033216.20552.23.camel@kernel.crashing.org> <1468033695.20552.24.camel@kernel.crashing.org> X-Mailer: Evolution 3.20.3 (3.20.3-1.fc24.1) Mime-Version: 1.0 X-MIME-Autoconverted: from 8bit to base64 by gate.crashing.org id u693MS83004425 X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.6.x X-Received-From: 63.228.1.57 Subject: [Qemu-devel] [PATCH] ppc: Fix support for odd MSR combinations 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: qemu-ppc@nongnu.org, qemu-devel@nongnu.org, =?ISO-8859-1?Q?C=E9dric?= Le Goater Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" MacOS uses an architecturally illegal MSR combination that seems nonetheless supported by 32-bit processors, which is to have MSR[PR]=1 and one or more of MSR[DR/IR/EE]=0. This adds support for it. To work properly we need to also properly include support for PR=1,{I,D}R=0 to the MMU index used by the qemu TLB. Signed-off-by: Benjamin Herrenschmidt --- This applies on top of the existing "ppc: Enforce setting MSR:EE, IR and DR when MSR:PR is set" patch, so don't revert it, and fixes booting MacOS 9. Mark: I haven't reproduced your problem with Darwin.  target-ppc/helper_regs.h | 46 ++++++++++++++++++++++------------------------  1 file changed, 22 insertions(+), 24 deletions(-) diff --git a/target-ppc/helper_regs.h b/target-ppc/helper_regs.h index 8fdfa5c..4015ce2 100644 --- a/target-ppc/helper_regs.h +++ b/target-ppc/helper_regs.h @@ -41,17 +41,19 @@ static inline void hreg_swap_gpr_tgpr(CPUPPCState *env)    static inline void hreg_compute_mem_idx(CPUPPCState *env)  { -    /* This is our encoding for server processors +    /* This is our encoding for server processors. The architecture +     * specifies that there is no such thing as userspace with +     * translation off, however it appears that MacOS does it and +     * some 32-bit CPUs support it. Weird...       *       *   0 = Guest User space virtual mode       *   1 = Guest Kernel space virtual mode -     *   2 = Guest Kernel space real mode -     *   3 = HV User space virtual mode -     *   4 = HV Kernel space virtual mode -     *   5 = HV Kernel space real mode -     * -     * The combination PR=1 IR&DR=0 is invalid, we will treat -     * it as IR=DR=1 +     *   2 = Guest User space real mode +     *   3 = Guest Kernel space real mode +     *   4 = HV User space virtual mode +     *   5 = HV Kernel space virtual mode +     *   6 = HV User space real mode +     *   7 = HV Kernel space real mode       *       * For BookE, we need 8 MMU modes as follow:       * @@ -71,20 +73,11 @@ static inline void hreg_compute_mem_idx(CPUPPCState *env)          env->immu_idx += msr_gs ? 4 : 0;          env->dmmu_idx += msr_gs ? 4 : 0;      } else { -        /* First calucalte a base value independent of HV */ -        if (msr_pr != 0) { -            /* User space, ignore IR and DR */ -            env->immu_idx = env->dmmu_idx = 0; -        } else { -            /* Kernel, setup a base I/D value */ -            env->immu_idx = msr_ir ? 1 : 2; -            env->dmmu_idx = msr_dr ? 1 : 2; -        } -        /* Then offset it for HV */ -        if (msr_hv) { -            env->immu_idx += 3; -            env->dmmu_idx += 3; -        } +        env->immu_idx = env->dmmu_idx = msr_pr ? 0 : 1; +        env->immu_idx += msr_ir ? 0 : 2; +        env->dmmu_idx += msr_dr ? 0 : 2; +        env->immu_idx += msr_hv ? 4 : 0; +        env->dmmu_idx += msr_hv ? 4 : 0;      }  }   @@ -136,8 +129,13 @@ static inline int hreg_store_msr(CPUPPCState *env, target_ulong value,          /* Change the exception prefix on PowerPC 601 */          env->excp_prefix = ((value >> MSR_EP) & 1) * 0xFFF00000;      } -    /* If PR=1 then EE, IR and DR must be 1 */ -    if ((value >> MSR_PR) & 1) { +    /* If PR=1 then EE, IR and DR must be 1 +     * +     * Note: We only enforce this on 64-bit processors. It appears that +     * 32-bit implementations supports PR=1 and EE/DR/IR=0 and MacOS +     * exploits it. +     */ +    if ((env->flags & PPC_64B) && ((value >> MSR_PR) & 1)) {          value |= (1 << MSR_EE) | (1 << MSR_DR) | (1 << MSR_IR);      }  #endif