Bug 1160148 - Disable CRT use of FMA3 on non-AVX2 processors. r=froydnj, a=lizzard
authorDavid Major <dmajor@mozilla.com>
Thu, 14 May 2015 08:47:00 -0400
changeset 267488 5a6082956d6c17d88a946a15419a8f1958ea6e26
parent 267487 301797f68aa2a3891550d2692fe850fe558f3967
child 267489 d2f1f08a52a235a4a64b2f58f6be0aa133e3d732
push id830
push userraliiev@mozilla.com
push dateFri, 19 Jun 2015 19:24:37 +0000
treeherdermozilla-release@932614382a68 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersfroydnj, lizzard
bugs1160148
milestone39.0
Bug 1160148 - Disable CRT use of FMA3 on non-AVX2 processors. r=froydnj, a=lizzard
mozglue/build/WindowsDllBlocklist.cpp
toolkit/xre/nsWindowsWMain.cpp
--- a/mozglue/build/WindowsDllBlocklist.cpp
+++ b/mozglue/build/WindowsDllBlocklist.cpp
@@ -697,16 +697,31 @@ continue_loading:
 
 WindowsDllInterceptor NtDllIntercept;
 
 } // anonymous namespace
 
 NS_EXPORT void
 DllBlocklist_Initialize()
 {
+#if defined(_MSC_VER) && _MSC_VER < 1900 && defined(_M_X64)
+  // The code below is not blocklist-related, but is the best place for it.
+  // This is the earliest place where msvcr120.dll is loaded, and this
+  // codepath is used by both firefox.exe and plugin-container.exe processes.
+
+  // Disable CRT use of FMA3 on non-AVX2 CPUs and on Win7RTM due to bug 1160148
+  int cpuid0[4] = {0};
+  int cpuid7[4] = {0};
+  __cpuid(cpuid0, 0); // Get the maximum supported CPUID function
+  __cpuid(cpuid7, 7); // AVX2 is function 7, subfunction 0, EBX, bit 5
+  if (cpuid0[0] < 7 || !(cpuid7[1] & 0x20) || !IsWin7SP1OrLater()) {
+    _set_FMA3_enable(0);
+  }
+#endif
+
   if (GetModuleHandleA("user32.dll")) {
     sUser32BeforeBlocklist = true;
   }
 
   NtDllIntercept.Init("ntdll.dll");
 
   ReentrancySentinel::InitializeStatics();
 
--- a/toolkit/xre/nsWindowsWMain.cpp
+++ b/toolkit/xre/nsWindowsWMain.cpp
@@ -6,16 +6,19 @@
 // similar bootstrap code. It converts wide-character windows wmain into UTF-8
 // narrow-character strings.
 
 #ifndef XP_WIN
 #error This file only makes sense on Windows.
 #endif
 
 #include "nsUTF8Utils.h"
+#include <intrin.h>
+#include <math.h>
+#include "mozilla/WindowsVersion.h"
 
 #ifndef XRE_DONT_PROTECT_DLL_LOAD
 #include "nsSetDllDirectory.h"
 #endif
 
 #if defined(MOZ_METRO) || defined(__GNUC__)
 #define XRE_DONT_SUPPORT_XPSP2
 #endif
@@ -83,16 +86,27 @@ FreeAllocStrings(int argc, char **argv)
 }
 
 int wmain(int argc, WCHAR **argv)
 {
 #if !defined(XRE_DONT_SUPPORT_XPSP2)
   WindowsCrtPatch::Init();
 #endif
 
+#if defined(_MSC_VER) && _MSC_VER < 1900 && defined(_M_X64)
+  // Disable CRT use of FMA3 on non-AVX2 CPUs and on Win7RTM due to bug 1160148
+  int cpuid0[4] = {0};
+  int cpuid7[4] = {0};
+  __cpuid(cpuid0, 0); // Get the maximum supported CPUID function
+  __cpuid(cpuid7, 7); // AVX2 is function 7, subfunction 0, EBX, bit 5
+  if (cpuid0[0] < 7 || !(cpuid7[1] & 0x20) || !mozilla::IsWin7SP1OrLater()) {
+    _set_FMA3_enable(0);
+  }
+#endif
+
 #ifndef XRE_DONT_PROTECT_DLL_LOAD
   mozilla::SanitizeEnvironmentVariables();
   SetDllDirectoryW(L"");
 #endif
 
   char **argvConverted = new char*[argc + 1];
   if (!argvConverted)
     return 127;