From patchwork Tue Jun 21 21:48:52 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?C=C3=A9dric_Le_Goater?= X-Patchwork-Id: 9191467 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id 16469601C0 for ; Tue, 21 Jun 2016 21:58:21 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id F38E42818B for ; Tue, 21 Jun 2016 21:58:20 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id E5475281DB; Tue, 21 Jun 2016 21:58:20 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-6.9 required=2.0 tests=BAYES_00,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id D00A12818B for ; Tue, 21 Jun 2016 21:58:19 +0000 (UTC) Received: from localhost ([::1]:54476 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1bFTgZ-00030r-0i for patchwork-qemu-devel@patchwork.kernel.org; Tue, 21 Jun 2016 17:58:19 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:59487) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1bFTZ2-0002JF-Ol for qemu-devel@nongnu.org; Tue, 21 Jun 2016 17:50:37 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1bFTYx-0001D7-SU for qemu-devel@nongnu.org; Tue, 21 Jun 2016 17:50:31 -0400 Received: from 19.mo1.mail-out.ovh.net ([178.32.97.206]:53727) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1bFTYx-0001Cz-Ef for qemu-devel@nongnu.org; Tue, 21 Jun 2016 17:50:27 -0400 Received: from player770.ha.ovh.net (b7.ovh.net [213.186.33.57]) by mo1.mail-out.ovh.net (Postfix) with ESMTP id CB538FF9BDC for ; Tue, 21 Jun 2016 23:50:26 +0200 (CEST) Received: from hermes.ibm.com (LFbn-1-2234-107.w90-76.abo.wanadoo.fr [90.76.55.107]) (Authenticated sender: clg@kaod.org) by player770.ha.ovh.net (Postfix) with ESMTPSA id 5C31F3C0069; Tue, 21 Jun 2016 23:50:20 +0200 (CEST) From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= To: qemu-ppc@nongnu.org Date: Tue, 21 Jun 2016 23:48:52 +0200 Message-Id: <1466545735-2555-8-git-send-email-clg@kaod.org> X-Mailer: git-send-email 2.1.4 In-Reply-To: <1466545735-2555-1-git-send-email-clg@kaod.org> References: <1466545735-2555-1-git-send-email-clg@kaod.org> MIME-Version: 1.0 X-Ovh-Tracer-Id: 13160081061562125139 X-VR-SPAMSTATE: OK X-VR-SPAMSCORE: -100 X-VR-SPAMCAUSE: gggruggvucftvghtrhhoucdtuddrfeeltddrtddugddthecutefuodetggdotefrodftvfcurfhrohhfihhlvgemucfqggfjnecuuegrihhlohhuthemuceftddtnecusecvtfgvtghiphhivghnthhsucdlqddutddtmd X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x (no timestamps) [generic] X-Received-From: 178.32.97.206 Subject: [Qemu-devel] [PATCH v2 07/10] ppc: Add real mode CI load/store instructions for P7 and P8 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-devel@nongnu.org, Cedric Le Goater , Alexander Graf , David Gibson Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP From: Benjamin Herrenschmidt Those instructions are only available in hypervisor real mode and allow cache inhibited garded access to devices in that mode. Signed-off-by: Benjamin Herrenschmidt [clg: fixed checkpatch.pl errors ] Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson --- target-ppc/cpu.h | 4 ++- target-ppc/translate.c | 59 ++++++++++++++++++++++++++++++++++++--------- target-ppc/translate_init.c | 6 +++-- 3 files changed, 55 insertions(+), 14 deletions(-) diff --git a/target-ppc/cpu.h b/target-ppc/cpu.h index f005549c352e..61a24b19ffce 100644 --- a/target-ppc/cpu.h +++ b/target-ppc/cpu.h @@ -1912,6 +1912,8 @@ enum { PPC_POPCNTB = 0x0000000000001000ULL, /* string load / store */ PPC_STRING = 0x0000000000002000ULL, + /* real mode cache inhibited load / store */ + PPC_CILDST = 0x0000000000004000ULL, /* Floating-point unit extensions */ /* Optional floating point instructions */ @@ -2026,7 +2028,7 @@ enum { | PPC_MFAPIDI | PPC_TLBIVA | PPC_TLBIVAX \ | PPC_4xx_COMMON | PPC_40x_ICBT | PPC_RFMCI \ | PPC_RFDI | PPC_DCR | PPC_DCRX | PPC_DCRUX \ - | PPC_POPCNTWD) + | PPC_POPCNTWD | PPC_CILDST) /* extended type values */ diff --git a/target-ppc/translate.c b/target-ppc/translate.c index 4da92dae69fd..ca7036b22678 100644 --- a/target-ppc/translate.c +++ b/target-ppc/translate.c @@ -192,7 +192,7 @@ struct DisasContext { uint32_t opcode; uint32_t exception; /* Routine used to access memory */ - bool pr, hv; + bool pr, hv, dr; bool lazy_tlb_flush; int mem_idx; int access_type; @@ -387,6 +387,7 @@ typedef struct opcode_t { #if defined(CONFIG_USER_ONLY) #define CHK_HV GEN_PRIV #define CHK_SV GEN_PRIV +#define CHK_HVRM GEN_PRIV #else #define CHK_HV \ do { \ @@ -400,6 +401,12 @@ typedef struct opcode_t { GEN_PRIV; \ } \ } while (0) +#define CHK_HVRM \ + do { \ + if (unlikely(ctx->pr || !ctx->hv || ctx->dr)) { \ + GEN_PRIV; \ + } \ + } while (0) #endif #define CHK_NONE @@ -2895,18 +2902,23 @@ static void glue(gen_, name##ux)(DisasContext *ctx) tcg_temp_free(EA); \ } -#define GEN_LDX_E(name, ldop, opc2, opc3, type, type2) \ +#define GEN_LDX_E(name, ldop, opc2, opc3, type, type2, chk) \ static void glue(gen_, name##x)(DisasContext *ctx) \ { \ TCGv EA; \ + chk; \ gen_set_access_type(ctx, ACCESS_INT); \ EA = tcg_temp_new(); \ gen_addr_reg_index(ctx, EA); \ gen_qemu_##ldop(ctx, cpu_gpr[rD(ctx->opcode)], EA); \ tcg_temp_free(EA); \ } + #define GEN_LDX(name, ldop, opc2, opc3, type) \ - GEN_LDX_E(name, ldop, opc2, opc3, type, PPC_NONE) + GEN_LDX_E(name, ldop, opc2, opc3, type, PPC_NONE, CHK_NONE) + +#define GEN_LDX_HVRM(name, ldop, opc2, opc3, type) \ + GEN_LDX_E(name, ldop, opc2, opc3, type, PPC_NONE, CHK_HVRM) #define GEN_LDS(name, ldop, op, type) \ GEN_LD(name, ldop, op | 0x20, type); \ @@ -2932,6 +2944,12 @@ GEN_LDUX(ld, ld64, 0x15, 0x01, PPC_64B); /* ldx */ GEN_LDX(ld, ld64, 0x15, 0x00, PPC_64B); +/* CI load/store variants */ +GEN_LDX_HVRM(ldcix, ld64, 0x15, 0x1b, PPC_CILDST) +GEN_LDX_HVRM(lwzcix, ld32u, 0x15, 0x15, PPC_CILDST) +GEN_LDX_HVRM(lhzcix, ld16u, 0x15, 0x19, PPC_CILDST) +GEN_LDX_HVRM(lbzcix, ld8u, 0x15, 0x1a, PPC_CILDST) + static void gen_ld(DisasContext *ctx) { TCGv EA; @@ -3050,10 +3068,11 @@ static void glue(gen_, name##ux)(DisasContext *ctx) tcg_temp_free(EA); \ } -#define GEN_STX_E(name, stop, opc2, opc3, type, type2) \ +#define GEN_STX_E(name, stop, opc2, opc3, type, type2, chk) \ static void glue(gen_, name##x)(DisasContext *ctx) \ { \ TCGv EA; \ + chk; \ gen_set_access_type(ctx, ACCESS_INT); \ EA = tcg_temp_new(); \ gen_addr_reg_index(ctx, EA); \ @@ -3061,7 +3080,10 @@ static void glue(gen_, name##x)(DisasContext *ctx) \ tcg_temp_free(EA); \ } #define GEN_STX(name, stop, opc2, opc3, type) \ - GEN_STX_E(name, stop, opc2, opc3, type, PPC_NONE) + GEN_STX_E(name, stop, opc2, opc3, type, PPC_NONE, CHK_NONE) + +#define GEN_STX_HVRM(name, stop, opc2, opc3, type) \ + GEN_STX_E(name, stop, opc2, opc3, type, PPC_NONE, CHK_HVRM) #define GEN_STS(name, stop, op, type) \ GEN_ST(name, stop, op | 0x20, type); \ @@ -3078,6 +3100,10 @@ GEN_STS(stw, st32, 0x04, PPC_INTEGER); #if defined(TARGET_PPC64) GEN_STUX(std, st64, 0x15, 0x05, PPC_64B); GEN_STX(std, st64, 0x15, 0x04, PPC_64B); +GEN_STX_HVRM(stdcix, st64, 0x15, 0x1f, PPC_CILDST) +GEN_STX_HVRM(stwcix, st32, 0x15, 0x1c, PPC_CILDST) +GEN_STX_HVRM(sthcix, st16, 0x15, 0x1d, PPC_CILDST) +GEN_STX_HVRM(stbcix, st8, 0x15, 0x1e, PPC_CILDST) static void gen_std(DisasContext *ctx) { @@ -3166,7 +3192,7 @@ static inline void gen_qemu_ld64ur(DisasContext *ctx, TCGv arg1, TCGv arg2) TCGMemOp op = MO_Q | (ctx->default_tcg_memop_mask ^ MO_BSWAP); tcg_gen_qemu_ld_i64(arg1, arg2, ctx->mem_idx, op); } -GEN_LDX_E(ldbr, ld64ur, 0x14, 0x10, PPC_NONE, PPC2_DBRX); +GEN_LDX_E(ldbr, ld64ur, 0x14, 0x10, PPC_NONE, PPC2_DBRX, CHK_NONE); #endif /* TARGET_PPC64 */ /* sthbrx */ @@ -3192,7 +3218,7 @@ static inline void gen_qemu_st64r(DisasContext *ctx, TCGv arg1, TCGv arg2) TCGMemOp op = MO_Q | (ctx->default_tcg_memop_mask ^ MO_BSWAP); tcg_gen_qemu_st_i64(arg1, arg2, ctx->mem_idx, op); } -GEN_STX_E(stdbr, st64r, 0x14, 0x14, PPC_NONE, PPC2_DBRX); +GEN_STX_E(stdbr, st64r, 0x14, 0x14, PPC_NONE, PPC2_DBRX, CHK_NONE); #endif /* TARGET_PPC64 */ /*** Integer load and store multiple ***/ @@ -10210,7 +10236,7 @@ GEN_HANDLER(name, opc, 0xFF, 0xFF, 0x00000000, type), GEN_HANDLER(name##u, opc, 0xFF, 0xFF, 0x00000000, type), #define GEN_LDUX(name, ldop, opc2, opc3, type) \ GEN_HANDLER(name##ux, 0x1F, opc2, opc3, 0x00000001, type), -#define GEN_LDX_E(name, ldop, opc2, opc3, type, type2) \ +#define GEN_LDX_E(name, ldop, opc2, opc3, type, type2, chk) \ GEN_HANDLER_E(name##x, 0x1F, opc2, opc3, 0x00000001, type, type2), #define GEN_LDS(name, ldop, op, type) \ GEN_LD(name, ldop, op | 0x20, type) \ @@ -10227,7 +10253,13 @@ GEN_LDUX(lwa, ld32s, 0x15, 0x0B, PPC_64B) GEN_LDX(lwa, ld32s, 0x15, 0x0A, PPC_64B) GEN_LDUX(ld, ld64, 0x15, 0x01, PPC_64B) GEN_LDX(ld, ld64, 0x15, 0x00, PPC_64B) -GEN_LDX_E(ldbr, ld64ur, 0x14, 0x10, PPC_NONE, PPC2_DBRX) +GEN_LDX_E(ldbr, ld64ur, 0x14, 0x10, PPC_NONE, PPC2_DBRX, CHK_NONE) + +/* HV/P7 and later only */ +GEN_LDX_HVRM(ldcix, ld64, 0x15, 0x1b, PPC_CILDST) +GEN_LDX_HVRM(lwzcix, ld32u, 0x15, 0x18, PPC_CILDST) +GEN_LDX_HVRM(lhzcix, ld16u, 0x15, 0x19, PPC_CILDST) +GEN_LDX_HVRM(lbzcix, ld8u, 0x15, 0x1a, PPC_CILDST) #endif GEN_LDX(lhbr, ld16ur, 0x16, 0x18, PPC_INTEGER) GEN_LDX(lwbr, ld32ur, 0x16, 0x10, PPC_INTEGER) @@ -10243,7 +10275,7 @@ GEN_HANDLER(name, opc, 0xFF, 0xFF, 0x00000000, type), GEN_HANDLER(stop##u, opc, 0xFF, 0xFF, 0x00000000, type), #define GEN_STUX(name, stop, opc2, opc3, type) \ GEN_HANDLER(name##ux, 0x1F, opc2, opc3, 0x00000001, type), -#define GEN_STX_E(name, stop, opc2, opc3, type, type2) \ +#define GEN_STX_E(name, stop, opc2, opc3, type, type2, chk) \ GEN_HANDLER_E(name##x, 0x1F, opc2, opc3, 0x00000001, type, type2), #define GEN_STS(name, stop, op, type) \ GEN_ST(name, stop, op | 0x20, type) \ @@ -10257,7 +10289,11 @@ GEN_STS(stw, st32, 0x04, PPC_INTEGER) #if defined(TARGET_PPC64) GEN_STUX(std, st64, 0x15, 0x05, PPC_64B) GEN_STX(std, st64, 0x15, 0x04, PPC_64B) -GEN_STX_E(stdbr, st64r, 0x14, 0x14, PPC_NONE, PPC2_DBRX) +GEN_STX_E(stdbr, st64r, 0x14, 0x14, PPC_NONE, PPC2_DBRX, CHK_NONE) +GEN_STX_HVRM(stdcix, st64, 0x15, 0x1f, PPC_CILDST) +GEN_STX_HVRM(stwcix, st32, 0x15, 0x1c, PPC_CILDST) +GEN_STX_HVRM(sthcix, st16, 0x15, 0x1d, PPC_CILDST) +GEN_STX_HVRM(stbcix, st8, 0x15, 0x1e, PPC_CILDST) #endif GEN_STX(sthbr, st16r, 0x16, 0x1C, PPC_INTEGER) GEN_STX(stwbr, st32r, 0x16, 0x14, PPC_INTEGER) @@ -11425,6 +11461,7 @@ void gen_intermediate_code(CPUPPCState *env, struct TranslationBlock *tb) ctx.spr_cb = env->spr_cb; ctx.pr = msr_pr; ctx.mem_idx = env->dmmu_idx; + ctx.dr = msr_dr; #if !defined(CONFIG_USER_ONLY) ctx.hv = msr_hv || !env->has_hv_mode; #endif diff --git a/target-ppc/translate_init.c b/target-ppc/translate_init.c index 3b4234b325d1..6f2f760728bb 100644 --- a/target-ppc/translate_init.c +++ b/target-ppc/translate_init.c @@ -8395,7 +8395,8 @@ POWERPC_FAMILY(POWER7)(ObjectClass *oc, void *data) PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_64B | PPC_64H | PPC_64BX | PPC_ALTIVEC | PPC_SEGMENT_64B | PPC_SLBI | - PPC_POPCNTB | PPC_POPCNTWD; + PPC_POPCNTB | PPC_POPCNTWD | + PPC_CILDST; pcc->insns_flags2 = PPC2_VSX | PPC2_DFP | PPC2_DBRX | PPC2_ISA205 | PPC2_PERM_ISA206 | PPC2_DIVE_ISA206 | PPC2_ATOMIC_ISA206 | PPC2_FP_CVT_ISA206 | @@ -8476,7 +8477,8 @@ POWERPC_FAMILY(POWER8)(ObjectClass *oc, void *data) PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_64B | PPC_64H | PPC_64BX | PPC_ALTIVEC | PPC_SEGMENT_64B | PPC_SLBI | - PPC_POPCNTB | PPC_POPCNTWD; + PPC_POPCNTB | PPC_POPCNTWD | + PPC_CILDST; pcc->insns_flags2 = PPC2_VSX | PPC2_VSX207 | PPC2_DFP | PPC2_DBRX | PPC2_PERM_ISA206 | PPC2_DIVE_ISA206 | PPC2_ATOMIC_ISA206 | PPC2_FP_CVT_ISA206 |