John Kitchin
John Kitchin

Reputation: 2433

How do I avoid eager macro expansion failures in emacs macros?

I defined this macro:

(defmacro with-current-directory (directory &rest body)
  "Set the working directory temporarily set to DIRECTORY and run BODY.
DIRECTORY is expanded"
  `(let ((default-directory
          ,(file-name-as-directory
            (expand-file-name (eval directory)))))
     ,@body))

which I use in some lisp functions that are loaded when emacs opens. I always get these warnings:

Eager macro-expansion failure: (void-variable repo-dir)
Eager macro-expansion failure: (wrong-type-argument stringp nil)

Which I understand is happening because those variables are not defined at load time, and emacs is trying to eval them. My question is, how do I avoid getting these warnings. Is there a way to define the macro so that doesn't happen? I cannot figure out how to use the value of the variable, and not the symbol for the variable itself.

Upvotes: 6

Views: 6305

Answers (2)

legoscia
legoscia

Reputation: 41568

Like this:

`(let ((default-directory
        (file-name-as-directory (expand-file-name ,directory))))

Since directory is not the value, but the lisp expression that would evaluate to the value, you need to insert (using the comma operator) the expression into the expansion of the macro. If you put the comma before the call to file-name-as-directory, you would have to be able to compute the directory at macro expansion time based only on the tokens of the expression, which you can't do if directory refers to a variable name.

Upvotes: 7

Jordon Biondo
Jordon Biondo

Reputation: 4029

Looks like some beat me to it. Look at the other answer.

You should not be evaluating the file name expansion at expansion time. Also the eval call should not be there. The only thing that should happen during macro expansion is placing the value of directory inside the returned expression. Remove eval and place your comma in front of directory.

It's nice to know that anytime you're using eval, you're probably doing something wrong

Upvotes: 1

Related Questions