From 76168c69c491c77c83c1e3a923225077fb2a027b Mon Sep 17 00:00:00 2001 From: Morten Welinder Date: Fri, 23 Mar 2018 11:12:38 -0400 Subject: [PATCH] FPU: Add sanity check for floating-point environment. Windows run Linux binaries in "double", not "extended", mode. --- ChangeLog | 4 ++++ NEWS | 3 +++ configure.ac | 3 +++ src/main-application.c | 27 +++++++++++++++++++++++++++ 4 files changed, 37 insertions(+) diff --git a/ChangeLog b/ChangeLog index 593984dea..069e8b2bf 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,7 @@ +2018-03-23 Morten Welinder + + * src/main-application.c (cpu_sanity_check): New function. + 2018-03-13 Morten Welinder * configure.ac: Post-release bump. diff --git a/NEWS b/NEWS index 97207ba12..b63cb6b72 100644 --- a/NEWS +++ b/NEWS @@ -1,5 +1,8 @@ Gnumeric 1.12.40 +Morten: + * Add floating-point environment sanity check. [#794515] + -------------------------------------------------------------------------- Gnumeric 1.12.39 diff --git a/configure.ac b/configure.ac index 007580d7c..4e3b9b877 100644 --- a/configure.ac +++ b/configure.ac @@ -543,6 +543,9 @@ AC_CHECK_HEADERS(langinfo.h) dnl check for rlimit AC_CHECK_HEADERS(sys/resource.h) +dnl we need to check fpu mode +AC_CHECK_HEADERS(fpu_control.h) + SAVE_CFLAGS=$CFLAGS SAVE_LIBS=$LIBS CFLAGS="$CFLAGS $GNUMERIC_CFLAGS" diff --git a/src/main-application.c b/src/main-application.c index 60eb357d3..a42b6e75e 100644 --- a/src/main-application.c +++ b/src/main-application.c @@ -46,6 +46,10 @@ #include #include +#ifdef HAVE_FPU_CONTROL_H +#include +#endif + static gboolean immediate_exit_flag = FALSE; static gboolean gnumeric_no_splash = FALSE; static gboolean gnumeric_no_warnings = FALSE; @@ -161,6 +165,27 @@ cb_workbook_removed (void) } } +static void +cpu_sanity_check (void) +{ +#if (defined(i386) || defined(__i386__) || defined(__i386) || defined(__x86_64__) || defined(__x86_64)) && HAVE_FPU_CONTROL_H + fpu_control_t state; + const fpu_control_t mask = _FPU_EXTENDED | _FPU_DOUBLE | _FPU_SINGLE; + + _FPU_GETCW (state); + if ((state & mask) != _FPU_EXTENDED) { + // Evidently currentlly happinging when Windows runs Linux + // binaries. See bug 794515. + g_warning ("Sanity check failed! The cpu is not in \"extended\" mode as it should be. Attempting to fix, but expect trouble."); + state = (state & ~mask) | _FPU_EXTENDED; + _FPU_SETCW (state); + } +#else + // Hope for the best +#endif +} + + int main (int argc, char const **argv) { @@ -177,6 +202,8 @@ main (int argc, char const **argv) /* No code before here, we need to init threads */ argv = gnm_pre_parse_init (argc, argv); + cpu_sanity_check (); + /* * Attempt to disable Ubuntu's funky, non-working scroll * bars. This needs to be done before gtk starts loading -- 2.11.4.GIT