github.com/ncw/rclone@v1.48.1-0.20190724201158-a35aa1360e3e/backend/cache/cache_mount_windows_test.go (about) 1 // +build windows 2 3 package cache_test 4 5 import ( 6 "fmt" 7 "os" 8 "testing" 9 "time" 10 11 "github.com/billziss-gh/cgofuse/fuse" 12 "github.com/ncw/rclone/cmd/cmount" 13 "github.com/ncw/rclone/cmd/mountlib" 14 "github.com/ncw/rclone/fs" 15 "github.com/pkg/errors" 16 "github.com/stretchr/testify/require" 17 ) 18 19 // waitFor runs fn() until it returns true or the timeout expires 20 func waitFor(fn func() bool) (ok bool) { 21 const totalWait = 10 * time.Second 22 const individualWait = 10 * time.Millisecond 23 for i := 0; i < int(totalWait/individualWait); i++ { 24 ok = fn() 25 if ok { 26 return ok 27 } 28 time.Sleep(individualWait) 29 } 30 return false 31 } 32 33 func (r *run) mountFs(t *testing.T, f fs.Fs) { 34 // FIXME implement cmount 35 t.Skip("windows not supported yet") 36 37 device := f.Name() + ":" + f.Root() 38 options := []string{ 39 "-o", "fsname=" + device, 40 "-o", "subtype=rclone", 41 "-o", fmt.Sprintf("max_readahead=%d", mountlib.MaxReadAhead), 42 "-o", "uid=-1", 43 "-o", "gid=-1", 44 "-o", "allow_other", 45 // This causes FUSE to supply O_TRUNC with the Open 46 // call which is more efficient for cmount. However 47 // it does not work with cgofuse on Windows with 48 // WinFSP so cmount must work with or without it. 49 "-o", "atomic_o_trunc", 50 "--FileSystemName=rclone", 51 } 52 53 fsys := cmount.NewFS(f) 54 host := fuse.NewFileSystemHost(fsys) 55 56 // Serve the mount point in the background returning error to errChan 57 r.unmountRes = make(chan error, 1) 58 go func() { 59 var err error 60 ok := host.Mount(r.mntDir, options) 61 if !ok { 62 err = errors.New("mount failed") 63 } 64 r.unmountRes <- err 65 }() 66 67 // unmount 68 r.unmountFn = func() error { 69 // Shutdown the VFS 70 fsys.VFS.Shutdown() 71 if host.Unmount() { 72 if !waitFor(func() bool { 73 _, err := os.Stat(r.mntDir) 74 return err != nil 75 }) { 76 t.Fatalf("mountpoint %q didn't disappear after unmount - continuing anyway", r.mntDir) 77 } 78 return nil 79 } 80 return errors.New("host unmount failed") 81 } 82 83 // Wait for the filesystem to become ready, checking the file 84 // system didn't blow up before starting 85 select { 86 case err := <-r.unmountRes: 87 require.NoError(t, err) 88 case <-time.After(time.Second * 3): 89 } 90 91 // Wait for the mount point to be available on Windows 92 // On Windows the Init signal comes slightly before the mount is ready 93 if !waitFor(func() bool { 94 _, err := os.Stat(r.mntDir) 95 return err == nil 96 }) { 97 t.Errorf("mountpoint %q didn't became available on mount", r.mntDir) 98 } 99 100 r.vfs = fsys.VFS 101 r.isMounted = true 102 } 103 104 func (r *run) unmountFs(t *testing.T, f fs.Fs) { 105 // FIXME implement cmount 106 t.Skip("windows not supported yet") 107 var err error 108 109 for i := 0; i < 4; i++ { 110 err = r.unmountFn() 111 if err != nil { 112 //log.Printf("signal to umount failed - retrying: %v", err) 113 time.Sleep(3 * time.Second) 114 continue 115 } 116 break 117 } 118 require.NoError(t, err) 119 err = <-r.unmountRes 120 require.NoError(t, err) 121 err = r.vfs.CleanUp() 122 require.NoError(t, err) 123 r.isMounted = false 124 }