From f3956ca1097ee20f2a76e1cd691c93e3fd1d788e Mon Sep 17 00:00:00 2001 From: Aaron Jacobs Date: Fri, 24 Jul 2015 12:57:29 +1000 Subject: [PATCH 1/3] Fixed some Linux build errors. --- internal/fusekernel/fuse_kernel_linux.go | 22 +++++++++++----------- internal/fuseshim/unmount_linux.go | 2 +- 2 files changed, 12 insertions(+), 12 deletions(-) diff --git a/internal/fusekernel/fuse_kernel_linux.go b/internal/fusekernel/fuse_kernel_linux.go index a464e50..0472e1d 100644 --- a/internal/fusekernel/fuse_kernel_linux.go +++ b/internal/fusekernel/fuse_kernel_linux.go @@ -1,8 +1,8 @@ -package fuseshim +package fusekernel import "time" -type attr struct { +type Attr struct { Ino uint64 Size uint64 Blocks uint64 @@ -21,31 +21,31 @@ type attr struct { padding uint32 } -func (a *attr) Crtime() time.Time { +func (a *Attr) Crtime() time.Time { return time.Time{} } -func (a *attr) SetCrtime(s uint64, ns uint32) { +func (a *Attr) SetCrtime(s uint64, ns uint32) { // Ignored on Linux. } -func (a *attr) SetFlags(f uint32) { +func (a *Attr) SetFlags(f uint32) { // Ignored on Linux. } -type setattrIn struct { +type SetattrIn struct { setattrInCommon } -func (in *setattrIn) BkupTime() time.Time { +func (in *SetattrIn) BkupTime() time.Time { return time.Time{} } -func (in *setattrIn) Chgtime() time.Time { +func (in *SetattrIn) Chgtime() time.Time { return time.Time{} } -func (in *setattrIn) Flags() uint32 { +func (in *SetattrIn) Flags() uint32 { return 0 } @@ -61,10 +61,10 @@ func openFlags(flags uint32) OpenFlags { return OpenFlags(flags) } -type getxattrIn struct { +type GetxattrIn struct { getxattrInCommon } -type setxattrIn struct { +type SetxattrIn struct { setxattrInCommon } diff --git a/internal/fuseshim/unmount_linux.go b/internal/fuseshim/unmount_linux.go index e4c18d6..6a165cc 100644 --- a/internal/fuseshim/unmount_linux.go +++ b/internal/fuseshim/unmount_linux.go @@ -1,4 +1,4 @@ -package bazilfuse +package fuseshim import ( "bytes" From ab8c5728eb860cba896865ec4f5cc6b0a94ed899 Mon Sep 17 00:00:00 2001 From: Aaron Jacobs Date: Fri, 24 Jul 2015 13:08:26 +1000 Subject: [PATCH 2/3] Fixed some size-related bugs on Linux. --- fuseops/convert.go | 32 +++++++++++++++++++------------- fuseops/ops.go | 18 ++++++++++++------ 2 files changed, 31 insertions(+), 19 deletions(-) diff --git a/fuseops/convert.go b/fuseops/convert.go index 87baa23..9e1c6fc 100644 --- a/fuseops/convert.go +++ b/fuseops/convert.go @@ -57,15 +57,17 @@ func Convert( } to := &LookUpInodeOp{ - Parent: InodeID(m.Hdr.Nodeid), - Name: string(buf[:n-1]), + protocol: protocol, + Parent: InodeID(m.Hdr.Nodeid), + Name: string(buf[:n-1]), } io = to co = &to.commonOp case fusekernel.OpGetattr: to := &GetInodeAttributesOp{ - Inode: InodeID(m.Hdr.Nodeid), + protocol: protocol, + Inode: InodeID(m.Hdr.Nodeid), } io = to co = &to.commonOp @@ -78,7 +80,8 @@ func Convert( } to := &SetInodeAttributesOp{ - Inode: InodeID(m.Hdr.Nodeid), + protocol: protocol, + Inode: InodeID(m.Hdr.Nodeid), } valid := fusekernel.SetattrValid(in.Valid) @@ -134,9 +137,10 @@ func Convert( name = name[:i] to := &MkDirOp{ - Parent: InodeID(m.Hdr.Nodeid), - Name: string(name), - Mode: fuseshim.FileMode(in.Mode), + protocol: protocol, + Parent: InodeID(m.Hdr.Nodeid), + Name: string(name), + Mode: fuseshim.FileMode(in.Mode), } io = to co = &to.commonOp @@ -157,9 +161,10 @@ func Convert( name = name[:i] to := &CreateFileOp{ - Parent: InodeID(m.Hdr.Nodeid), - Name: string(name), - Mode: fuseshim.FileMode(in.Mode), + protocol: protocol, + Parent: InodeID(m.Hdr.Nodeid), + Name: string(name), + Mode: fuseshim.FileMode(in.Mode), } io = to co = &to.commonOp @@ -179,9 +184,10 @@ func Convert( newName, target := names[0:i], names[i+1:len(names)-1] to := &CreateSymlinkOp{ - Parent: InodeID(m.Hdr.Nodeid), - Name: string(newName), - Target: string(target), + protocol: protocol, + Parent: InodeID(m.Hdr.Nodeid), + Name: string(newName), + Target: string(target), } io = to co = &to.commonOp diff --git a/fuseops/ops.go b/fuseops/ops.go index c3f7c68..cd528f1 100644 --- a/fuseops/ops.go +++ b/fuseops/ops.go @@ -60,6 +60,7 @@ type Op interface { // when resolving user paths to dentry structs, which are then cached. type LookUpInodeOp struct { commonOp + protocol fusekernel.Protocol // The ID of the directory inode to which the child belongs. Parent InodeID @@ -88,7 +89,7 @@ func (o *LookUpInodeOp) ShortDesc() (desc string) { } func (o *LookUpInodeOp) kernelResponse() (msg []byte) { - size := fusekernel.EntryOutSize(fusekernel.Protocol{0, 0}) + size := fusekernel.EntryOutSize(o.protocol) buf := fuseshim.NewBuffer(size) out := (*fusekernel.EntryOut)(buf.Alloc(size)) convertChildInodeEntry(&o.Entry, out) @@ -103,6 +104,7 @@ func (o *LookUpInodeOp) kernelResponse() (msg []byte) { // field of ChildInodeEntry, etc. type GetInodeAttributesOp struct { commonOp + protocol fusekernel.Protocol // The inode of interest. Inode InodeID @@ -123,7 +125,7 @@ func (o *GetInodeAttributesOp) DebugString() string { } func (o *GetInodeAttributesOp) kernelResponse() (msg []byte) { - size := fusekernel.AttrOutSize(fusekernel.Protocol{0, 0}) + size := fusekernel.AttrOutSize(o.protocol) buf := fuseshim.NewBuffer(size) out := (*fusekernel.AttrOut)(buf.Alloc(size)) out.AttrValid, out.AttrValidNsec = convertExpirationTime(o.AttributesExpiration) @@ -139,6 +141,7 @@ func (o *GetInodeAttributesOp) kernelResponse() (msg []byte) { // cases like ftrunctate(2). type SetInodeAttributesOp struct { commonOp + protocol fusekernel.Protocol // The inode of interest. Inode InodeID @@ -157,7 +160,7 @@ type SetInodeAttributesOp struct { } func (o *SetInodeAttributesOp) kernelResponse() (msg []byte) { - size := fusekernel.AttrOutSize(fusekernel.Protocol{0, 0}) + size := fusekernel.AttrOutSize(o.protocol) buf := fuseshim.NewBuffer(size) out := (*fusekernel.AttrOut)(buf.Alloc(size)) out.AttrValid, out.AttrValidNsec = convertExpirationTime(o.AttributesExpiration) @@ -238,6 +241,7 @@ func (o *ForgetInodeOp) kernelResponse() (msg []byte) { // Therefore the file system should return EEXIST if the name already exists. type MkDirOp struct { commonOp + protocol fusekernel.Protocol // The ID of parent directory inode within which to create the child. Parent InodeID @@ -259,7 +263,7 @@ func (o *MkDirOp) ShortDesc() (desc string) { } func (o *MkDirOp) kernelResponse() (msg []byte) { - size := fusekernel.EntryOutSize(fusekernel.Protocol{0, 0}) + size := fusekernel.EntryOutSize(o.protocol) buf := fuseshim.NewBuffer(size) out := (*fusekernel.EntryOut)(buf.Alloc(size)) convertChildInodeEntry(&o.Entry, out) @@ -280,6 +284,7 @@ func (o *MkDirOp) kernelResponse() (msg []byte) { // Therefore the file system should return EEXIST if the name already exists. type CreateFileOp struct { commonOp + protocol fusekernel.Protocol // The ID of parent directory inode within which to create the child file. Parent InodeID @@ -311,7 +316,7 @@ func (o *CreateFileOp) ShortDesc() (desc string) { } func (o *CreateFileOp) kernelResponse() (msg []byte) { - eSize := fusekernel.EntryOutSize(fusekernel.Protocol{0, 0}) + eSize := fusekernel.EntryOutSize(o.protocol) buf := fuseshim.NewBuffer(eSize + unsafe.Sizeof(fusekernel.OpenOut{})) e := (*fusekernel.EntryOut)(buf.Alloc(eSize)) @@ -328,6 +333,7 @@ func (o *CreateFileOp) kernelResponse() (msg []byte) { // return EEXIST (cf. the notes on CreateFileOp and MkDirOp). type CreateSymlinkOp struct { commonOp + protocol fusekernel.Protocol // The ID of parent directory inode within which to create the child symlink. Parent InodeID @@ -357,7 +363,7 @@ func (o *CreateSymlinkOp) ShortDesc() (desc string) { } func (o *CreateSymlinkOp) kernelResponse() (msg []byte) { - size := fusekernel.EntryOutSize(fusekernel.Protocol{0, 0}) + size := fusekernel.EntryOutSize(o.protocol) buf := fuseshim.NewBuffer(size) out := (*fusekernel.EntryOut)(buf.Alloc(size)) convertChildInodeEntry(&o.Entry, out) From f8a67d283f89b5c735a95a5cc480cda517c8faef Mon Sep 17 00:00:00 2001 From: Aaron Jacobs Date: Fri, 24 Jul 2015 13:23:39 +1000 Subject: [PATCH 3/3] Fixed a mkdir bug on Linux. --- fuseops/convert.go | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/fuseops/convert.go b/fuseops/convert.go index 9e1c6fc..fb30d8e 100644 --- a/fuseops/convert.go +++ b/fuseops/convert.go @@ -140,8 +140,16 @@ func Convert( protocol: protocol, Parent: InodeID(m.Hdr.Nodeid), Name: string(name), - Mode: fuseshim.FileMode(in.Mode), + + // On Linux, vfs_mkdir calls through to the inode with at most + // permissions and sticky bits set (cf. https://goo.gl/WxgQXk), and fuse + // passes that on directly (cf. https://goo.gl/f31aMo). In other words, + // the fact that this is a directory is implicit in the fact that the + // opcode is mkdir. But we want the correct mode to go through, so ensure + // that os.ModeDir is set. + Mode: fuseshim.FileMode(in.Mode) | os.ModeDir, } + io = to co = &to.commonOp