diff options
Diffstat (limited to 'pkg/sentry/fs/gofer/path.go')
-rw-r--r-- | pkg/sentry/fs/gofer/path.go | 37 |
1 files changed, 26 insertions, 11 deletions
diff --git a/pkg/sentry/fs/gofer/path.go b/pkg/sentry/fs/gofer/path.go index bfeab3833..15e9863fb 100644 --- a/pkg/sentry/fs/gofer/path.go +++ b/pkg/sentry/fs/gofer/path.go @@ -57,7 +57,7 @@ func (i *inodeOperations) Lookup(ctx context.Context, dir *fs.Inode, name string } // Construct the Inode operations. - sattr, node := newInodeOperations(ctx, i.fileState.s, newFile, qids[0], mask, p9attr) + sattr, node := newInodeOperations(ctx, i.fileState.s, newFile, qids[0], mask, p9attr, false) // Construct a positive Dirent. return fs.NewDirent(fs.NewInode(node, dir.MountSource, sattr), name), nil @@ -113,7 +113,7 @@ func (i *inodeOperations) Create(ctx context.Context, dir *fs.Inode, name string } // Construct the InodeOperations. - sattr, iops := newInodeOperations(ctx, i.fileState.s, unopened, qid, mask, p9attr) + sattr, iops := newInodeOperations(ctx, i.fileState.s, unopened, qid, mask, p9attr, false) // Construct the positive Dirent. d := fs.NewDirent(fs.NewInode(iops, dir.MountSource, sattr), name) @@ -175,10 +175,10 @@ func (i *inodeOperations) CreateDirectory(ctx context.Context, dir *fs.Inode, s return nil } -// Bind implements InodeOperations. -func (i *inodeOperations) Bind(ctx context.Context, dir *fs.Inode, name string, ep unix.BoundEndpoint, perm fs.FilePermissions) error { +// Bind implements InodeOperations.Bind. +func (i *inodeOperations) Bind(ctx context.Context, dir *fs.Inode, name string, ep unix.BoundEndpoint, perm fs.FilePermissions) (*fs.Dirent, error) { if i.session().endpoints == nil { - return syscall.EOPNOTSUPP + return nil, syscall.EOPNOTSUPP } // Create replaces the directory fid with the newly created/opened @@ -186,7 +186,7 @@ func (i *inodeOperations) Bind(ctx context.Context, dir *fs.Inode, name string, // this node. _, newFile, err := i.fileState.file.walk(ctx, nil) if err != nil { - return err + return nil, err } // Stabilize the endpoint map while creation is in progress. @@ -198,7 +198,7 @@ func (i *inodeOperations) Bind(ctx context.Context, dir *fs.Inode, name string, owner := fs.FileOwnerFromContext(ctx) hostFile, err := newFile.create(ctx, name, p9.ReadWrite, p9.FileMode(perm.LinuxMode()), p9.UID(owner.UID), p9.GID(owner.GID)) if err != nil { - return err + return nil, err } // We're not going to use this file. hostFile.Close() @@ -206,10 +206,10 @@ func (i *inodeOperations) Bind(ctx context.Context, dir *fs.Inode, name string, i.touchModificationTime(ctx, dir) // Get the attributes of the file to create inode key. - qid, _, attr, err := getattr(ctx, newFile) + qid, mask, attr, err := getattr(ctx, newFile) if err != nil { newFile.close(ctx) - return err + return nil, err } key := device.MultiDeviceKey{ @@ -217,9 +217,24 @@ func (i *inodeOperations) Bind(ctx context.Context, dir *fs.Inode, name string, SecondaryDevice: i.session().connID, Inode: qid.Path, } - i.session().endpoints.add(key, ep) - return nil + // Create child dirent. + + // Get an unopened p9.File for the file we created so that it can be + // cloned and re-opened multiple times after creation. + _, unopened, err := i.fileState.file.walk(ctx, []string{name}) + if err != nil { + newFile.close(ctx) + return nil, err + } + + // Construct the InodeOperations. + sattr, iops := newInodeOperations(ctx, i.fileState.s, unopened, qid, mask, attr, true) + + // Construct the positive Dirent. + childDir := fs.NewDirent(fs.NewInode(iops, dir.MountSource, sattr), name) + i.session().endpoints.add(key, childDir, ep) + return childDir, nil } // CreateFifo implements fs.InodeOperations.CreateFifo. Gofer nodes do not support the |