summaryrefslogtreecommitdiff
path: root/Source/Core/Common/XSaveWorkaround.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'Source/Core/Common/XSaveWorkaround.cpp')
-rw-r--r--Source/Core/Common/XSaveWorkaround.cpp51
1 files changed, 25 insertions, 26 deletions
diff --git a/Source/Core/Common/XSaveWorkaround.cpp b/Source/Core/Common/XSaveWorkaround.cpp
index 30a2a42b2b..b54f33eb4b 100644
--- a/Source/Core/Common/XSaveWorkaround.cpp
+++ b/Source/Core/Common/XSaveWorkaround.cpp
@@ -2,39 +2,38 @@
// Licensed under GPLv2
// Refer to the license.txt file included.
-#if defined(_WIN32) && defined(_ARCH_64)
+#if defined(_WIN32) && defined(_M_X86_64)
#include <math.h>
#include <Windows.h>
-// This puts the rest of this translation unit into a segment which is
-// initialized by the CRT *before* any of the other code (including C++
-// static initializers).
-#pragma warning(disable : 4075)
-#pragma init_seg(".CRT$XCB")
-
-struct EnableXSaveWorkaround
+void EnableXSaveWorkaround()
{
- EnableXSaveWorkaround()
+ // Some Windows environments may have hardware support for AVX/FMA,
+ // but the OS does not support it. The CRT math library does not support
+ // this scenario, so we have to manually tell it not to use FMA3
+ // instructions.
+
+ // The API name is somewhat misleading - we're testing for OS support
+ // here.
+ if (!IsProcessorFeaturePresent(PF_XSAVE_ENABLED))
{
- // Some Windows environments may have hardware support for AVX/FMA,
- // but the OS does not support it. The CRT math library does not support
- // this scenario, so we have to manually tell it not to use FMA3
- // instructions.
-
- // The API name is somewhat misleading - we're testing for OS support
- // here.
- if (!IsProcessorFeaturePresent(PF_XSAVE_ENABLED))
- {
- _set_FMA3_enable(0);
- }
+ _set_FMA3_enable(0);
}
+}
+
+// Create a segment which is recognized by the linker to be part of the CRT
+// initialization. XI* = C startup, XC* = C++ startup. "A" placement is reserved
+// for system use. Thus, the earliest we can get is XIB (C startup is before
+// C++).
+#pragma section(".CRT$XIB", read)
+
+// Place a symbol in the special segment, make it have C linkage so that
+// referencing it doesn't require ugly decorated names.
+// Use /include:XSaveWorkaround linker flag to enable this.
+extern "C" {
+ __declspec(allocate(".CRT$XIB"))
+ decltype(&EnableXSaveWorkaround) XSaveWorkaround = EnableXSaveWorkaround;
};
-static EnableXSaveWorkaround enableXSaveWorkaround;
-
-// N.B. Any code after this will still be in the .CRT$XCB segment. Please just
-// do not append any code here unless it is intended to be executed before
-// static initializers.
-
#endif