Browse Source

lib/fs: Try EvalSymlinks without '\\?\' prefix on failure (fixes #5226) (#5227)

Simon Frei 7 years ago
parent
commit
03d0f0dc34
4 changed files with 17 additions and 6 deletions
  1. 3 0
      lib/fs/basicfs_unix.go
  2. 1 5
      lib/fs/basicfs_watch.go
  3. 1 1
      lib/fs/basicfs_watch_test.go
  4. 12 0
      lib/fs/basicfs_windows.go

+ 3 - 0
lib/fs/basicfs_unix.go

@@ -11,6 +11,7 @@ package fs
 import (
 	"fmt"
 	"os"
+	"path/filepath"
 	"strings"
 )
 
@@ -73,3 +74,5 @@ func (f *BasicFilesystem) unrootedChecked(absPath, root string) string {
 func rel(path, prefix string) string {
 	return strings.TrimPrefix(strings.TrimPrefix(path, prefix), string(PathSeparator))
 }
+
+var evalSymlinks = filepath.EvalSymlinks

+ 1 - 5
lib/fs/basicfs_watch.go

@@ -12,7 +12,6 @@ import (
 	"context"
 	"errors"
 	"path/filepath"
-	"runtime"
 
 	"github.com/syncthing/notify"
 )
@@ -23,13 +22,10 @@ import (
 var backendBuffer = 500
 
 func (f *BasicFilesystem) Watch(name string, ignore Matcher, ctx context.Context, ignorePerms bool) (<-chan Event, error) {
-	evalRoot, err := filepath.EvalSymlinks(f.root)
+	evalRoot, err := evalSymlinks(f.root)
 	if err != nil {
 		return nil, err
 	}
-	if runtime.GOOS == "windows" {
-		evalRoot = longFilenameSupport(evalRoot)
-	}
 
 	absName, err := rooted(name, evalRoot)
 	if err != nil {

+ 1 - 1
lib/fs/basicfs_watch_test.go

@@ -34,7 +34,7 @@ func TestMain(m *testing.M) {
 		panic("Cannot get absolute path to working dir")
 	}
 
-	dir, err = filepath.EvalSymlinks(dir)
+	dir, err = evalSymlinks(dir)
 	if err != nil {
 		panic("Cannot get real path to working dir")
 	}

+ 12 - 0
lib/fs/basicfs_windows.go

@@ -210,3 +210,15 @@ func isMaybeWin83(absPath string) bool {
 	}
 	return strings.Contains(strings.TrimPrefix(filepath.Base(absPath), WindowsTempPrefix), "~")
 }
+
+func evalSymlinks(in string) (string, error) {
+	out, err := filepath.EvalSymlinks(in)
+	if err != nil && strings.HasPrefix(in, `\\?\`) {
+		// Try again without the `\\?\` prefix
+		out, err = filepath.EvalSymlinks(in[4:])
+	}
+	if err != nil {
+		return "", err
+	}
+	return longFilenameSupport(out), nil
+}