From patchwork Thu Sep 8 13:12:09 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Jan Beulich X-Patchwork-Id: 9321365 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 896286077F for ; Thu, 8 Sep 2016 13:14:20 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 797A329813 for ; Thu, 8 Sep 2016 13:14:20 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 6E51C29872; Thu, 8 Sep 2016 13:14: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=-4.2 required=2.0 tests=BAYES_00, RCVD_IN_DNSWL_MED autolearn=ham version=3.3.1 Received: from lists.xenproject.org (lists.xenproject.org [192.237.175.120]) (using TLSv1.2 with cipher AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 0D8F629813 for ; Thu, 8 Sep 2016 13:14:19 +0000 (UTC) Received: from localhost ([127.0.0.1] helo=lists.xenproject.org) by lists.xenproject.org with esmtp (Exim 4.84_2) (envelope-from ) id 1bhz7m-0000eQ-KX; Thu, 08 Sep 2016 13:12:14 +0000 Received: from mail6.bemta5.messagelabs.com ([195.245.231.135]) by lists.xenproject.org with esmtp (Exim 4.84_2) (envelope-from ) id 1bhz7l-0000eF-Iz for xen-devel@lists.xenproject.org; Thu, 08 Sep 2016 13:12:13 +0000 Received: from [85.158.139.211] by server-3.bemta-5.messagelabs.com id 23/20-01957-CA361D75; Thu, 08 Sep 2016 13:12:12 +0000 X-Brightmail-Tracker: H4sIAAAAAAAAA+NgFtrDIsWRWlGSWpSXmKPExsXS6fjDS3dN8sV wg+nNQhbft0xmcmD0OPzhCksAYxRrZl5SfkUCa8adKWdZChaZVDzZ1sTYwPhKuYuRk0NIIE/i 8//N7CA2r4CdxMnTH8BsCQFDiafvr7OB2CwCqhJf70xiArHZBNQl2p5tZ+1i5OAQETCQOHc0C cRkFtCX2LaOBaRCGKTz4kFGiOl2Es9OHQSLcwrYS3xpncMIUs4rICjxd4cwSJgZqGT9s19sEx h5ZiFkZiHJQNhaEg9/3WKBsLUlli18zTwLbK+0xPJ/HBBhK4lV/Z9YUZWA2K4SS9Z/YVvAyLG KUaM4tagstUjX0FAvqSgzPaMkNzEzR9fQwFQvN7W4ODE9NScxqVgvOT93EyMwVBmAYAfjynbn Q4ySHExKorw+xRfChfiS8lMqMxKLM+KLSnNSiw8xynBwKEnwhiddDBcSLEpNT61Iy8wBRg1MW oKDR0mEdxdImre4IDG3ODMdInWKUVFKnNcYJCEAksgozYNrg0XqJUZZKWFeRqBDhHgKUotyM0 tQ5V8xinMwKgnz5oNM4cnMK4Gb/gpoMRPQYqFT50EWlyQipKQaGMW909b+lk0Pe2Pdk9u75Pc /vn7ZK4JvzlWwT3Y+ypMvup7hejVHE1PWxZ+bvSU4j2ptn/AxtseP8SkTO7fTnh+7JvBtvlL8 zJEpYtnlG1xHDm6b6tP97GZOqabuLpNy0z7BhMu39glGB9uEbf0b0ee3NU9WYofI5zOytlx3J xYuXZjmFmD9WYmlOCPRUIu5qDgRAIaZSXrPAgAA X-Env-Sender: JBeulich@suse.com X-Msg-Ref: server-14.tower-206.messagelabs.com!1473340330!22116704!1 X-Originating-IP: [137.65.248.74] X-SpamReason: No, hits=0.0 required=7.0 tests= X-StarScan-Received: X-StarScan-Version: 8.84; banners=-,-,- X-VirusChecked: Checked Received: (qmail 59836 invoked from network); 8 Sep 2016 13:12:11 -0000 Received: from prv-mh.provo.novell.com (HELO prv-mh.provo.novell.com) (137.65.248.74) by server-14.tower-206.messagelabs.com with DHE-RSA-AES256-GCM-SHA384 encrypted SMTP; 8 Sep 2016 13:12:11 -0000 Received: from INET-PRV-MTA by prv-mh.provo.novell.com with Novell_GroupWise; Thu, 08 Sep 2016 07:12:09 -0600 Message-Id: <57D17FC9020000780010D17A@prv-mh.provo.novell.com> X-Mailer: Novell GroupWise Internet Agent 14.2.1 Date: Thu, 08 Sep 2016 07:12:09 -0600 From: "Jan Beulich" To: "xen-devel" References: <57D17C78020000780010D127@prv-mh.provo.novell.com> In-Reply-To: <57D17C78020000780010D127@prv-mh.provo.novell.com> Mime-Version: 1.0 Cc: Andrew Cooper Subject: [Xen-devel] [PATCH 06/17] x86emul: add EVEX decoding X-BeenThere: xen-devel@lists.xen.org X-Mailman-Version: 2.1.18 Precedence: list List-Id: Xen developer discussion List-Unsubscribe: , List-Post: List-Help: List-Subscribe: , Errors-To: xen-devel-bounces@lists.xen.org Sender: "Xen-devel" X-Virus-Scanned: ClamAV using ClamSMTP This way we can at least size (and e.g. skip) them if needed, and we also won't raise the wrong fault due to not having read all relevant bytes. Signed-off-by: Jan Beulich --- TBD: I'm kind of undecided whether to right away propagate evex.R into modrm_reg (and then also deal with the new meaning of evex.x for modrm_rm). Since that doesn't affect GPRs (and the extra bits would need masking off when accessing GPRs) I've left this out for now. x86emul: add EVEX decoding This way we can at least size (and e.g. skip) them if needed, and we also won't raise the wrong fault due to not having read all relevant bytes. Signed-off-by: Jan Beulich --- TBD: I'm kind of undecided whether to right away propagate evex.R into modrm_reg (and then also deal with the new meaning of evex.x for modrm_rm). Since that doesn't affect GPRs (and the extra bits would need masking off when accessing GPRs) I've left this out for now. --- a/xen/arch/x86/x86_emulate/x86_emulate.c +++ b/xen/arch/x86/x86_emulate/x86_emulate.c @@ -336,6 +336,27 @@ union vex { ptr[1] = rex | REX_PREFIX; \ } while (0) +union evex { + uint8_t raw[3]; + struct { + uint8_t opcx:2; + uint8_t :2; + uint8_t R:1; + uint8_t b:1; + uint8_t x:1; + uint8_t r:1; + uint8_t pfx:2; + uint8_t evex:1; + uint8_t reg:4; + uint8_t w:1; + uint8_t opmsk:3; + uint8_t RX:1; + uint8_t bcst:1; + uint8_t lr:2; + uint8_t z:1; + }; +}; + #define rep_prefix() (vex.pfx >= vex_f3) #define repe_prefix() (vex.pfx == vex_f3) #define repne_prefix() (vex.pfx == vex_f2) @@ -1596,6 +1617,7 @@ struct x86_emulate_state { bool lock_prefix; opcode_desc_t desc; union vex vex; + union evex evex; int override_seg; /* @@ -1623,6 +1645,7 @@ struct x86_emulate_state { #define rex_prefix (state->rex_prefix) #define lock_prefix (state->lock_prefix) #define vex (state->vex) +#define evex (state->evex) #define override_seg (state->override_seg) #define ea (state->ea) @@ -1811,7 +1834,8 @@ x86_decode( modrm = insn_fetch_type(uint8_t); modrm_mod = (modrm & 0xc0) >> 6; - if ( !ext && ((b & ~1) == 0xc4 || (b == 0x8f && (modrm & 0x18))) ) + if ( !ext && ((b & ~1) == 0xc4 || (b == 0x8f && (modrm & 0x18)) || + b == 0x62) ) switch ( def_ad_bytes ) { default: @@ -1825,7 +1849,7 @@ x86_decode( break; /* fall through */ case 8: - /* VEX / XOP */ + /* VEX / XOP / EVEX */ generate_exception_if(rex_prefix || vex.pfx, EXC_UD, -1); vex.raw[0] = modrm; @@ -1852,6 +1876,14 @@ x86_decode( op_bytes = 8; } } + if ( b == 0x62 ) + { + evex.raw[0] = vex.raw[0]; + evex.raw[1] = vex.raw[1]; + evex.raw[2] = insn_fetch_type(uint8_t); + + vex.opcx = evex.opcx; + } } if ( mode_64bit() && !vex.r ) rex_prefix |= REX_R; --- a/xen/arch/x86/x86_emulate/x86_emulate.c +++ b/xen/arch/x86/x86_emulate/x86_emulate.c @@ -336,6 +336,27 @@ union vex { ptr[1] = rex | REX_PREFIX; \ } while (0) +union evex { + uint8_t raw[3]; + struct { + uint8_t opcx:2; + uint8_t :2; + uint8_t R:1; + uint8_t b:1; + uint8_t x:1; + uint8_t r:1; + uint8_t pfx:2; + uint8_t evex:1; + uint8_t reg:4; + uint8_t w:1; + uint8_t opmsk:3; + uint8_t RX:1; + uint8_t bcst:1; + uint8_t lr:2; + uint8_t z:1; + }; +}; + #define rep_prefix() (vex.pfx >= vex_f3) #define repe_prefix() (vex.pfx == vex_f3) #define repne_prefix() (vex.pfx == vex_f2) @@ -1596,6 +1617,7 @@ struct x86_emulate_state { bool lock_prefix; opcode_desc_t desc; union vex vex; + union evex evex; int override_seg; /* @@ -1623,6 +1645,7 @@ struct x86_emulate_state { #define rex_prefix (state->rex_prefix) #define lock_prefix (state->lock_prefix) #define vex (state->vex) +#define evex (state->evex) #define override_seg (state->override_seg) #define ea (state->ea) @@ -1811,7 +1834,8 @@ x86_decode( modrm = insn_fetch_type(uint8_t); modrm_mod = (modrm & 0xc0) >> 6; - if ( !ext && ((b & ~1) == 0xc4 || (b == 0x8f && (modrm & 0x18))) ) + if ( !ext && ((b & ~1) == 0xc4 || (b == 0x8f && (modrm & 0x18)) || + b == 0x62) ) switch ( def_ad_bytes ) { default: @@ -1825,7 +1849,7 @@ x86_decode( break; /* fall through */ case 8: - /* VEX / XOP */ + /* VEX / XOP / EVEX */ generate_exception_if(rex_prefix || vex.pfx, EXC_UD, -1); vex.raw[0] = modrm; @@ -1852,6 +1876,14 @@ x86_decode( op_bytes = 8; } } + if ( b == 0x62 ) + { + evex.raw[0] = vex.raw[0]; + evex.raw[1] = vex.raw[1]; + evex.raw[2] = insn_fetch_type(uint8_t); + + vex.opcx = evex.opcx; + } } if ( mode_64bit() && !vex.r ) rex_prefix |= REX_R;