fixed a bug in quotient and div when given (least-fixnum) and -1.
This commit is contained in:
parent
4909a9ef08
commit
3b80d4f321
|
@ -534,7 +534,7 @@
|
|||
(S (cadr rands)
|
||||
(lambda (s)
|
||||
(make-asm-instr op d s))))]
|
||||
[(remainder)
|
||||
[(int-quotient)
|
||||
(S* rands
|
||||
(lambda (rands)
|
||||
(seq*
|
||||
|
@ -542,7 +542,7 @@
|
|||
(make-asm-instr 'cltd edx eax)
|
||||
(make-asm-instr 'idiv eax (cadr rands))
|
||||
(make-set d eax))))]
|
||||
[(quotient)
|
||||
[(int-remainder)
|
||||
(S* rands
|
||||
(lambda (rands)
|
||||
(seq*
|
||||
|
@ -2308,9 +2308,12 @@
|
|||
(unless (symbol? a)
|
||||
(error who "invalid arg to idiv"))
|
||||
(cond
|
||||
[(disp? b)
|
||||
(error who "invalid arg to idiv" b)]
|
||||
[else x])]
|
||||
[(or (var? b) (symbol? b)) x]
|
||||
[else
|
||||
(let ([u (mku)])
|
||||
(make-seq
|
||||
(E (make-asm-instr 'move u b))
|
||||
(E (make-asm-instr 'idiv a u))))])]
|
||||
[(sll sra srl sll/overflow)
|
||||
(unless (or (constant? b)
|
||||
(eq? b ecx))
|
||||
|
|
|
@ -171,7 +171,11 @@
|
|||
(die 'fxquotient "not a fixnum" y))
|
||||
(when ($fxzero? y)
|
||||
(die 'fxquotient "zero dividend" y))
|
||||
($fxquotient x y)))
|
||||
(if (eq? y -1)
|
||||
(if (eq? x (least-fixnum))
|
||||
(die 'fxquotient "overflow" x y)
|
||||
($fx- 0 x))
|
||||
($fxquotient x y))))
|
||||
|
||||
(define fxremainder
|
||||
(lambda (x y)
|
||||
|
|
|
@ -1632,6 +1632,15 @@
|
|||
(string-append
|
||||
($number->string xr r) (imag xi r) "i")]))]
|
||||
[else (die 'number->string "not a number" x)])))
|
||||
(define do-warn
|
||||
(lambda ()
|
||||
(set! do-warn values)
|
||||
(raise-continuable
|
||||
(condition
|
||||
(make-warning)
|
||||
(make-who-condition 'number->string)
|
||||
(make-message-condition
|
||||
"precision argument is not supported")))))
|
||||
(define number->string
|
||||
(case-lambda
|
||||
[(x) ($number->string x 10)]
|
||||
|
@ -1640,8 +1649,8 @@
|
|||
(die 'number->string "invalid radix" r))
|
||||
($number->string x r)]
|
||||
[(x r precision)
|
||||
(die 'number->string
|
||||
"BUG: precision is not supported yet")])))
|
||||
;(do-warn)
|
||||
(number->string x r)])))
|
||||
|
||||
(define modulo
|
||||
(lambda (n m)
|
||||
|
@ -2412,8 +2421,9 @@
|
|||
[(fixnum? x)
|
||||
(cond
|
||||
[(fixnum? y)
|
||||
(values (fxquotient x y)
|
||||
(fxremainder x y))]
|
||||
(if (eq? y -1)
|
||||
(values (- x) 0)
|
||||
(values (fxquotient x y) (fxremainder x y)))]
|
||||
[(bignum? y) (values 0 x)]
|
||||
[(flonum? y)
|
||||
(let ([v ($flonum->exact y)])
|
||||
|
@ -3235,6 +3245,7 @@
|
|||
[(and (fixnum? n) (fixnum? m))
|
||||
(cond
|
||||
[(eq? m 0) (error 'div "division by 0")]
|
||||
[(eq? m -1) (- n)]
|
||||
[else
|
||||
(let ([d0 ($fxquotient n m)])
|
||||
(if ($fx>= n ($fx* d0 m))
|
||||
|
|
|
@ -1 +1 @@
|
|||
1553
|
||||
1554
|
||||
|
|
|
@ -495,6 +495,8 @@
|
|||
[$fxsra $fx]
|
||||
[$fxquotient $fx]
|
||||
[$fxmodulo $fx]
|
||||
[$int-quotient $fx]
|
||||
[$int-remainder $fx]
|
||||
[$fxlogxor $fx]
|
||||
[$fxlogor $fx]
|
||||
[$fxlognot $fx]
|
||||
|
|
|
@ -896,18 +896,24 @@
|
|||
(define-primop $fxquotient unsafe
|
||||
[(V a b)
|
||||
(with-tmp ([b (T b)]) ;;; FIXME: why is quotient called remainder?
|
||||
(prm 'sll (prm 'remainder (T a) b) (K fx-shift)))]
|
||||
(prm 'sll (prm 'int-quotient (T a) b) (K fx-shift)))]
|
||||
[(P a b) (K #t)]
|
||||
[(E a b) (nop)])
|
||||
|
||||
(define-primop $int-quotient unsafe
|
||||
[(V a b)
|
||||
(prm 'sll (prm 'int-quotient (T a) (T b)) (K fx-shift))])
|
||||
|
||||
(define-primop $int-remainder unsafe
|
||||
[(V a b) (prm 'int-remainder (T a))])
|
||||
|
||||
(define-primop $fxmodulo unsafe
|
||||
[(V a b)
|
||||
(with-tmp ([b (T b)]) ;;; FIXME: why is modulo called quotient?
|
||||
(with-tmp ([b (T b)])
|
||||
(with-tmp ([c (prm 'logand b
|
||||
(prm 'sra (prm 'logxor b (T a))
|
||||
(K (sub1 (* 8 wordsize)))))])
|
||||
(prm 'int+ c (prm 'quotient (T a) b))))]
|
||||
(prm 'int+ c (prm 'int-remainder (T a) b))))]
|
||||
[(P a b) (K #t)]
|
||||
[(E a b) (nop)])
|
||||
|
||||
|
|
|
@ -1722,10 +1722,13 @@
|
|||
(let-values (((lhs* rhs* q) (quasi q lev)))
|
||||
(if (= lev 0)
|
||||
(let ((g (gensym)))
|
||||
(values (cons `(,g ...) lhs*) (cons p rhs*)
|
||||
(values
|
||||
(cons `(,g ...) lhs*)
|
||||
(cons p rhs*)
|
||||
`(,g ... . ,q)))
|
||||
(let-values (((lhs2* rhs2* p) (quasi p (- lev 1))))
|
||||
(values (append lhs2* lhs*)
|
||||
(values
|
||||
(append lhs2* lhs*)
|
||||
(append rhs2* rhs*)
|
||||
`((unsyntax-splicing ,p) . ,q))))))
|
||||
(unsyntax-splicing (= lev 0)
|
||||
|
|
|
@ -40,7 +40,10 @@
|
|||
(test +3 -7/11)
|
||||
(test -3 -7/11)
|
||||
|
||||
|
||||
(test (least-fixnum) -1)
|
||||
(test (least-fixnum) 1)
|
||||
(test (greatest-fixnum) -1)
|
||||
(test (greatest-fixnum) 1)
|
||||
|
||||
|
||||
)
|
||||
|
|
Loading…
Reference in New Issue