From 2b3d7fb021eef7360ac1946604b6da297939e4d3 Mon Sep 17 00:00:00 2001
From: rtoy <rtoy>
Date: Tue, 22 Jun 2010 03:24:49 +0000
Subject: [PATCH] Fix issue where the debugger (and TRACE) would get the wrong
 floating-point values for arguments because the x87 registers were used
 instead of the sse2 registers in the sigcontext.

code/x86-vm.lisp:
o For SSE2 on Mac OS X, call os_sigcontext_fpu_reg_sse2 to get the
  SSE2 register values from the sigcontext.

lisp/Darwin-os.c:
o Add os_sigcontext_fpu_reg_sse2 to get the SSE2 floating point
  values.

general-info/release-20b.txt:
o Document this change.
---
 code/x86-vm.lisp             | 14 ++++++++++++-
 general-info/release-20b.txt |  7 +++++++
 lisp/Darwin-os.c             | 38 +++++++++++++++++++++++++++++++++++-
 3 files changed, 57 insertions(+), 2 deletions(-)

diff --git a/code/x86-vm.lisp b/code/x86-vm.lisp
index 856abb810..9f09115a4 100644
--- a/code/x86-vm.lisp
+++ b/code/x86-vm.lisp
@@ -7,7 +7,7 @@
 ;;; Scott Fahlman or slisp-group@cs.cmu.edu.
 ;;;
 (ext:file-comment
-  "$Header: /Volumes/share2/src/cmucl/cvs2git/cvsroot/src/code/x86-vm.lisp,v 1.35 2010/04/20 17:57:45 rtoy Exp $")
+  "$Header: /Volumes/share2/src/cmucl/cvs2git/cvsroot/src/code/x86-vm.lisp,v 1.36 2010/06/22 03:24:49 rtoy Exp $")
 ;;;
 ;;; **********************************************************************
 ;;;
@@ -250,6 +250,7 @@
 ;;; Like SIGCONTEXT-REGISTER, but returns the value of a float register.
 ;;; Format is the type of float to return.
 ;;;
+#-(and sse2 (or darwin))
 (defun sigcontext-float-register (scp index format)
   (declare (type (alien (* sigcontext)) scp))
   (let ((fn (extern-alien "os_sigcontext_fpu_reg"
@@ -257,6 +258,17 @@
 				    (* sigcontext)
 				    (integer 32)))))
     (coerce (sap-ref-long (alien-funcall fn scp index) 0) format)))
+
+#+(and sse2 (or darwin))
+(defun sigcontext-float-register (scp index format)
+  (declare (type (alien (* sigcontext)) scp))
+  (let ((fn (extern-alien "os_sigcontext_fpu_reg_sse2"
+			  (function system-area-pointer
+				    (* sigcontext)
+				    (integer 32)))))
+    (if (eq format 'double-float)
+	(coerce (sap-ref-double (alien-funcall fn scp index) 0) format)
+	(coerce (sap-ref-single (alien-funcall fn scp index) 0) format))))
 ;;;
 (defun %set-sigcontext-float-register (scp index format new)
   (declare (type (alien (* sigcontext)) scp))
diff --git a/general-info/release-20b.txt b/general-info/release-20b.txt
index 38d3cffe0..12df3a36b 100644
--- a/general-info/release-20b.txt
+++ b/general-info/release-20b.txt
@@ -141,6 +141,13 @@ New in this release:
       The SSE state is saved along with the x87 state.
     - GCD of positive integers no longer returns a negative result for
       certain arguments.
+    - When printing out argument values in the debugger and also
+      during TRACE, the incorrect values were returned for the SSE2
+      core.  This was caused by using the x87 values instead of the
+      sse2 values in the sigcontext.  This is fixed for Mac OS X.
+      This bug still exists on Linux which doesn't seem to have any
+      way to access the SSE2 registers in the sigcontext in 32-bit
+      binaries and on FreeBSD.
 
   * Trac Tickets:
     #33: get-dispatch-macro-character doesn't signal errors in
diff --git a/lisp/Darwin-os.c b/lisp/Darwin-os.c
index 2b8bb66e7..30db779cd 100644
--- a/lisp/Darwin-os.c
+++ b/lisp/Darwin-os.c
@@ -14,7 +14,7 @@
  * Frobbed for OpenBSD by Pierre R. Mai, 2001.
  * Frobbed for Darwin by Pierre R. Mai, 2003.
  *
- * $Header: /Volumes/share2/src/cmucl/cvs2git/cvsroot/src/lisp/Darwin-os.c,v 1.27 2010/02/01 16:04:43 rtoy Exp $
+ * $Header: /Volumes/share2/src/cmucl/cvs2git/cvsroot/src/lisp/Darwin-os.c,v 1.28 2010/06/22 03:24:49 rtoy Exp $
  *
  */
 
@@ -223,6 +223,16 @@ sc_reg(os_context_t * context, int offset)
 #define __fpu_fcw   fpu_fcw
 #define __fpu_fsw   fpu_fsw
 #define __fpu_mxcsr fpu_mxcsr
+#ifdef FEATURE_SSE2
+#define __fpu_xmm0 fpu_xmm0
+#define __fpu_xmm1 fpu_xmm1
+#define __fpu_xmm2 fpu_xmm2
+#define __fpu_xmm3 fpu_xmm3
+#define __fpu_xmm4 fpu_xmm4
+#define __fpu_xmm5 fpu_xmm5
+#define __fpu_xmm6 fpu_xmm6
+#define __fpu_xmm7 fpu_xmm7
+#endif
 #endif
 
 unsigned long *
@@ -279,6 +289,32 @@ os_sigcontext_fpu_reg(ucontext_t *scp, int index)
     return NULL;
 }
 
+#ifdef FEATURE_SSE2
+unsigned char *
+os_sigcontext_fpu_reg_sse2(ucontext_t *scp, int index)
+{
+    switch (index) {
+    case 0:
+	return (unsigned char *) &scp->uc_mcontext->__fs.__fpu_xmm0;
+    case 1:
+	return (unsigned char *) &scp->uc_mcontext->__fs.__fpu_xmm1;
+    case 2:
+	return (unsigned char *) &scp->uc_mcontext->__fs.__fpu_xmm2;
+    case 3:
+	return (unsigned char *) &scp->uc_mcontext->__fs.__fpu_xmm3;
+    case 4:
+	return (unsigned char *) &scp->uc_mcontext->__fs.__fpu_xmm4;
+    case 5:
+	return (unsigned char *) &scp->uc_mcontext->__fs.__fpu_xmm5;
+    case 6:
+	return (unsigned char *) &scp->uc_mcontext->__fs.__fpu_xmm6;
+    case 7:
+	return (unsigned char *) &scp->uc_mcontext->__fs.__fpu_stmm7;
+    }
+    return NULL;
+}
+#endif
+
 unsigned int
 os_sigcontext_fpu_modes(ucontext_t *scp)
 {
-- 
GitLab