about summary refs log tree commit diff
path: root/sysdeps/x86_64/fpu/math_private.h
diff options
context:
space:
mode:
authorUlrich Drepper <drepper@gmail.com>2011-10-18 09:00:46 -0400
committerUlrich Drepper <drepper@gmail.com>2011-10-18 09:00:46 -0400
commitd38f1dba009689d78af371cffa091b27e4ebe17d (patch)
treeda7daa82001d244a4dbc1ce6dc72cf4e8eac45db /sysdeps/x86_64/fpu/math_private.h
parent83c7615c2dc344562f6a1a499a269b114f74c7e5 (diff)
downloadglibc-d38f1dba009689d78af371cffa091b27e4ebe17d.tar.gz
glibc-d38f1dba009689d78af371cffa091b27e4ebe17d.tar.xz
glibc-d38f1dba009689d78af371cffa091b27e4ebe17d.zip
Start optimizing the use of the fenv interfaces in libm itself
Diffstat (limited to 'sysdeps/x86_64/fpu/math_private.h')
-rw-r--r--sysdeps/x86_64/fpu/math_private.h42
1 files changed, 42 insertions, 0 deletions
diff --git a/sysdeps/x86_64/fpu/math_private.h b/sysdeps/x86_64/fpu/math_private.h
index 6cff8b3161..4886c64dc3 100644
--- a/sysdeps/x86_64/fpu/math_private.h
+++ b/sysdeps/x86_64/fpu/math_private.h
@@ -118,3 +118,45 @@ do {								\
      __res; })
 # endif
 #endif
+
+
+/* Specialized variants of the <fenv.h> interfaces which only handle
+   either the FPU or the SSE unit.  */
+#undef libc_fegetround
+#define libc_fegetround() \
+  ({									      \
+     unsigned int mxcsr;						      \
+     asm volatile ("stmxcsr %0" : "=m" (*&mxcsr));			      \
+     (mxcsr & 0x6000) >> 3;						      \
+  })
+// #define libc_fegetroundf() fegetround ()
+// #define libc_fegetroundl() fegetround ()
+
+#undef libc_fesetround
+#define libc_fesetround(r) \
+  do {									      \
+     unsigned int mxcsr;						      \
+     asm ("stmxcsr %0" : "=m" (*&mxcsr));				      \
+     mxcsr = (mxcsr & ~0x6000) | ((r) << 3);				      \
+     asm volatile ("ldmxcsr %0" : : "m" (*&mxcsr));			      \
+  } while (0)
+// #define libc_fesetroundf(r) (void) fesetround (r)
+// #define libc_fesetroundl(r) (void) fesetround (r)
+
+#undef libc_feholdexcept
+#define libc_feholdexcept(e) \
+  do {			     \
+     unsigned int mxcsr;						      \
+     asm ("stmxcsr %0" : "=m" (*&mxcsr));				      \
+     (e)->__mxcsr = mxcsr;						      \
+     mxcsr = (mxcsr | 0x1f80) & ~0x3f;					      \
+     asm volatile ("ldmxcsr %0" : : "m" (*&mxcsr));			      \
+  } while (0)
+// #define libc_feholdexceptf(e) (void) feholdexcept (e)
+// #define libc_feholdexceptl(e) (void) feholdexcept (e)
+
+#undef libc_fesetenv
+#define libc_fesetenv(e) \
+  asm volatile ("ldmxcsr %0" : : "m" ((e)->__mxcsr))
+// #define libc_fesetenvf(e) (void) fesetenv (e)
+// #define libc_fesetenvl(e) (void) fesetenv (e)