diff options
Diffstat (limited to 'pkg/sentry')
26 files changed, 453 insertions, 396 deletions
diff --git a/pkg/sentry/arch/arch_amd64_abi_autogen_unsafe.go b/pkg/sentry/arch/arch_amd64_abi_autogen_unsafe.go index dd850b1b8..42cc106a1 100644 --- a/pkg/sentry/arch/arch_amd64_abi_autogen_unsafe.go +++ b/pkg/sentry/arch/arch_amd64_abi_autogen_unsafe.go @@ -36,7 +36,7 @@ func (s *SignalContext64) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (s *SignalContext64) MarshalBytes(dst []byte) { +func (s *SignalContext64) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint64(dst[:8], uint64(s.R8)) dst = dst[8:] hostarch.ByteOrder.PutUint64(dst[:8], uint64(s.R9)) @@ -85,8 +85,7 @@ func (s *SignalContext64) MarshalBytes(dst []byte) { dst = dst[8:] hostarch.ByteOrder.PutUint64(dst[:8], uint64(s.Trapno)) dst = dst[8:] - s.Oldmask.MarshalBytes(dst[:s.Oldmask.SizeBytes()]) - dst = dst[s.Oldmask.SizeBytes():] + dst = s.Oldmask.MarshalBytes(dst) hostarch.ByteOrder.PutUint64(dst[:8], uint64(s.Cr2)) dst = dst[8:] hostarch.ByteOrder.PutUint64(dst[:8], uint64(s.Fpstate)) @@ -95,10 +94,11 @@ func (s *SignalContext64) MarshalBytes(dst []byte) { hostarch.ByteOrder.PutUint64(dst[:8], uint64(s.Reserved[idx])) dst = dst[8:] } + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (s *SignalContext64) UnmarshalBytes(src []byte) { +func (s *SignalContext64) UnmarshalBytes(src []byte) []byte { s.R8 = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] s.R9 = uint64(hostarch.ByteOrder.Uint64(src[:8])) @@ -147,8 +147,7 @@ func (s *SignalContext64) UnmarshalBytes(src []byte) { src = src[8:] s.Trapno = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] - s.Oldmask.UnmarshalBytes(src[:s.Oldmask.SizeBytes()]) - src = src[s.Oldmask.SizeBytes():] + src = s.Oldmask.UnmarshalBytes(src) s.Cr2 = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] s.Fpstate = uint64(hostarch.ByteOrder.Uint64(src[:8])) @@ -157,6 +156,7 @@ func (s *SignalContext64) UnmarshalBytes(src []byte) { s.Reserved[idx] = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] } + return src } // Packed implements marshal.Marshallable.Packed. @@ -166,23 +166,25 @@ func (s *SignalContext64) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (s *SignalContext64) MarshalUnsafe(dst []byte) { +func (s *SignalContext64) MarshalUnsafe(dst []byte) []byte { if s.Oldmask.Packed() { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(s), uintptr(s.SizeBytes())) - } else { - // Type SignalContext64 doesn't have a packed layout in memory, fallback to MarshalBytes. - s.MarshalBytes(dst) + size := s.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(s), uintptr(size)) + return dst[size:] } + // Type SignalContext64 doesn't have a packed layout in memory, fallback to MarshalBytes. + return s.MarshalBytes(dst) } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (s *SignalContext64) UnmarshalUnsafe(src []byte) { +func (s *SignalContext64) UnmarshalUnsafe(src []byte) []byte { if s.Oldmask.Packed() { - gohacks.Memmove(unsafe.Pointer(s), unsafe.Pointer(&src[0]), uintptr(s.SizeBytes())) - } else { - // Type SignalContext64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. - s.UnmarshalBytes(src) + size := s.SizeBytes() + gohacks.Memmove(unsafe.Pointer(s), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } + // Type SignalContext64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. + return s.UnmarshalBytes(src) } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -275,31 +277,27 @@ func (u *UContext64) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (u *UContext64) MarshalBytes(dst []byte) { +func (u *UContext64) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint64(dst[:8], uint64(u.Flags)) dst = dst[8:] hostarch.ByteOrder.PutUint64(dst[:8], uint64(u.Link)) dst = dst[8:] - u.Stack.MarshalBytes(dst[:u.Stack.SizeBytes()]) - dst = dst[u.Stack.SizeBytes():] - u.MContext.MarshalBytes(dst[:u.MContext.SizeBytes()]) - dst = dst[u.MContext.SizeBytes():] - u.Sigset.MarshalBytes(dst[:u.Sigset.SizeBytes()]) - dst = dst[u.Sigset.SizeBytes():] + dst = u.Stack.MarshalBytes(dst) + dst = u.MContext.MarshalBytes(dst) + dst = u.Sigset.MarshalBytes(dst) + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (u *UContext64) UnmarshalBytes(src []byte) { +func (u *UContext64) UnmarshalBytes(src []byte) []byte { u.Flags = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] u.Link = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] - u.Stack.UnmarshalBytes(src[:u.Stack.SizeBytes()]) - src = src[u.Stack.SizeBytes():] - u.MContext.UnmarshalBytes(src[:u.MContext.SizeBytes()]) - src = src[u.MContext.SizeBytes():] - u.Sigset.UnmarshalBytes(src[:u.Sigset.SizeBytes()]) - src = src[u.Sigset.SizeBytes():] + src = u.Stack.UnmarshalBytes(src) + src = u.MContext.UnmarshalBytes(src) + src = u.Sigset.UnmarshalBytes(src) + return src } // Packed implements marshal.Marshallable.Packed. @@ -309,23 +307,25 @@ func (u *UContext64) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (u *UContext64) MarshalUnsafe(dst []byte) { +func (u *UContext64) MarshalUnsafe(dst []byte) []byte { if u.MContext.Packed() && u.Sigset.Packed() && u.Stack.Packed() { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(u), uintptr(u.SizeBytes())) - } else { - // Type UContext64 doesn't have a packed layout in memory, fallback to MarshalBytes. - u.MarshalBytes(dst) + size := u.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(u), uintptr(size)) + return dst[size:] } + // Type UContext64 doesn't have a packed layout in memory, fallback to MarshalBytes. + return u.MarshalBytes(dst) } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (u *UContext64) UnmarshalUnsafe(src []byte) { +func (u *UContext64) UnmarshalUnsafe(src []byte) []byte { if u.MContext.Packed() && u.Sigset.Packed() && u.Stack.Packed() { - gohacks.Memmove(unsafe.Pointer(u), unsafe.Pointer(&src[0]), uintptr(u.SizeBytes())) - } else { - // Type UContext64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. - u.UnmarshalBytes(src) + size := u.SizeBytes() + gohacks.Memmove(unsafe.Pointer(u), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } + // Type UContext64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. + return u.UnmarshalBytes(src) } // CopyOutN implements marshal.Marshallable.CopyOutN. diff --git a/pkg/sentry/arch/arch_arm64_abi_autogen_unsafe.go b/pkg/sentry/arch/arch_arm64_abi_autogen_unsafe.go index 52ca0b185..035134fa7 100644 --- a/pkg/sentry/arch/arch_arm64_abi_autogen_unsafe.go +++ b/pkg/sentry/arch/arch_arm64_abi_autogen_unsafe.go @@ -38,9 +38,8 @@ func (f *FpsimdContext) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (f *FpsimdContext) MarshalBytes(dst []byte) { - f.Head.MarshalBytes(dst[:f.Head.SizeBytes()]) - dst = dst[f.Head.SizeBytes():] +func (f *FpsimdContext) MarshalBytes(dst []byte) []byte { + dst = f.Head.MarshalBytes(dst) hostarch.ByteOrder.PutUint32(dst[:4], uint32(f.Fpsr)) dst = dst[4:] hostarch.ByteOrder.PutUint32(dst[:4], uint32(f.Fpcr)) @@ -49,12 +48,12 @@ func (f *FpsimdContext) MarshalBytes(dst []byte) { hostarch.ByteOrder.PutUint64(dst[:8], uint64(f.Vregs[idx])) dst = dst[8:] } + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (f *FpsimdContext) UnmarshalBytes(src []byte) { - f.Head.UnmarshalBytes(src[:f.Head.SizeBytes()]) - src = src[f.Head.SizeBytes():] +func (f *FpsimdContext) UnmarshalBytes(src []byte) []byte { + src = f.Head.UnmarshalBytes(src) f.Fpsr = uint32(hostarch.ByteOrder.Uint32(src[:4])) src = src[4:] f.Fpcr = uint32(hostarch.ByteOrder.Uint32(src[:4])) @@ -63,6 +62,7 @@ func (f *FpsimdContext) UnmarshalBytes(src []byte) { f.Vregs[idx] = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] } + return src } // Packed implements marshal.Marshallable.Packed. @@ -72,23 +72,25 @@ func (f *FpsimdContext) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (f *FpsimdContext) MarshalUnsafe(dst []byte) { +func (f *FpsimdContext) MarshalUnsafe(dst []byte) []byte { if f.Head.Packed() { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(f), uintptr(f.SizeBytes())) - } else { - // Type FpsimdContext doesn't have a packed layout in memory, fallback to MarshalBytes. - f.MarshalBytes(dst) + size := f.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(f), uintptr(size)) + return dst[size:] } + // Type FpsimdContext doesn't have a packed layout in memory, fallback to MarshalBytes. + return f.MarshalBytes(dst) } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (f *FpsimdContext) UnmarshalUnsafe(src []byte) { +func (f *FpsimdContext) UnmarshalUnsafe(src []byte) []byte { if f.Head.Packed() { - gohacks.Memmove(unsafe.Pointer(f), unsafe.Pointer(&src[0]), uintptr(f.SizeBytes())) - } else { - // Type FpsimdContext doesn't have a packed layout in memory, fallback to UnmarshalBytes. - f.UnmarshalBytes(src) + size := f.SizeBytes() + gohacks.Memmove(unsafe.Pointer(f), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } + // Type FpsimdContext doesn't have a packed layout in memory, fallback to UnmarshalBytes. + return f.UnmarshalBytes(src) } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -181,7 +183,7 @@ func (s *SignalContext64) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (s *SignalContext64) MarshalBytes(dst []byte) { +func (s *SignalContext64) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint64(dst[:8], uint64(s.FaultAddr)) dst = dst[8:] for idx := 0; idx < 31; idx++ { @@ -198,12 +200,12 @@ func (s *SignalContext64) MarshalBytes(dst []byte) { dst[0] = byte(s._pad[idx]) dst = dst[1:] } - s.Fpsimd64.MarshalBytes(dst[:s.Fpsimd64.SizeBytes()]) - dst = dst[s.Fpsimd64.SizeBytes():] + dst = s.Fpsimd64.MarshalBytes(dst) + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (s *SignalContext64) UnmarshalBytes(src []byte) { +func (s *SignalContext64) UnmarshalBytes(src []byte) []byte { s.FaultAddr = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] for idx := 0; idx < 31; idx++ { @@ -220,8 +222,8 @@ func (s *SignalContext64) UnmarshalBytes(src []byte) { s._pad[idx] = src[0] src = src[1:] } - s.Fpsimd64.UnmarshalBytes(src[:s.Fpsimd64.SizeBytes()]) - src = src[s.Fpsimd64.SizeBytes():] + src = s.Fpsimd64.UnmarshalBytes(src) + return src } // Packed implements marshal.Marshallable.Packed. @@ -231,23 +233,25 @@ func (s *SignalContext64) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (s *SignalContext64) MarshalUnsafe(dst []byte) { +func (s *SignalContext64) MarshalUnsafe(dst []byte) []byte { if s.Fpsimd64.Packed() { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(s), uintptr(s.SizeBytes())) - } else { - // Type SignalContext64 doesn't have a packed layout in memory, fallback to MarshalBytes. - s.MarshalBytes(dst) + size := s.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(s), uintptr(size)) + return dst[size:] } + // Type SignalContext64 doesn't have a packed layout in memory, fallback to MarshalBytes. + return s.MarshalBytes(dst) } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (s *SignalContext64) UnmarshalUnsafe(src []byte) { +func (s *SignalContext64) UnmarshalUnsafe(src []byte) []byte { if s.Fpsimd64.Packed() { - gohacks.Memmove(unsafe.Pointer(s), unsafe.Pointer(&src[0]), uintptr(s.SizeBytes())) - } else { - // Type SignalContext64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. - s.UnmarshalBytes(src) + size := s.SizeBytes() + gohacks.Memmove(unsafe.Pointer(s), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } + // Type SignalContext64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. + return s.UnmarshalBytes(src) } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -342,15 +346,13 @@ func (u *UContext64) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (u *UContext64) MarshalBytes(dst []byte) { +func (u *UContext64) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint64(dst[:8], uint64(u.Flags)) dst = dst[8:] hostarch.ByteOrder.PutUint64(dst[:8], uint64(u.Link)) dst = dst[8:] - u.Stack.MarshalBytes(dst[:u.Stack.SizeBytes()]) - dst = dst[u.Stack.SizeBytes():] - u.Sigset.MarshalBytes(dst[:u.Sigset.SizeBytes()]) - dst = dst[u.Sigset.SizeBytes():] + dst = u.Stack.MarshalBytes(dst) + dst = u.Sigset.MarshalBytes(dst) for idx := 0; idx < 120; idx++ { dst[0] = byte(u._pad[idx]) dst = dst[1:] @@ -359,20 +361,18 @@ func (u *UContext64) MarshalBytes(dst []byte) { dst[0] = byte(u._pad2[idx]) dst = dst[1:] } - u.MContext.MarshalBytes(dst[:u.MContext.SizeBytes()]) - dst = dst[u.MContext.SizeBytes():] + dst = u.MContext.MarshalBytes(dst) + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (u *UContext64) UnmarshalBytes(src []byte) { +func (u *UContext64) UnmarshalBytes(src []byte) []byte { u.Flags = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] u.Link = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] - u.Stack.UnmarshalBytes(src[:u.Stack.SizeBytes()]) - src = src[u.Stack.SizeBytes():] - u.Sigset.UnmarshalBytes(src[:u.Sigset.SizeBytes()]) - src = src[u.Sigset.SizeBytes():] + src = u.Stack.UnmarshalBytes(src) + src = u.Sigset.UnmarshalBytes(src) for idx := 0; idx < 120; idx++ { u._pad[idx] = src[0] src = src[1:] @@ -381,8 +381,8 @@ func (u *UContext64) UnmarshalBytes(src []byte) { u._pad2[idx] = src[0] src = src[1:] } - u.MContext.UnmarshalBytes(src[:u.MContext.SizeBytes()]) - src = src[u.MContext.SizeBytes():] + src = u.MContext.UnmarshalBytes(src) + return src } // Packed implements marshal.Marshallable.Packed. @@ -392,23 +392,25 @@ func (u *UContext64) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (u *UContext64) MarshalUnsafe(dst []byte) { +func (u *UContext64) MarshalUnsafe(dst []byte) []byte { if u.MContext.Packed() && u.Sigset.Packed() && u.Stack.Packed() { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(u), uintptr(u.SizeBytes())) - } else { - // Type UContext64 doesn't have a packed layout in memory, fallback to MarshalBytes. - u.MarshalBytes(dst) + size := u.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(u), uintptr(size)) + return dst[size:] } + // Type UContext64 doesn't have a packed layout in memory, fallback to MarshalBytes. + return u.MarshalBytes(dst) } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (u *UContext64) UnmarshalUnsafe(src []byte) { +func (u *UContext64) UnmarshalUnsafe(src []byte) []byte { if u.MContext.Packed() && u.Sigset.Packed() && u.Stack.Packed() { - gohacks.Memmove(unsafe.Pointer(u), unsafe.Pointer(&src[0]), uintptr(u.SizeBytes())) - } else { - // Type UContext64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. - u.UnmarshalBytes(src) + size := u.SizeBytes() + gohacks.Memmove(unsafe.Pointer(u), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } + // Type UContext64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. + return u.UnmarshalBytes(src) } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -498,19 +500,21 @@ func (a *aarch64Ctx) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (a *aarch64Ctx) MarshalBytes(dst []byte) { +func (a *aarch64Ctx) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint32(dst[:4], uint32(a.Magic)) dst = dst[4:] hostarch.ByteOrder.PutUint32(dst[:4], uint32(a.Size)) dst = dst[4:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (a *aarch64Ctx) UnmarshalBytes(src []byte) { +func (a *aarch64Ctx) UnmarshalBytes(src []byte) []byte { a.Magic = uint32(hostarch.ByteOrder.Uint32(src[:4])) src = src[4:] a.Size = uint32(hostarch.ByteOrder.Uint32(src[:4])) src = src[4:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -520,13 +524,17 @@ func (a *aarch64Ctx) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (a *aarch64Ctx) MarshalUnsafe(dst []byte) { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(a), uintptr(a.SizeBytes())) +func (a *aarch64Ctx) MarshalUnsafe(dst []byte) []byte { + size := a.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(a), uintptr(size)) + return dst[size:] } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (a *aarch64Ctx) UnmarshalUnsafe(src []byte) { - gohacks.Memmove(unsafe.Pointer(a), unsafe.Pointer(&src[0]), uintptr(a.SizeBytes())) +func (a *aarch64Ctx) UnmarshalUnsafe(src []byte) []byte { + size := a.SizeBytes() + gohacks.Memmove(unsafe.Pointer(a), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } // CopyOutN implements marshal.Marshallable.CopyOutN. diff --git a/pkg/sentry/fsimpl/fuse/fusefs.go b/pkg/sentry/fsimpl/fuse/fusefs.go index af16098d2..00b520c31 100644 --- a/pkg/sentry/fsimpl/fuse/fusefs.go +++ b/pkg/sentry/fsimpl/fuse/fusefs.go @@ -489,7 +489,7 @@ func (i *inode) Open(ctx context.Context, rp *vfs.ResolvingPath, d *kernfs.Dentr // Lookup implements kernfs.Inode.Lookup. func (i *inode) Lookup(ctx context.Context, name string) (kernfs.Inode, error) { - in := linux.FUSELookupIn{Name: name} + in := linux.FUSELookupIn{Name: linux.CString(name)} return i.newEntry(ctx, name, 0, linux.FUSE_LOOKUP, &in) } @@ -520,7 +520,7 @@ func (i *inode) NewFile(ctx context.Context, name string, opts vfs.OpenOptions) Mode: uint32(opts.Mode) | linux.S_IFREG, Umask: uint32(kernelTask.FSContext().Umask()), }, - Name: name, + Name: linux.CString(name), } return i.newEntry(ctx, name, linux.S_IFREG, linux.FUSE_CREATE, &in) } @@ -533,7 +533,7 @@ func (i *inode) NewNode(ctx context.Context, name string, opts vfs.MknodOptions) Rdev: linux.MakeDeviceID(uint16(opts.DevMajor), opts.DevMinor), Umask: uint32(kernel.TaskFromContext(ctx).FSContext().Umask()), }, - Name: name, + Name: linux.CString(name), } return i.newEntry(ctx, name, opts.Mode.FileType(), linux.FUSE_MKNOD, &in) } @@ -541,8 +541,8 @@ func (i *inode) NewNode(ctx context.Context, name string, opts vfs.MknodOptions) // NewSymlink implements kernfs.Inode.NewSymlink. func (i *inode) NewSymlink(ctx context.Context, name, target string) (kernfs.Inode, error) { in := linux.FUSESymLinkIn{ - Name: name, - Target: target, + Name: linux.CString(name), + Target: linux.CString(target), } return i.newEntry(ctx, name, linux.S_IFLNK, linux.FUSE_SYMLINK, &in) } @@ -554,7 +554,7 @@ func (i *inode) Unlink(ctx context.Context, name string, child kernfs.Inode) err log.Warningf("fusefs.Inode.newEntry: couldn't get kernel task from context", i.nodeID) return linuxerr.EINVAL } - in := linux.FUSEUnlinkIn{Name: name} + in := linux.FUSEUnlinkIn{Name: linux.CString(name)} req := i.fs.conn.NewRequest(auth.CredentialsFromContext(ctx), uint32(kernelTask.ThreadID()), i.nodeID, linux.FUSE_UNLINK, &in) res, err := i.fs.conn.Call(kernelTask, req) if err != nil { @@ -571,7 +571,7 @@ func (i *inode) NewDir(ctx context.Context, name string, opts vfs.MkdirOptions) Mode: uint32(opts.Mode), Umask: uint32(kernel.TaskFromContext(ctx).FSContext().Umask()), }, - Name: name, + Name: linux.CString(name), } return i.newEntry(ctx, name, linux.S_IFDIR, linux.FUSE_MKDIR, &in) } @@ -581,7 +581,7 @@ func (i *inode) RmDir(ctx context.Context, name string, child kernfs.Inode) erro fusefs := i.fs task, creds := kernel.TaskFromContext(ctx), auth.CredentialsFromContext(ctx) - in := linux.FUSERmDirIn{Name: name} + in := linux.FUSERmDirIn{Name: linux.CString(name)} req := fusefs.conn.NewRequest(creds, uint32(task.ThreadID()), i.nodeID, linux.FUSE_RMDIR, &in) res, err := i.fs.conn.Call(task, req) if err != nil { diff --git a/pkg/sentry/fsimpl/fuse/request_response.go b/pkg/sentry/fsimpl/fuse/request_response.go index 8a72489fa..ec76ec2a4 100644 --- a/pkg/sentry/fsimpl/fuse/request_response.go +++ b/pkg/sentry/fsimpl/fuse/request_response.go @@ -41,7 +41,7 @@ type fuseInitRes struct { } // UnmarshalBytes deserializes src to the initOut attribute in a fuseInitRes. -func (r *fuseInitRes) UnmarshalBytes(src []byte) { +func (r *fuseInitRes) UnmarshalBytes(src []byte) []byte { out := &r.initOut // Introduced before FUSE kernel version 7.13. @@ -70,7 +70,7 @@ func (r *fuseInitRes) UnmarshalBytes(src []byte) { out.MaxPages = uint16(hostarch.ByteOrder.Uint16(src[:2])) src = src[2:] } - _ = src // Remove unused warning. + return src } // SizeBytes is the size of the payload of the FUSE_INIT response. diff --git a/pkg/sentry/kernel/auth/auth_abi_autogen_unsafe.go b/pkg/sentry/kernel/auth/auth_abi_autogen_unsafe.go index 393dcea8c..770e66602 100644 --- a/pkg/sentry/kernel/auth/auth_abi_autogen_unsafe.go +++ b/pkg/sentry/kernel/auth/auth_abi_autogen_unsafe.go @@ -23,13 +23,15 @@ func (gid *GID) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (gid *GID) MarshalBytes(dst []byte) { +func (gid *GID) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint32(dst[:4], uint32(*gid)) + return dst[4:] } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (gid *GID) UnmarshalBytes(src []byte) { +func (gid *GID) UnmarshalBytes(src []byte) []byte { *gid = GID(uint32(hostarch.ByteOrder.Uint32(src[:4]))) + return src[4:] } // Packed implements marshal.Marshallable.Packed. @@ -40,13 +42,17 @@ func (gid *GID) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (gid *GID) MarshalUnsafe(dst []byte) { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(gid), uintptr(gid.SizeBytes())) +func (gid *GID) MarshalUnsafe(dst []byte) []byte { + size := gid.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(gid), uintptr(size)) + return dst[size:] } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (gid *GID) UnmarshalUnsafe(src []byte) { - gohacks.Memmove(unsafe.Pointer(gid), unsafe.Pointer(&src[0]), uintptr(gid.SizeBytes())) +func (gid *GID) UnmarshalUnsafe(src []byte) []byte { + size := gid.SizeBytes() + gohacks.Memmove(unsafe.Pointer(gid), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -190,13 +196,15 @@ func (uid *UID) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (uid *UID) MarshalBytes(dst []byte) { +func (uid *UID) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint32(dst[:4], uint32(*uid)) + return dst[4:] } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (uid *UID) UnmarshalBytes(src []byte) { +func (uid *UID) UnmarshalBytes(src []byte) []byte { *uid = UID(uint32(hostarch.ByteOrder.Uint32(src[:4]))) + return src[4:] } // Packed implements marshal.Marshallable.Packed. @@ -207,13 +215,17 @@ func (uid *UID) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (uid *UID) MarshalUnsafe(dst []byte) { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(uid), uintptr(uid.SizeBytes())) +func (uid *UID) MarshalUnsafe(dst []byte) []byte { + size := uid.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(uid), uintptr(size)) + return dst[size:] } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (uid *UID) UnmarshalUnsafe(src []byte) { - gohacks.Memmove(unsafe.Pointer(uid), unsafe.Pointer(&src[0]), uintptr(uid.SizeBytes())) +func (uid *UID) UnmarshalUnsafe(src []byte) []byte { + size := uid.SizeBytes() + gohacks.Memmove(unsafe.Pointer(uid), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } // CopyOutN implements marshal.Marshallable.CopyOutN. diff --git a/pkg/sentry/kernel/kernel_abi_autogen_unsafe.go b/pkg/sentry/kernel/kernel_abi_autogen_unsafe.go index 83ed0f8ac..fe5ee7463 100644 --- a/pkg/sentry/kernel/kernel_abi_autogen_unsafe.go +++ b/pkg/sentry/kernel/kernel_abi_autogen_unsafe.go @@ -23,13 +23,15 @@ func (tid *ThreadID) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (tid *ThreadID) MarshalBytes(dst []byte) { +func (tid *ThreadID) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint32(dst[:4], uint32(*tid)) + return dst[4:] } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (tid *ThreadID) UnmarshalBytes(src []byte) { +func (tid *ThreadID) UnmarshalBytes(src []byte) []byte { *tid = ThreadID(int32(hostarch.ByteOrder.Uint32(src[:4]))) + return src[4:] } // Packed implements marshal.Marshallable.Packed. @@ -40,13 +42,17 @@ func (tid *ThreadID) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (tid *ThreadID) MarshalUnsafe(dst []byte) { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(tid), uintptr(tid.SizeBytes())) +func (tid *ThreadID) MarshalUnsafe(dst []byte) []byte { + size := tid.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(tid), uintptr(size)) + return dst[size:] } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (tid *ThreadID) UnmarshalUnsafe(src []byte) { - gohacks.Memmove(unsafe.Pointer(tid), unsafe.Pointer(&src[0]), uintptr(tid.SizeBytes())) +func (tid *ThreadID) UnmarshalUnsafe(src []byte) []byte { + size := tid.SizeBytes() + gohacks.Memmove(unsafe.Pointer(tid), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -111,7 +117,7 @@ func (v *vdsoParams) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (v *vdsoParams) MarshalBytes(dst []byte) { +func (v *vdsoParams) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint64(dst[:8], uint64(v.monotonicReady)) dst = dst[8:] hostarch.ByteOrder.PutUint64(dst[:8], uint64(v.monotonicBaseCycles)) @@ -128,10 +134,11 @@ func (v *vdsoParams) MarshalBytes(dst []byte) { dst = dst[8:] hostarch.ByteOrder.PutUint64(dst[:8], uint64(v.realtimeFrequency)) dst = dst[8:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (v *vdsoParams) UnmarshalBytes(src []byte) { +func (v *vdsoParams) UnmarshalBytes(src []byte) []byte { v.monotonicReady = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] v.monotonicBaseCycles = int64(hostarch.ByteOrder.Uint64(src[:8])) @@ -148,6 +155,7 @@ func (v *vdsoParams) UnmarshalBytes(src []byte) { src = src[8:] v.realtimeFrequency = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -157,13 +165,17 @@ func (v *vdsoParams) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (v *vdsoParams) MarshalUnsafe(dst []byte) { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(v), uintptr(v.SizeBytes())) +func (v *vdsoParams) MarshalUnsafe(dst []byte) []byte { + size := v.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(v), uintptr(size)) + return dst[size:] } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (v *vdsoParams) UnmarshalUnsafe(src []byte) { - gohacks.Memmove(unsafe.Pointer(v), unsafe.Pointer(&src[0]), uintptr(v.SizeBytes())) +func (v *vdsoParams) UnmarshalUnsafe(src []byte) []byte { + size := v.SizeBytes() + gohacks.Memmove(unsafe.Pointer(v), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } // CopyOutN implements marshal.Marshallable.CopyOutN. diff --git a/pkg/sentry/loader/elf.go b/pkg/sentry/loader/elf.go index fb213d109..09b148164 100644 --- a/pkg/sentry/loader/elf.go +++ b/pkg/sentry/loader/elf.go @@ -212,8 +212,7 @@ func parseHeader(ctx context.Context, f fullReader) (elfInfo, error) { phdrs := make([]elf.ProgHeader, hdr.Phnum) for i := range phdrs { var prog64 linux.ElfProg64 - prog64.UnmarshalUnsafe(phdrBuf[:prog64Size]) - phdrBuf = phdrBuf[prog64Size:] + phdrBuf = prog64.UnmarshalUnsafe(phdrBuf) phdrs[i] = elf.ProgHeader{ Type: elf.ProgType(prog64.Type), Flags: elf.ProgFlag(prog64.Flags), diff --git a/pkg/sentry/socket/control/control.go b/pkg/sentry/socket/control/control.go index 6077b2150..4b036b323 100644 --- a/pkg/sentry/socket/control/control.go +++ b/pkg/sentry/socket/control/control.go @@ -17,6 +17,8 @@ package control import ( + "time" + "gvisor.dev/gvisor/pkg/abi/linux" "gvisor.dev/gvisor/pkg/bits" "gvisor.dev/gvisor/pkg/context" @@ -29,7 +31,6 @@ import ( "gvisor.dev/gvisor/pkg/sentry/kernel/auth" "gvisor.dev/gvisor/pkg/sentry/socket" "gvisor.dev/gvisor/pkg/sentry/socket/unix/transport" - "time" ) // SCMCredentials represents a SCM_CREDENTIALS socket control message. @@ -63,10 +64,10 @@ type RightsFiles []*fs.File // NewSCMRights creates a new SCM_RIGHTS socket control message representation // using local sentry FDs. -func NewSCMRights(t *kernel.Task, fds []int32) (SCMRights, error) { +func NewSCMRights(t *kernel.Task, fds []primitive.Int32) (SCMRights, error) { files := make(RightsFiles, 0, len(fds)) for _, fd := range fds { - file := t.GetFile(fd) + file := t.GetFile(int32(fd)) if file == nil { files.Release(t) return nil, linuxerr.EBADF @@ -486,26 +487,25 @@ func CmsgsSpace(t *kernel.Task, cmsgs socket.ControlMessages) int { func Parse(t *kernel.Task, socketOrEndpoint interface{}, buf []byte, width uint) (socket.ControlMessages, error) { var ( cmsgs socket.ControlMessages - fds linux.ControlMessageRights + fds []primitive.Int32 ) - for i := 0; i < len(buf); { - if i+linux.SizeOfControlMessageHeader > len(buf) { + for len(buf) > 0 { + if linux.SizeOfControlMessageHeader > len(buf) { return cmsgs, linuxerr.EINVAL } var h linux.ControlMessageHeader - h.UnmarshalUnsafe(buf[i : i+linux.SizeOfControlMessageHeader]) + buf = h.UnmarshalUnsafe(buf) if h.Length < uint64(linux.SizeOfControlMessageHeader) { return socket.ControlMessages{}, linuxerr.EINVAL } - if h.Length > uint64(len(buf)-i) { - return socket.ControlMessages{}, linuxerr.EINVAL - } - i += linux.SizeOfControlMessageHeader length := int(h.Length) - linux.SizeOfControlMessageHeader + if length > len(buf) { + return socket.ControlMessages{}, linuxerr.EINVAL + } switch h.Level { case linux.SOL_SOCKET: @@ -518,11 +518,9 @@ func Parse(t *kernel.Task, socketOrEndpoint interface{}, buf []byte, width uint) return socket.ControlMessages{}, linuxerr.EINVAL } - for j := i; j < i+rightsSize; j += linux.SizeOfControlMessageRight { - fds = append(fds, int32(hostarch.ByteOrder.Uint32(buf[j:j+linux.SizeOfControlMessageRight]))) - } - - i += bits.AlignUp(length, width) + curFDs := make([]primitive.Int32, numRights) + primitive.UnmarshalUnsafeInt32Slice(curFDs, buf[:rightsSize]) + fds = append(fds, curFDs...) case linux.SCM_CREDENTIALS: if length < linux.SizeOfControlMessageCredentials { @@ -530,23 +528,21 @@ func Parse(t *kernel.Task, socketOrEndpoint interface{}, buf []byte, width uint) } var creds linux.ControlMessageCredentials - creds.UnmarshalUnsafe(buf[i : i+linux.SizeOfControlMessageCredentials]) + creds.UnmarshalUnsafe(buf) scmCreds, err := NewSCMCredentials(t, creds) if err != nil { return socket.ControlMessages{}, err } cmsgs.Unix.Credentials = scmCreds - i += bits.AlignUp(length, width) case linux.SO_TIMESTAMP: if length < linux.SizeOfTimeval { return socket.ControlMessages{}, linuxerr.EINVAL } var ts linux.Timeval - ts.UnmarshalUnsafe(buf[i : i+linux.SizeOfTimeval]) + ts.UnmarshalUnsafe(buf) cmsgs.IP.Timestamp = ts.ToTime() cmsgs.IP.HasTimestamp = true - i += bits.AlignUp(length, width) default: // Unknown message type. @@ -560,9 +556,8 @@ func Parse(t *kernel.Task, socketOrEndpoint interface{}, buf []byte, width uint) } cmsgs.IP.HasTOS = true var tos primitive.Uint8 - tos.UnmarshalUnsafe(buf[i : i+linux.SizeOfControlMessageTOS]) + tos.UnmarshalUnsafe(buf) cmsgs.IP.TOS = uint8(tos) - i += bits.AlignUp(length, width) case linux.IP_PKTINFO: if length < linux.SizeOfControlMessageIPPacketInfo { @@ -571,19 +566,16 @@ func Parse(t *kernel.Task, socketOrEndpoint interface{}, buf []byte, width uint) cmsgs.IP.HasIPPacketInfo = true var packetInfo linux.ControlMessageIPPacketInfo - packetInfo.UnmarshalUnsafe(buf[i : i+linux.SizeOfControlMessageIPPacketInfo]) - + packetInfo.UnmarshalUnsafe(buf) cmsgs.IP.PacketInfo = packetInfo - i += bits.AlignUp(length, width) case linux.IP_RECVORIGDSTADDR: var addr linux.SockAddrInet if length < addr.SizeBytes() { return socket.ControlMessages{}, linuxerr.EINVAL } - addr.UnmarshalUnsafe(buf[i : i+addr.SizeBytes()]) + addr.UnmarshalUnsafe(buf) cmsgs.IP.OriginalDstAddress = &addr - i += bits.AlignUp(length, width) case linux.IP_RECVERR: var errCmsg linux.SockErrCMsgIPv4 @@ -591,9 +583,8 @@ func Parse(t *kernel.Task, socketOrEndpoint interface{}, buf []byte, width uint) return socket.ControlMessages{}, linuxerr.EINVAL } - errCmsg.UnmarshalBytes(buf[i : i+errCmsg.SizeBytes()]) + errCmsg.UnmarshalBytes(buf) cmsgs.IP.SockErr = &errCmsg - i += bits.AlignUp(length, width) default: return socket.ControlMessages{}, linuxerr.EINVAL @@ -606,18 +597,16 @@ func Parse(t *kernel.Task, socketOrEndpoint interface{}, buf []byte, width uint) } cmsgs.IP.HasTClass = true var tclass primitive.Uint32 - tclass.UnmarshalUnsafe(buf[i : i+linux.SizeOfControlMessageTClass]) + tclass.UnmarshalUnsafe(buf) cmsgs.IP.TClass = uint32(tclass) - i += bits.AlignUp(length, width) case linux.IPV6_RECVORIGDSTADDR: var addr linux.SockAddrInet6 if length < addr.SizeBytes() { return socket.ControlMessages{}, linuxerr.EINVAL } - addr.UnmarshalUnsafe(buf[i : i+addr.SizeBytes()]) + addr.UnmarshalUnsafe(buf) cmsgs.IP.OriginalDstAddress = &addr - i += bits.AlignUp(length, width) case linux.IPV6_RECVERR: var errCmsg linux.SockErrCMsgIPv6 @@ -625,9 +614,8 @@ func Parse(t *kernel.Task, socketOrEndpoint interface{}, buf []byte, width uint) return socket.ControlMessages{}, linuxerr.EINVAL } - errCmsg.UnmarshalBytes(buf[i : i+errCmsg.SizeBytes()]) + errCmsg.UnmarshalBytes(buf) cmsgs.IP.SockErr = &errCmsg - i += bits.AlignUp(length, width) default: return socket.ControlMessages{}, linuxerr.EINVAL @@ -635,6 +623,11 @@ func Parse(t *kernel.Task, socketOrEndpoint interface{}, buf []byte, width uint) default: return socket.ControlMessages{}, linuxerr.EINVAL } + if shift := bits.AlignUp(length, width); shift > len(buf) { + buf = buf[:0] + } else { + buf = buf[shift:] + } } if cmsgs.Unix.Credentials == nil { diff --git a/pkg/sentry/socket/control/control_vfs2.go b/pkg/sentry/socket/control/control_vfs2.go index 0a989cbeb..a638cb955 100644 --- a/pkg/sentry/socket/control/control_vfs2.go +++ b/pkg/sentry/socket/control/control_vfs2.go @@ -18,6 +18,7 @@ import ( "gvisor.dev/gvisor/pkg/abi/linux" "gvisor.dev/gvisor/pkg/context" "gvisor.dev/gvisor/pkg/errors/linuxerr" + "gvisor.dev/gvisor/pkg/marshal/primitive" "gvisor.dev/gvisor/pkg/sentry/kernel" "gvisor.dev/gvisor/pkg/sentry/socket/unix/transport" "gvisor.dev/gvisor/pkg/sentry/vfs" @@ -45,10 +46,10 @@ type RightsFilesVFS2 []*vfs.FileDescription // NewSCMRightsVFS2 creates a new SCM_RIGHTS socket control message // representation using local sentry FDs. -func NewSCMRightsVFS2(t *kernel.Task, fds []int32) (SCMRightsVFS2, error) { +func NewSCMRightsVFS2(t *kernel.Task, fds []primitive.Int32) (SCMRightsVFS2, error) { files := make(RightsFilesVFS2, 0, len(fds)) for _, fd := range fds { - file := t.GetFileVFS2(fd) + file := t.GetFileVFS2(int32(fd)) if file == nil { files.Release(t) return nil, linuxerr.EBADF diff --git a/pkg/sentry/socket/hostinet/socket.go b/pkg/sentry/socket/hostinet/socket.go index 6e2318f75..a31f3ebec 100644 --- a/pkg/sentry/socket/hostinet/socket.go +++ b/pkg/sentry/socket/hostinet/socket.go @@ -578,7 +578,7 @@ func parseUnixControlMessages(unixControlMessages []unix.SocketControlMessage) s case linux.SO_TIMESTAMP: controlMessages.IP.HasTimestamp = true ts := linux.Timeval{} - ts.UnmarshalUnsafe(unixCmsg.Data[:linux.SizeOfTimeval]) + ts.UnmarshalUnsafe(unixCmsg.Data) controlMessages.IP.Timestamp = ts.ToTime() } @@ -587,18 +587,18 @@ func parseUnixControlMessages(unixControlMessages []unix.SocketControlMessage) s case linux.IP_TOS: controlMessages.IP.HasTOS = true var tos primitive.Uint8 - tos.UnmarshalUnsafe(unixCmsg.Data[:tos.SizeBytes()]) + tos.UnmarshalUnsafe(unixCmsg.Data) controlMessages.IP.TOS = uint8(tos) case linux.IP_PKTINFO: controlMessages.IP.HasIPPacketInfo = true var packetInfo linux.ControlMessageIPPacketInfo - packetInfo.UnmarshalUnsafe(unixCmsg.Data[:packetInfo.SizeBytes()]) + packetInfo.UnmarshalUnsafe(unixCmsg.Data) controlMessages.IP.PacketInfo = packetInfo case linux.IP_RECVORIGDSTADDR: var addr linux.SockAddrInet - addr.UnmarshalUnsafe(unixCmsg.Data[:addr.SizeBytes()]) + addr.UnmarshalUnsafe(unixCmsg.Data) controlMessages.IP.OriginalDstAddress = &addr case unix.IP_RECVERR: @@ -612,12 +612,12 @@ func parseUnixControlMessages(unixControlMessages []unix.SocketControlMessage) s case linux.IPV6_TCLASS: controlMessages.IP.HasTClass = true var tclass primitive.Uint32 - tclass.UnmarshalUnsafe(unixCmsg.Data[:tclass.SizeBytes()]) + tclass.UnmarshalUnsafe(unixCmsg.Data) controlMessages.IP.TClass = uint32(tclass) case linux.IPV6_RECVORIGDSTADDR: var addr linux.SockAddrInet6 - addr.UnmarshalUnsafe(unixCmsg.Data[:addr.SizeBytes()]) + addr.UnmarshalUnsafe(unixCmsg.Data) controlMessages.IP.OriginalDstAddress = &addr case unix.IPV6_RECVERR: @@ -631,7 +631,7 @@ func parseUnixControlMessages(unixControlMessages []unix.SocketControlMessage) s case linux.TCP_INQ: controlMessages.IP.HasInq = true var inq primitive.Int32 - inq.UnmarshalUnsafe(unixCmsg.Data[:linux.SizeOfControlMessageInq]) + inq.UnmarshalUnsafe(unixCmsg.Data) controlMessages.IP.Inq = int32(inq) } } diff --git a/pkg/sentry/socket/hostinet/stack.go b/pkg/sentry/socket/hostinet/stack.go index 61111ac6c..c84ab3fb7 100644 --- a/pkg/sentry/socket/hostinet/stack.go +++ b/pkg/sentry/socket/hostinet/stack.go @@ -138,7 +138,7 @@ func ExtractHostInterfaces(links []syscall.NetlinkMessage, addrs []syscall.Netli return fmt.Errorf("RTM_GETLINK returned RTM_NEWLINK message with invalid data length (%d bytes, expected at least %d bytes)", len(link.Data), unix.SizeofIfInfomsg) } var ifinfo linux.InterfaceInfoMessage - ifinfo.UnmarshalUnsafe(link.Data[:ifinfo.SizeBytes()]) + ifinfo.UnmarshalUnsafe(link.Data) inetIF := inet.Interface{ DeviceType: ifinfo.Type, Flags: ifinfo.Flags, @@ -169,7 +169,7 @@ func ExtractHostInterfaces(links []syscall.NetlinkMessage, addrs []syscall.Netli return fmt.Errorf("RTM_GETADDR returned RTM_NEWADDR message with invalid data length (%d bytes, expected at least %d bytes)", len(addr.Data), unix.SizeofIfAddrmsg) } var ifaddr linux.InterfaceAddrMessage - ifaddr.UnmarshalUnsafe(addr.Data[:ifaddr.SizeBytes()]) + ifaddr.UnmarshalUnsafe(addr.Data) inetAddr := inet.InterfaceAddr{ Family: ifaddr.Family, PrefixLen: ifaddr.PrefixLen, @@ -201,7 +201,7 @@ func ExtractHostRoutes(routeMsgs []syscall.NetlinkMessage) ([]inet.Route, error) } var ifRoute linux.RouteMessage - ifRoute.UnmarshalUnsafe(routeMsg.Data[:ifRoute.SizeBytes()]) + ifRoute.UnmarshalUnsafe(routeMsg.Data) inetRoute := inet.Route{ Family: ifRoute.Family, DstLen: ifRoute.DstLen, diff --git a/pkg/sentry/socket/netfilter/extensions.go b/pkg/sentry/socket/netfilter/extensions.go index 3f1b4a17b..7606d2bbb 100644 --- a/pkg/sentry/socket/netfilter/extensions.go +++ b/pkg/sentry/socket/netfilter/extensions.go @@ -80,9 +80,8 @@ func marshalEntryMatch(name string, data []byte) []byte { copy(matcher.Name[:], name) buf := make([]byte, size) - entryLen := matcher.XTEntryMatch.SizeBytes() - matcher.XTEntryMatch.MarshalUnsafe(buf[:entryLen]) - copy(buf[entryLen:], matcher.Data) + bufRemain := matcher.XTEntryMatch.MarshalUnsafe(buf) + copy(bufRemain, matcher.Data) return buf } diff --git a/pkg/sentry/socket/netfilter/ipv4.go b/pkg/sentry/socket/netfilter/ipv4.go index af31cbc5b..6cbfee8b6 100644 --- a/pkg/sentry/socket/netfilter/ipv4.go +++ b/pkg/sentry/socket/netfilter/ipv4.go @@ -141,10 +141,9 @@ func modifyEntries4(task *kernel.Task, stk *stack.Stack, optVal []byte, replace nflog("optVal has insufficient size for entry %d", len(optVal)) return nil, syserr.ErrInvalidArgument } - var entry linux.IPTEntry - entry.UnmarshalUnsafe(optVal[:entry.SizeBytes()]) initialOptValLen := len(optVal) - optVal = optVal[entry.SizeBytes():] + var entry linux.IPTEntry + optVal = entry.UnmarshalUnsafe(optVal) if entry.TargetOffset < linux.SizeOfIPTEntry { nflog("entry has too-small target offset %d", entry.TargetOffset) diff --git a/pkg/sentry/socket/netfilter/ipv6.go b/pkg/sentry/socket/netfilter/ipv6.go index 6cefe0b9c..902707abf 100644 --- a/pkg/sentry/socket/netfilter/ipv6.go +++ b/pkg/sentry/socket/netfilter/ipv6.go @@ -144,10 +144,9 @@ func modifyEntries6(task *kernel.Task, stk *stack.Stack, optVal []byte, replace nflog("optVal has insufficient size for entry %d", len(optVal)) return nil, syserr.ErrInvalidArgument } - var entry linux.IP6TEntry - entry.UnmarshalUnsafe(optVal[:entry.SizeBytes()]) initialOptValLen := len(optVal) - optVal = optVal[entry.SizeBytes():] + var entry linux.IP6TEntry + optVal = entry.UnmarshalUnsafe(optVal) if entry.TargetOffset < linux.SizeOfIP6TEntry { nflog("entry has too-small target offset %d", entry.TargetOffset) diff --git a/pkg/sentry/socket/netfilter/netfilter.go b/pkg/sentry/socket/netfilter/netfilter.go index 01f2f8c77..f2cdf091d 100644 --- a/pkg/sentry/socket/netfilter/netfilter.go +++ b/pkg/sentry/socket/netfilter/netfilter.go @@ -176,9 +176,7 @@ func setHooksAndUnderflow(info *linux.IPTGetinfo, table stack.Table, offset uint // net/ipv4/netfilter/ip_tables.c:translate_table for reference. func SetEntries(task *kernel.Task, stk *stack.Stack, optVal []byte, ipv6 bool) *syserr.Error { var replace linux.IPTReplace - replaceBuf := optVal[:linux.SizeOfIPTReplace] - optVal = optVal[linux.SizeOfIPTReplace:] - replace.UnmarshalBytes(replaceBuf) + optVal = replace.UnmarshalBytes(optVal) var table stack.Table switch replace.Name.String() { @@ -306,8 +304,7 @@ func parseMatchers(task *kernel.Task, filter stack.IPHeaderFilter, optVal []byte return nil, fmt.Errorf("optVal has insufficient size for entry match: %d", len(optVal)) } var match linux.XTEntryMatch - buf := optVal[:match.SizeBytes()] - match.UnmarshalUnsafe(buf) + match.UnmarshalUnsafe(optVal) nflog("set entries: parsed entry match %q: %+v", match.Name.String(), match) // Check some invariants. diff --git a/pkg/sentry/socket/netfilter/netfilter_abi_autogen_unsafe.go b/pkg/sentry/socket/netfilter/netfilter_abi_autogen_unsafe.go index 786b62935..65e39de64 100644 --- a/pkg/sentry/socket/netfilter/netfilter_abi_autogen_unsafe.go +++ b/pkg/sentry/socket/netfilter/netfilter_abi_autogen_unsafe.go @@ -26,19 +26,17 @@ func (n *nfNATTarget) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (n *nfNATTarget) MarshalBytes(dst []byte) { - n.Target.MarshalBytes(dst[:n.Target.SizeBytes()]) - dst = dst[n.Target.SizeBytes():] - n.Range.MarshalBytes(dst[:n.Range.SizeBytes()]) - dst = dst[n.Range.SizeBytes():] +func (n *nfNATTarget) MarshalBytes(dst []byte) []byte { + dst = n.Target.MarshalBytes(dst) + dst = n.Range.MarshalBytes(dst) + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (n *nfNATTarget) UnmarshalBytes(src []byte) { - n.Target.UnmarshalBytes(src[:n.Target.SizeBytes()]) - src = src[n.Target.SizeBytes():] - n.Range.UnmarshalBytes(src[:n.Range.SizeBytes()]) - src = src[n.Range.SizeBytes():] +func (n *nfNATTarget) UnmarshalBytes(src []byte) []byte { + src = n.Target.UnmarshalBytes(src) + src = n.Range.UnmarshalBytes(src) + return src } // Packed implements marshal.Marshallable.Packed. @@ -48,23 +46,25 @@ func (n *nfNATTarget) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (n *nfNATTarget) MarshalUnsafe(dst []byte) { +func (n *nfNATTarget) MarshalUnsafe(dst []byte) []byte { if n.Range.Packed() && n.Target.Packed() { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(n), uintptr(n.SizeBytes())) - } else { - // Type nfNATTarget doesn't have a packed layout in memory, fallback to MarshalBytes. - n.MarshalBytes(dst) + size := n.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(n), uintptr(size)) + return dst[size:] } + // Type nfNATTarget doesn't have a packed layout in memory, fallback to MarshalBytes. + return n.MarshalBytes(dst) } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (n *nfNATTarget) UnmarshalUnsafe(src []byte) { +func (n *nfNATTarget) UnmarshalUnsafe(src []byte) []byte { if n.Range.Packed() && n.Target.Packed() { - gohacks.Memmove(unsafe.Pointer(n), unsafe.Pointer(&src[0]), uintptr(n.SizeBytes())) - } else { - // Type nfNATTarget doesn't have a packed layout in memory, fallback to UnmarshalBytes. - n.UnmarshalBytes(src) + size := n.SizeBytes() + gohacks.Memmove(unsafe.Pointer(n), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } + // Type nfNATTarget doesn't have a packed layout in memory, fallback to UnmarshalBytes. + return n.UnmarshalBytes(src) } // CopyOutN implements marshal.Marshallable.CopyOutN. diff --git a/pkg/sentry/socket/netfilter/owner_matcher.go b/pkg/sentry/socket/netfilter/owner_matcher.go index 6eff2ae65..d83d7e535 100644 --- a/pkg/sentry/socket/netfilter/owner_matcher.go +++ b/pkg/sentry/socket/netfilter/owner_matcher.go @@ -73,7 +73,7 @@ func (ownerMarshaler) unmarshal(task *kernel.Task, buf []byte, filter stack.IPHe // For alignment reasons, the match's total size may // exceed what's strictly necessary to hold matchData. var matchData linux.IPTOwnerInfo - matchData.UnmarshalUnsafe(buf[:linux.SizeOfIPTOwnerInfo]) + matchData.UnmarshalUnsafe(buf) nflog("parsed IPTOwnerInfo: %+v", matchData) var owner OwnerMatcher diff --git a/pkg/sentry/socket/netfilter/targets.go b/pkg/sentry/socket/netfilter/targets.go index b9c15daab..eaf601543 100644 --- a/pkg/sentry/socket/netfilter/targets.go +++ b/pkg/sentry/socket/netfilter/targets.go @@ -199,7 +199,7 @@ func (*standardTargetMaker) unmarshal(buf []byte, filter stack.IPHeaderFilter) ( return nil, syserr.ErrInvalidArgument } var standardTarget linux.XTStandardTarget - standardTarget.UnmarshalUnsafe(buf[:standardTarget.SizeBytes()]) + standardTarget.UnmarshalUnsafe(buf) if standardTarget.Verdict < 0 { // A Verdict < 0 indicates a non-jump verdict. @@ -253,7 +253,6 @@ func (*errorTargetMaker) unmarshal(buf []byte, filter stack.IPHeaderFilter) (tar return nil, syserr.ErrInvalidArgument } var errTgt linux.XTErrorTarget - buf = buf[:linux.SizeOfXTErrorTarget] errTgt.UnmarshalUnsafe(buf) // Error targets are used in 2 cases: @@ -316,7 +315,6 @@ func (*redirectTargetMaker) unmarshal(buf []byte, filter stack.IPHeaderFilter) ( } var rt linux.XTRedirectTarget - buf = buf[:linux.SizeOfXTRedirectTarget] rt.UnmarshalUnsafe(buf) // Copy linux.XTRedirectTarget to stack.RedirectTarget. @@ -405,8 +403,7 @@ func (*nfNATTargetMaker) unmarshal(buf []byte, filter stack.IPHeaderFilter) (tar } var natRange linux.NFNATRange - buf = buf[linux.SizeOfXTEntryTarget:nfNATMarshalledSize] - natRange.UnmarshalUnsafe(buf) + natRange.UnmarshalUnsafe(buf[linux.SizeOfXTEntryTarget:]) // We don't support port or address ranges. if natRange.MinAddr != natRange.MaxAddr { @@ -477,7 +474,6 @@ func (*snatTargetMakerV4) unmarshal(buf []byte, filter stack.IPHeaderFilter) (ta } var st linux.XTSNATTarget - buf = buf[:linux.SizeOfXTSNATTarget] st.UnmarshalUnsafe(buf) // Copy linux.XTSNATTarget to stack.SNATTarget. @@ -557,8 +553,7 @@ func (*snatTargetMakerV6) unmarshal(buf []byte, filter stack.IPHeaderFilter) (ta } var natRange linux.NFNATRange - buf = buf[linux.SizeOfXTEntryTarget:nfNATMarshalledSize] - natRange.UnmarshalUnsafe(buf) + natRange.UnmarshalUnsafe(buf[linux.SizeOfXTEntryTarget:]) // TODO(gvisor.dev/issue/5697): Support port or address ranges. if natRange.MinAddr != natRange.MaxAddr { @@ -621,7 +616,9 @@ func parseTarget(filter stack.IPHeaderFilter, optVal []byte, ipv6 bool) (stack.T return nil, syserr.ErrInvalidArgument } var target linux.XTEntryTarget - target.UnmarshalUnsafe(optVal[:target.SizeBytes()]) + // Do not advance optVal as targetMake.unmarshal() may unmarshal + // XTEntryTarget again but with some added fields. + target.UnmarshalUnsafe(optVal) return unmarshalTarget(target, filter, optVal) } diff --git a/pkg/sentry/socket/netfilter/tcp_matcher.go b/pkg/sentry/socket/netfilter/tcp_matcher.go index e5b73a976..a621a6a16 100644 --- a/pkg/sentry/socket/netfilter/tcp_matcher.go +++ b/pkg/sentry/socket/netfilter/tcp_matcher.go @@ -59,7 +59,7 @@ func (tcpMarshaler) unmarshal(_ *kernel.Task, buf []byte, filter stack.IPHeaderF // For alignment reasons, the match's total size may // exceed what's strictly necessary to hold matchData. var matchData linux.XTTCP - matchData.UnmarshalUnsafe(buf[:matchData.SizeBytes()]) + matchData.UnmarshalUnsafe(buf) nflog("parseMatchers: parsed XTTCP: %+v", matchData) if matchData.Option != 0 || diff --git a/pkg/sentry/socket/netfilter/udp_matcher.go b/pkg/sentry/socket/netfilter/udp_matcher.go index aa72ee70c..2ca854764 100644 --- a/pkg/sentry/socket/netfilter/udp_matcher.go +++ b/pkg/sentry/socket/netfilter/udp_matcher.go @@ -59,7 +59,7 @@ func (udpMarshaler) unmarshal(_ *kernel.Task, buf []byte, filter stack.IPHeaderF // For alignment reasons, the match's total size may exceed what's // strictly necessary to hold matchData. var matchData linux.XTUDP - matchData.UnmarshalUnsafe(buf[:matchData.SizeBytes()]) + matchData.UnmarshalUnsafe(buf) nflog("parseMatchers: parsed XTUDP: %+v", matchData) if matchData.InverseFlags != 0 { diff --git a/pkg/sentry/socket/netlink/socket.go b/pkg/sentry/socket/netlink/socket.go index 267155807..19c8f340d 100644 --- a/pkg/sentry/socket/netlink/socket.go +++ b/pkg/sentry/socket/netlink/socket.go @@ -223,7 +223,7 @@ func ExtractSockAddr(b []byte) (*linux.SockAddrNetlink, *syserr.Error) { } var sa linux.SockAddrNetlink - sa.UnmarshalUnsafe(b[:sa.SizeBytes()]) + sa.UnmarshalUnsafe(b) if sa.Family != linux.AF_NETLINK { return nil, syserr.ErrInvalidArgument diff --git a/pkg/sentry/socket/netstack/netstack.go b/pkg/sentry/socket/netstack/netstack.go index c35cf06f6..e38c4e5da 100644 --- a/pkg/sentry/socket/netstack/netstack.go +++ b/pkg/sentry/socket/netstack/netstack.go @@ -660,7 +660,7 @@ func (s *socketOpsCommon) Bind(_ *kernel.Task, sockaddr []byte) *syserr.Error { if len(sockaddr) < sockAddrLinkSize { return syserr.ErrInvalidArgument } - a.UnmarshalBytes(sockaddr[:sockAddrLinkSize]) + a.UnmarshalBytes(sockaddr) addr = tcpip.FullAddress{ NIC: tcpip.NICID(a.InterfaceIndex), @@ -1839,7 +1839,7 @@ func setSockOptSocket(t *kernel.Task, s socket.SocketOps, ep commonEndpoint, nam } var v linux.Timeval - v.UnmarshalBytes(optVal[:linux.SizeOfTimeval]) + v.UnmarshalBytes(optVal) if v.Usec < 0 || v.Usec >= int64(time.Second/time.Microsecond) { return syserr.ErrDomain } @@ -1852,7 +1852,7 @@ func setSockOptSocket(t *kernel.Task, s socket.SocketOps, ep commonEndpoint, nam } var v linux.Timeval - v.UnmarshalBytes(optVal[:linux.SizeOfTimeval]) + v.UnmarshalBytes(optVal) if v.Usec < 0 || v.Usec >= int64(time.Second/time.Microsecond) { return syserr.ErrDomain } @@ -1883,7 +1883,7 @@ func setSockOptSocket(t *kernel.Task, s socket.SocketOps, ep commonEndpoint, nam } var v linux.Linger - v.UnmarshalBytes(optVal[:linux.SizeOfLinger]) + v.UnmarshalBytes(optVal) if v != (linux.Linger{}) { socket.SetSockOptEmitUnimplementedEvent(t, name) @@ -2222,12 +2222,12 @@ func copyInMulticastRequest(optVal []byte, allowAddr bool) (linux.InetMulticastR if len(optVal) >= inetMulticastRequestWithNICSize { var req linux.InetMulticastRequestWithNIC - req.UnmarshalUnsafe(optVal[:inetMulticastRequestWithNICSize]) + req.UnmarshalUnsafe(optVal) return req, nil } var req linux.InetMulticastRequestWithNIC - req.InetMulticastRequest.UnmarshalUnsafe(optVal[:inetMulticastRequestSize]) + req.InetMulticastRequest.UnmarshalUnsafe(optVal) return req, nil } @@ -2237,7 +2237,7 @@ func copyInMulticastV6Request(optVal []byte) (linux.Inet6MulticastRequest, *syse } var req linux.Inet6MulticastRequest - req.UnmarshalUnsafe(optVal[:inet6MulticastRequestSize]) + req.UnmarshalUnsafe(optVal) return req, nil } diff --git a/pkg/sentry/socket/socket.go b/pkg/sentry/socket/socket.go index fc5431eb1..01073df72 100644 --- a/pkg/sentry/socket/socket.go +++ b/pkg/sentry/socket/socket.go @@ -595,19 +595,19 @@ func UnmarshalSockAddr(family int, data []byte) linux.SockAddr { switch family { case unix.AF_INET: var addr linux.SockAddrInet - addr.UnmarshalUnsafe(data[:addr.SizeBytes()]) + addr.UnmarshalUnsafe(data) return &addr case unix.AF_INET6: var addr linux.SockAddrInet6 - addr.UnmarshalUnsafe(data[:addr.SizeBytes()]) + addr.UnmarshalUnsafe(data) return &addr case unix.AF_UNIX: var addr linux.SockAddrUnix - addr.UnmarshalUnsafe(data[:addr.SizeBytes()]) + addr.UnmarshalUnsafe(data) return &addr case unix.AF_NETLINK: var addr linux.SockAddrNetlink - addr.UnmarshalUnsafe(data[:addr.SizeBytes()]) + addr.UnmarshalUnsafe(data) return &addr default: panic(fmt.Sprintf("Unsupported socket family %v", family)) @@ -738,7 +738,7 @@ func AddressAndFamily(addr []byte) (tcpip.FullAddress, uint16, *syserr.Error) { if len(addr) < sockAddrInetSize { return tcpip.FullAddress{}, family, syserr.ErrInvalidArgument } - a.UnmarshalUnsafe(addr[:sockAddrInetSize]) + a.UnmarshalUnsafe(addr) out := tcpip.FullAddress{ Addr: BytesToIPAddress(a.Addr[:]), @@ -751,7 +751,7 @@ func AddressAndFamily(addr []byte) (tcpip.FullAddress, uint16, *syserr.Error) { if len(addr) < sockAddrInet6Size { return tcpip.FullAddress{}, family, syserr.ErrInvalidArgument } - a.UnmarshalUnsafe(addr[:sockAddrInet6Size]) + a.UnmarshalUnsafe(addr) out := tcpip.FullAddress{ Addr: BytesToIPAddress(a.Addr[:]), @@ -767,7 +767,7 @@ func AddressAndFamily(addr []byte) (tcpip.FullAddress, uint16, *syserr.Error) { if len(addr) < sockAddrLinkSize { return tcpip.FullAddress{}, family, syserr.ErrInvalidArgument } - a.UnmarshalUnsafe(addr[:sockAddrLinkSize]) + a.UnmarshalUnsafe(addr) // TODO(https://gvisor.dev/issue/6530): Do not assume all interfaces have // an ethernet address. if a.Family != linux.AF_PACKET || a.HardwareAddrLen != header.EthernetAddressSize { diff --git a/pkg/sentry/strace/socket.go b/pkg/sentry/strace/socket.go index f4aab25b0..b164d9107 100644 --- a/pkg/sentry/strace/socket.go +++ b/pkg/sentry/strace/socket.go @@ -161,12 +161,10 @@ var controlMessageType = map[int32]string{ linux.SO_TIMESTAMP: "SO_TIMESTAMP", } -func unmarshalControlMessageRights(src []byte) linux.ControlMessageRights { +func unmarshalControlMessageRights(src []byte) []primitive.Int32 { count := len(src) / linux.SizeOfControlMessageRight - cmr := make(linux.ControlMessageRights, count) - for i, _ := range cmr { - cmr[i] = int32(hostarch.ByteOrder.Uint32(src[i*linux.SizeOfControlMessageRight:])) - } + cmr := make([]primitive.Int32, count) + primitive.UnmarshalUnsafeInt32Slice(cmr, src) return cmr } @@ -182,14 +180,14 @@ func cmsghdr(t *kernel.Task, addr hostarch.Addr, length uint64, maxBytes uint64) var strs []string - for i := 0; i < len(buf); { - if i+linux.SizeOfControlMessageHeader > len(buf) { + for len(buf) > 0 { + if linux.SizeOfControlMessageHeader > len(buf) { strs = append(strs, "{invalid control message (too short)}") break } var h linux.ControlMessageHeader - h.UnmarshalUnsafe(buf[i : i+linux.SizeOfControlMessageHeader]) + buf = h.UnmarshalUnsafe(buf) var skipData bool level := "SOL_SOCKET" @@ -204,7 +202,9 @@ func cmsghdr(t *kernel.Task, addr hostarch.Addr, length uint64, maxBytes uint64) typ = fmt.Sprint(h.Type) } - if h.Length > uint64(len(buf)-i) { + width := t.Arch().Width() + length := int(h.Length) - linux.SizeOfControlMessageHeader + if length > len(buf) { strs = append(strs, fmt.Sprintf( "{level=%s, type=%s, length=%d, content extends beyond buffer}", level, @@ -214,9 +214,6 @@ func cmsghdr(t *kernel.Task, addr hostarch.Addr, length uint64, maxBytes uint64) break } - i += linux.SizeOfControlMessageHeader - width := t.Arch().Width() - length := int(h.Length) - linux.SizeOfControlMessageHeader if length < 0 { strs = append(strs, fmt.Sprintf( "{level=%s, type=%s, length=%d, content too short}", @@ -229,78 +226,80 @@ func cmsghdr(t *kernel.Task, addr hostarch.Addr, length uint64, maxBytes uint64) if skipData { strs = append(strs, fmt.Sprintf("{level=%s, type=%s, length=%d}", level, typ, h.Length)) - i += bits.AlignUp(length, width) - continue - } - - switch h.Type { - case linux.SCM_RIGHTS: - rightsSize := bits.AlignDown(length, linux.SizeOfControlMessageRight) - fds := unmarshalControlMessageRights(buf[i : i+rightsSize]) - rights := make([]string, 0, len(fds)) - for _, fd := range fds { - rights = append(rights, fmt.Sprint(fd)) - } + } else { + switch h.Type { + case linux.SCM_RIGHTS: + rightsSize := bits.AlignDown(length, linux.SizeOfControlMessageRight) + fds := unmarshalControlMessageRights(buf[:rightsSize]) + rights := make([]string, 0, len(fds)) + for _, fd := range fds { + rights = append(rights, fmt.Sprint(fd)) + } - strs = append(strs, fmt.Sprintf( - "{level=%s, type=%s, length=%d, content: %s}", - level, - typ, - h.Length, - strings.Join(rights, ","), - )) - - case linux.SCM_CREDENTIALS: - if length < linux.SizeOfControlMessageCredentials { strs = append(strs, fmt.Sprintf( - "{level=%s, type=%s, length=%d, content too short}", + "{level=%s, type=%s, length=%d, content: %s}", level, typ, h.Length, + strings.Join(rights, ","), )) - break - } - var creds linux.ControlMessageCredentials - creds.UnmarshalUnsafe(buf[i : i+linux.SizeOfControlMessageCredentials]) + case linux.SCM_CREDENTIALS: + if length < linux.SizeOfControlMessageCredentials { + strs = append(strs, fmt.Sprintf( + "{level=%s, type=%s, length=%d, content too short}", + level, + typ, + h.Length, + )) + break + } - strs = append(strs, fmt.Sprintf( - "{level=%s, type=%s, length=%d, pid: %d, uid: %d, gid: %d}", - level, - typ, - h.Length, - creds.PID, - creds.UID, - creds.GID, - )) + var creds linux.ControlMessageCredentials + creds.UnmarshalUnsafe(buf) - case linux.SO_TIMESTAMP: - if length < linux.SizeOfTimeval { strs = append(strs, fmt.Sprintf( - "{level=%s, type=%s, length=%d, content too short}", + "{level=%s, type=%s, length=%d, pid: %d, uid: %d, gid: %d}", level, typ, h.Length, + creds.PID, + creds.UID, + creds.GID, )) - break - } - var tv linux.Timeval - tv.UnmarshalUnsafe(buf[i : i+linux.SizeOfTimeval]) + case linux.SO_TIMESTAMP: + if length < linux.SizeOfTimeval { + strs = append(strs, fmt.Sprintf( + "{level=%s, type=%s, length=%d, content too short}", + level, + typ, + h.Length, + )) + break + } - strs = append(strs, fmt.Sprintf( - "{level=%s, type=%s, length=%d, Sec: %d, Usec: %d}", - level, - typ, - h.Length, - tv.Sec, - tv.Usec, - )) + var tv linux.Timeval + tv.UnmarshalUnsafe(buf) - default: - panic("unreachable") + strs = append(strs, fmt.Sprintf( + "{level=%s, type=%s, length=%d, Sec: %d, Usec: %d}", + level, + typ, + h.Length, + tv.Sec, + tv.Usec, + )) + + default: + panic("unreachable") + } + } + if shift := bits.AlignUp(length, width); shift > len(buf) { + buf = buf[:0] + } else { + buf = buf[shift:] } - i += bits.AlignUp(length, width) } return fmt.Sprintf("%#x %s", addr, strings.Join(strs, ", ")) diff --git a/pkg/sentry/syscalls/linux/linux_abi_autogen_unsafe.go b/pkg/sentry/syscalls/linux/linux_abi_autogen_unsafe.go index 409927919..2ebafff21 100644 --- a/pkg/sentry/syscalls/linux/linux_abi_autogen_unsafe.go +++ b/pkg/sentry/syscalls/linux/linux_abi_autogen_unsafe.go @@ -28,19 +28,19 @@ func (d *direntHdr) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (d *direntHdr) MarshalBytes(dst []byte) { - d.OldHdr.MarshalBytes(dst[:d.OldHdr.SizeBytes()]) - dst = dst[d.OldHdr.SizeBytes():] +func (d *direntHdr) MarshalBytes(dst []byte) []byte { + dst = d.OldHdr.MarshalBytes(dst) dst[0] = byte(d.Typ) dst = dst[1:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (d *direntHdr) UnmarshalBytes(src []byte) { - d.OldHdr.UnmarshalBytes(src[:d.OldHdr.SizeBytes()]) - src = src[d.OldHdr.SizeBytes():] +func (d *direntHdr) UnmarshalBytes(src []byte) []byte { + src = d.OldHdr.UnmarshalBytes(src) d.Typ = uint8(src[0]) src = src[1:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -50,15 +50,15 @@ func (d *direntHdr) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (d *direntHdr) MarshalUnsafe(dst []byte) { +func (d *direntHdr) MarshalUnsafe(dst []byte) []byte { // Type direntHdr doesn't have a packed layout in memory, fallback to MarshalBytes. - d.MarshalBytes(dst) + return d.MarshalBytes(dst) } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (d *direntHdr) UnmarshalUnsafe(src []byte) { +func (d *direntHdr) UnmarshalUnsafe(src []byte) []byte { // Type direntHdr doesn't have a packed layout in memory, fallback to UnmarshalBytes. - d.UnmarshalBytes(src) + return d.UnmarshalBytes(src) } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -103,23 +103,25 @@ func (o *oldDirentHdr) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (o *oldDirentHdr) MarshalBytes(dst []byte) { +func (o *oldDirentHdr) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint64(dst[:8], uint64(o.Ino)) dst = dst[8:] hostarch.ByteOrder.PutUint64(dst[:8], uint64(o.Off)) dst = dst[8:] hostarch.ByteOrder.PutUint16(dst[:2], uint16(o.Reclen)) dst = dst[2:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (o *oldDirentHdr) UnmarshalBytes(src []byte) { +func (o *oldDirentHdr) UnmarshalBytes(src []byte) []byte { o.Ino = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] o.Off = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] o.Reclen = uint16(hostarch.ByteOrder.Uint16(src[:2])) src = src[2:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -129,15 +131,15 @@ func (o *oldDirentHdr) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (o *oldDirentHdr) MarshalUnsafe(dst []byte) { +func (o *oldDirentHdr) MarshalUnsafe(dst []byte) []byte { // Type oldDirentHdr doesn't have a packed layout in memory, fallback to MarshalBytes. - o.MarshalBytes(dst) + return o.MarshalBytes(dst) } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (o *oldDirentHdr) UnmarshalUnsafe(src []byte) { +func (o *oldDirentHdr) UnmarshalUnsafe(src []byte) []byte { // Type oldDirentHdr doesn't have a packed layout in memory, fallback to UnmarshalBytes. - o.UnmarshalBytes(src) + return o.UnmarshalBytes(src) } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -182,19 +184,21 @@ func (r *rlimit64) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (r *rlimit64) MarshalBytes(dst []byte) { +func (r *rlimit64) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint64(dst[:8], uint64(r.Cur)) dst = dst[8:] hostarch.ByteOrder.PutUint64(dst[:8], uint64(r.Max)) dst = dst[8:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (r *rlimit64) UnmarshalBytes(src []byte) { +func (r *rlimit64) UnmarshalBytes(src []byte) []byte { r.Cur = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] r.Max = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -204,13 +208,17 @@ func (r *rlimit64) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (r *rlimit64) MarshalUnsafe(dst []byte) { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(r), uintptr(r.SizeBytes())) +func (r *rlimit64) MarshalUnsafe(dst []byte) []byte { + size := r.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(r), uintptr(size)) + return dst[size:] } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (r *rlimit64) UnmarshalUnsafe(src []byte) { - gohacks.Memmove(unsafe.Pointer(r), unsafe.Pointer(&src[0]), uintptr(r.SizeBytes())) +func (r *rlimit64) UnmarshalUnsafe(src []byte) []byte { + size := r.SizeBytes() + gohacks.Memmove(unsafe.Pointer(r), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -275,15 +283,17 @@ func (s *SchedParam) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (s *SchedParam) MarshalBytes(dst []byte) { +func (s *SchedParam) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint32(dst[:4], uint32(s.schedPriority)) dst = dst[4:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (s *SchedParam) UnmarshalBytes(src []byte) { +func (s *SchedParam) UnmarshalBytes(src []byte) []byte { s.schedPriority = int32(hostarch.ByteOrder.Uint32(src[:4])) src = src[4:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -293,13 +303,17 @@ func (s *SchedParam) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (s *SchedParam) MarshalUnsafe(dst []byte) { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(s), uintptr(s.SizeBytes())) +func (s *SchedParam) MarshalUnsafe(dst []byte) []byte { + size := s.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(s), uintptr(size)) + return dst[size:] } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (s *SchedParam) UnmarshalUnsafe(src []byte) { - gohacks.Memmove(unsafe.Pointer(s), unsafe.Pointer(&src[0]), uintptr(s.SizeBytes())) +func (s *SchedParam) UnmarshalUnsafe(src []byte) []byte { + size := s.SizeBytes() + gohacks.Memmove(unsafe.Pointer(s), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -365,23 +379,25 @@ func (u *userSockFprog) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (u *userSockFprog) MarshalBytes(dst []byte) { +func (u *userSockFprog) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint16(dst[:2], uint16(u.Len)) dst = dst[2:] // Padding: dst[:sizeof(byte)*6] ~= [6]byte{0} dst = dst[1*(6):] hostarch.ByteOrder.PutUint64(dst[:8], uint64(u.Filter)) dst = dst[8:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (u *userSockFprog) UnmarshalBytes(src []byte) { +func (u *userSockFprog) UnmarshalBytes(src []byte) []byte { u.Len = uint16(hostarch.ByteOrder.Uint16(src[:2])) src = src[2:] // Padding: ~ copy([6]byte(u._), src[:sizeof(byte)*6]) src = src[1*(6):] u.Filter = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -391,13 +407,17 @@ func (u *userSockFprog) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (u *userSockFprog) MarshalUnsafe(dst []byte) { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(u), uintptr(u.SizeBytes())) +func (u *userSockFprog) MarshalUnsafe(dst []byte) []byte { + size := u.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(u), uintptr(size)) + return dst[size:] } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (u *userSockFprog) UnmarshalUnsafe(src []byte) { - gohacks.Memmove(unsafe.Pointer(u), unsafe.Pointer(&src[0]), uintptr(u.SizeBytes())) +func (u *userSockFprog) UnmarshalUnsafe(src []byte) []byte { + size := u.SizeBytes() + gohacks.Memmove(unsafe.Pointer(u), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -462,7 +482,7 @@ func (m *MessageHeader64) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (m *MessageHeader64) MarshalBytes(dst []byte) { +func (m *MessageHeader64) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint64(dst[:8], uint64(m.Name)) dst = dst[8:] hostarch.ByteOrder.PutUint32(dst[:4], uint32(m.NameLen)) @@ -481,10 +501,11 @@ func (m *MessageHeader64) MarshalBytes(dst []byte) { dst = dst[4:] // Padding: dst[:sizeof(int32)] ~= int32(0) dst = dst[4:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (m *MessageHeader64) UnmarshalBytes(src []byte) { +func (m *MessageHeader64) UnmarshalBytes(src []byte) []byte { m.Name = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] m.NameLen = uint32(hostarch.ByteOrder.Uint32(src[:4])) @@ -503,6 +524,7 @@ func (m *MessageHeader64) UnmarshalBytes(src []byte) { src = src[4:] // Padding: var _ int32 ~= src[:sizeof(int32)] src = src[4:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -512,13 +534,17 @@ func (m *MessageHeader64) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (m *MessageHeader64) MarshalUnsafe(dst []byte) { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(m), uintptr(m.SizeBytes())) +func (m *MessageHeader64) MarshalUnsafe(dst []byte) []byte { + size := m.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(m), uintptr(size)) + return dst[size:] } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (m *MessageHeader64) UnmarshalUnsafe(src []byte) { - gohacks.Memmove(unsafe.Pointer(m), unsafe.Pointer(&src[0]), uintptr(m.SizeBytes())) +func (m *MessageHeader64) UnmarshalUnsafe(src []byte) []byte { + size := m.SizeBytes() + gohacks.Memmove(unsafe.Pointer(m), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -584,23 +610,23 @@ func (m *multipleMessageHeader64) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (m *multipleMessageHeader64) MarshalBytes(dst []byte) { - m.msgHdr.MarshalBytes(dst[:m.msgHdr.SizeBytes()]) - dst = dst[m.msgHdr.SizeBytes():] +func (m *multipleMessageHeader64) MarshalBytes(dst []byte) []byte { + dst = m.msgHdr.MarshalBytes(dst) hostarch.ByteOrder.PutUint32(dst[:4], uint32(m.msgLen)) dst = dst[4:] // Padding: dst[:sizeof(int32)] ~= int32(0) dst = dst[4:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (m *multipleMessageHeader64) UnmarshalBytes(src []byte) { - m.msgHdr.UnmarshalBytes(src[:m.msgHdr.SizeBytes()]) - src = src[m.msgHdr.SizeBytes():] +func (m *multipleMessageHeader64) UnmarshalBytes(src []byte) []byte { + src = m.msgHdr.UnmarshalBytes(src) m.msgLen = uint32(hostarch.ByteOrder.Uint32(src[:4])) src = src[4:] // Padding: var _ int32 ~= src[:sizeof(int32)] src = src[4:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -610,23 +636,25 @@ func (m *multipleMessageHeader64) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (m *multipleMessageHeader64) MarshalUnsafe(dst []byte) { +func (m *multipleMessageHeader64) MarshalUnsafe(dst []byte) []byte { if m.msgHdr.Packed() { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(m), uintptr(m.SizeBytes())) - } else { - // Type multipleMessageHeader64 doesn't have a packed layout in memory, fallback to MarshalBytes. - m.MarshalBytes(dst) + size := m.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(m), uintptr(size)) + return dst[size:] } + // Type multipleMessageHeader64 doesn't have a packed layout in memory, fallback to MarshalBytes. + return m.MarshalBytes(dst) } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (m *multipleMessageHeader64) UnmarshalUnsafe(src []byte) { +func (m *multipleMessageHeader64) UnmarshalUnsafe(src []byte) []byte { if m.msgHdr.Packed() { - gohacks.Memmove(unsafe.Pointer(m), unsafe.Pointer(&src[0]), uintptr(m.SizeBytes())) - } else { - // Type multipleMessageHeader64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. - m.UnmarshalBytes(src) + size := m.SizeBytes() + gohacks.Memmove(unsafe.Pointer(m), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } + // Type multipleMessageHeader64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. + return m.UnmarshalBytes(src) } // CopyOutN implements marshal.Marshallable.CopyOutN. diff --git a/pkg/sentry/syscalls/linux/vfs2/vfs2_abi_autogen_unsafe.go b/pkg/sentry/syscalls/linux/vfs2/vfs2_abi_autogen_unsafe.go index 01b0d465f..fbbb520b9 100644 --- a/pkg/sentry/syscalls/linux/vfs2/vfs2_abi_autogen_unsafe.go +++ b/pkg/sentry/syscalls/linux/vfs2/vfs2_abi_autogen_unsafe.go @@ -23,19 +23,21 @@ func (s *sigSetWithSize) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (s *sigSetWithSize) MarshalBytes(dst []byte) { +func (s *sigSetWithSize) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint64(dst[:8], uint64(s.sigsetAddr)) dst = dst[8:] hostarch.ByteOrder.PutUint64(dst[:8], uint64(s.sizeofSigset)) dst = dst[8:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (s *sigSetWithSize) UnmarshalBytes(src []byte) { +func (s *sigSetWithSize) UnmarshalBytes(src []byte) []byte { s.sigsetAddr = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] s.sizeofSigset = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -45,13 +47,17 @@ func (s *sigSetWithSize) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (s *sigSetWithSize) MarshalUnsafe(dst []byte) { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(s), uintptr(s.SizeBytes())) +func (s *sigSetWithSize) MarshalUnsafe(dst []byte) []byte { + size := s.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(s), uintptr(size)) + return dst[size:] } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (s *sigSetWithSize) UnmarshalUnsafe(src []byte) { - gohacks.Memmove(unsafe.Pointer(s), unsafe.Pointer(&src[0]), uintptr(s.SizeBytes())) +func (s *sigSetWithSize) UnmarshalUnsafe(src []byte) []byte { + size := s.SizeBytes() + gohacks.Memmove(unsafe.Pointer(s), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -116,7 +122,7 @@ func (m *MessageHeader64) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (m *MessageHeader64) MarshalBytes(dst []byte) { +func (m *MessageHeader64) MarshalBytes(dst []byte) []byte { hostarch.ByteOrder.PutUint64(dst[:8], uint64(m.Name)) dst = dst[8:] hostarch.ByteOrder.PutUint32(dst[:4], uint32(m.NameLen)) @@ -135,10 +141,11 @@ func (m *MessageHeader64) MarshalBytes(dst []byte) { dst = dst[4:] // Padding: dst[:sizeof(int32)] ~= int32(0) dst = dst[4:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (m *MessageHeader64) UnmarshalBytes(src []byte) { +func (m *MessageHeader64) UnmarshalBytes(src []byte) []byte { m.Name = uint64(hostarch.ByteOrder.Uint64(src[:8])) src = src[8:] m.NameLen = uint32(hostarch.ByteOrder.Uint32(src[:4])) @@ -157,6 +164,7 @@ func (m *MessageHeader64) UnmarshalBytes(src []byte) { src = src[4:] // Padding: var _ int32 ~= src[:sizeof(int32)] src = src[4:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -166,13 +174,17 @@ func (m *MessageHeader64) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (m *MessageHeader64) MarshalUnsafe(dst []byte) { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(m), uintptr(m.SizeBytes())) +func (m *MessageHeader64) MarshalUnsafe(dst []byte) []byte { + size := m.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(m), uintptr(size)) + return dst[size:] } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (m *MessageHeader64) UnmarshalUnsafe(src []byte) { - gohacks.Memmove(unsafe.Pointer(m), unsafe.Pointer(&src[0]), uintptr(m.SizeBytes())) +func (m *MessageHeader64) UnmarshalUnsafe(src []byte) []byte { + size := m.SizeBytes() + gohacks.Memmove(unsafe.Pointer(m), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } // CopyOutN implements marshal.Marshallable.CopyOutN. @@ -238,23 +250,23 @@ func (m *multipleMessageHeader64) SizeBytes() int { } // MarshalBytes implements marshal.Marshallable.MarshalBytes. -func (m *multipleMessageHeader64) MarshalBytes(dst []byte) { - m.msgHdr.MarshalBytes(dst[:m.msgHdr.SizeBytes()]) - dst = dst[m.msgHdr.SizeBytes():] +func (m *multipleMessageHeader64) MarshalBytes(dst []byte) []byte { + dst = m.msgHdr.MarshalBytes(dst) hostarch.ByteOrder.PutUint32(dst[:4], uint32(m.msgLen)) dst = dst[4:] // Padding: dst[:sizeof(int32)] ~= int32(0) dst = dst[4:] + return dst } // UnmarshalBytes implements marshal.Marshallable.UnmarshalBytes. -func (m *multipleMessageHeader64) UnmarshalBytes(src []byte) { - m.msgHdr.UnmarshalBytes(src[:m.msgHdr.SizeBytes()]) - src = src[m.msgHdr.SizeBytes():] +func (m *multipleMessageHeader64) UnmarshalBytes(src []byte) []byte { + src = m.msgHdr.UnmarshalBytes(src) m.msgLen = uint32(hostarch.ByteOrder.Uint32(src[:4])) src = src[4:] // Padding: var _ int32 ~= src[:sizeof(int32)] src = src[4:] + return src } // Packed implements marshal.Marshallable.Packed. @@ -264,23 +276,25 @@ func (m *multipleMessageHeader64) Packed() bool { } // MarshalUnsafe implements marshal.Marshallable.MarshalUnsafe. -func (m *multipleMessageHeader64) MarshalUnsafe(dst []byte) { +func (m *multipleMessageHeader64) MarshalUnsafe(dst []byte) []byte { if m.msgHdr.Packed() { - gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(m), uintptr(m.SizeBytes())) - } else { - // Type multipleMessageHeader64 doesn't have a packed layout in memory, fallback to MarshalBytes. - m.MarshalBytes(dst) + size := m.SizeBytes() + gohacks.Memmove(unsafe.Pointer(&dst[0]), unsafe.Pointer(m), uintptr(size)) + return dst[size:] } + // Type multipleMessageHeader64 doesn't have a packed layout in memory, fallback to MarshalBytes. + return m.MarshalBytes(dst) } // UnmarshalUnsafe implements marshal.Marshallable.UnmarshalUnsafe. -func (m *multipleMessageHeader64) UnmarshalUnsafe(src []byte) { +func (m *multipleMessageHeader64) UnmarshalUnsafe(src []byte) []byte { if m.msgHdr.Packed() { - gohacks.Memmove(unsafe.Pointer(m), unsafe.Pointer(&src[0]), uintptr(m.SizeBytes())) - } else { - // Type multipleMessageHeader64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. - m.UnmarshalBytes(src) + size := m.SizeBytes() + gohacks.Memmove(unsafe.Pointer(m), unsafe.Pointer(&src[0]), uintptr(size)) + return src[size:] } + // Type multipleMessageHeader64 doesn't have a packed layout in memory, fallback to UnmarshalBytes. + return m.UnmarshalBytes(src) } // CopyOutN implements marshal.Marshallable.CopyOutN. |