diff --git a/lib/fs/filesystem.go b/lib/fs/filesystem.go index a727e2239..d46e957ba 100644 --- a/lib/fs/filesystem.go +++ b/lib/fs/filesystem.go @@ -261,6 +261,11 @@ func NewFilesystem(fsType FilesystemType, uri string, opts ...Option) Filesystem } } + // Case handling is the innermost, as any filesystem calls by wrappers should be case-resolved + if caseOpt != nil { + fs = caseOpt.apply(fs) + } + // mtime handling should happen inside walking, as filesystem calls while // walking should be mtime-resolved too if mtimeOpt != nil { @@ -269,35 +274,15 @@ func NewFilesystem(fsType FilesystemType, uri string, opts ...Option) Filesystem fs = &metricsFS{next: fs} - layersAboveWalkFilesystem := 0 - if caseOpt != nil { - // DirNames calls made to check the case of a name will also be - // attributed to the calling function. - layersAboveWalkFilesystem++ - } if l.ShouldDebug("walkfs") { - // A walkFilesystem is not a layer to skip, it embeds the underlying - // filesystem, passing calls directly trough. Except for calls made - // during walking, however those are truly originating in the walk - // filesystem. - fs = NewWalkFilesystem(newLogFilesystem(fs, layersAboveWalkFilesystem)) - } else if l.ShouldDebug("fs") { - fs = newLogFilesystem(NewWalkFilesystem(fs), layersAboveWalkFilesystem) - } else { - fs = NewWalkFilesystem(fs) + return NewWalkFilesystem(&logFilesystem{fs}) } - // Case handling is at the outermost layer to resolve all input names. - // Reason being is that the only names/paths that are potentially "wrong" - // come from outside the fs package. Any paths that result from filesystem - // operations itself already have the correct case. Thus there's e.g. no - // point to check the case on all the stating the walk filesystem does, it - // just adds overhead. - if caseOpt != nil { - fs = caseOpt.apply(fs) + if l.ShouldDebug("fs") { + return &logFilesystem{NewWalkFilesystem(fs)} } - return fs + return NewWalkFilesystem(fs) } // IsInternal returns true if the file, as a path relative to the folder diff --git a/lib/fs/logfs.go b/lib/fs/logfs.go index bb90d797f..38b95e0f6 100644 --- a/lib/fs/logfs.go +++ b/lib/fs/logfs.go @@ -16,20 +16,10 @@ import ( type logFilesystem struct { Filesystem - // Number of filesystem layers on top of logFilesystem to skip when looking - // for the true caller of the filesystem - layers int } -func newLogFilesystem(fs Filesystem, layers int) *logFilesystem { - return &logFilesystem{ - Filesystem: fs, - layers: layers, - } -} - -func (fs *logFilesystem) getCaller() string { - _, file, line, ok := runtime.Caller(fs.layers + 1) +func getCaller() string { + _, file, line, ok := runtime.Caller(2) if !ok { return "unknown" } @@ -38,139 +28,139 @@ func (fs *logFilesystem) getCaller() string { func (fs *logFilesystem) Chmod(name string, mode FileMode) error { err := fs.Filesystem.Chmod(name, mode) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Chmod", name, mode, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Chmod", name, mode, err) return err } func (fs *logFilesystem) Chtimes(name string, atime time.Time, mtime time.Time) error { err := fs.Filesystem.Chtimes(name, atime, mtime) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Chtimes", name, atime, mtime, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Chtimes", name, atime, mtime, err) return err } func (fs *logFilesystem) Create(name string) (File, error) { file, err := fs.Filesystem.Create(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Create", name, file, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Create", name, file, err) return file, err } func (fs *logFilesystem) CreateSymlink(target, name string) error { err := fs.Filesystem.CreateSymlink(target, name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "CreateSymlink", target, name, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "CreateSymlink", target, name, err) return err } func (fs *logFilesystem) DirNames(name string) ([]string, error) { names, err := fs.Filesystem.DirNames(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "DirNames", name, names, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "DirNames", name, names, err) return names, err } func (fs *logFilesystem) Lstat(name string) (FileInfo, error) { info, err := fs.Filesystem.Lstat(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Lstat", name, info, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Lstat", name, info, err) return info, err } func (fs *logFilesystem) Mkdir(name string, perm FileMode) error { err := fs.Filesystem.Mkdir(name, perm) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Mkdir", name, perm, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Mkdir", name, perm, err) return err } func (fs *logFilesystem) MkdirAll(name string, perm FileMode) error { err := fs.Filesystem.MkdirAll(name, perm) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "MkdirAll", name, perm, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "MkdirAll", name, perm, err) return err } func (fs *logFilesystem) Open(name string) (File, error) { file, err := fs.Filesystem.Open(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Open", name, file, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Open", name, file, err) return file, err } func (fs *logFilesystem) OpenFile(name string, flags int, mode FileMode) (File, error) { file, err := fs.Filesystem.OpenFile(name, flags, mode) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "OpenFile", name, flags, mode, file, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "OpenFile", name, flags, mode, file, err) return file, err } func (fs *logFilesystem) ReadSymlink(name string) (string, error) { target, err := fs.Filesystem.ReadSymlink(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "ReadSymlink", name, target, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "ReadSymlink", name, target, err) return target, err } func (fs *logFilesystem) Remove(name string) error { err := fs.Filesystem.Remove(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Remove", name, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Remove", name, err) return err } func (fs *logFilesystem) RemoveAll(name string) error { err := fs.Filesystem.RemoveAll(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "RemoveAll", name, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "RemoveAll", name, err) return err } func (fs *logFilesystem) Rename(oldname, newname string) error { err := fs.Filesystem.Rename(oldname, newname) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Rename", oldname, newname, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Rename", oldname, newname, err) return err } func (fs *logFilesystem) Stat(name string) (FileInfo, error) { info, err := fs.Filesystem.Stat(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Stat", name, info, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Stat", name, info, err) return info, err } func (fs *logFilesystem) SymlinksSupported() bool { supported := fs.Filesystem.SymlinksSupported() - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "SymlinksSupported", supported) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "SymlinksSupported", supported) return supported } func (fs *logFilesystem) Walk(root string, walkFn WalkFunc) error { err := fs.Filesystem.Walk(root, walkFn) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Walk", root, walkFn, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Walk", root, walkFn, err) return err } func (fs *logFilesystem) Watch(path string, ignore Matcher, ctx context.Context, ignorePerms bool) (<-chan Event, <-chan error, error) { evChan, errChan, err := fs.Filesystem.Watch(path, ignore, ctx, ignorePerms) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Watch", path, ignore, ignorePerms, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Watch", path, ignore, ignorePerms, err) return evChan, errChan, err } func (fs *logFilesystem) Unhide(name string) error { err := fs.Filesystem.Unhide(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Unhide", name, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Unhide", name, err) return err } func (fs *logFilesystem) Hide(name string) error { err := fs.Filesystem.Hide(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Hide", name, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Hide", name, err) return err } func (fs *logFilesystem) Glob(name string) ([]string, error) { names, err := fs.Filesystem.Glob(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Glob", name, names, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Glob", name, names, err) return names, err } func (fs *logFilesystem) Roots() ([]string, error) { roots, err := fs.Filesystem.Roots() - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Roots", roots, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Roots", roots, err) return roots, err } func (fs *logFilesystem) Usage(name string) (Usage, error) { usage, err := fs.Filesystem.Usage(name) - l.Debugln(fs.getCaller(), fs.Type(), fs.URI(), "Usage", name, usage, err) + l.Debugln(getCaller(), fs.Type(), fs.URI(), "Usage", name, usage, err) return usage, err }