;;; bignum-logical-and bignum-logical-ior bignum-logical-xor
;;; bignum-logical-not bignum-load-byte bignum-deposit-byte
;;; bignum-truncate bignum-plus-p bignum-compare make-small-bignum
-;;; bignum-logcount
+;;; bignum-logbitp bignum-logcount
;;; These symbols define the interface to the compiler:
;;; bignum-type bignum-element-type bignum-index %allocate-bignum
;;; %bignum-length %bignum-set-length %bignum-ref %bignum-set
(%normalize-bignum res res-len))
res)))))
((> count bignum-len)
- 0)
+ (if (%bignum-0-or-plusp bignum bignum-len) 0 -1))
;; Since a FIXNUM should be big enough to address anything in
;; memory, including arrays of bits, and since arrays of bits
;; take up about the same space as corresponding fixnums, there
;; should be no way that we fall through to this case: any shift
;; right by a bignum should give zero. But let's check anyway:
- (t (error "bignum overflow: can't shift right by ~S")))))
+ (t (error "bignum overflow: can't shift right by ~S" count)))))
(defun bignum-ashift-right-digits (bignum digits)
(declare (type bignum-type bignum)
(bignum-ashift-left-unaligned bignum digits n-bits res-len))))
;; Left shift by a number too big to be represented as a fixnum
;; would exceed our memory capacity, since a fixnum is big enough
- ;; index any array, including a bit array.
+ ;; to index any array, including a bit array.
(error "can't represent result of left shift")))
(defun bignum-ashift-left-digits (bignum bignum-len digits)
(t
(round-up))))))
\f
-;;;; integer length and logcount
+;;;; integer length and logbitp/logcount
(defun bignum-integer-length (bignum)
(declare (type bignum-type bignum))
(+ (integer-length (%fixnum-digit-with-correct-sign digit))
(* len-1 digit-size))))
+(defun bignum-logbitp (index bignum)
+ (declare (type bignum-type bignum))
+ (let ((len (%bignum-length bignum)))
+ (declare (type bignum-index len))
+ (multiple-value-bind (word-index bit-index)
+ (floor index digit-size)
+ (if (>= word-index len)
+ (not (bignum-plus-p bignum))
+ (not (zerop (logand (%bignum-ref bignum word-index)
+ (ash 1 bit-index))))))))
+
(defun bignum-logcount (bignum)
(declare (type bignum-type bignum))
(let* ((length (%bignum-length bignum))