diff options
Diffstat (limited to 'pkg/p9')
-rw-r--r-- | pkg/p9/file.go | 8 | ||||
-rw-r--r-- | pkg/p9/handlers.go | 39 |
2 files changed, 37 insertions, 10 deletions
diff --git a/pkg/p9/file.go b/pkg/p9/file.go index d4ffbc8e3..cab35896f 100644 --- a/pkg/p9/file.go +++ b/pkg/p9/file.go @@ -97,12 +97,12 @@ type File interface { // free to ignore the hint entirely (i.e. the value returned may be larger // than size). All size checking is done independently at the syscall layer. // - // TODO(b/127675828): Determine concurrency guarantees once implemented. + // On the server, GetXattr has a read concurrency guarantee. GetXattr(name string, size uint64) (string, error) // SetXattr sets extended attributes on this node. // - // TODO(b/127675828): Determine concurrency guarantees once implemented. + // On the server, SetXattr has a write concurrency guarantee. SetXattr(name, value string, flags uint32) error // ListXattr lists the names of the extended attributes on this node. @@ -113,12 +113,12 @@ type File interface { // free to ignore the hint entirely (i.e. the value returned may be larger // than size). All size checking is done independently at the syscall layer. // - // TODO(b/148303075): Determine concurrency guarantees once implemented. + // On the server, ListXattr has a read concurrency guarantee. ListXattr(size uint64) (map[string]struct{}, error) // RemoveXattr removes extended attributes on this node. // - // TODO(b/148303075): Determine concurrency guarantees once implemented. + // On the server, RemoveXattr has a write concurrency guarantee. RemoveXattr(name string) error // Allocate allows the caller to directly manipulate the allocated disk space diff --git a/pkg/p9/handlers.go b/pkg/p9/handlers.go index 2ac45eb80..a8b714cf5 100644 --- a/pkg/p9/handlers.go +++ b/pkg/p9/handlers.go @@ -920,8 +920,15 @@ func (t *Tgetxattr) handle(cs *connState) message { } defer ref.DecRef() - val, err := ref.file.GetXattr(t.Name, t.Size) - if err != nil { + var val string + if err := ref.safelyRead(func() (err error) { + // Don't allow getxattr on files that have been deleted. + if ref.isDeleted() { + return syscall.EINVAL + } + val, err = ref.file.GetXattr(t.Name, t.Size) + return err + }); err != nil { return newErr(err) } return &Rgetxattr{Value: val} @@ -935,7 +942,13 @@ func (t *Tsetxattr) handle(cs *connState) message { } defer ref.DecRef() - if err := ref.file.SetXattr(t.Name, t.Value, t.Flags); err != nil { + if err := ref.safelyWrite(func() error { + // Don't allow setxattr on files that have been deleted. + if ref.isDeleted() { + return syscall.EINVAL + } + return ref.file.SetXattr(t.Name, t.Value, t.Flags) + }); err != nil { return newErr(err) } return &Rsetxattr{} @@ -949,10 +962,18 @@ func (t *Tlistxattr) handle(cs *connState) message { } defer ref.DecRef() - xattrs, err := ref.file.ListXattr(t.Size) - if err != nil { + var xattrs map[string]struct{} + if err := ref.safelyRead(func() (err error) { + // Don't allow listxattr on files that have been deleted. + if ref.isDeleted() { + return syscall.EINVAL + } + xattrs, err = ref.file.ListXattr(t.Size) + return err + }); err != nil { return newErr(err) } + xattrList := make([]string, 0, len(xattrs)) for x := range xattrs { xattrList = append(xattrList, x) @@ -968,7 +989,13 @@ func (t *Tremovexattr) handle(cs *connState) message { } defer ref.DecRef() - if err := ref.file.RemoveXattr(t.Name); err != nil { + if err := ref.safelyWrite(func() error { + // Don't allow removexattr on files that have been deleted. + if ref.isDeleted() { + return syscall.EINVAL + } + return ref.file.RemoveXattr(t.Name) + }); err != nil { return newErr(err) } return &Rremovexattr{} |