miniscm: add mutable string emulation and char->integer

This commit is contained in:
Peter McGoron 2024-08-26 17:52:19 -04:00
parent 9d08c1f59e
commit 1b56759726
3 changed files with 54 additions and 3 deletions

View File

@ -20,7 +20,7 @@ designed to be used by a severely limited Scheme interpreter, which
(except ``open-input-port``, ``close-input-port``, ``read-char``, (except ``open-input-port``, ``close-input-port``, ``read-char``,
``open-output-port``, ``close-output-port``, ``write-char``) ``open-output-port``, ``close-output-port``, ``write-char``)
* has fixnums only * has fixnums only
* minimizes the use of strings * only uses immutable strings
* does not use "load" recursively * does not use "load" recursively
The goal is to have the compiler run under MiniScheme 0.85 in DOS. The goal is to have the compiler run under MiniScheme in DOS.

View File

@ -1,6 +1,8 @@
; This is a init file for Mini-Scheme. ; This is a init file for Mini-Scheme.
; Modified for UNSLISP. ; Modified for UNSLISP.
(define modulo remainder)
(define (caar x) (car (car x))) (define (caar x) (car (car x)))
(define (cadr x) (car (cdr x))) (define (cadr x) (car (cdr x)))
(define (cdar x) (cdr (car x))) (define (cdar x) (cdr (car x)))
@ -48,6 +50,16 @@
(define vector-ref list-ref) (define vector-ref list-ref)
(define vector-set! list-set!) (define vector-set! list-set!)
(define make-vector
(lambda (num)
(letrec
((loop
(lambda (iter cell)
(if (= iter 0)
cell
(loop (- iter 1) (cons #f cell))))))
(loop num '()))))
(define (head stream) (car stream)) (define (head stream) (car stream))
(define (tail stream) (force (cdr stream))) (define (tail stream) (force (cdr stream)))
@ -75,3 +87,30 @@
(equal? (cdr x) (cdr y))) (equal? (cdr x) (cdr y)))
(and (not (pair? y)) (and (not (pair? y))
(eqv? x y)))) (eqv? x y))))
;;; Emulation of mutable strings.
(define string-ref list-ref)
(define string-set! list-set!)
(define string list)
(define list<=>
(lambda (x y <=>)
(cond
((and (null? x) (null? y)) '=)
((null? x) '<)
((null? y) '>)
(else
(let ((dir (<=> (car x) (car y))))
(if (eq? dir '=)
(list<=> (cdr x) (cdr y) <=>)
dir))))))
(define string<=>
(lambda (x y)
(list<=> x y (lambda (x y)
(if (eqv? x y)
'=
(if (< (char->integer x) (char->integer y))
'<
'>))))))

View File

@ -1213,6 +1213,8 @@ register pointer a, b;
#define OP_CLOSEOUT 109 #define OP_CLOSEOUT 109
#define OP_WRITEOUT 110 #define OP_WRITEOUT 110
#define OP_CHAR2INT 111
static FILE *tmpfp; static FILE *tmpfp;
static int tok; static int tok;
static int print_flag; static int print_flag;
@ -1771,6 +1773,12 @@ register short op;
} else { } else {
Error_0("Unable to set-cdr! for non-cons cell"); Error_0("Unable to set-cdr! for non-cons cell");
} }
case OP_CHAR2INT: /* char->integer */
if (ischar(car(args))) {
s_return(mk_number(ivalue(car(args))));
} else {
Error_0("char->integer: argument must be char");
}
default: default:
sprintf(strbuff, "%d is illegal operator", operator); sprintf(strbuff, "%d is illegal operator", operator);
@ -2447,7 +2455,9 @@ pointer (*dispatch_table[])() = {
opexe_7, /* OP_READIN */ opexe_7, /* OP_READIN */
opexe_7, /* OP_OPENOUT */ opexe_7, /* OP_OPENOUT */
opexe_7, /* OP_CLOSEOUT */ opexe_7, /* OP_CLOSEOUT */
opexe_7 /* OP_WRITEOUT */ opexe_7, /* OP_WRITEOUT */
opexe_2 /* OP_CHAR2INT */
}; };
@ -2604,6 +2614,8 @@ init_procs()
mk_proc(OP_OPENOUT, "open-output-file"); mk_proc(OP_OPENOUT, "open-output-file");
mk_proc(OP_CLOSEOUT, "close-output-port"); mk_proc(OP_CLOSEOUT, "close-output-port");
mk_proc(OP_WRITEOUT, "write-char"); mk_proc(OP_WRITEOUT, "write-char");
mk_proc(OP_CHAR2INT, "char->integer");
} }