On 25/05/11 14:46, Simon Kelley wrote: > cp file file.new > mv file.new file > > has the desired effect and atomically changes the mtime without a race > window where the contents of file may be invalid.
The current code (i.e., in my first patch) doesn't suffer from a race because it acts upon a temporary file before the latter is mv'ed (atomically) to the active name. I was thinking about this issue last night and had the idea of just checking the time before writing the temporary file. This could be done with "date", I realize, but can also be done with bash's printf, as in the attached patch, which is a bit shorter than the previous one. -- Thomas
--- dnsmasq_ORIG 2011-02-20 03:21:14.000000000 +0100 +++ dnsmasq 2011-05-25 15:26:06.146862344 +0200 @@ -1,4 +1,4 @@ -#!/bin/sh +#!/bin/bash # # Script to update the resolver list for dnsmasq # @@ -8,12 +8,10 @@ # # Assumption: On entry, PWD contains the resolv.conf-type files # -# Depends: resolvconf (>= 1.14) +# Requires bash because it uses a non-POSIX printf extension. # # Licensed under the GNU GPL. See /usr/share/common-licenses/GPL. # -# History -# June 2003 - June 2004: Written by Thomas Hood <jdth...@yahoo.co.uk> set -e @@ -55,16 +53,18 @@ NMSRVRS="$RSLT" fi +# Dnsmasq uses the mtime of $RSLVRLIST_FILE, with a resolution of one second, +# to detect changes in the file. This means that if a resolvconf update occurs +# within one second of the previous one then dnsmasq may fail to notice the +# more recent change. To work around this problem we sleep here to ensure +# that the new mtime is different. +if [ -f "$RSLVRLIST_FILE" ] && [ "$(ls -go --time-style='+%s' "$RSLVRLIST_FILE" | { read p h s t n ; echo "$t" ; })" = "$(printf '%(%s)T' "-1")" ] ; then + sleep 1 +fi + clean_up() { rm -f "$TMP_FILE" ; } trap clean_up EXIT : >| "$TMP_FILE" for N in $NMSRVRS ; do echo "nameserver $N" >> "$TMP_FILE" ; done mv -f "$TMP_FILE" "$RSLVRLIST_FILE" -# dnsmasq uses the mtime of the file to detect changes. This has a resolution of one second, -# so it's possible that if two or more changes occur rapidly, the second change could -# be missed. We avoid this possibility by delaying here. -sleep 1 - - -