I managed to add two more sections to my article on writing
robust shell scripts including using trap and making more atomic
changes. Had some useful feedback including making the fact that a few
small tweaks made it apply to more than just bash. Following from that
I’ve added an article about changing your bash
prompt and how mine has
been built up over the years to something useful to me. Hopefully it’ll
give other people some ideas.
on said:
maybe you like:
http://ngolde.de/farben2.sh
on said:
This:
| if [ ! -e $lockfile ]; then
| trap “rm -f $lockfile; exit” INT TERM EXIT
| touch $lockfile
| critical-section
| rm $lockfile
| trap – INT TERM EXIT
| else
| echo “critical-section is already running”
| fi
is not atomic. Between the test whether $lockfile exists, and its touching is a race.
You could avoid that by hard-linking to a file. Making sure the source file for the hard linke is on the same volume/partition and exists, while also providing some method to clean it up is not totally trivial.
Provided you use a POSIX shell, you could turn off globbing with `set -C’. The test to enter the critical section could just be trying to redirect into the file then, e.g.,
set -C
if echo lock >”$lockfile”; then
echo “yes, I have it”
else
echo “no”
fi
Whether you should then trigger the trap inside the “yes” part or before the echo depends on your desired semantics (whether the lock ever lives outside of running your script). In the former case you can’t avoid the race that hitting ^C at the right time will still leave you with a stray lockfile hanging around.
Cheers,
Ralf
on said:
the “bash -u” trick doesn’t seem to work very well on my distro.
$ echo #!/bin/bash -u > foo
$ chmod +x foo
$ ./foo
/bin/bash: line 55: PS1: unbound variable
$
on said:
beebo david% echo #!/bin/bash -u > foo
beebo david% chmod +x foo
beebo david% ./foo
beebo david%
I’d suggest that your distribution has a screwed /etc/profile or /etc/bash.bashrc file. What distribution are you using? You might be able to test what is going on by running bash -x -v -u and if that doesn’t help you, then using strace will tell you what files the shell is opening.