diff options
| author | hilimd <68371223+hilimd@users.noreply.github.com> | 2021-04-06 13:39:26 +0800 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2021-04-06 13:39:26 +0800 |
| commit | 8693cdacae5b4201ccd259382a02392250b0890e (patch) | |
| tree | b565af4380b0f59a61b1d3c9fad8f04cbb802e7c /weed/filesys | |
| parent | 17d02264f33f501e124060ade7b0b39e687aaa3d (diff) | |
| parent | a37eca78cd680858d021cd864766b0847328a8d7 (diff) | |
| download | seaweedfs-8693cdacae5b4201ccd259382a02392250b0890e.tar.xz seaweedfs-8693cdacae5b4201ccd259382a02392250b0890e.zip | |
Merge pull request #75 from chrislusf/master
sync
Diffstat (limited to 'weed/filesys')
| -rw-r--r-- | weed/filesys/dir.go | 29 | ||||
| -rw-r--r-- | weed/filesys/dir_link.go | 8 | ||||
| -rw-r--r-- | weed/filesys/dir_rename.go | 4 | ||||
| -rw-r--r-- | weed/filesys/dir_test.go | 34 | ||||
| -rw-r--r-- | weed/filesys/file.go | 36 | ||||
| -rw-r--r-- | weed/filesys/filehandle.go | 21 | ||||
| -rw-r--r-- | weed/filesys/wfs.go | 1 |
7 files changed, 84 insertions, 49 deletions
diff --git a/weed/filesys/dir.go b/weed/filesys/dir.go index 33e1a0a3a..46457f858 100644 --- a/weed/filesys/dir.go +++ b/weed/filesys/dir.go @@ -128,6 +128,10 @@ func (dir *Dir) newDirectory(fullpath util.FullPath, entry *filer_pb.Entry) fs.N func (dir *Dir) Create(ctx context.Context, req *fuse.CreateRequest, resp *fuse.CreateResponse) (fs.Node, fs.Handle, error) { + if dir.wfs.option.ReadOnly { + return nil, nil, fuse.EPERM + } + request, err := dir.doCreateEntry(req.Name, req.Mode, req.Uid, req.Gid, req.Flags&fuse.OpenExclusive != 0) if err != nil { @@ -148,6 +152,10 @@ func (dir *Dir) Create(ctx context.Context, req *fuse.CreateRequest, func (dir *Dir) Mknod(ctx context.Context, req *fuse.MknodRequest) (fs.Node, error) { + if dir.wfs.option.ReadOnly { + return nil, fuse.EPERM + } + request, err := dir.doCreateEntry(req.Name, req.Mode, req.Uid, req.Gid, false) if err != nil { @@ -202,6 +210,10 @@ func (dir *Dir) doCreateEntry(name string, mode os.FileMode, uid, gid uint32, ex func (dir *Dir) Mkdir(ctx context.Context, req *fuse.MkdirRequest) (fs.Node, error) { + if dir.wfs.option.ReadOnly { + return nil, fuse.EPERM + } + glog.V(4).Infof("mkdir %s: %s", dir.FullPath(), req.Name) newEntry := &filer_pb.Entry{ @@ -356,6 +368,11 @@ func findFileType(mode uint16) fuse.DirentType { func (dir *Dir) Remove(ctx context.Context, req *fuse.RemoveRequest) error { + if dir.wfs.option.ReadOnly { + return fuse.EPERM + } + + if !req.Dir { return dir.removeOneFile(req) } @@ -429,6 +446,10 @@ func (dir *Dir) removeFolder(req *fuse.RemoveRequest) error { func (dir *Dir) Setattr(ctx context.Context, req *fuse.SetattrRequest, resp *fuse.SetattrResponse) error { + if dir.wfs.option.ReadOnly { + return fuse.EPERM + } + glog.V(4).Infof("%v dir setattr %+v", dir.FullPath(), req) if err := dir.maybeLoadEntry(); err != nil { @@ -457,6 +478,10 @@ func (dir *Dir) Setattr(ctx context.Context, req *fuse.SetattrRequest, resp *fus func (dir *Dir) Setxattr(ctx context.Context, req *fuse.SetxattrRequest) error { + if dir.wfs.option.ReadOnly { + return fuse.EPERM + } + glog.V(4).Infof("dir Setxattr %s: %s", dir.FullPath(), req.Name) if err := dir.maybeLoadEntry(); err != nil { @@ -473,6 +498,10 @@ func (dir *Dir) Setxattr(ctx context.Context, req *fuse.SetxattrRequest) error { func (dir *Dir) Removexattr(ctx context.Context, req *fuse.RemovexattrRequest) error { + if dir.wfs.option.ReadOnly { + return fuse.EPERM + } + glog.V(4).Infof("dir Removexattr %s: %s", dir.FullPath(), req.Name) if err := dir.maybeLoadEntry(); err != nil { diff --git a/weed/filesys/dir_link.go b/weed/filesys/dir_link.go index 606e52fcb..6266e492d 100644 --- a/weed/filesys/dir_link.go +++ b/weed/filesys/dir_link.go @@ -24,6 +24,10 @@ const ( func (dir *Dir) Link(ctx context.Context, req *fuse.LinkRequest, old fs.Node) (fs.Node, error) { + if dir.wfs.option.ReadOnly { + return nil, fuse.EPERM + } + oldFile, ok := old.(*File) if !ok { glog.Errorf("old node is not a file: %+v", old) @@ -105,6 +109,10 @@ func (dir *Dir) Link(ctx context.Context, req *fuse.LinkRequest, old fs.Node) (f func (dir *Dir) Symlink(ctx context.Context, req *fuse.SymlinkRequest) (fs.Node, error) { + if dir.wfs.option.ReadOnly { + return nil, fuse.EPERM + } + glog.V(4).Infof("Symlink: %v/%v to %v", dir.FullPath(), req.NewName, req.Target) request := &filer_pb.CreateEntryRequest{ diff --git a/weed/filesys/dir_rename.go b/weed/filesys/dir_rename.go index d2acad4b2..28316c3bd 100644 --- a/weed/filesys/dir_rename.go +++ b/weed/filesys/dir_rename.go @@ -13,6 +13,10 @@ import ( func (dir *Dir) Rename(ctx context.Context, req *fuse.RenameRequest, newDirectory fs.Node) error { + if dir.wfs.option.ReadOnly { + return fuse.EPERM + } + newDir := newDirectory.(*Dir) newPath := util.NewFullPath(newDir.FullPath(), req.NewName) diff --git a/weed/filesys/dir_test.go b/weed/filesys/dir_test.go deleted file mode 100644 index 49c76eb5e..000000000 --- a/weed/filesys/dir_test.go +++ /dev/null @@ -1,34 +0,0 @@ -package filesys - -import ( - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestDirPath(t *testing.T) { - - p := &Dir{name: "/some"} - p = &Dir{name: "path", parent: p} - p = &Dir{name: "to", parent: p} - p = &Dir{name: "a", parent: p} - p = &Dir{name: "file", parent: p} - - assert.Equal(t, "/some/path/to/a/file", p.FullPath()) - - p = &Dir{name: "/some"} - assert.Equal(t, "/some", p.FullPath()) - - p = &Dir{name: "/"} - assert.Equal(t, "/", p.FullPath()) - - p = &Dir{name: "/"} - p = &Dir{name: "path", parent: p} - assert.Equal(t, "/path", p.FullPath()) - - p = &Dir{name: "/"} - p = &Dir{name: "path", parent: p} - p = &Dir{name: "to", parent: p} - assert.Equal(t, "/path/to", p.FullPath()) - -} diff --git a/weed/filesys/file.go b/weed/filesys/file.go index 5931dd2ff..2433be590 100644 --- a/weed/filesys/file.go +++ b/weed/filesys/file.go @@ -56,6 +56,10 @@ func (file *File) Attr(ctx context.Context, attr *fuse.Attr) (err error) { } } + if entry == nil { + return fuse.ENOENT + } + // attr.Inode = file.fullpath().AsInode() attr.Valid = time.Second attr.Mode = os.FileMode(entry.Attributes.FileMode) @@ -106,6 +110,10 @@ func (file *File) Open(ctx context.Context, req *fuse.OpenRequest, resp *fuse.Op func (file *File) Setattr(ctx context.Context, req *fuse.SetattrRequest, resp *fuse.SetattrResponse) error { + if file.wfs.option.ReadOnly { + return fuse.EPERM + } + glog.V(4).Infof("%v file setattr %+v", file.fullpath(), req) entry, err := file.maybeLoadEntry(ctx) @@ -147,7 +155,7 @@ func (file *File) Setattr(ctx context.Context, req *fuse.SetattrRequest, resp *f } entry.Chunks = chunks file.entryViewCache, _ = filer.NonOverlappingVisibleIntervals(file.wfs.LookupFn(), chunks) - file.reader = nil + file.setReader(nil) } entry.Attributes.FileSize = req.Size file.dirtyMetadata = true @@ -196,6 +204,10 @@ func (file *File) Setattr(ctx context.Context, req *fuse.SetattrRequest, resp *f func (file *File) Setxattr(ctx context.Context, req *fuse.SetxattrRequest) error { + if file.wfs.option.ReadOnly { + return fuse.EPERM + } + glog.V(4).Infof("file Setxattr %s: %s", file.fullpath(), req.Name) entry, err := file.maybeLoadEntry(ctx) @@ -213,6 +225,10 @@ func (file *File) Setxattr(ctx context.Context, req *fuse.SetxattrRequest) error func (file *File) Removexattr(ctx context.Context, req *fuse.RemovexattrRequest) error { + if file.wfs.option.ReadOnly { + return fuse.EPERM + } + glog.V(4).Infof("file Removexattr %s: %s", file.fullpath(), req.Name) entry, err := file.maybeLoadEntry(ctx) @@ -257,6 +273,8 @@ func (file *File) Forget() { t := util.NewFullPath(file.dir.FullPath(), file.Name) glog.V(4).Infof("Forget file %s", t) file.wfs.fsNodeCache.DeleteFsNode(t) + file.wfs.ReleaseHandle(t, 0) + file.setReader(nil) } func (file *File) maybeLoadEntry(ctx context.Context) (entry *filer_pb.Entry, err error) { @@ -323,19 +341,29 @@ func (file *File) addChunks(chunks []*filer_pb.FileChunk) { file.entryViewCache = filer.MergeIntoVisibles(file.entryViewCache, chunk) } - file.reader = nil + file.setReader(nil) glog.V(4).Infof("%s existing %d chunks adds %d more", file.fullpath(), len(entry.Chunks), len(chunks)) entry.Chunks = append(entry.Chunks, newChunks...) } +func (file *File) setReader(reader io.ReaderAt) { + r := file.reader + if r != nil { + if closer, ok := r.(io.Closer); ok { + closer.Close() + } + } + file.reader = reader +} + func (file *File) setEntry(entry *filer_pb.Entry) { file.entryLock.Lock() defer file.entryLock.Unlock() file.entry = entry file.entryViewCache, _ = filer.NonOverlappingVisibleIntervals(file.wfs.LookupFn(), entry.Chunks) - file.reader = nil + file.setReader(nil) } func (file *File) clearEntry() { @@ -343,7 +371,7 @@ func (file *File) clearEntry() { defer file.entryLock.Unlock() file.entry = nil file.entryViewCache = nil - file.reader = nil + file.setReader(nil) } func (file *File) saveEntry(entry *filer_pb.Entry) error { diff --git a/weed/filesys/filehandle.go b/weed/filesys/filehandle.go index 25eaf7033..4419888c4 100644 --- a/weed/filesys/filehandle.go +++ b/weed/filesys/filehandle.go @@ -23,7 +23,7 @@ type FileHandle struct { dirtyPages *ContinuousDirtyPages contentType string handle uint64 - sync.RWMutex + sync.Mutex f *File RequestId fuse.RequestID // unique ID for request @@ -59,8 +59,8 @@ var _ = fs.HandleReleaser(&FileHandle{}) func (fh *FileHandle) Read(ctx context.Context, req *fuse.ReadRequest, resp *fuse.ReadResponse) error { glog.V(4).Infof("%s read fh %d: [%d,%d) size %d resp.Data cap=%d", fh.f.fullpath(), fh.handle, req.Offset, req.Offset+int64(req.Size), req.Size, cap(resp.Data)) - fh.RLock() - defer fh.RUnlock() + fh.Lock() + defer fh.Unlock() if req.Size <= 0 { return nil @@ -130,7 +130,7 @@ func (fh *FileHandle) readFromChunks(buff []byte, offset int64) (int64, error) { if chunkResolveErr != nil { return 0, fmt.Errorf("fail to resolve chunk manifest: %v", chunkResolveErr) } - fh.f.reader = nil + fh.f.setReader(nil) } reader := fh.f.reader @@ -138,7 +138,7 @@ func (fh *FileHandle) readFromChunks(buff []byte, offset int64) (int64, error) { chunkViews := filer.ViewFromVisibleIntervals(fh.f.entryViewCache, 0, math.MaxInt64) reader = filer.NewChunkReaderAtFromClient(fh.f.wfs.LookupFn(), chunkViews, fh.f.wfs.chunkCache, fileSize) } - fh.f.reader = reader + fh.f.setReader(reader) totalRead, err := reader.ReadAt(buff, offset) @@ -154,6 +154,10 @@ func (fh *FileHandle) readFromChunks(buff []byte, offset int64) (int64, error) { // Write to the file handle func (fh *FileHandle) Write(ctx context.Context, req *fuse.WriteRequest, resp *fuse.WriteResponse) error { + if fh.f.wfs.option.ReadOnly { + return fuse.EPERM + } + fh.Lock() defer fh.Unlock() @@ -207,12 +211,7 @@ func (fh *FileHandle) Release(ctx context.Context, req *fuse.ReleaseRequest) err fh.f.isOpen-- fh.f.wfs.ReleaseHandle(fh.f.fullpath(), fuse.HandleID(fh.handle)) - if closer, ok := fh.f.reader.(io.Closer); ok { - if closer != nil { - closer.Close() - } - } - fh.f.reader = nil + fh.f.setReader(nil) } return nil diff --git a/weed/filesys/wfs.go b/weed/filesys/wfs.go index c6d9080a1..ba5eb4b6b 100644 --- a/weed/filesys/wfs.go +++ b/weed/filesys/wfs.go @@ -43,6 +43,7 @@ type Option struct { DataCenter string EntryCacheTtl time.Duration Umask os.FileMode + ReadOnly bool MountUid uint32 MountGid uint32 |
