The Dired command ! (
dired-do-shell-command) reads a
shell command string in the minibuffer, and runs that shell command on
one or more files. The files that the shell command operates on are
determined in the usual way for Dired commands (see Operating on Files). The command X is a synonym for !.
The command & (
dired-do-async-shell-command) does the
same, except that it runs the shell command asynchronously. (You can
also do this with !, by appending a ‘&’ character to the
end of the shell command.) When the command operates on more than one
file, it runs multiple parallel copies of the specified shell command,
one for each file. As an exception, if the specified shell command
ends in ‘;’ or ‘;&’, the shell command is run in the
background on each file sequentially; Emacs waits for each invoked
shell command to terminate before running the next one.
For both ! and &, the working directory for the shell command is the top-level directory of the Dired buffer.
If you tell ! or & to operate on more than one file, the shell command string determines how those files are passed to the shell command:
Thus, ! tar cf foo.tar * RET runs
tar on the entire
list of file names, putting them into one tar file foo.tar.
If you want to use ‘*’ as a shell wildcard with whitespace around it, write ‘*""’. In the shell, this is equivalent to ‘*’; but since the ‘*’ is not surrounded by whitespace, Dired does not treat it specially.
uudecodeon each file.
To iterate over the file names in a more complicated fashion, use an explicit shell loop. For example, here is how to uuencode each file, making the output file name by appending ‘.uu’ to the input file name:
for file in * ; do uuencode "$file" "$file" >"$file".uu; done
The ! and & commands do not attempt to update the Dired buffer to show new or modified files, because they don’t know what files will be changed. Use the g command to update the Dired buffer (see Dired Updating).
See Single Shell, for information about running shell commands outside Dired.