Subject: bug#27016: possible bug in `defsetf'

From: [email-masked]
Date: Thu, 13 Jul 2017 20:39:27 -0400

Stefan Monnier <[email-masked]> writes:

> Looks about right.

Except that it isn't.  While compiling map.el, I get

../../emacs-master/lisp/emacs-lisp/map.el:292:1:Error: Symbol’s function definition is void: internal-make-closure

I can fix this with

@@ -146,7 +146,7 @@ (defmacro gv-define-expander (name handler)
 HANDLER is a function which takes an argument DO followed by the same
 arguments as NAME.  DO is a function as defined in `gv-get'."
   (declare (indent 1) (debug (sexp form)))
-  `(function-put ',name 'gv-expander ,handler))
+  `(function-put ',name 'gv-expander (eval-when-compile ,handler)))

But that doesn't look like the right thing.

> I know it's not how it's done everywhere now, but I like to put the
> byte-defop-compiler-1 next to the handler function.

Makes sense.

>> +(defun byte-compile-function-put (form)
>> +  (pcase form
>> +    (`(,_ (,(or 'quote 'function) ,(and fun (guard (symbolp fun))))
>> +          ',prop ,(or `#',value (and value (guard (functionp value)))))
>
> The value doesn't have to be `functionp` (it is in the case of
> gv-expander, but it depends on the property).

Right.  I got a bit turned around with the quoting levels.  And given
the error above, I'm still not sure I have it worked out correctly.

>> +     (let ((fplist (assq fun byte-compile-plist-environment)))
>> +       (if fplist
>> +           (setcdr fplist (plist-put (cdr fplist) prop value))
>> +         (push (cons fun (list prop value))
>> +               byte-compile-plist-environment)))))
>
> I'd just unconditionally use `push`:
>
>          (push (cons fun `(,prop ,value . ,fplist))
>                byte-compile-plist-environment)))))

Yeah, that is simpler.