LIARC_BUNDLES = $(LIARC_BOOT_BUNDLES) ffi sos ssp xml
SUBDIRS = $(INSTALLED_SUBDIRS) win32 xdoc
-INSTALLED_SUBDIRS = microcode runtime $(OPTION_SUBDIRS) $(LIARC_BUNDLES)
+INSTALLED_SUBDIRS = microcode runtime libraries $(OPTION_SUBDIRS) $(LIARC_BUNDLES)
BASICS_SUBDIRS = microcode runtime $(LIARC_BUNDLES)
OPTION_SUBDIRS = @OPTION_SUBDIRS@
### cross-compiler. We should have a way to do that, and eliminate
### these.
+################
+# Libraries
+################
+
+.PHONY: compile-libraries
+compile-libraries: lib/all.com
+compile-libraries: microcode/scheme
+ (echo '(with-working-directory-pathname "libraries"' && \
+ echo ' (lambda () (load "compile")))') \
+ | ./run-build --batch-mode --no-init-file
+
################
# blowfish
################
cross-target: lib/all.com
cross-target: lib/runtime.com
cross-target: microcode/scheme
+cross-target: compile-libraries
################
# Microcode
. etc/functions.sh
-INSTALLED_SUBDIRS="cref ffi sf sos ssp star-parser xml"
+INSTALLED_SUBDIRS="cref ffi libraries sf sos ssp star-parser xml"
PLUGIN_SUBDIRS="blowfish edwin gdbm imail pgsql mcrypt x11 x11-screen"
OTHER_SUBDIRS="6001 compiler runtime win32 xdoc microcode"
maybe_link lib/edwin ../edwin
maybe_link lib/ffi ../ffi
maybe_link lib/imail ../imail
+maybe_link lib/libraries ../libraries
maybe_link lib/runtime ../runtime
maybe_link lib/sf ../sf
maybe_link lib/sos ../sos
ffi \
gdbm \
imail \
+ libraries \
mcrypt \
microcode \
pgsql \
dnl Process this file with autoconf to produce a configure script.
-AC_INIT([MIT/GNU Scheme], [10.1.2], [bug-mit-scheme@gnu.org], [mit-scheme])
+AC_INIT([MIT/GNU Scheme], [10.90], [bug-mit-scheme@gnu.org], [mit-scheme])
AC_CONFIG_SRCDIR([microcode/boot.c])
AC_CONFIG_AUX_DIR([microcode])
AC_PROG_MAKE_SET
compiler/Makefile
cref/Makefile
ffi/Makefile
+libraries/Makefile
runtime/Makefile
sf/Makefile
sos/Makefile
(cd lib; rm -f ${BN}; ${LN_S} ../${BN} .)
done
mkdir -p lib/lib
- for BUNDLE in 6001 compiler cref ffi sf sos ssp star-parser \
+ for BUNDLE in 6001 compiler cref ffi libraries sf sos ssp star-parser \
xdoc xml; do
SO=${BUNDLE}.so
(cd lib/lib; rm -f ${SO}; ${LN_S} ../../${BUNDLE}/${SO} .)
run_cmd rm -f compiler/machine compiler/compiler.pkg
-for SUBDIR in ${BUNDLES} runtime win32; do
+for SUBDIR in ${BUNDLES} runtime libraries win32; do
echo "creating ${SUBDIR}/Makefile.in"
rm -f ${SUBDIR}/Makefile.in
cat etc/std-makefile-prefix ${SUBDIR}/Makefile-fragment \
--- /dev/null
+TARGET_DIR = $(AUXDIR)/libraries
+
+install:
+ $(mkinstalldirs) $(DESTDIR)$(TARGET_DIR)
+ $(INSTALL_COM) *.com $(DESTDIR)$(TARGET_DIR)/.
+ $(INSTALL_DATA) *.bci $(DESTDIR)$(TARGET_DIR)/.
--- /dev/null
+#| -*-Scheme-*-
+
+Copyright (C) 1986, 1987, 1988, 1989, 1990, 1991, 1992, 1993, 1994,
+ 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
+ 2006, 2007, 2008, 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016,
+ 2017, 2018, 2019 Massachusetts Institute of Technology
+
+This file is part of MIT/GNU Scheme.
+
+MIT/GNU Scheme is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2 of the License, or (at
+your option) any later version.
+
+MIT/GNU Scheme is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with MIT/GNU Scheme; if not, write to the Free Software
+Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301,
+USA.
+
+|#
+
+(for-each (lambda (pn)
+ (if (not (string=? "compile" (pathname-name pn)))
+ (compile-file pn)))
+ (directory-read
+ (merge-pathnames "*.scm"
+ (directory-pathname (current-load-pathname)))))
\ No newline at end of file
--- /dev/null
+#| -*-Scheme-*-
+
+Copyright (C) 1986, 1987, 1988, 1989, 1990, 1991, 1992, 1993, 1994,
+ 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
+ 2006, 2007, 2008, 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016,
+ 2017, 2018, 2019 Massachusetts Institute of Technology
+
+This file is part of MIT/GNU Scheme.
+
+MIT/GNU Scheme is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2 of the License, or (at
+your option) any later version.
+
+MIT/GNU Scheme is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with MIT/GNU Scheme; if not, write to the Free Software
+Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301,
+USA.
+
+|#
+
+;;;; Simple in-line tests
+
+;;; The idea behind this tester is that it executes a file of expressions, in
+;;; order, except that some of the expressions will be annotated with
+;;; "expectations" that must be satisfied by the evaluation of the corresponding
+;;; expression.
+
+;;; For example,
+;;;
+;;; (fib 20)
+;;; 'expect eqv? 6765
+;;;
+;;; is a trivial example. There are also expectations involving
+;;; printed output, and others can be defined as needed.
+
+;;; This style of testing closely resembles a transcript, and has the advantage
+;;; that the code can just be loaded normally and it does the same thing without
+;;; checking the expectations.
+
+;;; This was developed as a response to GJS's dislike of the standard testing
+;;; framework. Gerry prefers to just type at the interpreter and keep a
+;;; transcript of the results around; this closely mirrors his testing style.
+
+(define-library (mit inline-testing)
+ (import (scheme base)
+ (scheme char)
+ (scheme cxr)
+ (scheme eval)
+ (scheme read)
+ (scheme write)
+ (srfi 1)
+ (srfi 6)
+ (mit library)
+ (only (mit legacy runtime)
+ ->namestring
+ alist->bundle
+ bundle
+ call-with-output-string
+ call-with-truncated-output-string
+ call-with-truncated-output-string
+ condition?
+ default-object
+ default-object?
+ environment?
+ fresh-line
+ keyword-option-parser
+ make-bundle-predicate
+ make-settable-parameter
+ nearest-repl/environment
+ pathname-default-type
+ pp
+ read-file
+ warn
+ with-notification
+ write-to-string))
+ (export define-error-expectation
+ define-output-expectation
+ define-value-expectation
+ run-inline-tests)
+ (begin
+\f
+(define (run-inline-tests filename . options)
+ (let-values (((*eval *env *notify? *summarize?)
+ (run-option-parser options 'run-inline-tests))
+ ((exprs imports) (read-test-file filename)))
+ (let ((groups (parse-expression-groups exprs)))
+ (parameterize ((test-eval *eval)
+ (test-env (if imports
+ (apply environment imports)
+ *env))
+ (notify? *notify?)
+ (summarize? *summarize?))
+ (summarize-test-results
+ (notify-filename filename
+ (lambda ()
+ (execute-expression-groups groups))))))))
+
+(define run-option-parser
+ (keyword-option-parser
+ (list (list 'eval procedure? (lambda () eval))
+ (list 'env environment? nearest-repl/environment)
+ (list 'notify? boolean? (lambda () #f))
+ (list 'summarize? boolean? (lambda () #t)))))
+
+(define test-eval (make-parameter (default-object)))
+(define test-env (make-parameter (default-object)))
+(define notify? (make-parameter (default-object)))
+(define summarize? (make-parameter (default-object)))
+
+(define (notify-filename filename thunk)
+ (if (notify?)
+ (with-notification
+ (lambda (port)
+ (display "loading test: " port)
+ (write (->namestring filename) port))
+ thunk)
+ (thunk)))
+\f
+(define (read-test-file filename)
+ (let ((pn (pathname-default-type filename "scm")))
+ (let ((source (read-r7rs-source pn)))
+ (if source
+ (let ((program (r7rs-source-program source)))
+ (if (not program)
+ (error "Inline testing requires a program:" source))
+ (if (not (null? (r7rs-source-libraries source)))
+ (error "Inline testing doesn't support inline libraries:"
+ source))
+ (values (cdr (car (library-parsed-contents program)))
+ (library-parsed-imports program)))
+ (values (read-file pn) #f)))))
+
+(define (parse-expression-groups exprs)
+ (if (pair? exprs)
+ (let ((to-eval (car exprs)))
+ (let ((r (parse-expectations (cdr exprs))))
+ (cons (make-group to-eval (reverse (car r)))
+ (parse-expression-groups (cdr r)))))
+ '()))
+
+(define make-group cons)
+(define group-expression car)
+(define group-expectations cdr)
+
+(define (parse-expectations exprs)
+ (let ((expectation
+ (and (pair? exprs)
+ (parse-expectation (car exprs)))))
+ (if expectation
+ (let ((r (parse-expectations (cdr exprs))))
+ (cons (cons expectation (car r))
+ (cdr r)))
+ (cons (list) exprs))))
+
+(define (parse-expectation expr)
+ (and (is-quotation? expr)
+ (let ((text (quotation-text expr)))
+ (let loop ((rules expectation-rules))
+ (if (pair? rules)
+ (or (match-rule (car rules) text)
+ (loop (cdr rules)))
+ (begin
+ (warn "Unrecognized expectation:" text)
+ #f))))))
+
+(define (match-rule rule text)
+ (let ((keyword (expectation-rule-keyword rule))
+ (n-args (expectation-rule-n-args rule))
+ (handler (expectation-rule-handler rule)))
+ (cond ((and (pair? text)
+ (eq? (car text) keyword)
+ (list? (cdr text))
+ (= (length (cdr text)) n-args))
+ (cons handler (cdr text)))
+ ((and (eq? text keyword)
+ (= n-args 0))
+ (list handler))
+ (else #f))))
+
+(define (is-quotation? object)
+ (and (pair? object)
+ (eq? (car object) 'quote)
+ (pair? (cdr object))
+ (null? (cddr object))))
+
+(define (quotation-text expr)
+ (cadr expr))
+\f
+;;; Lots or hair here to let the test driver deal with "interesting" uses of
+;;; continuations. In particular, the state of the driver is moved outside of
+;;; the control structure, so that if there are multiple returns from evaluating
+;;; an expression, the "current" expectations are used for each.
+
+(define groups-to-test (make-settable-parameter (default-object)))
+(define current-group (make-settable-parameter (default-object)))
+(define test-results (make-settable-parameter (default-object)))
+
+(define (execute-expression-groups groups)
+ (parameterize ((groups-to-test groups)
+ (current-group #f)
+ (test-results '()))
+ (let loop ()
+ (if (pair? (groups-to-test))
+ (begin
+ (current-group (car (groups-to-test)))
+ (groups-to-test (cdr (groups-to-test)))
+ (test-results
+ (cons (execute-expression-group (current-group))
+ (test-results)))
+ (loop))))
+ (reverse (test-results))))
+
+(define (execute-expression-group group)
+ (let ((context (eval-to-context (car group))))
+ (cons (car group)
+ (filter-map (lambda (expectation)
+ (apply (car expectation)
+ context
+ (map (lambda (expr)
+ (eval expr (test-env)))
+ (cdr expectation))))
+ (cdr group)))))
+
+(define (eval-to-context expr)
+ (let ((output-port (open-output-string)))
+ (call-with-current-continuation
+ (lambda (k)
+ (with-exception-handler
+ (lambda (condition)
+ (k
+ (make-error-expectation-context
+ (get-output-string output-port)
+ condition)))
+ (lambda ()
+ (let ((value
+ (parameterize ((current-output-port output-port))
+ ((test-eval) expr (test-env)))))
+ (make-value-expectation-context
+ (get-output-string output-port)
+ value))))))))
+
+(define (make-error-expectation-context output condition)
+ (define (is-error?) #t)
+ (let ((port (open-input-string output)))
+ (define (get-port) port)
+ (define (get-condition) condition)
+ (bundle expectation-context? is-error? get-port get-condition)))
+
+(define (make-value-expectation-context output value)
+ (define (is-error?) #f)
+ (let ((port (open-input-string output)))
+ (define (get-port) port)
+ (define (get-value) value)
+ (bundle expectation-context? is-error? get-port get-value)))
+
+(define expectation-context?
+ (make-bundle-predicate 'expectation-context))
+\f
+(define (summarize-test-results results)
+ (if (summarize?)
+ (let ((failing-results (filter failing-test-result? results)))
+ (let ((failures (length failing-results))
+ (all (length results)))
+ (fresh-line)
+ (display "Ran ")
+ (write all)
+ (display " test")
+ (if (not (= 1 all))
+ (display "s"))
+ (display "; ")
+ (write failures)
+ (display " failure")
+ (if (not (= 1 failures))
+ (display "s")))
+ (for-each summarize-failing-result failing-results))))
+
+(define (failing-test-result? result)
+ (pair? (cdr result)))
+
+(define (summarize-failing-result failure)
+ (newline)
+ (newline)
+ (display "evaluating ")
+ (newline)
+ (pp (car failure))
+ (display "failed the following expectations:")
+ (newline)
+ (for-each (lambda (error)
+ (display error)
+ (newline))
+ (cdr failure)))
+
+(define (pp-to-string object)
+ (call-with-output-string
+ (lambda (port)
+ (pp object port))))
+\f
+;;;; Expectation rules
+
+(define (define-expectation keyword n-args handler)
+ (let ((rule (make-expectation-rule keyword n-args handler))
+ (tail
+ (find-tail (lambda (rule)
+ (eq? keyword
+ (expectation-rule-keyword rule)))
+ expectation-rules)))
+ (if tail
+ (set-car! tail rule)
+ (set! expectation-rules
+ (cons rule
+ expectation-rules)))))
+
+(define (define-error-expectation keyword n-args handler)
+ (define-expectation keyword n-args
+ (lambda (context . args)
+ (if (context 'is-error?)
+ (apply handler (context 'get-condition) args)
+ (string-append "expected error but instead got value\n"
+ (write-to-string (context 'get-value)))))))
+
+(define (define-value-expectation keyword n-args handler)
+ (define-expectation keyword n-args
+ (lambda (context . args)
+ (if (context 'is-error?)
+ (string-append "Expected non-error but instead got error: "
+ (write-to-string (context 'get-condition)))
+ (apply handler (context 'get-value) args)))))
+
+(define (define-output-expectation keyword n-args handler)
+ (define-expectation keyword n-args
+ (lambda (context . args)
+ (if (context 'is-error?)
+ (string-append "Expected non-error but instead got error: "
+ (write-to-string (context 'get-condition)))
+ (let ((objects (read-objects (context 'get-port))))
+ (if (condition? objects)
+ "Error while reading output"
+ (apply handler objects args)))))))
+
+(define (read-objects port)
+ (call-with-current-continuation
+ (lambda (k)
+ (with-exception-handler
+ (lambda (condition)
+ (k condition))
+ (lambda ()
+ (let loop ((objects '()))
+ (let ((object (read port)))
+ (if (eof-object? object)
+ (reverse objects)
+ (loop (cons object objects))))))))))
+
+(define expectation-rules
+ '())
+
+(define (make-expectation-rule keyword n-args handler)
+ (list 'expectation-rule keyword n-args handler))
+
+(define expectation-rule-keyword cadr)
+(define expectation-rule-n-args caddr)
+(define expectation-rule-handler cadddr)
+\f
+(define-value-expectation 'expect 2
+ (lambda (value pred expected)
+ (if (pred expected value)
+ #f
+ (string-append "expected value\n"
+ (write-to-string expected)
+ "\nbut instead got value\n"
+ (write-to-string value)))))
+
+(define-value-expectation 'expect-not 2
+ (lambda (value pred expected)
+ (if (pred expected value)
+ (string-append "expected value different from\n"
+ (write-to-string expected)
+ "\nbut instead got value\n"
+ (write-to-string value))
+ #f)))
+
+(define-value-expectation 'expect-true 0
+ (lambda (value)
+ (if value
+ #f
+ (string-append "expected true value but got false"))))
+
+(define-value-expectation 'expect-false 0
+ (lambda (value)
+ (if value
+ (string-append "expected false value but got\n"
+ (write-to-string value))
+ #f)))
+
+(define-error-expectation 'expect-error 0
+ (lambda (condition)
+ (declare (ignore condition))
+ #f))
+
+;;; General written output expectation.
+(define-output-expectation 'expect-output 2
+ (lambda (objects pred expected)
+ (let ((v (pred expected objects)))
+ (cond ((string? v) v)
+ ((eq? #t v) #f)
+ ((eq? #f v)
+ (string-append "Output\n"
+ (pp-to-string objects)
+ "doesn't satisfy predicate\n"
+ (pp-to-string pred)
+ "with expected value\n"
+ (pp-to-string expected)))
+ (else
+ (error "illegal predicate value:" v))))))
+
+(define-output-expectation 'expect-write 1
+ (lambda (objects expected)
+ (if (and (pair? objects)
+ (null? (cdr objects))
+ (equal? (car objects) expected))
+ #f
+ (string-append "expected to see output "
+ (write-to-string expected)
+ "\nbut instead saw "
+ (write-to-string objects)))))
+
+(define-output-expectation 'expect-pp-description 1
+ (lambda (objects expected)
+ (if (and (pair? objects)
+ (equal? (cdr objects) expected))
+ #f
+ (string-append "expected to see pp description "
+ (write-to-string expected)
+ "\nbut instead saw "
+ (write-to-string objects)))))
+
+(define-output-expectation 'expect-no-output 0
+ (lambda (objects)
+ (if (null? objects)
+ #f
+ (string-append "expected no output but found "
+ objects))))
+
+;; end of library
+))
\ No newline at end of file
--- /dev/null
+#| -*-Scheme-*-
+
+Copyright (C) 1986, 1987, 1988, 1989, 1990, 1991, 1992, 1993, 1994,
+ 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
+ 2006, 2007, 2008, 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016,
+ 2017, 2018, 2019 Massachusetts Institute of Technology
+
+This file is part of MIT/GNU Scheme.
+
+MIT/GNU Scheme is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2 of the License, or (at
+your option) any later version.
+
+MIT/GNU Scheme is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with MIT/GNU Scheme; if not, write to the Free Software
+Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301,
+USA.
+
+|#
+
+;;;; SRFI 133
+
+;;; Loosely based on the SRFI's sample implementation.
+
+(define-library (srfi 133)
+ (import (scheme base)
+ (scheme cxr)
+ (srfi 8)
+ (only (mit legacy runtime)
+ error:bad-range-argument
+ fix:+
+ fix:-
+ fix:<
+ fix:<=
+ fix:=
+ fix:>
+ fix:>=
+ fix:end-index
+ fix:min
+ fix:quotient
+ fix:start-index
+ guarantee
+ index-fixnum?
+ unspecific))
+ (export reverse-list->vector
+ reverse-vector->list
+ vector-any
+ vector-append-subvectors
+ vector-cumulate
+ vector-empty?
+ vector-every
+ vector-fold
+ vector-fold-right
+ vector-index
+ vector-index-right
+ vector-map!
+ vector-partition
+ vector-reverse!
+ vector-reverse-copy
+ vector-skip
+ vector-skip-right
+ vector-swap!
+ vector-unfold
+ vector-unfold!
+ vector-unfold-right
+ vector-unfold-right!
+ vector=
+ vector-binary-search
+ vector-concatenate
+ vector-count
+ vector-reverse-copy!)
+ (begin
+\f
+;;; Constructors
+
+(define (vector-unfold proc n . initial-seeds)
+ (let ((v (make-vector n)))
+ (apply vector-unfold! proc v 0 n initial-seeds)
+ v))
+
+(define (vector-unfold-right proc n . initial-seeds)
+ (let ((v (make-vector n)))
+ (apply vector-unfold-right! proc v 0 n initial-seeds)
+ v))
+
+(define (vector-copy v #!optional start end)
+ (let* ((end (fix:end-index end (vector-length v) 'vector-copy))
+ (start (fix:start-index start end 'vector-copy))
+ (n (fix:- end start))
+ (result (make-vector n)))
+ (do ((i 0 (fix:+ i 1)))
+ ((not (fix:< i n)) result)
+ (vector-set! result i (vector-ref v (fix:+ start i))))))
+
+(define (vector-reverse-copy v #!optional start end)
+ (let* ((end (fix:end-index end (vector-length v) 'vector-reverse-copy))
+ (start (fix:start-index start end 'vector-reverse-copy))
+ (n (fix:- end start))
+ (last (fix:- end 1))
+ (result (make-vector n)))
+ (do ((i 0 (fix:+ i 1)))
+ ((not (fix:< i n)) result)
+ (vector-set! result i (vector-ref v (fix:- last i))))))
+
+(define (vector-append . vs)
+ (vector-concatenate vs))
+
+(define (vector-concatenate vs)
+ (let ((result
+ (make-vector
+ (let loop ((vs vs) (n 0))
+ (if (pair? vs)
+ (loop (cdr vs)
+ (fix:+ (vector-length (car vs)) n))
+ n)))))
+ (let loop ((vs vs) (index 0))
+ (if (pair? vs)
+ (let* ((v (car vs))
+ (n (vector-length v)))
+ (do ((i 0 (fix:+ i 1))
+ (j index (fix:+ j 1)))
+ ((not (fix:< i n))
+ (loop (cdr vs) j))
+ (vector-set! result j (vector-ref v i))))
+ result))))
+
+(define (vector-append-subvectors . args)
+
+ (define (parse-specs args)
+ (let ((caller 'vector-append-subvectors))
+ (let loop ((args args) (specs '()))
+ (if (pair? args)
+ (loop (cdddr args)
+ (cons (let* ((v (car args))
+ (end
+ (fix:end-index (caddr args)
+ (vector-length v)
+ caller)))
+ (vector v
+ (fix:start-index (cadr args) end caller)
+ end))
+ specs))
+ (reverse specs)))))
+
+ (define (compute-length specs)
+ (let loop ((specs specs) (n 0))
+ (if (pair? specs)
+ (loop (cdr specs)
+ (fix:+ n
+ (fix:- (vector-ref (car specs) 2)
+ (vector-ref (car specs) 1))))
+ n)))
+
+ (define (do-copies result specs)
+ (let loop ((specs specs) (at 0))
+ (if (pair? specs)
+ (let ((v (vector-ref (car specs) 0))
+ (start (vector-ref (car specs) 1))
+ (end (vector-ref (car specs) 2)))
+ (do ((i start (fix:+ i 1))
+ (at at (fix:+ at 1)))
+ ((not (fix:< i end))
+ (loop (cdr specs) at))
+ (vector-set! result at (vector-ref v i)))))))
+
+ (let* ((specs (parse-specs args))
+ (result (make-vector (compute-length specs))))
+ (do-copies result specs)
+ result))
+\f
+;;; Predicates
+
+(define (vector-empty? v)
+ (fix:= 0 (vector-length v)))
+
+(define (vector= elt= . vs)
+ (or (not (pair? vs))
+ (let* ((v (car vs))
+ (n (vector-length v)))
+ ;; Check lengths first since that's fast.
+ (and (let check-lengths ((vs* (cdr vs)))
+ (or (not (pair? vs*))
+ (and (fix:= n (vector-length (car vs*)))
+ (check-lengths (cdr vs*)))))
+ (let check-elts ((vs (cdr vs)))
+ (or (not (pair? vs))
+ (let ((v* (car vs)))
+ (let loop ((i 0))
+ (if (fix:< i n)
+ (and (elt= (vector-ref v i)
+ (vector-ref v* i))
+ (loop (fix:+ i 1)))
+ (check-elts (cdr vs)))))))))))
+\f
+;;; Iteration
+
+(define (vector-fold kons knil v . vs)
+ (if (null? vs)
+ (let ((n (vector-length v)))
+ (do ((i 0 (fix:+ i 1))
+ (knil* knil (kons knil* (vector-ref v i))))
+ ((not (fix:< i n)) knil*)))
+ (let* ((vs (cons v vs))
+ (n (vectors-length vs)))
+ (do ((i 0 (fix:+ i 1))
+ (knil* knil (apply kons knil* (vectors-ref vs i))))
+ ((not (fix:< i n)) knil*)))))
+
+(define (vector-fold-right kons knil v . vs)
+ (if (null? vs)
+ (do ((i (fix:- (vector-length v) 1) (fix:- i 1))
+ (knil* knil (kons knil* (vector-ref v i))))
+ ((not (fix:>= i 0)) knil*))
+ (let ((vs (cons v vs)))
+ (do ((i (fix:- (vectors-length vs) 1) (fix:- i 1))
+ (knil* knil (apply kons knil* (vectors-ref vs i))))
+ ((not (fix:>= i 0)) knil*)))))
+
+(define (vector-map proc v . vs)
+ (if (null? vs)
+ (let* ((n (vector-length v))
+ (target (make-vector n)))
+ (do ((i 0 (fix:+ i 1)))
+ ((not (fix:< i n)) target)
+ (vector-set! target i (proc (vector-ref v i)))))
+ (let* ((vs (cons v vs))
+ (n (vectors-length vs))
+ (target (make-vector n)))
+ (do ((i 0 (fix:+ i 1)))
+ ((not (fix:< i n)) target)
+ (vector-set! target i (apply proc (vectors-ref v i)))))))
+
+(define (vector-map! proc v . vs)
+ (if (null? vs)
+ (let* ((n (vector-length v)))
+ (do ((i 0 (fix:+ i 1)))
+ ((not (fix:< i n)) unspecific)
+ (vector-set! v i (proc (vector-ref v i)))))
+ (let* ((vs (cons v vs))
+ (n (vectors-length vs)))
+ (do ((i 0 (fix:+ i 1)))
+ ((not (fix:< i n)) unspecific)
+ (vector-set! v i (apply proc (vectors-ref vs i)))))))
+
+(define (vector-for-each proc v . vs)
+ (if (null? vs)
+ (let ((n (vector-length v)))
+ (do ((i 0 (fix:+ i 1)))
+ ((not (fix:< i n)) unspecific)
+ (proc (vector-ref v i))))
+ (let* ((vs (cons v vs))
+ (n (vectors-length vs)))
+ (do ((i 0 (fix:+ i 1)))
+ ((not (fix:< i n)) unspecific)
+ (apply proc (vectors-ref vs i))))))
+
+(define (vector-count pred v . vs)
+ (if (null? vs)
+ (let ((n (vector-length v)))
+ (do ((i 0 (fix:+ i 1))
+ (j 0 (if (pred (vector-ref v i)) (fix:+ j 1) j)))
+ ((not (fix:< i n)) j)))
+ (let* ((vs (cons v vs))
+ (n (vectors-length vs)))
+ (do ((i 0 (fix:+ i 1))
+ (j 0 (if (apply pred (vectors-ref vs i)) (fix:+ j 1) j)))
+ ((not (fix:< i n)) j)))))
+
+(define (vector-cumulate proc knil v)
+ (let* ((n (vector-length v))
+ (result (make-vector n)))
+ (let loop ((i 0) (left knil))
+ (if (fix:< i n)
+ (let ((left* (proc left (vector-ref v i))))
+ (vector-set! result i left*)
+ (loop (fix:+ i 1) left*))
+ result))))
+\f
+;;; Searching
+
+(define (vector-index pred v . vs)
+ (if (null? vs)
+ (let ((n (vector-length v)))
+ (let loop ((i 0))
+ (and (fix:< i n)
+ (if (pred (vector-ref v i))
+ i
+ (loop (fix:+ i 1))))))
+ (let* ((vs (cons v vs))
+ (n (vectors-length vs)))
+ (let loop ((i 0))
+ (and (fix:< i n)
+ (if (apply pred (vectors-ref vs i))
+ i
+ (loop (fix:+ i 1))))))))
+
+(define (vector-index-right pred v . vs)
+ (if (null? v)
+ (let loop ((i (fix:- (vector-length v) 1)))
+ (and (fix:>= i 0)
+ (if (pred (vector-ref v i))
+ i
+ (loop (fix:- i 1)))))
+ (let ((vs (cons v vs)))
+ (let loop ((i (fix:- (vectors-length vs) 1)))
+ (and (fix:>= i 0)
+ (if (apply pred (vectors-ref vs i))
+ i
+ (loop (fix:- i 1))))))))
+
+(define (vector-skip pred v . vs)
+ (if (null? vs)
+ (let ((n (vector-length v)))
+ (let loop ((i 0))
+ (and (fix:< i n)
+ (if (pred (vector-ref v i))
+ (loop (fix:+ i 1))
+ i))))
+ (let* ((vs (cons v vs))
+ (n (vectors-length vs)))
+ (let loop ((i 0))
+ (and (fix:< i n)
+ (if (apply pred (vectors-ref vs i))
+ (loop (fix:+ i 1))
+ i))))))
+
+(define (vector-skip-right pred v . vs)
+ (if (null? v)
+ (let loop ((i (fix:- (vector-length v) 1)))
+ (and (fix:>= i 0)
+ (if (pred (vector-ref v i))
+ (loop (fix:- i 1))
+ i)))
+ (let ((vs (cons v vs)))
+ (let loop ((i (fix:- (vectors-length vs) 1)))
+ (and (fix:>= i 0)
+ (if (apply pred (vectors-ref vs i))
+ (loop (fix:- i 1))
+ i))))))
+
+(define (vector-binary-search v value cmp)
+ (let loop ((start 0) (end (vector-length v)))
+ (and (fix:< start end)
+ (let ((midpoint (fix:quotient (fix:+ start end) 2)))
+ (let ((c (cmp (vector-ref v midpoint) value)))
+ (cond ((zero? c) midpoint)
+ ((positive? c) (loop start midpoint))
+ (else (loop (fix:+ midpoint 1) end))))))))
+
+(define (vector-any pred v . vs)
+ (if (null? vs)
+ (let ((n (vector-length v)))
+ (let loop ((i 0))
+ (and (fix:< i n)
+ (or (pred (vector-ref v i))
+ (loop (fix:+ i 1))))))
+ (let ((vs (cons v vs))
+ (n (vectors-length vs)))
+ (let loop ((i 0))
+ (and (fix:< i n)
+ (or (apply pred (vectors-ref vs i))
+ (loop (fix:+ i 1))))))))
+
+(define (vector-every pred v . vs)
+ (if (null? vs)
+ (let ((n (vector-length v)))
+ (let loop ((i 0))
+ (if (fix:< i n)
+ (and (pred (vector-ref v i))
+ (loop (fix:+ i 1)))
+ #t)))
+ (let ((vs (cons v vs))
+ (n (vectors-length vs)))
+ (let loop ((i 0))
+ (if (fix:< i n)
+ (and (apply pred (vectors-ref vs i))
+ (loop (fix:+ i 1)))
+ #t)))))
+
+(define (vector-partition pred v)
+ (let* ((n (vector-length v))
+ (result (make-vector n)))
+ (let loop ((i 0) (yes 0) (no (fix:- n 1)))
+ (if (fix:< i n)
+ (let ((elt (vector-ref v i)))
+ (if (pred elt)
+ (begin
+ (vector-set! result yes elt)
+ (loop (fix:+ i 1) (fix:+ yes 1) no))
+ (begin
+ (vector-set! result no elt)
+ (loop (fix:+ i 1) yes (fix:- no 1)))))
+ (begin
+ (%vector-reverse! result yes n)
+ (values result yes))))))
+\f
+;;; Mutators
+
+(define (vector-swap! v i1 i2)
+ (let ((x (vector-ref v i1)))
+ (vector-set! v i1 (vector-ref v i2))
+ (vector-set! v i2 x)))
+
+(define (vector-reverse! v #!optional start end)
+ (let ((end (fix:end-index end (vector-length v) 'vector-reverse!)))
+ (%vector-reverse! v
+ (fix:start-index start end 'vector-reverse!)
+ end)))
+
+(define (%vector-reverse! v start end)
+ (let loop ((i start) (j (fix:- end 1)))
+ (if (fix:< i j)
+ (let ((elt (vector-ref v i)))
+ (vector-set! v i (vector-ref v j))
+ (vector-set! v j elt)
+ (loop (fix:+ i 1) (fix:- j 1))))))
+
+(define (vector-copy! to at from #!optional start end)
+ (let* ((end (fix:end-index end (vector-length from) 'vector-copy!))
+ (start (fix:start-index start end 'vector-copy!)))
+ (let ((tend
+ (to-end-index at
+ (fix:- end start)
+ (vector-length to)
+ 'vector-copy!)))
+ (cond ((or (not (eq? to from)) (fix:< at start))
+ (do ((i start (fix:+ i 1))
+ (j at (fix:+ j 1)))
+ ((not (fix:< i end)) unspecific)
+ (vector-set! to j (vector-ref from i))))
+ ((fix:> at start)
+ (do ((i (fix:- end 1) (fix:- i 1))
+ (j (fix:- tend 1) (fix:- j 1)))
+ ((not (fix:>= i start)) unspecific)
+ (vector-set! to j (vector-ref from i))))))))
+
+(define (vector-reverse-copy! to at from #!optional start end)
+ (let* ((end (fix:end-index end (vector-length from) 'vector-reverse-copy!))
+ (start (fix:start-index start end 'vector-reverse-copy!)))
+ (let ((tend
+ (to-end-index at
+ (fix:- end start)
+ (vector-length to)
+ 'vector-copy!)))
+
+ (define (do-copy tend start end)
+ (do ((i start (fix:+ i 1))
+ (j (fix:- tend 1) (fix:- j 1)))
+ ((not (fix:< i end)) unspecific)
+ (vector-set! to j (vector-ref from i))))
+
+ (cond ((or (not (eq? to from)) (fix:<= end at) (fix:<= tend start))
+ (do-copy tend start end))
+ ((fix:< at start)
+ (do-copy at tend end)
+ (%vector-reverse! to start tend))
+ ((fix:> at start)
+ (do-copy start end tend)
+ (%vector-reverse! to at end))))))
+
+(define (vector-unfold! proc v start end . initial-seeds)
+ (let* ((end (fix:end-index end (vector-length v) 'vector-unfold!))
+ (start (fix:start-index start end 'vector-unfold!)))
+ (cond ((null? initial-seeds)
+ (do ((i start (fix:+ i 1)))
+ ((not (fix:< i end)) unspecific)
+ (vector-set! v i (proc i))))
+ ((null? (cdr initial-seeds))
+ (let loop ((i start) (seed (car initial-seeds)))
+ (if (fix:< i end)
+ (receive (elt seed*) (proc i seed)
+ (vector-set! v i elt)
+ (loop (fix:+ i 1) seed*)))))
+ (else
+ (let loop ((i start) (seeds initial-seeds))
+ (if (fix:< i end)
+ (receive (elt . seeds*) (apply proc i seeds)
+ (vector-set! v i elt)
+ (loop (fix:+ i 1) seeds*))))))))
+
+(define (vector-unfold-right! proc v start end . initial-seeds)
+ (let* ((end (fix:end-index end (vector-length v) 'vector-unfold!))
+ (start (fix:start-index start end 'vector-unfold!)))
+ (cond ((null? initial-seeds)
+ (do ((i (fix:- end 1) (fix:- i 1)))
+ ((not (fix:>= i start)) unspecific)
+ (vector-set! v i (proc i))))
+ ((null? (cdr initial-seeds))
+ (let loop ((i (fix:- end 1)) (seed (car initial-seeds)))
+ (if (fix:>= i start)
+ (receive (elt seed*) (proc i seed)
+ (vector-set! v i elt)
+ (loop (fix:- i 1) seed*)))))
+ (else
+ (let loop ((i (fix:- end 1)) (seeds initial-seeds))
+ (if (fix:>= i start)
+ (receive (elt . seeds*) (apply proc i seeds)
+ (vector-set! v i elt)
+ (loop (fix:- i 1) seeds*))))))))
+\f
+;;; Conversion
+
+(define (vector->list v #!optional start end)
+ (let* ((end (fix:end-index end (vector-length v) 'vector->list))
+ (start (fix:start-index start end 'vector->list)))
+ (do ((i (fix:- end 1) (fix:- i 1))
+ (result '() (cons (vector-ref v i) result)))
+ ((not (fix:>= i start)) result))))
+
+(define (reverse-vector->list v #!optional start end)
+ (let* ((end (fix:end-index end (vector-length v) 'reverse-vector->list))
+ (start (fix:start-index start end 'reverse-vector->list)))
+ (do ((i start (fix:+ i 1))
+ (result '() (cons (vector-ref v i) result)))
+ ((not (fix:< i end)) result))))
+
+(define (list->vector l)
+ (let* ((n (length l))
+ (result (make-vector n)))
+ (do ((i 0 (fix:+ i 1))
+ (l l (cdr l)))
+ ((not (fix:< i n)) result)
+ (vector-set! result i (car l)))))
+
+(define (reverse-list->vector l)
+ (let* ((n (length l))
+ (result (make-vector n)))
+ (do ((i (fix:- n 1) (fix:- i 1))
+ (l l (cdr l)))
+ ((not (fix:>= i 0)) result)
+ (vector-set! result i (car l)))))
+
+;;; Internal
+
+(define (vectors-ref vs i)
+ (let loop ((vs vs))
+ (if (pair? vs)
+ (cons (vector-ref (car vs) i)
+ (loop (cdr vs)))
+ '())))
+
+(define (vectors-length vs)
+ (let loop ((vs (cdr vs)) (n (vector-length (car vs))))
+ (if (pair? vs)
+ (loop (cdr vs) (fix:min n (vector-length (car vs))))
+ n)))
+
+(define (to-end-index start n limit caller)
+ (guarantee index-fixnum? start caller)
+ (let ((end (fix:+ start n)))
+ (if (not (fix:<= n limit))
+ (error:bad-range-argument start caller))
+ end))
+
+;; end of library
+))
\ No newline at end of file
--- /dev/null
+(import (scheme base)
+ (srfi 133))
+
+(define v (make-vector 3 3))
+
+(vector? #(1 2 3)) 'expect-true
+(vector? (make-vector 10)) 'expect-true
+(vector-ref v 0) '(expect eqv? 3)
+(vector-ref v 1) '(expect eqv? 3)
+(vector-ref v 2) '(expect eqv? 3)
+(vector-ref v -1) 'expect-error
+(vector-ref v 3) 'expect-error
+
+(vector-set! v 0 -32)
+(vector-ref v 0) '(expect eqv? -32)
+(vector-length v) '(expect = 3)
+(vector-length '#()) '(expect = 0)
+
+(define a2i '#(a b c d e f g h i))
+
+(vector 0 1 2 3 4) '(expect equal? '#(0 1 2 3 4))
+(vector-copy a2i) '(expect equal? a2i)
+(vector-copy a2i) '(expect-not eqv? a2i)
+
+(vector-unfold (lambda (i x) (declare (ignore i)) (values x (- x 1))) 10 0)
+'(expect equal? '#(0 -1 -2 -3 -4 -5 -6 -7 -8 -9))
+(vector-unfold values 7)
+'(expect equal? '#(0 1 2 3 4 5 6))
+(vector-unfold-right (lambda (i x) (values (cons i x) (+ x 1))) 5 0)
+'(expect equal? '#((0 . 4) (1 . 3) (2 . 2) (3 . 1) (4 . 0)))
+
+(vector-copy a2i 6) '(expect equal? '#(g h i))
+(vector-copy a2i 3 6) '(expect equal? '#(d e f))
+(vector-reverse-copy '#(5 4 3 2 1 0) 1 5) '(expect equal? '#(1 2 3 4))
+
+(vector-append '#(x) '#(y)) '(expect equal? '#(x y))
+(vector-append '#(a) '#(b c d)) '(expect equal? '#(a b c d))
+(vector-append '#(a #(b)) '#(#(c))) '(expect equal? '#(a #(b) #(c)))
+(vector-concatenate '(#(a b) #(c d))) '(expect equal? '#(a b c d))
+
+(vector-append-subvectors '#(a b c d e) 0 2 '#(f g h i j) 2 4)
+'(expect equal? '#(a b h i))
+
+(vector-empty? '#(a)) 'expect-false
+(vector-empty? '#(())) 'expect-false
+(vector-empty? '#(#())) 'expect-false
+(vector-empty? '#()) 'expect-true
+(vector= eq? '#(a b c d) '#(a b c d)) 'expect-true
+(vector= eq? '#(a b c d) '#(a b d c)) 'expect-false
+(vector= = '#(1 2 3 4 5) '#(1 2 3 4)) 'expect-false
+(vector= = '#(+nan.0) '#(+nan.0)) 'expect-false
+(let ((nan '+nan.0)) (vector= = (vector nan) (vector nan))) 'expect-false
+(let ((nanvec '#(+nan.0))) (vector= = nanvec nanvec)) 'expect-false
+(vector= eq?) 'expect-true
+(vector= eq? '#(a)) 'expect-true
+(vector= eq? (vector (vector 'a)) (vector (vector 'a))) 'expect-false
+(vector= equal? (vector (vector 'a)) (vector (vector 'a))) 'expect-true
+
+(define vos '#("abc" "abcde" "abcd"))
+(define vec '#(0 1 2 3 4 5))
+(define vec2 (vector 0 1 2 3 4))
+(define vec3 (vector 1 2 3 4 5))
+(define result '())
+(define (sqr x) (* x x))
+(vector-fold (lambda (len str) (max (string-length str) len)) 0 vos)
+'(expect eqv? 5)
+(vector-fold (lambda (tail elt) (cons elt tail)) '() vec)
+'(expect equal? '(5 4 3 2 1 0))
+(vector-fold (lambda (ctr n) (if (even? n) (+ ctr 1) ctr)) 0 vec)
+'(expect eqv? 3)
+(vector-fold-right (lambda (tail elt) (cons elt tail)) '() '#(a b c d))
+'(expect equal? '(a b c d))
+(vector-map sqr '#(1 2 3 4))
+'(expect equal? '#(1 4 9 16))
+(vector-map * '#(1 2 3 4 5) '#(5 4 3 2 1))
+'(expect equal? '#(5 8 9 8 5))
+(vector-map! sqr vec2)
+(vector-copy vec2)
+'(expect equal? '#(0 1 4 9 16))
+(vector-map! * vec2 vec3)
+(vector-copy vec2)
+'(expect equal? '#(0 2 12 36 80))
+(vector-for-each (lambda (x) (set! result (cons x result))) vec)
+(cons (car result) (cdr result))
+'(expect equal? '(5 4 3 2 1 0))
+(vector-count even? '#(3 1 4 1 5 9 2 5 6))
+'(expect eqv? 3)
+(vector-count < '#(1 3 6 9) '#(2 4 6 8 10 12))
+'(expect eqv? 2)
+(vector-cumulate + 0 '#(3 1 4 1 5 9 2 5 6))
+'(expect equal? '#(3 4 8 9 14 23 25 30 36))
+
+(define (cmp a b)
+ (cond
+ ((< a b) -1)
+ ((= a b) 0)
+ (else 1)))
+(define v '#(0 2 4 6 8 10 12))
+(vector-index even? '#(3 1 4 1 5 9 6)) '(expect eqv? 2)
+(vector-index < '#(3 1 4 1 5 9 2 5 6) '#(2 7 1 8 2)) '(expect eqv? 1)
+(vector-index = '#(3 1 4 1 5 9 2 5 6) '#(2 7 1 8 2)) 'expect-false
+(vector-index-right odd? '#(3 1 4 1 5 9 6)) '(expect eqv? 5)
+(vector-index-right < '#(3 1 4 1 5) '#(2 7 1 8 2)) '(expect eqv? 3)
+(vector-skip number? '#(1 2 a b 3 4 c d)) '(expect eqv? 2)
+(vector-skip = '#(1 2 3 4 5) '#(1 2 -3 4)) '(expect eqv? 2)
+(vector-skip-right number? '#(1 2 a b 3 4 c d)) '(expect eqv? 7)
+(vector-skip-right = '#(1 2 3 4 5) '#(1 2 -3 -4 5)) '(expect eqv? 3)
+(vector-binary-search v 0 cmp) '(expect eqv? 0)
+(vector-binary-search v 6 cmp) '(expect eqv? 3)
+(vector-binary-search v 1 cmp) 'expect-false
+(vector-any number? '#(1 2 x y z)) 'expect-true
+(vector-any < '#(1 2 3 4 5) '#(2 1 3 4 5)) 'expect-true
+(vector-any number? '#(a b c d e)) 'expect-false
+(vector-any > '#(1 2 3 4 5) '#(1 2 3 4 5)) 'expect-false
+(vector-every number? '#(1 2 x y z)) 'expect-false
+(vector-every number? '#(1 2 3 4 5)) 'expect-true
+(vector-every < '#(1 2 3) '#(2 3 3)) 'expect-false
+(vector-every < '#(1 2 3) '#(2 3 4)) 'expect-true
+(vector-any (lambda (x) (if (number? x) 'yes #f)) '#(1 2 x y z))
+ '(expect eqv? 'yes)
+
+(define vp
+ (let-values (((new off) (vector-partition number? '#(1 x 2 y 3 z))))
+ (cons new off)))
+(vector-copy (car vp)) '(expect equal? '#(1 2 3 x y z))
+(cdr vp) '(expect eqv? 3)
+
+(define vs (vector 1 2 3))
+(define vf0 (vector 1 2 3))
+(define vf1 (vector 1 2 3))
+(define vf2 (vector 1 2 3))
+(define vr0 (vector 1 2 3))
+(define vr1 (vector 1 2 3))
+(define vr2 (vector 1 2 3))
+(define vc0 (vector 1 2 3 4 5))
+(define vc1 (vector 1 2 3 4 5))
+(define vc2 (vector 1 2 3 4 5))
+(define vrc0 (vector 1 2 3 4 5))
+(define vrc1 (vector 1 2 3 4 5))
+(define vrc2 (vector 1 2 3 4 5))
+(define vu0 (vector 1 2 3 4 5))
+(define vu1 (vector 1 2 3 4 5))
+(define vu2 (vector 1 2 3 4 5))
+(define vur0 (vector 1 2 3 4 5))
+(define vur1 (vector 1 2 3 4 5))
+(define vur2 (vector 1 2 3 4 5))
+(vector-swap! vs 0 1)
+(vector-copy vs)
+'(expect equal? '#(2 1 3))
+(vector-fill! vf0 0)
+(vector-copy vf0)
+'(expect equal? '#(0 0 0))
+(vector-fill! vf1 0 1)
+(vector-copy vf1)
+'(expect equal? '#(1 0 0))
+(vector-fill! vf2 0 0 1)
+(vector-copy vf2)
+'(expect equal? '#(0 2 3))
+(vector-reverse! vr0)
+(vector-copy vr0)
+'(expect equal? '#(3 2 1))
+(vector-reverse! vr1 1)
+(vector-copy vr1)
+'(expect equal? '#(1 3 2))
+(vector-reverse! vr2 0 2)
+(vector-copy vr2)
+'(expect equal? '#(2 1 3))
+(vector-copy! vc0 1 '#(10 20 30))
+(vector-copy vc0)
+'(expect equal? '#(1 10 20 30 5))
+(vector-copy! vc1 1 '#(0 10 20 30 40) 1)
+(vector-copy vc1)
+'(expect equal? '#(1 10 20 30 40))
+(vector-copy! vc2 1 '#(0 10 20 30 40) 1 4)
+(vector-copy vc2)
+'(expect equal? '#(1 10 20 30 5))
+(vector-reverse-copy! vrc0 1 '#(10 20 30))
+(vector-copy vrc0)
+'(expect equal? '#(1 30 20 10 5))
+(vector-reverse-copy! vrc1 1 '#(0 10 20 30 40) 1)
+(vector-copy vrc1)
+'(expect equal? '#(1 40 30 20 10))
+(vector-reverse-copy! vrc2 1 '#(0 10 20 30 40) 1 4)
+(vector-copy vrc2)
+'(expect equal? '#(1 30 20 10 5))
+(vector-unfold! (lambda (i) (+ 10 i)) vu0 1 4)
+(vector-copy vu0)
+'(expect equal? '#(1 11 12 13 5))
+(vector-unfold! (lambda (i x) (values (+ i x) (+ x 1))) vu1 1 4 0)
+(vector-copy vu1)
+'(expect equal? '#(1 1 3 5 5))
+(vector-unfold! (lambda (i x y) (values (+ i x y) (+ x 1) (+ x 1))) vu2 1 4 0 0)
+(vector-copy vu2)
+'(expect equal? '#(1 1 4 7 5))
+(vector-unfold-right! (lambda (i) (+ 10 i)) vur0 1 4)
+(vector-copy vur0)
+'(expect equal? '#(1 11 12 13 5))
+(vector-unfold-right! (lambda (i x) (values (+ i x) (+ x 1))) vur1 1 4 0)
+(vector-copy vur1)
+'(expect equal? '#(1 3 3 3 5))
+(vector-unfold-right! (lambda (i x y) (values (+ i x y) (+ x 1) (+ x 1)))
+ vur2 1 4 0 0)
+(vector-copy vur2)
+'(expect equal? '#(1 5 4 3 5))
+
+(vector->list '#(1 2 3)) '(expect equal? '(1 2 3))
+(vector->list '#(1 2 3) 1) '(expect equal? '(2 3))
+(vector->list '#(1 2 3) 0 2) '(expect equal? '(1 2))
+(list->vector '(1 2 3)) '(expect equal? '#(1 2 3))
+(reverse-vector->list '#(1 2 3)) '(expect equal? '(3 2 1))
+(reverse-vector->list '#(1 2 3) 1) '(expect equal? '(3 2))
+(reverse-vector->list '#(1 2 3) 0 2) '(expect equal? '(2 1))
+(reverse-list->vector '(1 2 3)) '(expect equal? '#(3 2 1))
+(vector->string '#(#\a #\b #\c)) '(expect equal? "abc")
+(vector->string '#(#\a #\b #\c) 1) '(expect equal? "bc")
+(vector->string '#(#\a #\b #\c) 0 2) '(expect equal? "ab")
+(string->vector "abc") '(expect equal? '#(#\a #\b #\c))
+(string->vector "abc" 1) '(expect equal? '#(#\b #\c))
+(string->vector "abc" 0 2) '(expect equal? '#(#\a #\b))