From 45ce540b9b756f372840e923b73cfd7e3edd85f8 Mon Sep 17 00:00:00 2001 From: Wunk Date: Sun, 2 Oct 2022 02:17:19 -0700 Subject: ARMeilleure: Add `gfni` acceleration (#3669) * ARMeilleure: Add `GFNI` detection This is intended for utilizing the `gf2p8affineqb` instruction * ARMeilleure: Add `gf2p8affineqb` Not using the VEX or EVEX-form of this instruction is intentional. There are `GFNI`-chips that do not support AVX(so no VEX encoding) such as Tremont(Lakefield) chips as well as Jasper Lake. https://github.com/InstLatx64/InstLatx64/blob/13df339fe7150b114929f71b19a6b2fe72fc751e/GenuineIntel/GenuineIntel00806A1_Lakefield_LC_InstLatX64.txt#L1297-L1299 https://github.com/InstLatx64/InstLatx64/blob/13df339fe7150b114929f71b19a6b2fe72fc751e/GenuineIntel/GenuineIntel00906C0_JasperLake_InstLatX64.txt#L1252-L1254 * ARMeilleure: Add `gfni` acceleration of `Rbit_V` Passes all `Rbit_V*` unit tests on my `i9-11900k` * ARMeilleure: Add `gfni` acceleration of `S{l,r}i_V` Also added a fast-path for when the shift amount is greater than the size of the element. * ARMeilleure: Add `gfni` acceleration of `Shl_V` and `Sshr_V` * ARMeilleure: Increment InternalVersion * ARMeilleure: Fix Intrinsic and Assembler Table alignment `gf2p8affineqb` is the longest instruction name I know of. It shouldn't get any wider than this. * ARMeilleure: Remove SSE2+SHA requirement for GFNI * ARMeilleure Add `X86GetGf2p8LogicalShiftLeft` Used to generate GF(2^8) 8x8 bit-matrices for bit-shifting for the `gf2p8affineqb` instruction. * ARMeilleure: Append `FeatureInfo7Ecx` to `FeatureInfo` --- ARMeilleure/CodeGen/X86/HardwareCapabilities.cs | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) (limited to 'ARMeilleure/CodeGen/X86/HardwareCapabilities.cs') diff --git a/ARMeilleure/CodeGen/X86/HardwareCapabilities.cs b/ARMeilleure/CodeGen/X86/HardwareCapabilities.cs index a29dd5be..c12a4e28 100644 --- a/ARMeilleure/CodeGen/X86/HardwareCapabilities.cs +++ b/ARMeilleure/CodeGen/X86/HardwareCapabilities.cs @@ -20,8 +20,9 @@ namespace ARMeilleure.CodeGen.X86 if (maxNum >= 7) { - (_, int ebx7, _, _) = X86Base.CpuId(0x00000007, 0x00000000); + (_, int ebx7, int ecx7, _) = X86Base.CpuId(0x00000007, 0x00000000); FeatureInfo7Ebx = (FeatureFlags7Ebx)ebx7; + FeatureInfo7Ecx = (FeatureFlags7Ecx)ecx7; } } @@ -54,9 +55,16 @@ namespace ARMeilleure.CodeGen.X86 Sha = 1 << 29 } + [Flags] + public enum FeatureFlags7Ecx + { + Gfni = 1 << 8, + } + public static FeatureFlags1Edx FeatureInfo1Edx { get; } public static FeatureFlags1Ecx FeatureInfo1Ecx { get; } public static FeatureFlags7Ebx FeatureInfo7Ebx { get; } = 0; + public static FeatureFlags7Ecx FeatureInfo7Ecx { get; } = 0; public static bool SupportsSse => FeatureInfo1Edx.HasFlag(FeatureFlags1Edx.Sse); public static bool SupportsSse2 => FeatureInfo1Edx.HasFlag(FeatureFlags1Edx.Sse2); @@ -72,6 +80,7 @@ namespace ARMeilleure.CodeGen.X86 public static bool SupportsAvx2 => FeatureInfo7Ebx.HasFlag(FeatureFlags7Ebx.Avx2) && SupportsAvx; public static bool SupportsF16c => FeatureInfo1Ecx.HasFlag(FeatureFlags1Ecx.F16c); public static bool SupportsSha => FeatureInfo7Ebx.HasFlag(FeatureFlags7Ebx.Sha); + public static bool SupportsGfni => FeatureInfo7Ecx.HasFlag(FeatureFlags7Ecx.Gfni); public static bool ForceLegacySse { get; set; } -- cgit v1.2.3