From e3c5e3f1c8db31e62bbb781a238da4cf76ed1ffc Mon Sep 17 00:00:00 2001 From: Jakob Unterwurzacher Date: Mon, 28 Nov 2016 23:09:47 +0100 Subject: [PATCH] fusefronted: preserve owner for device nodes and sockets https://github.com/rfjakob/gocryptfs/issues/64 --- internal/fusefrontend/fs.go | 31 ++++++++++++++++++----------- internal/nametransform/longnames.go | 3 ++- 2 files changed, 21 insertions(+), 13 deletions(-) diff --git a/internal/fusefrontend/fs.go b/internal/fusefrontend/fs.go index 261d690..8e12997 100644 --- a/internal/fusefrontend/fs.go +++ b/internal/fusefrontend/fs.go @@ -195,36 +195,43 @@ func (fs *FS) Mknod(path string, mode uint32, dev uint32, context *fuse.Context) if fs.isFiltered(path) { return fuse.EPERM } - cPath, err := fs.encryptPath(path) + cPath, err := fs.getBackingPath(path) if err != nil { return fuse.ToStatus(err) } - - // Handle long file name + // Create ".name" file to store long file name cName := filepath.Base(cPath) if nametransform.IsLongContent(cName) { - dirfd, err := os.Open(filepath.Dir(cPath)) + var dirfd *os.File + dirfd, err = os.Open(filepath.Dir(cPath)) if err != nil { return fuse.ToStatus(err) } defer dirfd.Close() - - // Create ".name" err = fs.nameTransform.WriteLongName(dirfd, cName, path) if err != nil { return fuse.ToStatus(err) } - - // Create device node - err = syscallcompat.Mknodat(int(dirfd.Fd()), cName, uint32(mode), int(dev)) + // Create "gocryptfs.longfile." device node + err = syscallcompat.Mknodat(int(dirfd.Fd()), cName, mode, int(dev)) if err != nil { nametransform.DeleteLongName(dirfd, cName) } - + } else { + // Create regular device node + err = syscall.Mknod(cPath, mode, int(dev)) + } + if err != nil { return fuse.ToStatus(err) } - - return fs.FileSystem.Mknod(cPath, mode, dev, context) + // Set owner + if fs.args.PreserveOwner { + err = os.Lchown(cPath, int(context.Owner.Uid), int(context.Owner.Gid)) + if err != nil { + tlog.Warn.Printf("Mknod: Lchown failed: %v", err) + } + } + return fuse.OK } // Truncate implements pathfs.Filesystem. diff --git a/internal/nametransform/longnames.go b/internal/nametransform/longnames.go index be00bb4..71a4c16 100644 --- a/internal/nametransform/longnames.go +++ b/internal/nametransform/longnames.go @@ -57,7 +57,8 @@ func NameType(cName string) int { return LongNameContent } -// IsLongContent returns true if "cName" is the content store of a long name file. +// IsLongContent returns true if "cName" is the content store of a long name +// file (looks like "gocryptfs.longname.[sha256]"). func IsLongContent(cName string) bool { return NameType(cName) == LongNameContent }