Further avoid exposing zero timestamps.

Change-Id: If37266ea10586a97eaf519b0f4468633bfce8ce3
diff --git a/fs/gitilesfs.go b/fs/gitilesfs.go
index 32b4fcb..809f0a0 100644
--- a/fs/gitilesfs.go
+++ b/fs/gitilesfs.go
@@ -70,6 +70,10 @@
 func (n *linkNode) GetAttr(out *fuse.Attr, file nodefs.File, context *fuse.Context) (code fuse.Status) {
 	out.Size = uint64(len(n.linkTarget))
 	out.Mode = fuse.S_IFLNK
+
+	t := time.Unix(1, 0)
+	out.SetTimes(nil, &t, nil)
+
 	return fuse.OK
 }
 
@@ -223,6 +227,9 @@
 func (n *dataNode) GetAttr(out *fuse.Attr, file nodefs.File, context *fuse.Context) (code fuse.Status) {
 	out.Size = uint64(len(n.data))
 	out.Mode = fuse.S_IFREG | 0644
+	t := time.Unix(1, 0)
+	out.SetTimes(nil, &t, nil)
+
 	return fuse.OK
 }
 
@@ -243,7 +250,7 @@
 // NewGitilesRoot returns the root node for a file system.
 func NewGitilesRoot(c *cache.Cache, tree *gitiles.Tree, service *gitiles.RepoService, options GitilesOptions) nodefs.Node {
 	r := &gitilesRoot{
-		Node:      nodefs.NewDefaultNode(),
+		Node:      newDirNode(),
 		service:   service,
 		nodeCache: newNodeCache(),
 		cache:     c,
@@ -272,6 +279,21 @@
 	}
 }
 
+type dirNode struct {
+	nodefs.Node
+}
+
+func (n *dirNode) GetAttr(out *fuse.Attr, file nodefs.File, context *fuse.Context) (code fuse.Status) {
+	out.Mode = fuse.S_IFDIR | 0755
+	t := time.Unix(1, 0)
+	out.SetTimes(nil, &t, nil)
+	return fuse.OK
+}
+
+func newDirNode() nodefs.Node {
+	return &dirNode{nodefs.NewDefaultNode()}
+}
+
 func (r *gitilesRoot) onMount(fsConn *nodefs.FileSystemConnector) error {
 	for _, e := range r.tree.Entries {
 		if e.Type == "commit" {
@@ -287,7 +309,7 @@
 
 		parent, left := fsConn.Node(r.Inode(), dir)
 		for _, l := range left {
-			ch := parent.NewChild(l, true, nodefs.NewDefaultNode())
+			ch := parent.NewChild(l, true, newDirNode())
 			parent = ch
 		}
 		id, err := git.NewOid(e.ID)
diff --git a/fs/gitilesfs_test.go b/fs/gitilesfs_test.go
index 714c37c..42bcef7 100644
--- a/fs/gitilesfs_test.go
+++ b/fs/gitilesfs_test.go
@@ -25,6 +25,7 @@
 	"path/filepath"
 	"reflect"
 	"regexp"
+	"sort"
 	"strings"
 	"syscall"
 	"testing"
@@ -386,7 +387,30 @@
 	}
 }
 
-func TestManifestFS(t *testing.T) {
+func TestManifestFSTimestamps(t *testing.T) {
+	fix, err := newManifestTestFixture(testManifest)
+	if err != nil {
+		t.Fatal("newTestFixture", err)
+	}
+	defer fix.cleanup()
+
+	var zeroFiles []string
+	if err := filepath.Walk(fix.mntDir, func(n string, fi os.FileInfo, err error) error {
+		if fi != nil && fi.ModTime().UnixNano() == 0 {
+			r, _ := filepath.Rel(fix.mntDir, n)
+			zeroFiles = append(zeroFiles, r)
+		}
+		return nil
+	}); err != nil {
+		t.Fatalf("Walk: %v", err)
+	}
+	if len(zeroFiles) > 0 {
+		sort.Strings(zeroFiles)
+		t.Errorf("found files with zero timestamps: %v", zeroFiles)
+	}
+}
+
+func TestManifestFSBasic(t *testing.T) {
 	fix, err := newManifestTestFixture(testManifest)
 	if err != nil {
 		t.Fatal("newTestFixture", err)
diff --git a/fs/manifestfs.go b/fs/manifestfs.go
index ec5d973..fe57340 100644
--- a/fs/manifestfs.go
+++ b/fs/manifestfs.go
@@ -58,7 +58,7 @@
 		return nil, err
 	}
 	root := &manifestFSRoot{
-		Node:        nodefs.NewDefaultNode(),
+		Node:        newDirNode(),
 		nodeCache:   newNodeCache(),
 		cache:       cache,
 		service:     service,
@@ -121,7 +121,7 @@
 			dir, base := filepath.Split(p)
 			parent, left := fsConn.Node(fs.Inode(), dir)
 			for _, c := range left {
-				ch := parent.NewChild(c, true, nodefs.NewDefaultNode())
+				ch := parent.NewChild(c, true, newDirNode())
 				parent = ch
 			}