Having a bash with bash

Let’s say we want to write a command that allows you to take the output of the previous command and stick it in your editor so you can page through it, save it, email it, etc.

One way to do it is with bash’s “process substitution” feature. Try this:

$ ls -l
$ cat <($(tail -1 $HISTFILE)) | vim -

One problem with this is it won’t work if you change “vim” to “emacs”, because Emacs doesn’t like to read stdin. I tried all kinds of stuff including “emacs -nw -t /dev/tty /dev/stdin” and such.

Well, here’s an even more general solution:

with-temp-file ()
{
    local _prefix=$1; shift
    local _tmpfile_var=$1 ; shift
    local ${_tmpfile_var}=$(mktemp -t ${_prefix})
    eval local _tmpfile_value=\${$_tmpfile_var}
    eval "$@"
    rm ${_tmpfile_value}
}

edlo ()
{
    with-temp-file "edlo" tmpfile \
        '$(tail -1 $HISTFILE) > $tmpfile && $EDITOR $tmpfile'
}

Actually for bash versions 2 and up, it turns out we can clean this up a tad using the new syntax for indirect references to variables:

--- edlo.sh.2006-04-29-152010   Sat Apr 29 15:19:53 2006
+++ edlo.sh     Sat Apr 29 15:25:11 2006
@@ -3,7 +3,7 @@
     local _prefix=$1; shift
     local _tmpfile_var=$1 ; shift
     local ${_tmpfile_var}=$(mktemp -t ${_prefix})
-    eval local _tmpfile_value=\${$_tmpfile_var}
+    local _tmpfile_value=${!_tmpfile_var}
     eval "$@"
     rm ${_tmpfile_value}
 }

This should work in any editor, including X11 editors since we’re not using stdin. And the with-temp-file function is a general utility function that could be used for other stuff. Here’s another function that uses it:

eoo () 
{ 
    local _cmd="$@";
    with-temp-file "eoo" tmpfile '$_cmd > $tmpfile && $EDITOR $tmpfile'
}

This one is when you already know that you want to capture the output of a particular command – e.g.:

$ eoo ls -l
$ eoo finger

Enjoy.

Unix Power Tools, Third Edition

Emacs functions for toggling between “.” and “->” in C code

The first function simply toggles the characters at the point between “.” and “->”. Not terribly useful.

The second function is a little more interesting. You can put the point by a struct-type variable which is or isn’t a pointer and this function will toggle both the “*” and all of the “.”s and “->”s in the function.

Continue reading

Emacs 22 reference card

There are lots of Emacs reference cards out there online, but I couldn’t manage to find one for Emacs 22 (the latest development version) in a couple of minutes of web searching so I generated one from the TeX source file that comes with Emacs:

emacs_22_reference_card

Emacs 22 reference card (PDF)

Here’s how I generated it on my Mac with teTeX, Ghostscript, and Emacs 22 installed from Fink:

tex /sw/share/emacs/22.0.50/etc/refcard.tex 
dvips -t letter -t landscape -o refcard.ps refcard.dvi
ps2pdf refcard.ps

Update 2006-04-11

For people who had trouble opening the PDF in Adobe Acrobat, try this PDF and let me know if it works. I used ps2pdf14 to generate it, which spits out a newer version of the PDF standard, which perhaps Acrobat can deal with better. I also uploaded a PostScript file and a DVI file, in case one of those works better for people. If you try them, please leave a comment below and at reddit.

Learning GNU Emacs, Third Edition