Check at runtime whether feenableexcept does anything.
authorTaylor R Campbell <campbell@mumble.net>
Wed, 23 Jan 2019 07:50:38 +0000 (07:50 +0000)
committerTaylor R Campbell <campbell@mumble.net>
Wed, 21 Aug 2019 21:34:05 +0000 (21:34 +0000)
The bits are defined on aarch64, but apparently some CPUs are
fabricated without support for them so they just read back as zers.
Bummer!

src/microcode/floenv.c

index 82e0f49dc9ef99c84d77e0dccee755207b7dcf6e..2672996d3c10b8c890baf3d23a497327524b9c04 100644 (file)
@@ -594,7 +594,22 @@ DEFINE_PRIMITIVE ("HAVE-FLOAT-TRAP-ENABLE/DISABLE?", Prim_have_float_trap_enable
 {
   PRIMITIVE_HEADER (0);
 #if ((defined (HAVE_FEENABLEEXCEPT)) && (defined (HAVE_FEDISABLEEXCEPT)))
-  PRIMITIVE_RETURN (SHARP_T);
+  static int have = -1;
+  if (have == -1)
+    {
+      fenv_t fenv;
+      int excepts = (fegetexcept ());
+      /* Prevent traps while we futz with stuff.  */
+      feholdexcept (&fenv);
+      /* Reverse the sense.  */
+      feenableexcept (FE_ALL_EXCEPT &~ excepts);
+      fedisableexcept (excepts);
+      /* Check whether that had any effect.  */
+      have = ((fegetexcept ()) != excepts);
+      /* Restore the environment without raising exceptions.  */
+      fesetenv (&fenv);
+    }
+  PRIMITIVE_RETURN (have ? SHARP_T : SHARP_F);
 #else
   PRIMITIVE_RETURN (SHARP_F);
 #endif