I have had (global-set-key [f9] 'compile) in my Emacs init file for many years. With this setup, hitting [f9] and doing M-x compile RET should run the same commands the same way, right?

But today I was having trouble with a Bash script. I ran it, as usual, by hitting [f9], but got a mysterious error. After several vain attempts to find a bug in my script, I suddenly discovered that when I execute it with M-x compile instead, it succeeds, and that it also succeeds when run on a VT or gnome-terminal. So it turns out — to my big surprise — that running compile via a shortcut key or via M-x do not always do the same thing.

( Minimal working example (saved as /tmp/ledger-test; the drewr3.dat file was copied from Ledger's GIT source):

#! /bin/bash
# run ledger under env -i, to leave no room for possible differences in environment:
env -i TERM=ansi ledger --no-color -f $ledgerfile balance

When I set compile-command to "bash /tmp/ledger-test" and run the script via M-x compile, it runs normally. But when I run it by hitting [f9] , it fails:

While evaluating value expression:
  ansify_if(justify(scrub(display_total), 20, (20 + int(prepend_width)), true, color), (should_bold ? (bold : null)))
While calling function 'int ':
While calling function 'justify ($ -3,804.00, <#EXPR {20}>, <#EXPR ({20} + int(prepend_width))>, 1, 0)':
While calling function 'ansify_if (<#EXPR justify(scrub(display_total), {20}, ({20} + int(prepend_width)), true, color)>, )':
Error: bad lexical cast: source type value could not be interpreted as target


What's going on, and how to make [f9] work identically with M-x compile?

I am running Emacs 28.1 on Arch Linux. (Running Emacs with -Q does not help.)

P.S. I tried to work around the trouble by creating a keyboard macro that runs compile, and binding it to [f9]:

M-x global-unset-key RET [f9]
C-x ( M-x compile RET C-x ) 
M-x name-last-keyboard-macro RET my-compile RET
M-x global-set-key RET [f9] my-compile RET

But this did not help: when I hit [f9] now, I get the same error again.

  • What does C-h k <f9> in that buffer report?
    – phils
    May 26, 2022 at 10:17
  • @phils First line: "<f9> runs the command compile (found in global-map), which is an autoloaded interactive compiled Lisp function in ‘compile.el’." This is followed by bindings for compile (including <f9>), signature of the compile function and its docstring.
    – toomas
    May 26, 2022 at 10:39
  • Ok; that was my one and only idea (that <f9> unexpectedly had a different binding). I also think it should be the same as M-x compile in this case. That the method of invocation would somehow vary the outcome of running the script is bizarre, but I would suggest you focus on debugging the script failure as a way to glean some insight into what the actual difference was, and then see if you can relate that back to Emacs somehow.
    – phils
    May 26, 2022 at 10:50
  • I can't reproduce it: I bound compile to C-c z - <f9> is in use already in my case - and do M-x compile RET bash /tmp/foo.sh and C-c z RET which has the bash /tmp/foo.sh command defaulted. I get identical output in both cases: a *compilation* buffer with more or less the same output as executing the script from the command line (more or less because the TERM=ansi setting makes ledger produce ansi escape codes in the output which are not interpreted when sent to the *compilation* buffer). Setting compile-command to bash /tmp/foo.sh works in exactly the same way.
    – NickD
    May 26, 2022 at 19:53


Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Browse other questions tagged or ask your own question.