From 8c6ff1fa7e4ef2fd5277859f22fecaf684567a85 Mon Sep 17 00:00:00 2001 From: Nick Craig-Wood Date: Wed, 11 Jan 2023 16:23:40 +0000 Subject: [PATCH] cmount: fix creating and renaming files on case insensitive backends Before this fix, we told cgofuse/WinFSP that the backend was case insensitive but didn't implement the Getpath backend function to return the normalised case of a file. Resently cgofuse started implementing case insensitive files properly but since we hadn't implemented Getpath, the file names were taking the default of all in UPPER CASE. This patch implements Getpath for cgofuse which fixes the case problems. This problem came to light when we upgraded cgofuse and WinFSP (to 1.12) which had the code to implement Getpath. Fixes #6682 --- cmd/cmount/fs.go | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/cmd/cmount/fs.go b/cmd/cmount/fs.go index c097611b7..a60bd8336 100644 --- a/cmd/cmount/fs.go +++ b/cmd/cmount/fs.go @@ -8,6 +8,7 @@ import ( "io" "os" "path" + "strings" "sync" "sync/atomic" "time" @@ -567,6 +568,21 @@ func (fsys *FS) Listxattr(path string, fill func(name string) bool) (errc int) { return -fuse.ENOSYS } +// Getpath allows a case-insensitive file system to report the correct case of +// a file path. +func (fsys *FS) Getpath(path string, fh uint64) (errc int, normalisedPath string) { + defer log.Trace(path, "Getpath fh=%d", fh)("errc=%d, normalisedPath=%q", &errc, &normalisedPath) + node, _, errc := fsys.getNode(path, fh) + if errc != 0 { + return errc, "" + } + normalisedPath = node.Path() + if !strings.HasPrefix("/", normalisedPath) { + normalisedPath = "/" + normalisedPath + } + return 0, normalisedPath +} + // Translate errors from mountlib func translateError(err error) (errc int) { if err == nil { @@ -631,6 +647,7 @@ func translateOpenFlags(inFlags int) (outFlags int) { var ( _ fuse.FileSystemInterface = (*FS)(nil) _ fuse.FileSystemOpenEx = (*FS)(nil) + _ fuse.FileSystemGetpath = (*FS)(nil) //_ fuse.FileSystemChflags = (*FS)(nil) //_ fuse.FileSystemSetcrtime = (*FS)(nil) //_ fuse.FileSystemSetchgtime = (*FS)(nil)