Skip to content
This repository was archived by the owner on Aug 22, 2020. It is now read-only.

Commit ea910ea

Browse files
author
Mya Pitzeruse
authored
gh-23: fixed bug in read only files (#24)
* gh-23: fixed bug in read only files. we would originally open the file on create and immediately close it, making it fail when it finally flushed changes to disk. * gh-23: stopped delegating fsync to flush
1 parent 322b55d commit ea910ea

File tree

2 files changed

+56
-92
lines changed

2 files changed

+56
-92
lines changed

cmd/gitfs/main.go

+3
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,16 @@ package main
22

33
import (
44
"fmt"
5+
"github.com/sirupsen/logrus"
56
"os"
67

78
"github.com/mjpitz/gitfs/cmd"
89
"github.com/spf13/cobra"
910
)
1011

1112
func main() {
13+
logrus.SetOutput(os.Stdout)
14+
1215
rootCmd := &cobra.Command{
1316
Use: "gitfs",
1417
}

pkg/filesystem/billy.go

+53-92
Original file line numberDiff line numberDiff line change
@@ -19,9 +19,8 @@ import (
1919
var _ INode = &BillyNode{}
2020

2121
const defaultPerms = 0644
22-
const allPerms = 0777
2322
const maxFileSize = math.MaxUint64
24-
const createFileFlags = os.O_RDWR | os.O_CREATE | os.O_TRUNC
23+
const createFileFlags = os.O_WRONLY | os.O_CREATE | os.O_TRUNC
2524
const maxInt = uint64(int(^uint(0) >> 1))
2625

2726
type BillyUser struct {
@@ -52,9 +51,8 @@ type BillyNode struct {
5251

5352
func (n *BillyNode) Fsync(ctx context.Context, req *fuse.FsyncRequest) error {
5453
n.debug("Fsync", req)
55-
56-
// call flush for now
57-
return n.Flush(ctx, nil)
54+
// not quite sure what to do here, but it needs to be implemented and return nil.
55+
return nil
5856
}
5957

6058
// symlink functions
@@ -95,27 +93,29 @@ func (n *BillyNode) Flush(ctx context.Context, req *fuse.FlushRequest) error {
9593
n.mu.Lock()
9694
defer n.mu.Unlock()
9795

98-
file, err := n.fs.OpenFile(n.path, os.O_WRONLY, n.mode)
96+
file, err := n.fs.OpenFile(n.path, createFileFlags, n.mode)
9997
if err != nil {
98+
n.error("Flush", err)
10099
return err
101100
}
102101

103102
if err = file.Lock(); err != nil {
104-
n.error("load", err)
103+
n.error("Flush", err)
105104
return fuse.ENOENT
106105
}
107106

108107
defer func() {
109108
if err := file.Unlock(); err != nil {
110-
n.error("load", err)
109+
n.error("Flush", err)
111110
}
112111

113112
if err := file.Close(); err != nil {
114-
n.error("load", err)
113+
n.error("Flush", err)
115114
}
116115
}()
117116

118117
if _, err := file.Write(n.data); err != nil {
118+
n.error("Flush", err)
119119
return err
120120
}
121121

@@ -281,17 +281,21 @@ func (n *BillyNode) Create(ctx context.Context, req *fuse.CreateRequest, resp *f
281281
n.mu.Lock()
282282
defer n.mu.Unlock()
283283

284-
node, err := n.createOrOpen(req.Name, true, req.Mode)
285-
if err != nil {
286-
n.error("Create", err)
287-
return nil, nil, err
288-
}
284+
fullPath := n.fs.Join(n.path, req.Name)
289285

290-
// force load the data
291-
// ensure proper file handle
292-
err = node.load()
286+
node := &BillyNode{
287+
repourl: n.repourl,
288+
fs: n.fs,
289+
path: fullPath,
290+
target: "",
291+
user: n.user,
292+
mode: req.Mode,
293+
size: uint64(0),
294+
data: make([]byte, 0),
295+
mu: &sync.Mutex{},
296+
}
293297

294-
return node, node, err
298+
return node, node, nil
295299
}
296300

297301
func (n *BillyNode) Mkdir(ctx context.Context, req *fuse.MkdirRequest) (fs.Node, error) {
@@ -366,13 +370,40 @@ func (n *BillyNode) Lookup(ctx context.Context, name string) (fs.Node, error) {
366370
n.mu.Lock()
367371
defer n.mu.Unlock()
368372

369-
node, err := n.createOrOpen(name, false, defaultPerms)
373+
fullPath := n.fs.Join(n.path, name)
370374

371-
if err != nil {
372-
return nil, fuse.ENOENT
375+
// symlink
376+
if target, err := n.fs.Readlink(fullPath); err == nil {
377+
node := &BillyNode{
378+
repourl: n.repourl,
379+
fs: n.fs,
380+
path: fullPath,
381+
target: target,
382+
user: n.user,
383+
mode: os.ModeSymlink | 0755,
384+
size: uint64(len(target)),
385+
data: nil,
386+
mu: &sync.Mutex{},
387+
}
388+
return node, nil
373389
}
374390

375-
return node, nil
391+
if finfo, err := n.fs.Stat(fullPath); err != nil {
392+
// assumed file does not exist
393+
return nil, fuse.ENOENT
394+
} else {
395+
return &BillyNode{
396+
repourl: n.repourl,
397+
fs: n.fs,
398+
path: fullPath,
399+
target: "",
400+
user: n.user,
401+
mode: finfo.Mode(),
402+
size: uint64(finfo.Size()),
403+
data: nil,
404+
mu: &sync.Mutex{},
405+
}, nil
406+
}
376407
}
377408

378409
// node functions
@@ -435,76 +466,6 @@ func (n *BillyNode) Attr(ctx context.Context, attr *fuse.Attr) error {
435466

436467
// helper functions
437468

438-
func (n *BillyNode) createOrOpen(name string, create bool, mode os.FileMode) (*BillyNode, error) {
439-
n.debug("createOrOpen", name)
440-
441-
fullPath := n.fs.Join(n.path, name)
442-
443-
// symlink
444-
if target, err := n.fs.Readlink(fullPath); err == nil {
445-
node := &BillyNode{
446-
repourl: n.repourl,
447-
fs: n.fs,
448-
path: fullPath,
449-
target: target,
450-
user: n.user,
451-
mode: os.ModeSymlink | defaultPerms,
452-
size: uint64(len(target)),
453-
data: nil,
454-
mu: &sync.Mutex{},
455-
}
456-
return node, nil
457-
}
458-
459-
finfo, err := n.fs.Stat(fullPath)
460-
if err == nil {
461-
// file exists, create reference
462-
node := &BillyNode{
463-
repourl: n.repourl,
464-
fs: n.fs,
465-
path: fullPath,
466-
target: "",
467-
user: n.user,
468-
mode: finfo.Mode(),
469-
size: uint64(finfo.Size()),
470-
data: nil,
471-
mu: &sync.Mutex{},
472-
}
473-
474-
return node, nil
475-
} else if !create {
476-
// file does not exist, not creating
477-
return nil, fuse.ENOENT
478-
}
479-
480-
// don't use bfs.Create since it assigns 666 permissions
481-
file, err := n.fs.OpenFile(fullPath, createFileFlags, mode)
482-
if err != nil {
483-
n.error("createOrOpen", err)
484-
// shouldn't really happen but lets just account for it just in case
485-
return nil, fuse.EEXIST
486-
}
487-
488-
if err := file.Close(); err != nil {
489-
n.error("createOrOpen", err)
490-
return nil, fuse.EEXIST
491-
}
492-
493-
node := &BillyNode{
494-
repourl: n.repourl,
495-
fs: n.fs,
496-
path: fullPath,
497-
target: "",
498-
user: n.user,
499-
mode: mode,
500-
size: 0,
501-
data: make([]byte, 0),
502-
mu: &sync.Mutex{},
503-
}
504-
505-
return node, nil
506-
}
507-
508469
func (n *BillyNode) load() error {
509470
if n.data != nil {
510471
// already loaded, nothing to do

0 commit comments

Comments
 (0)