diff options
Diffstat (limited to 'pkg/sentry/fs/tty')
-rw-r--r-- | pkg/sentry/fs/tty/BUILD | 2 | ||||
-rw-r--r-- | pkg/sentry/fs/tty/dir.go | 108 | ||||
-rw-r--r-- | pkg/sentry/fs/tty/inode.go | 145 | ||||
-rw-r--r-- | pkg/sentry/fs/tty/master.go | 23 | ||||
-rw-r--r-- | pkg/sentry/fs/tty/slave.go | 25 |
5 files changed, 37 insertions, 266 deletions
diff --git a/pkg/sentry/fs/tty/BUILD b/pkg/sentry/fs/tty/BUILD index 2b45069a6..011cb6955 100644 --- a/pkg/sentry/fs/tty/BUILD +++ b/pkg/sentry/fs/tty/BUILD @@ -7,7 +7,6 @@ go_library( srcs = [ "dir.go", "fs.go", - "inode.go", "line_discipline.go", "master.go", "queue.go", @@ -25,7 +24,6 @@ go_library( "//pkg/sentry/fs", "//pkg/sentry/fs/fsutil", "//pkg/sentry/kernel/auth", - "//pkg/sentry/kernel/time", "//pkg/sentry/socket/unix/transport", "//pkg/sentry/unimpl", "//pkg/sentry/usermem", diff --git a/pkg/sentry/fs/tty/dir.go b/pkg/sentry/fs/tty/dir.go index e32b05c1d..485cdb456 100644 --- a/pkg/sentry/fs/tty/dir.go +++ b/pkg/sentry/fs/tty/dir.go @@ -52,13 +52,17 @@ import ( // // +stateify savable type dirInodeOperations struct { - fsutil.DeprecatedFileOperations `state:"nosave"` - fsutil.InodeNotSocket `state:"nosave"` + fsutil.InodeGenericChecker `state:"nosave"` + fsutil.InodeNoExtendedAttributes `state:"nosave"` + fsutil.InodeNoopWriteOut `state:"nosave"` + fsutil.InodeNotMappable `state:"nosave"` fsutil.InodeNotRenameable `state:"nosave"` fsutil.InodeNotSymlink `state:"nosave"` - fsutil.InodeNoExtendedAttributes `state:"nosave"` - fsutil.NoMappable `state:"nosave"` - fsutil.NoopWriteOut `state:"nosave"` + fsutil.InodeNotSocket `state:"nosave"` + fsutil.InodeNotTruncatable `state:"nosave"` + fsutil.InodeVirtual `state:"nosave"` + + fsutil.InodeSimpleAttributes // msrc is the super block this directory is on. // @@ -68,9 +72,6 @@ type dirInodeOperations struct { // mu protects the fields below. mu sync.Mutex `state:"nosave"` - // attr contains the UnstableAttrs. - attr fsutil.InMemoryAttributes - // master is the master PTY inode. master *fs.Inode @@ -97,15 +98,10 @@ var _ fs.InodeOperations = (*dirInodeOperations)(nil) // newDir creates a new dir with a ptmx file and no terminals. func newDir(ctx context.Context, m *fs.MountSource) *fs.Inode { d := &dirInodeOperations{ - attr: fsutil.InMemoryAttributes{ - Unstable: fs.WithCurrentTime(ctx, fs.UnstableAttr{ - Owner: fs.RootOwner, - Perms: fs.FilePermsFromMode(0555), - }), - }, - msrc: m, - slaves: make(map[uint32]*fs.Inode), - dentryMap: fs.NewSortedDentryMap(nil), + InodeSimpleAttributes: fsutil.NewInodeSimpleAttributes(ctx, fs.RootOwner, fs.FilePermsFromMode(0555), linux.DEVPTS_SUPER_MAGIC), + msrc: m, + slaves: make(map[uint32]*fs.Inode), + dentryMap: fs.NewSortedDentryMap(nil), } // Linux devpts uses a default mode of 0000 for ptmx which can be // changed with the ptmxmode mount option. However, that default is not @@ -224,70 +220,6 @@ func (d *dirInodeOperations) GetFile(ctx context.Context, dirent *fs.Dirent, fla return fs.NewFile(ctx, dirent, flags, &dirFileOperations{di: d}), nil } -// UnstableAttr implements fs.InodeOperations.UnstableAttr. -func (d *dirInodeOperations) UnstableAttr(ctx context.Context, inode *fs.Inode) (fs.UnstableAttr, error) { - d.mu.Lock() - defer d.mu.Unlock() - return d.attr.Unstable, nil -} - -// Check implements fs.InodeOperations.Check. -func (d *dirInodeOperations) Check(ctx context.Context, inode *fs.Inode, p fs.PermMask) bool { - return fs.ContextCanAccessFile(ctx, inode, p) -} - -// SetPermissions implements fs.InodeOperations.SetPermissions. -func (d *dirInodeOperations) SetPermissions(ctx context.Context, inode *fs.Inode, p fs.FilePermissions) bool { - d.mu.Lock() - defer d.mu.Unlock() - return d.attr.SetPermissions(ctx, p) -} - -// SetOwner implements fs.InodeOperations.SetOwner. -func (d *dirInodeOperations) SetOwner(ctx context.Context, inode *fs.Inode, owner fs.FileOwner) error { - d.mu.Lock() - defer d.mu.Unlock() - return d.attr.SetOwner(ctx, owner) -} - -// SetTimestamps implements fs.InodeOperations.SetTimestamps. -func (d *dirInodeOperations) SetTimestamps(ctx context.Context, inode *fs.Inode, ts fs.TimeSpec) error { - d.mu.Lock() - defer d.mu.Unlock() - return d.attr.SetTimestamps(ctx, ts) -} - -// Truncate implements fs.InodeOperations.Truncate. -func (d *dirInodeOperations) Truncate(ctx context.Context, inode *fs.Inode, size int64) error { - return syserror.EINVAL -} - -// AddLink implements fs.InodeOperations.AddLink. -func (d *dirInodeOperations) AddLink() {} - -// DropLink implements fs.InodeOperations.DropLink. -func (d *dirInodeOperations) DropLink() {} - -// NotifyStatusChange implements fs.InodeOperations.NotifyStatusChange. -func (d *dirInodeOperations) NotifyStatusChange(ctx context.Context) { - d.mu.Lock() - defer d.mu.Unlock() - - d.attr.TouchStatusChangeTime(ctx) -} - -// IsVirtual implements fs.InodeOperations.IsVirtual. -func (d *dirInodeOperations) IsVirtual() bool { - return true -} - -// StatFS implements fs.InodeOperations.StatFS. -func (d *dirInodeOperations) StatFS(ctx context.Context) (fs.Info, error) { - return fs.Info{ - Type: linux.DEVPTS_SUPER_MAGIC, - }, nil -} - // allocateTerminal creates a new Terminal and installs a pts node for it. // // The caller must call DecRef when done with the returned Terminal. @@ -353,13 +285,13 @@ func (d *dirInodeOperations) masterClose(t *Terminal) { // // +stateify savable type dirFileOperations struct { - waiter.AlwaysReady `state:"nosave"` - fsutil.NoopRelease `state:"nosave"` - fsutil.GenericSeek `state:"nosave"` - fsutil.NoFsync `state:"nosave"` - fsutil.NoopFlush `state:"nosave"` - fsutil.NoMMap `state:"nosave"` - fsutil.NoIoctl `state:"nosave"` + waiter.AlwaysReady `state:"nosave"` + fsutil.FileNoopRelease `state:"nosave"` + fsutil.FileGenericSeek `state:"nosave"` + fsutil.FileNoFsync `state:"nosave"` + fsutil.FileNoopFlush `state:"nosave"` + fsutil.FileNoMMap `state:"nosave"` + fsutil.FileNoIoctl `state:"nosave"` // di is the inode operations. di *dirInodeOperations diff --git a/pkg/sentry/fs/tty/inode.go b/pkg/sentry/fs/tty/inode.go deleted file mode 100644 index d5d1caafc..000000000 --- a/pkg/sentry/fs/tty/inode.go +++ /dev/null @@ -1,145 +0,0 @@ -// Copyright 2018 Google LLC -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -package tty - -import ( - "sync" - - "gvisor.googlesource.com/gvisor/pkg/abi/linux" - "gvisor.googlesource.com/gvisor/pkg/sentry/context" - "gvisor.googlesource.com/gvisor/pkg/sentry/fs" - "gvisor.googlesource.com/gvisor/pkg/sentry/fs/fsutil" - ktime "gvisor.googlesource.com/gvisor/pkg/sentry/kernel/time" - "gvisor.googlesource.com/gvisor/pkg/syserror" -) - -// inodeOperations are the base fs.InodeOperations for master and slave Inodes. -// -// inodeOperations does not implement: -// -// * fs.InodeOperations.Release -// * fs.InodeOperations.GetFile -// -// +stateify savable -type inodeOperations struct { - fsutil.DeprecatedFileOperations `state:"nosave"` - fsutil.InodeNoExtendedAttributes `state:"nosave"` - fsutil.InodeNotDirectory `state:"nosave"` - fsutil.InodeNotRenameable `state:"nosave"` - fsutil.InodeNotSocket `state:"nosave"` - fsutil.InodeNotSymlink `state:"nosave"` - fsutil.NoMappable `state:"nosave"` - fsutil.NoopWriteOut `state:"nosave"` - - // mu protects the fields below. - mu sync.Mutex `state:"nosave"` - - // uattr is the inode's UnstableAttr. - uattr fs.UnstableAttr -} - -// UnstableAttr implements fs.InodeOperations.UnstableAttr. -func (i *inodeOperations) UnstableAttr(ctx context.Context, inode *fs.Inode) (fs.UnstableAttr, error) { - i.mu.Lock() - defer i.mu.Unlock() - return i.uattr, nil -} - -// Check implements fs.InodeOperations.Check. -func (i *inodeOperations) Check(ctx context.Context, inode *fs.Inode, p fs.PermMask) bool { - return fs.ContextCanAccessFile(ctx, inode, p) -} - -// SetPermissions implements fs.InodeOperations.SetPermissions -func (i *inodeOperations) SetPermissions(ctx context.Context, inode *fs.Inode, p fs.FilePermissions) bool { - i.mu.Lock() - defer i.mu.Unlock() - i.uattr.Perms = p - i.uattr.StatusChangeTime = ktime.NowFromContext(ctx) - return true -} - -// SetOwner implements fs.InodeOperations.SetOwner. -func (i *inodeOperations) SetOwner(ctx context.Context, inode *fs.Inode, owner fs.FileOwner) error { - i.mu.Lock() - defer i.mu.Unlock() - if owner.UID.Ok() { - i.uattr.Owner.UID = owner.UID - } - if owner.GID.Ok() { - i.uattr.Owner.GID = owner.GID - } - return nil -} - -// SetTimestamps implements fs.InodeOperations.SetTimestamps. -func (i *inodeOperations) SetTimestamps(ctx context.Context, inode *fs.Inode, ts fs.TimeSpec) error { - if ts.ATimeOmit && ts.MTimeOmit { - return nil - } - - i.mu.Lock() - defer i.mu.Unlock() - - now := ktime.NowFromContext(ctx) - if !ts.ATimeOmit { - if ts.ATime.IsZero() { - i.uattr.AccessTime = now - } else { - i.uattr.AccessTime = ts.ATime - } - } - if !ts.MTimeOmit { - if ts.MTime.IsZero() { - i.uattr.ModificationTime = now - } else { - i.uattr.ModificationTime = ts.MTime - } - } - i.uattr.StatusChangeTime = now - return nil -} - -// Truncate implements fs.InodeOperations.Truncate. -func (i *inodeOperations) Truncate(ctx context.Context, inode *fs.Inode, size int64) error { - return syserror.EINVAL -} - -// AddLink implements fs.InodeOperations.AddLink. -func (i *inodeOperations) AddLink() { -} - -// DropLink implements fs.InodeOperations.DropLink. -func (i *inodeOperations) DropLink() { -} - -// NotifyStatusChange implements fs.InodeOperations.NotifyStatusChange. -func (i *inodeOperations) NotifyStatusChange(ctx context.Context) { - i.mu.Lock() - defer i.mu.Unlock() - i.uattr.StatusChangeTime = ktime.NowFromContext(ctx) -} - -// IsVirtual implements fs.InodeOperations.IsVirtual. -func (i *inodeOperations) IsVirtual() bool { - return true -} - -// StatFS implements fs.InodeOperations.StatFS. -func (i *inodeOperations) StatFS(ctx context.Context) (fs.Info, error) { - return fs.Info{ - Type: linux.DEVPTS_SUPER_MAGIC, - }, nil -} diff --git a/pkg/sentry/fs/tty/master.go b/pkg/sentry/fs/tty/master.go index 00bec4c2c..b5e13ab36 100644 --- a/pkg/sentry/fs/tty/master.go +++ b/pkg/sentry/fs/tty/master.go @@ -31,7 +31,7 @@ import ( // // +stateify savable type masterInodeOperations struct { - inodeOperations + fsutil.SimpleFileInode // d is the containing dir. d *dirInodeOperations @@ -42,15 +42,8 @@ var _ fs.InodeOperations = (*masterInodeOperations)(nil) // newMasterInode creates an Inode for the master end of a terminal. func newMasterInode(ctx context.Context, d *dirInodeOperations, owner fs.FileOwner, p fs.FilePermissions) *fs.Inode { iops := &masterInodeOperations{ - inodeOperations: inodeOperations{ - uattr: fs.WithCurrentTime(ctx, fs.UnstableAttr{ - Owner: owner, - Perms: p, - Links: 1, - // Size and Blocks are always 0. - }), - }, - d: d, + SimpleFileInode: *fsutil.NewSimpleFileInode(ctx, owner, p, linux.DEVPTS_SUPER_MAGIC), + d: d, } return fs.NewInode(iops, d.msrc, fs.StableAttr{ @@ -102,11 +95,11 @@ func (mi *masterInodeOperations) GetFile(ctx context.Context, d *fs.Dirent, flag // // +stateify savable type masterFileOperations struct { - fsutil.PipeSeek `state:"nosave"` - fsutil.NotDirReaddir `state:"nosave"` - fsutil.NoFsync `state:"nosave"` - fsutil.NoopFlush `state:"nosave"` - fsutil.NoMMap `state:"nosave"` + fsutil.FilePipeSeek `state:"nosave"` + fsutil.FileNotDirReaddir `state:"nosave"` + fsutil.FileNoFsync `state:"nosave"` + fsutil.FileNoopFlush `state:"nosave"` + fsutil.FileNoMMap `state:"nosave"` // d is the containing dir. d *dirInodeOperations diff --git a/pkg/sentry/fs/tty/slave.go b/pkg/sentry/fs/tty/slave.go index a696fbb51..6dbce90b4 100644 --- a/pkg/sentry/fs/tty/slave.go +++ b/pkg/sentry/fs/tty/slave.go @@ -30,7 +30,7 @@ import ( // // +stateify savable type slaveInodeOperations struct { - inodeOperations + fsutil.SimpleFileInode // d is the containing dir. d *dirInodeOperations @@ -46,16 +46,9 @@ var _ fs.InodeOperations = (*slaveInodeOperations)(nil) // newSlaveInode takes ownership of t. func newSlaveInode(ctx context.Context, d *dirInodeOperations, t *Terminal, owner fs.FileOwner, p fs.FilePermissions) *fs.Inode { iops := &slaveInodeOperations{ - inodeOperations: inodeOperations{ - uattr: fs.WithCurrentTime(ctx, fs.UnstableAttr{ - Owner: owner, - Perms: p, - Links: 1, - // Size and Blocks are always 0. - }), - }, - d: d, - t: t, + SimpleFileInode: *fsutil.NewSimpleFileInode(ctx, owner, p, linux.DEVPTS_SUPER_MAGIC), + d: d, + t: t, } return fs.NewInode(iops, d.msrc, fs.StableAttr{ @@ -91,11 +84,11 @@ func (si *slaveInodeOperations) GetFile(ctx context.Context, d *fs.Dirent, flags // // +stateify savable type slaveFileOperations struct { - fsutil.PipeSeek `state:"nosave"` - fsutil.NotDirReaddir `state:"nosave"` - fsutil.NoFsync `state:"nosave"` - fsutil.NoopFlush `state:"nosave"` - fsutil.NoMMap `state:"nosave"` + fsutil.FilePipeSeek `state:"nosave"` + fsutil.FileNotDirReaddir `state:"nosave"` + fsutil.FileNoFsync `state:"nosave"` + fsutil.FileNoopFlush `state:"nosave"` + fsutil.FileNoMMap `state:"nosave"` // si is the inode operations. si *slaveInodeOperations |