Subject: Re: bug#13149: 24.3.50;Emacs thinks file was changed outside Emacs, but it was not

From: Paul Eggert <[email-masked]>
Date: Fri, 01 Feb 2013 13:05:38 -0800

I stared at the code a bit and found an unlikely bug
that would cause the reported symptoms.  The bug occurs if the
first write-region to a buggy file system happens to be
an append that appends nothing.  If this occurs, Emacs
incorrectly concludes that the file system is not buggy,
and later uses of write-region to that file system (assuming
no other non-buggy file systems are used in the meantime)
will behave in the bad way that Drew reported.

I installed a fix for this bug as trunk bzr 111656.
I'd be surprised if this fixes Drew's bug though.

Eli, does MS-Windows conform to POSIX by updating st_mtime when
Emacs creates a file (open with O_CREAT on a file that didn't
previous exist) or truncates a file (open with O_TRUNC
on a file that previously existed)?
For example, if Emacs uses O_TRUNC on a file that is already
empty, does MS-Windows update the file's time
stamp even though the file has not changed?  If not,
that might explain the bug as well.

Drew, can you please try using the following hacky patch
for a while, and report what's in your *Messages* buffer
if you see the problem again?

=== modified file 'src/fileio.c'
--- src/fileio.c	2013-02-01 20:51:12 +0000
+++ src/fileio.c	2013-02-01 21:03:11 +0000
@@ -5051,6 +5051,23 @@ This calls `write-region-annotate-functi
 		  st.st_size = st1.st_size;
 		  modtime = modtime1;
 		}
+
+	      {
+		char format[sizeof "write-region ? .000000000 .000000000: %s"
+			    + 2 * INT_STRLEN_BOUND (long)];
+		if (valid_timestamp_file_system
+		    && st.st_dev == timestamp_file_system)
+		  sprintf (format, "write-region = %ld.%09d: %%s",
+			   (long) EMACS_SECS (modtime),
+			   (int) EMACS_NSECS (modtime));
+		else
+		  sprintf (format, "write-region ? %ld.%09d %ld.%09d: %%s",
+			   (long) EMACS_SECS (modtime),
+			   (int) EMACS_NSECS (modtime),
+			   (long) EMACS_SECS (modtime1),
+			   (int) EMACS_NSECS (modtime1));
+		add_to_log (format, filename, Qnil);
+	      }
 	    }
 	  emacs_close (desc1);
 	}