From 6cb6bdbd0a38e9b5f5c4f676afb72a23b6bfb1b5 Mon Sep 17 00:00:00 2001 From: Julian Seward Date: Sat, 22 Dec 2018 06:06:19 +0100 Subject: [PATCH] amd64 hosts: detect SSSE3 (not SSE3) capabilities on the host. As-yet unused. n-i-bz. --- VEX/priv/guest_amd64_toIR.c | 6 +++--- VEX/priv/host_amd64_isel.c | 1 + VEX/priv/main_main.c | 22 ++++++++++++++-------- VEX/pub/libvex.h | 1 + coregrind/m_machine.c | 13 ++++++++++--- 5 files changed, 29 insertions(+), 14 deletions(-) diff --git a/VEX/priv/guest_amd64_toIR.c b/VEX/priv/guest_amd64_toIR.c index 2cabf80c9f..e753ffa726 100644 --- a/VEX/priv/guest_amd64_toIR.c +++ b/VEX/priv/guest_amd64_toIR.c @@ -22071,21 +22071,21 @@ Long dis_ESC_0F ( /* This isn't entirely correct, CPUID should depend on the VEX capabilities, not on the underlying CPU. See bug #324882. */ - if ((archinfo->hwcaps & VEX_HWCAPS_AMD64_SSE3) && + if ((archinfo->hwcaps & VEX_HWCAPS_AMD64_SSSE3) && (archinfo->hwcaps & VEX_HWCAPS_AMD64_CX16) && (archinfo->hwcaps & VEX_HWCAPS_AMD64_AVX2)) { fName = "amd64g_dirtyhelper_CPUID_avx2"; fAddr = &amd64g_dirtyhelper_CPUID_avx2; /* This is a Core-i7-4910-like machine */ } - else if ((archinfo->hwcaps & VEX_HWCAPS_AMD64_SSE3) && + else if ((archinfo->hwcaps & VEX_HWCAPS_AMD64_SSSE3) && (archinfo->hwcaps & VEX_HWCAPS_AMD64_CX16) && (archinfo->hwcaps & VEX_HWCAPS_AMD64_AVX)) { fName = "amd64g_dirtyhelper_CPUID_avx_and_cx16"; fAddr = &amd64g_dirtyhelper_CPUID_avx_and_cx16; /* This is a Core-i5-2300-like machine */ } - else if ((archinfo->hwcaps & VEX_HWCAPS_AMD64_SSE3) && + else if ((archinfo->hwcaps & VEX_HWCAPS_AMD64_SSSE3) && (archinfo->hwcaps & VEX_HWCAPS_AMD64_CX16)) { fName = "amd64g_dirtyhelper_CPUID_sse42_and_cx16"; fAddr = &amd64g_dirtyhelper_CPUID_sse42_and_cx16; diff --git a/VEX/priv/host_amd64_isel.c b/VEX/priv/host_amd64_isel.c index 1787e8725a..05e2e725af 100644 --- a/VEX/priv/host_amd64_isel.c +++ b/VEX/priv/host_amd64_isel.c @@ -4953,6 +4953,7 @@ HInstrArray* iselSB_AMD64 ( const IRSB* bb, vassert(arch_host == VexArchAMD64); vassert(0 == (hwcaps_host & ~(VEX_HWCAPS_AMD64_SSE3 + | VEX_HWCAPS_AMD64_SSSE3 | VEX_HWCAPS_AMD64_CX16 | VEX_HWCAPS_AMD64_LZCNT | VEX_HWCAPS_AMD64_AVX diff --git a/VEX/priv/main_main.c b/VEX/priv/main_main.c index 41ad371564..f387f166b7 100644 --- a/VEX/priv/main_main.c +++ b/VEX/priv/main_main.c @@ -1575,6 +1575,7 @@ static const HChar* show_hwcaps_amd64 ( UInt hwcaps ) { VEX_HWCAPS_AMD64_LZCNT, "lzcnt" }, { VEX_HWCAPS_AMD64_RDTSCP, "rdtscp" }, { VEX_HWCAPS_AMD64_SSE3, "sse3" }, + { VEX_HWCAPS_AMD64_SSSE3, "ssse3" }, { VEX_HWCAPS_AMD64_AVX, "avx" }, { VEX_HWCAPS_AMD64_AVX2, "avx2" }, { VEX_HWCAPS_AMD64_BMI, "bmi" }, @@ -1881,15 +1882,20 @@ static void check_hwcaps ( VexArch arch, UInt hwcaps ) orthogonal. */ /* Throw out obviously stupid cases: */ - Bool have_sse3 = (hwcaps & VEX_HWCAPS_AMD64_SSE3) != 0; - Bool have_avx = (hwcaps & VEX_HWCAPS_AMD64_AVX) != 0; - Bool have_bmi = (hwcaps & VEX_HWCAPS_AMD64_BMI) != 0; - Bool have_avx2 = (hwcaps & VEX_HWCAPS_AMD64_AVX2) != 0; - - /* AVX without SSE3 */ - if (have_avx && !have_sse3) + Bool have_sse3 = (hwcaps & VEX_HWCAPS_AMD64_SSE3) != 0; + Bool have_ssse3 = (hwcaps & VEX_HWCAPS_AMD64_SSSE3) != 0; + Bool have_avx = (hwcaps & VEX_HWCAPS_AMD64_AVX) != 0; + Bool have_bmi = (hwcaps & VEX_HWCAPS_AMD64_BMI) != 0; + Bool have_avx2 = (hwcaps & VEX_HWCAPS_AMD64_AVX2) != 0; + + /* SSSE3 without SSE3 */ + if (have_ssse3 && !have_sse3) + invalid_hwcaps(arch, hwcaps, + "Support for SSSE3 requires SSE3 capabilities\n"); + /* AVX without SSSE3 */ + if (have_avx && !have_ssse3) invalid_hwcaps(arch, hwcaps, - "Support for AVX requires SSE3 capabilities\n"); + "Support for AVX requires SSSE3 capabilities\n"); /* AVX2 or BMI without AVX */ if (have_avx2 && !have_avx) invalid_hwcaps(arch, hwcaps, diff --git a/VEX/pub/libvex.h b/VEX/pub/libvex.h index e6c19744d5..629a258a91 100644 --- a/VEX/pub/libvex.h +++ b/VEX/pub/libvex.h @@ -92,6 +92,7 @@ typedef /* amd64: baseline capability is SSE2, with cmpxchg8b but not cmpxchg16b. */ #define VEX_HWCAPS_AMD64_SSE3 (1<<5) /* SSE3 support */ +#define VEX_HWCAPS_AMD64_SSSE3 (1<<12) /* Supplemental SSE3 support */ #define VEX_HWCAPS_AMD64_CX16 (1<<6) /* cmpxchg16b support */ #define VEX_HWCAPS_AMD64_LZCNT (1<<7) /* SSE4a LZCNT insn */ #define VEX_HWCAPS_AMD64_AVX (1<<8) /* AVX instructions */ diff --git a/coregrind/m_machine.c b/coregrind/m_machine.c index 31b0e1b6b4..7aa051bd12 100644 --- a/coregrind/m_machine.c +++ b/coregrind/m_machine.c @@ -943,7 +943,7 @@ Bool VG_(machine_get_hwcaps)( void ) } #elif defined(VGA_amd64) - { Bool have_sse3, have_cx8, have_cx16; + { Bool have_sse3, have_ssse3, have_cx8, have_cx16; Bool have_lzcnt, have_avx, have_bmi, have_avx2; Bool have_rdtscp; UInt eax, ebx, ecx, edx, max_basic, max_extended; @@ -951,6 +951,12 @@ Bool VG_(machine_get_hwcaps)( void ) HChar vstr[13]; vstr[0] = 0; + have_sse3 = have_ssse3 = have_cx8 = have_cx16 + = have_lzcnt = have_avx = have_bmi = have_avx2 + = have_rdtscp = False; + + eax = ebx = ecx = edx = max_basic = max_extended = 0; + if (!VG_(has_cpuid)()) /* we can't do cpuid at all. Give up. */ return False; @@ -975,8 +981,8 @@ Bool VG_(machine_get_hwcaps)( void ) VG_(cpuid)(1, 0, &eax, &ebx, &ecx, &edx); // we assume that SSE1 and SSE2 are available by default - have_sse3 = (ecx & (1<<0)) != 0; /* True => have sse3 insns */ - // ssse3 is ecx:9 + have_sse3 = (ecx & (1<<0)) != 0; /* True => have sse3 insns */ + have_ssse3 = (ecx & (1<<9)) != 0; /* True => have Sup SSE3 insns */ // sse41 is ecx:19 // sse42 is ecx:20 @@ -1054,6 +1060,7 @@ Bool VG_(machine_get_hwcaps)( void ) va = VexArchAMD64; vai.endness = VexEndnessLE; vai.hwcaps = (have_sse3 ? VEX_HWCAPS_AMD64_SSE3 : 0) + | (have_ssse3 ? VEX_HWCAPS_AMD64_SSSE3 : 0) | (have_cx16 ? VEX_HWCAPS_AMD64_CX16 : 0) | (have_lzcnt ? VEX_HWCAPS_AMD64_LZCNT : 0) | (have_avx ? VEX_HWCAPS_AMD64_AVX : 0) -- 2.47.2