lib/protocol, lib/model: Implement high precision time stamps (fixes #3305)

This adds a new nanoseconds field to the FileInfo, populates it during
scans and sets the non-truncated time in Chtimes calls.

The actual file modification time is defined as modified_s seconds +
modified_ns nanoseconds. It's expected that the modified_ns field is <=
1e9 (that is, all whole seconds should go in the modified_s field) but
not really enforced. Given that it's an int32 the timestamp can be
adjusted += ~2.9 seconds by the modified_ns field...

GitHub-Pull-Request: https://github.com/syncthing/syncthing/pull/3431
This commit is contained in:
Jakob Borg
2016-08-06 13:05:59 +00:00
committed by Audrius Butkevicius
parent 0655991a19
commit ea87bcefd6
21 changed files with 321 additions and 240 deletions

View File

@@ -310,7 +310,7 @@ func (w *walker) walkRegular(relPath string, info os.FileInfo, fchan chan protoc
// - has the same size as previously
cf, ok := w.CurrentFiler.CurrentFile(relPath)
permUnchanged := w.IgnorePerms || !cf.HasPermissionBits() || PermsEqual(cf.Permissions, curMode)
if ok && permUnchanged && !cf.IsDeleted() && cf.Modified == info.ModTime().Unix() && !cf.IsDirectory() &&
if ok && permUnchanged && !cf.IsDeleted() && cf.ModTime().Equal(info.ModTime()) && !cf.IsDirectory() &&
!cf.IsSymlink() && !cf.IsInvalid() && cf.Size == info.Size() {
return nil
}
@@ -323,7 +323,8 @@ func (w *walker) walkRegular(relPath string, info os.FileInfo, fchan chan protoc
Version: cf.Version.Update(w.ShortID),
Permissions: curMode & uint32(maskModePerm),
NoPermissions: w.IgnorePerms,
Modified: info.ModTime().Unix(),
ModifiedS: info.ModTime().Unix(),
ModifiedNs: int32(info.ModTime().Nanosecond()),
Size: info.Size(),
}
l.Debugln("to hash:", relPath, f)
@@ -357,7 +358,8 @@ func (w *walker) walkDir(relPath string, info os.FileInfo, dchan chan protocol.F
Version: cf.Version.Update(w.ShortID),
Permissions: uint32(info.Mode() & maskModePerm),
NoPermissions: w.IgnorePerms,
Modified: info.ModTime().Unix(),
ModifiedS: info.ModTime().Unix(),
ModifiedNs: int32(info.ModTime().Nanosecond()),
}
l.Debugln("dir:", relPath, f)
@@ -416,7 +418,6 @@ func (w *walker) walkSymlink(absPath, relPath string, dchan chan protocol.FileIn
Name: relPath,
Type: SymlinkType(targetType),
Version: cf.Version.Update(w.ShortID),
Modified: 0,
NoPermissions: true, // Symlinks don't have permissions of their own
Blocks: blocks,
}