diff options
author | Jakob Unterwurzacher | 2016-09-22 23:28:11 +0200 |
---|---|---|
committer | Jakob Unterwurzacher | 2016-09-25 16:43:17 +0200 |
commit | a6a7b424f8e8a0f8ddd1c94b7463250ef1337811 (patch) | |
tree | 2281d7062d893d70209ecb7a82589e49decac164 /internal/fusefrontend_reverse/virtualfile.go | |
parent | 35bcc2dca2dc928e3b7c31e34d785b7a42c06722 (diff) |
reverse: resolve long names in Open and GetAttr
The last patch added functionality for generating gocryptfs.longname.*
files, this patch adds support for mapping them back to the full
filenames.
Note that resolving a long name needs a full readdir. A cache
will be implemented later on to improve performance.
Diffstat (limited to 'internal/fusefrontend_reverse/virtualfile.go')
-rw-r--r-- | internal/fusefrontend_reverse/virtualfile.go | 57 |
1 files changed, 57 insertions, 0 deletions
diff --git a/internal/fusefrontend_reverse/virtualfile.go b/internal/fusefrontend_reverse/virtualfile.go new file mode 100644 index 0000000..5373b48 --- /dev/null +++ b/internal/fusefrontend_reverse/virtualfile.go @@ -0,0 +1,57 @@ +package fusefrontend_reverse + +import ( + "fmt" + "syscall" + + "github.com/hanwen/go-fuse/fuse" + "github.com/hanwen/go-fuse/fuse/nodefs" +) + +type virtualFile struct { + // Embed nodefs.defaultFile for a ENOSYS implementation of all methods + nodefs.File + // file content + content []byte + // absolute path to a parent file + parentFile string + // inode number + ino uint64 +} + +func (rfs *reverseFS) NewVirtualFile(content []byte, parentFile string) (nodefs.File, fuse.Status) { + return &virtualFile{ + File: nodefs.NewDefaultFile(), + content: content, + parentFile: parentFile, + ino: rfs.inoGen.next(), + }, fuse.OK +} + +// Read - FUSE call +func (f *virtualFile) Read(buf []byte, off int64) (resultData fuse.ReadResult, status fuse.Status) { + if off >= int64(len(f.content)) { + return nil, fuse.OK + } + end := int(off) + len(buf) + if end > len(f.content) { + end = len(f.content) + } + return fuse.ReadResultData(f.content[off:end]), fuse.OK +} + +// GetAttr - FUSE call +func (f *virtualFile) GetAttr(a *fuse.Attr) fuse.Status { + var st syscall.Stat_t + err := syscall.Lstat(f.parentFile, &st) + if err != nil { + fmt.Printf("Lstat %q: %v\n", f.parentFile, err) + return fuse.ToStatus(err) + } + st.Ino = f.ino + st.Size = int64(len(f.content)) + st.Mode = syscall.S_IFREG | 0400 + st.Nlink = 1 + a.FromStat(&st) + return fuse.OK +} |