X-Git-Url: http://repo.macrolet.net/gitweb/?a=blobdiff_plain;f=src%2Fboot.lisp;h=3541b23a863e800e602dc220d4542eb2eba185b3;hb=18ada11fb234e336a3d2ac4370d384d80d36f9f0;hp=dc9b45f4bbe65a29befdf35b6cabef776de1ac4b;hpb=162bfa35d0b1a8a698dc813f6bc0874a043a225c;p=jscl.git diff --git a/src/boot.lisp b/src/boot.lisp index dc9b45f..3541b23 100644 --- a/src/boot.lisp +++ b/src/boot.lisp @@ -22,6 +22,8 @@ ;;; Lisp world from scratch. This code has to define enough language ;;; to the compiler to be able to run. +(/debug "loading boot.lisp!") + (eval-when-compile (let ((defmacro-macroexpander '#'(lambda (form) @@ -44,7 +46,7 @@ (declaim (special ,name)) (declaim (constant ,name)) (setq ,name ,value) - ,@(when (stringp docstring) `((oset ',name "vardoc" ,docstring))) + ,@(when (stringp docstring) `((oset ,docstring ',name "vardoc"))) ',name)) (defconstant t 't) @@ -64,13 +66,13 @@ `(progn (declaim (special ,name)) ,@(when value-p `((unless (boundp ',name) (setq ,name ,value)))) - ,@(when (stringp docstring) `((oset ',name "vardoc" ,docstring))) + ,@(when (stringp docstring) `((oset ,docstring ',name "vardoc"))) ',name)) (defmacro defparameter (name value &optional docstring) `(progn (setq ,name ,value) - ,@(when (stringp docstring) `((oset ',name "vardoc" ,docstring))) + ,@(when (stringp docstring) `((oset ,docstring ',name "vardoc"))) ',name)) (defmacro defun (name args &rest body) @@ -87,7 +89,7 @@ (defvar *gensym-counter* 0) (defun gensym (&optional (prefix "G")) (setq *gensym-counter* (+ *gensym-counter* 1)) - (make-symbol (concat-two prefix (integer-to-string *gensym-counter*)))) + (make-symbol (concat prefix (integer-to-string *gensym-counter*)))) (defun boundp (x) (boundp x)) @@ -291,7 +293,9 @@ (defmacro do (varlist endlist &body body) `(block nil - (let ,(mapcar (lambda (x) (list (first x) (second x))) varlist) + (let ,(mapcar (lambda (x) (if (symbolp x) + (list x nil) + (list (first x) (second x)))) varlist) (while t (when ,(car endlist) (return (progn ,@(cdr endlist)))) @@ -299,13 +303,16 @@ (psetq ,@(apply #'append (mapcar (lambda (v) - (and (consp (cddr v)) + (and (listp v) + (consp (cddr v)) (list (first v) (third v)))) varlist))))))) (defmacro do* (varlist endlist &body body) `(block nil - (let* ,(mapcar (lambda (x) (list (first x) (second x))) varlist) + (let* ,(mapcar (lambda (x1) (if (symbolp x1) + (list x1 nil) + (list (first x1) (second x1)))) varlist) (while t (when ,(car endlist) (return (progn ,@(cdr endlist)))) @@ -313,7 +320,8 @@ (setq ,@(apply #'append (mapcar (lambda (v) - (and (consp (cddr v)) + (and (listp v) + (consp (cddr v)) (list (first v) (third v)))) varlist))))))) @@ -333,9 +341,6 @@ ((listp seq) (list-length seq)))) -(defun concat-two (s1 s2) - (concat-two s1 s2)) - (defmacro with-collect (&body body) (let ((head (gensym)) (tail (gensym))) @@ -469,14 +474,15 @@ ((null (cddr pairs)) (let ((place (!macroexpand-1 (first pairs))) (value (second pairs))) - (multiple-value-bind (vars vals store-vars writer-form) + (multiple-value-bind (vars vals store-vars writer-form reader-form) (get-setf-expansion place) ;; TODO: Optimize the expansion a little bit to avoid let* ;; or multiple-value-bind when unnecesary. `(let* ,(mapcar #'list vars vals) (multiple-value-bind ,store-vars ,value - ,writer-form))))) + ,writer-form + ,reader-form))))) (t `(progn ,@(do ((pairs pairs (cddr pairs)) @@ -491,11 +497,13 @@ (cond ,@(mapcar (lambda (c) (if (eq (car c) t) - `((t ,@(rest c))) + `(t ,@(rest c)) `((,(ecase (car c) (integer 'integerp) (cons 'consp) (symbol 'symbolp) + (function 'functionp) + (float 'floatp) (array 'arrayp) (string 'stringp) (atom 'atom) @@ -510,7 +518,7 @@ `(let ((,g!x ,x)) (typecase ,g!x ,@clausules - (t (error "~X fell through etypeacase expression." ,g!x)))))) + (t (error "~X fell through etypecase expression." ,g!x)))))) (defun notany (fn seq) (not (some fn seq))) @@ -534,3 +542,8 @@ (defun error (fmt &rest args) (%throw (apply #'format nil fmt args))) + +(defmacro nth-value (n form) + `(multiple-value-call (lambda (&rest values) + (nth ,n values)) + ,form))