aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRoss Smith II <ross@smithii.com>2023-05-03 10:51:24 +0200
committerJakob Borg <jakob@kastelo.net>2023-05-09 10:01:57 +0000
commit3adfe2f91f6c3e170f70d04c76b6bcbcee31db26 (patch)
treeb27fd1098da1b69ff5778c2605829516e212e106
parent1103a27337ba97ba17e7ec77bd002fb4061c5d24 (diff)
downloadsyncthing-3adfe2f91f6c3e170f70d04c76b6bcbcee31db26.tar.gz
syncthing-3adfe2f91f6c3e170f70d04c76b6bcbcee31db26.zip
lib/fs: Fix root path handling for Windows (fixes #8778)
Co-authored-by: Jakob Borg <jakob@kastelo.net>
-rw-r--r--lib/fs/basicfs.go12
-rw-r--r--lib/fs/basicfs_windows_test.go29
2 files changed, 30 insertions, 11 deletions
diff --git a/lib/fs/basicfs.go b/lib/fs/basicfs.go
index 8ae132592..51e598ed2 100644
--- a/lib/fs/basicfs.go
+++ b/lib/fs/basicfs.go
@@ -51,8 +51,10 @@ type BasicFilesystem struct {
groupCache *groupCache
}
-type userCache = valueCache[string, *user.User]
-type groupCache = valueCache[string, *user.Group]
+type (
+ userCache = valueCache[string, *user.User]
+ groupCache = valueCache[string, *user.Group]
+)
func newBasicFilesystem(root string, opts ...Option) *BasicFilesystem {
if root == "" {
@@ -62,11 +64,11 @@ func newBasicFilesystem(root string, opts ...Option) *BasicFilesystem {
// The reason it's done like this:
// C: -> C:\ -> C:\ (issue that this is trying to fix)
// C:\somedir -> C:\somedir\ -> C:\somedir
- // C:\somedir\ -> C:\somedir\\ -> C:\somedir
+ // C:\somedir\ -> C:\somedir\ -> C:\somedir
// This way in the tests, we get away without OS specific separators
// in the test configs.
sep := string(filepath.Separator)
- root = filepath.Dir(root + sep)
+ root = filepath.Clean(filepath.Dir(root + sep))
// Attempt tilde expansion; leave unchanged in case of error
if path, err := ExpandTilde(root); err == nil {
@@ -215,7 +217,7 @@ func (f *BasicFilesystem) DirNames(name string) ([]string, error) {
if err != nil {
return nil, err
}
- fd, err := os.OpenFile(name, OptReadOnly, 0777)
+ fd, err := os.OpenFile(name, OptReadOnly, 0o777)
if err != nil {
return nil, err
}
diff --git a/lib/fs/basicfs_windows_test.go b/lib/fs/basicfs_windows_test.go
index 5526dd220..d3ead2421 100644
--- a/lib/fs/basicfs_windows_test.go
+++ b/lib/fs/basicfs_windows_test.go
@@ -12,29 +12,46 @@ package fs
import (
"os"
"path/filepath"
+ "runtime"
"strings"
"syscall"
"testing"
)
func TestWindowsPaths(t *testing.T) {
- testCases := []struct {
+ type testCase struct {
input string
expectedRoot string
expectedURI string
- }{
+ }
+ testCases := []testCase{
+ {`e:`, `\\?\e:\`, `e:\`},
{`e:\`, `\\?\e:\`, `e:\`},
+ {`e:\\`, `\\?\e:\`, `e:\`},
+ {`\\?\e:`, `\\?\e:\`, `e:\`},
{`\\?\e:\`, `\\?\e:\`, `e:\`},
+ {`\\?\e:\\`, `\\?\e:\`, `e:\`},
+ {`e:\x`, `\\?\e:\x`, `e:\x`},
+ {`e:\x\`, `\\?\e:\x`, `e:\x`},
+ {`e:\x\\`, `\\?\e:\x`, `e:\x`},
{`\\192.0.2.22\network\share`, `\\192.0.2.22\network\share`, `\\192.0.2.22\network\share`},
}
- for _, testCase := range testCases {
+ if runtime.Version() >= "go1.20" {
+ testCases = append(testCases,
+ testCase{`\\.\e:`, `\\.\e:\`, `e:\`},
+ testCase{`\\.\e:\`, `\\.\e:\`, `e:\`},
+ testCase{`\\.\e:\\`, `\\.\e:\`, `e:\`},
+ )
+ }
+
+ for i, testCase := range testCases {
fs := newBasicFilesystem(testCase.input)
if fs.root != testCase.expectedRoot {
- t.Errorf("root %q != %q", fs.root, testCase.expectedRoot)
+ t.Errorf("test %d: root: expected `%s`, got `%s`", i, testCase.expectedRoot, fs.root)
}
if fs.URI() != testCase.expectedURI {
- t.Errorf("uri %q != %q", fs.URI(), testCase.expectedURI)
+ t.Errorf("test %d: uri: expected `%s`, got `%s`", i, testCase.expectedURI, fs.URI())
}
}
@@ -195,7 +212,7 @@ func TestGetFinalPath(t *testing.T) {
}
func TestRemoveWindowsDirIcon(t *testing.T) {
- //Try to delete a folder with a custom icon with os.Remove (simulated by the readonly file attribute)
+ // Try to delete a folder with a custom icon with os.Remove (simulated by the readonly file attribute)
fs, dir := setup(t)
relativePath := "folder_with_icon"