[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

(setf (foo #) value), foo being undefined yet



Preliminaries:
> (defun fact (n) (setf (foo n) t))

*** - Illegal SETF place: (FOO N)
1. Break> 
I guess that this is a normal behaviour for CLtLI Lisps.


I came accross the following code:

* (macroexpand-1 '(defroutine add1-nam ((:nam e) (:nam i) n)
  (cond ((< i n) (setf e (+ e 1)))
        (t nil))))

(PROGN
 (DEFUN ADD1-NAM** (N)
   (LET ((N (EVAL N)))		; I believe that EVAL to be wrong,
                                ; but that's another story.
     (COND ((< (I**) N) (SETF (E**) (+ (E**) 1))) (T NIL))
     (VALUES)))
 (DEFMACRO ADD1-NAM (E I N)
   `(PROGN
     ,@(DEFTHUNK 'E** E)
     ,@(DEFTHUNK 'I** I)
     (MULTIPLE-VALUE-BIND NIL (ADD1-NAM** ,N))
     NIL)))
T
* (defthunk 'e** 'foobar)

((SETF (SYMBOL-FUNCTION 'E**) #'(LAMBDA () FOOBAR))
 (SETF (SYMBOL-FUNCTION 'E**-SET) #'(LAMBDA (VAL) (SETF FOOBAR VAL)))
 (DEFSETF E** E**-SET))
* 

Loading a file containing the above defroutine leads to the following
error:
*** - Illegal SETF place: (E**)
1. Break> where

EVAL-Frame für Form (LABELS ((ADD1-NAM** (N) (BLOCK ADD1-NAM** (LET ((N (EVAL N))) (COND ((< (I**) N) (SETF (E**) (+ (E**) 1))) (T NIL)) (VALUES))))) #'ADD1-NAM**)
1. Break> 

The error comes from the (SETF (E**) #) call in ADD1-NAM**, the
defsetf for e** would only occur when the add1-nam macro is actually
called/used, not in the defroutine call.

I wonder whether the above code using a yet undefined setf is correct
for CLtLI or CLtLII. In CLtLII, setf, seeing an unknown (setf (f #) #)
form, has been expanded to produce a call to the (setf f) function,
whereas in CLtLI (setf f) was not considered as being a function name.
I'm not sure whether the above code intended to make use of this
extended setf behaviour and thus was written for CLtLII. When
compiling the above, CMULISP (CLtLII) generates warnings about
undefined functions (SETF E**), E** and I**.

I'm tempted to believe that the above code is wrong w.r.t. both
standards and that it should have been written in another way (perhaps
with all needed defsetfs before the defun in the defroutine
macro-expansion, even if the used functions are not defined at that
time (is this allowed?), and maybe with some preceeding (declare
(notinline E** E**-SET))).

Thanks for your help,
 	Joerg.
hoehle@inf-wiss.ivp.uni-konstanz.de