Raymond Toy pushed to branch issue-425-correctly-rounded-math-functions at cmucl / cmucl
Commits:
-
70542bd9
by Raymond Toy at 2025-08-07T17:10:40-07:00
-
5edb2d90
by Raymond Toy at 2025-08-08T06:49:06-07:00
-
387ed142
by Raymond Toy at 2025-08-08T07:11:42-07:00
-
4d1f287c
by Raymond Toy at 2025-08-08T18:29:40-07:00
-
84ee222f
by Raymond Toy at 2025-08-08T19:59:15-07:00
-
f47f8f07
by Raymond Toy at 2025-08-08T20:00:17-07:00
4 changed files:
- src/compiler/x86/float-sse2.lisp
- src/compiler/x86/sse2-c-call.lisp
- src/lisp/GNUmakefile
- tests/float.lisp
Changes:
... | ... | @@ -1265,7 +1265,7 @@ |
1265 | 1265 | |
1266 | 1266 | ;;;; Float mode hackery:
|
1267 | 1267 | |
1268 | -(deftype float-modes () '(unsigned-byte 24))
|
|
1268 | +(deftype float-modes () '(unsigned-byte 30))
|
|
1269 | 1269 | |
1270 | 1270 | ;; For the record, here is the format of the MXCSR register.
|
1271 | 1271 | ;;
|
... | ... | @@ -36,12 +36,23 @@ |
36 | 36 | :from :eval :to :result) edx)
|
37 | 37 | (:temporary (:sc single-stack) temp-single)
|
38 | 38 | (:temporary (:sc double-stack) temp-double)
|
39 | + (:temporary (:sc unsigned-stack) save-fpu-cw)
|
|
40 | + (:temporary (:sc unsigned-stack) fpu-cw)
|
|
39 | 41 | (:node-var node)
|
40 | 42 | (:vop-var vop)
|
41 | 43 | (:save-p t)
|
42 | - (:ignore args ecx edx)
|
|
44 | + (:ignore args ecx #+nil edx)
|
|
43 | 45 | (:guard (backend-featurep :sse2))
|
44 | - (:generator 0
|
|
46 | + (:generator 0
|
|
47 | + ;; Save the x87 FPU control word. Then modify it to set the
|
|
48 | + ;; precision bits to double (2).
|
|
49 | + (inst fnstcw save-fpu-cw)
|
|
50 | + (move edx save-fpu-cw)
|
|
51 | + (inst and edx (dpb 0 (byte 2 8) #xffff)) ; Zap the precision control bits
|
|
52 | + (inst or edx (dpb 2 (byte 2 8) 0)) ; Set precision control to double
|
|
53 | + (move fpu-cw edx)
|
|
54 | + (inst fldcw fpu-cw) ; New CW
|
|
55 | + |
|
45 | 56 | (cond ((policy node (> space speed))
|
46 | 57 | (move eax function)
|
47 | 58 | (inst call (make-fixup (extern-alien-name "call_into_c") :foreign)))
|
... | ... | @@ -63,7 +74,9 @@ |
63 | 74 | (inst movss xmm0-tn (ea-for-sf-stack temp-single)))
|
64 | 75 | (double-reg
|
65 | 76 | (inst fstpd (ea-for-df-stack temp-double))
|
66 | - (inst movsd xmm0-tn (ea-for-df-stack temp-double)))))))
|
|
77 | + (inst movsd xmm0-tn (ea-for-df-stack temp-double)))))
|
|
78 | + ;; Restore the x87 FPU control settings
|
|
79 | + (inst fldcw save-fpu-cw)))
|
|
67 | 80 | |
68 | 81 | (define-vop (alloc-number-stack-space)
|
69 | 82 | (:info amount)
|
... | ... | @@ -83,7 +83,7 @@ lisp: ${OBJS} ${CORE64_OBJS} version.o |
83 | 83 | # Create a library out of all the object files so we can build an
|
84 | 84 | # executable. However, we need to remove exec-init.o from the library
|
85 | 85 | lisp.a: version.o ${OBJS} ${CORE64_OBJS} ${EXEC_FINAL_OBJ}
|
86 | - $(AR) crs lisp.a ${OBJS} version.o
|
|
86 | + $(AR) crs lisp.a ${OBJS} ${CORE64_OBJS} version.o
|
|
87 | 87 | ifneq (${EXEC_FINAL_OBJ},)
|
88 | 88 | $(AR) d lisp.a exec-init.o
|
89 | 89 | endif
|
... | ... | @@ -333,3 +333,13 @@ |
333 | 333 | (declare (ignore c))
|
334 | 334 | (values (invoke-restart 'lisp::largest-float)))))
|
335 | 335 | (read-from-string string))))))
|
336 | + |
|
337 | +#+x86
|
|
338 | +(define-test x87-set-floating-point-modes
|
|
339 | + (:tag :issues)
|
|
340 | + (let ((new-mode (setf (x86::x87-floating-point-modes)
|
|
341 | + (dpb 2 (byte 2 24)
|
|
342 | + (x86::x87-floating-point-modes)))))
|
|
343 | + (assert-true (typep new-mode 'x86::float-modes))
|
|
344 | + (assert-equal new-mode (setf (x86::x87-floating-point-modes) new-mode))))
|
|
345 | + |