From 94adf4f43be1b1c94fbda046662336f6bafc9601 Mon Sep 17 00:00:00 2001 From: Nick Craig-Wood Date: Thu, 16 Nov 2017 09:27:26 +0000 Subject: [PATCH] cmount: translate FUSE open flags into OS flags On Windows the fuse.O_* flags do not have the same values as the os.O_* flags so translate between the two representations. They are mostly the same which is why this hasn't caused a problem before. --- cmd/cmount/fs.go | 32 ++++++++++++++++++++++++++++++-- 1 file changed, 30 insertions(+), 2 deletions(-) diff --git a/cmd/cmount/fs.go b/cmd/cmount/fs.go index ce57ecd84..0c827935e 100644 --- a/cmd/cmount/fs.go +++ b/cmd/cmount/fs.go @@ -282,8 +282,8 @@ func (fsys *FS) Statfs(path string, stat *fuse.Statfs_t) (errc int) { func (fsys *FS) Open(path string, flags int) (errc int, fh uint64) { defer fs.Trace(path, "flags=0x%X", flags)("errc=%d, fh=0x%X", &errc, &fh) - // fuse flags are based off syscall flags as are os flags, so - // should be compatible + // translate the fuse flags to os flags + flags = translateOpenFlags(flags) handle, err := fsys.VFS.OpenFile(path, flags, 0777) if errc != 0 { return translateError(err), fhUnset @@ -303,6 +303,8 @@ func (fsys *FS) Create(filePath string, flags int, mode uint32) (errc int, fh ui if err != nil { return translateError(err), fhUnset } + // translate the fuse flags to os flags + flags = translateOpenFlags(flags) handle, err := file.Open(flags) if err != nil { return translateError(err), fhUnset @@ -556,3 +558,29 @@ func translateError(err error) (errc int) { fs.Errorf(nil, "IO error: %v", err) return -fuse.EIO } + +// Translate Open Flags from FUSE to os (as used in the vfs layer) +func translateOpenFlags(inFlags int) (outFlags int) { + switch inFlags & fuse.O_ACCMODE { + case fuse.O_RDONLY: + outFlags = os.O_RDONLY + case fuse.O_WRONLY: + outFlags = os.O_WRONLY + case fuse.O_RDWR: + outFlags = os.O_RDWR + } + if inFlags&fuse.O_APPEND != 0 { + outFlags |= os.O_APPEND + } + if inFlags&fuse.O_CREAT != 0 { + outFlags |= os.O_CREATE + } + if inFlags&fuse.O_EXCL != 0 { + outFlags |= os.O_EXCL + } + if inFlags&fuse.O_TRUNC != 0 { + outFlags |= os.O_TRUNC + } + // NB O_SYNC isn't defined by fuse + return outFlags +}