mirror of
https://github.com/opencontainers/runc.git
synced 2026-07-11 06:03:57 +08:00
int/linux: add/use Dup3, Open, Openat
Signed-off-by: Kir Kolyshkin <kolyshkin@gmail.com>
This commit is contained in:
@@ -6,6 +6,14 @@ import (
|
|||||||
"golang.org/x/sys/unix"
|
"golang.org/x/sys/unix"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Dup3 wraps [unix.Dup3].
|
||||||
|
func Dup3(oldfd, newfd, flags int) error {
|
||||||
|
err := retryOnEINTR(func() error {
|
||||||
|
return unix.Dup3(oldfd, newfd, flags)
|
||||||
|
})
|
||||||
|
return os.NewSyscallError("dup3", err)
|
||||||
|
}
|
||||||
|
|
||||||
// Exec wraps [unix.Exec].
|
// Exec wraps [unix.Exec].
|
||||||
func Exec(cmd string, args []string, env []string) error {
|
func Exec(cmd string, args []string, env []string) error {
|
||||||
err := retryOnEINTR(func() error {
|
err := retryOnEINTR(func() error {
|
||||||
@@ -23,6 +31,28 @@ func Getwd() (wd string, err error) {
|
|||||||
return wd, os.NewSyscallError("getwd", err)
|
return wd, os.NewSyscallError("getwd", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Open wraps [unix.Open].
|
||||||
|
func Open(path string, mode int, perm uint32) (fd int, err error) {
|
||||||
|
fd, err = retryOnEINTR2(func() (int, error) {
|
||||||
|
return unix.Open(path, mode, perm)
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
return -1, &os.PathError{Op: "open", Path: path, Err: err}
|
||||||
|
}
|
||||||
|
return fd, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// Openat wraps [unix.Openat].
|
||||||
|
func Openat(dirfd int, path string, mode int, perm uint32) (fd int, err error) {
|
||||||
|
fd, err = retryOnEINTR2(func() (int, error) {
|
||||||
|
return unix.Openat(dirfd, path, mode, perm)
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
return -1, &os.PathError{Op: "openat", Path: path, Err: err}
|
||||||
|
}
|
||||||
|
return fd, nil
|
||||||
|
}
|
||||||
|
|
||||||
// Sendmsg wraps [unix.Sendmsg].
|
// Sendmsg wraps [unix.Sendmsg].
|
||||||
func Sendmsg(fd int, p, oob []byte, to unix.Sockaddr, flags int) error {
|
func Sendmsg(fd int, p, oob []byte, to unix.Sockaddr, flags int) error {
|
||||||
err := retryOnEINTR(func() error {
|
err := retryOnEINTR(func() error {
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ package libcontainer
|
|||||||
import (
|
import (
|
||||||
"os"
|
"os"
|
||||||
|
|
||||||
|
"github.com/opencontainers/runc/internal/linux"
|
||||||
"golang.org/x/sys/unix"
|
"golang.org/x/sys/unix"
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -26,16 +27,12 @@ func mountConsole(slavePath string) error {
|
|||||||
// dupStdio opens the slavePath for the console and dups the fds to the current
|
// dupStdio opens the slavePath for the console and dups the fds to the current
|
||||||
// processes stdio, fd 0,1,2.
|
// processes stdio, fd 0,1,2.
|
||||||
func dupStdio(slavePath string) error {
|
func dupStdio(slavePath string) error {
|
||||||
fd, err := unix.Open(slavePath, unix.O_RDWR, 0)
|
fd, err := linux.Open(slavePath, unix.O_RDWR, 0)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &os.PathError{
|
return err
|
||||||
Op: "open",
|
|
||||||
Path: slavePath,
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
for _, i := range []int{0, 1, 2} {
|
for _, i := range []int{0, 1, 2} {
|
||||||
if err := unix.Dup3(fd, i, 0); err != nil {
|
if err := linux.Dup3(fd, i, 0); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -24,6 +24,7 @@ import (
|
|||||||
"github.com/opencontainers/cgroups"
|
"github.com/opencontainers/cgroups"
|
||||||
devices "github.com/opencontainers/cgroups/devices/config"
|
devices "github.com/opencontainers/cgroups/devices/config"
|
||||||
"github.com/opencontainers/cgroups/fs2"
|
"github.com/opencontainers/cgroups/fs2"
|
||||||
|
"github.com/opencontainers/runc/internal/linux"
|
||||||
"github.com/opencontainers/runc/libcontainer/configs"
|
"github.com/opencontainers/runc/libcontainer/configs"
|
||||||
"github.com/opencontainers/runc/libcontainer/utils"
|
"github.com/opencontainers/runc/libcontainer/utils"
|
||||||
)
|
)
|
||||||
@@ -883,12 +884,8 @@ func reOpenDevNull() error {
|
|||||||
}
|
}
|
||||||
if stat.Rdev == devNullStat.Rdev {
|
if stat.Rdev == devNullStat.Rdev {
|
||||||
// Close and re-open the fd.
|
// Close and re-open the fd.
|
||||||
if err := unix.Dup3(int(file.Fd()), fd, 0); err != nil {
|
if err := linux.Dup3(int(file.Fd()), fd, 0); err != nil {
|
||||||
return &os.PathError{
|
return err
|
||||||
Op: "dup3",
|
|
||||||
Path: "fd " + strconv.Itoa(int(file.Fd())),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1063,15 +1060,15 @@ func pivotRoot(rootfs string) error {
|
|||||||
// with pivot_root this allows us to pivot without creating directories in
|
// with pivot_root this allows us to pivot without creating directories in
|
||||||
// the rootfs. Shout-outs to the LXC developers for giving us this idea.
|
// the rootfs. Shout-outs to the LXC developers for giving us this idea.
|
||||||
|
|
||||||
oldroot, err := unix.Open("/", unix.O_DIRECTORY|unix.O_RDONLY, 0)
|
oldroot, err := linux.Open("/", unix.O_DIRECTORY|unix.O_RDONLY, 0)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &os.PathError{Op: "open", Path: "/", Err: err}
|
return err
|
||||||
}
|
}
|
||||||
defer unix.Close(oldroot)
|
defer unix.Close(oldroot)
|
||||||
|
|
||||||
newroot, err := unix.Open(rootfs, unix.O_DIRECTORY|unix.O_RDONLY, 0)
|
newroot, err := linux.Open(rootfs, unix.O_DIRECTORY|unix.O_RDONLY, 0)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &os.PathError{Op: "open", Path: rootfs, Err: err}
|
return err
|
||||||
}
|
}
|
||||||
defer unix.Close(newroot)
|
defer unix.Close(newroot)
|
||||||
|
|
||||||
|
|||||||
@@ -262,9 +262,9 @@ func (l *linuxStandardInit) Init() error {
|
|||||||
// user process. We open it through /proc/self/fd/$fd, because the fd that
|
// user process. We open it through /proc/self/fd/$fd, because the fd that
|
||||||
// was given to us was an O_PATH fd to the fifo itself. Linux allows us to
|
// was given to us was an O_PATH fd to the fifo itself. Linux allows us to
|
||||||
// re-open an O_PATH fd through /proc.
|
// re-open an O_PATH fd through /proc.
|
||||||
fd, err := unix.Open(fifoPath, unix.O_WRONLY|unix.O_CLOEXEC, 0)
|
fd, err := linux.Open(fifoPath, unix.O_WRONLY|unix.O_CLOEXEC, 0)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &os.PathError{Op: "open exec fifo", Path: fifoPath, Err: err}
|
return err
|
||||||
}
|
}
|
||||||
if _, err := unix.Write(fd, []byte("0")); err != nil {
|
if _, err := unix.Write(fd, []byte("0")); err != nil {
|
||||||
return &os.PathError{Op: "write exec fifo", Path: fifoPath, Err: err}
|
return &os.PathError{Op: "write exec fifo", Path: fifoPath, Err: err}
|
||||||
|
|||||||
@@ -14,6 +14,7 @@ import (
|
|||||||
_ "unsafe" // for go:linkname
|
_ "unsafe" // for go:linkname
|
||||||
|
|
||||||
securejoin "github.com/cyphar/filepath-securejoin"
|
securejoin "github.com/cyphar/filepath-securejoin"
|
||||||
|
"github.com/opencontainers/runc/internal/linux"
|
||||||
"github.com/sirupsen/logrus"
|
"github.com/sirupsen/logrus"
|
||||||
"golang.org/x/sys/unix"
|
"golang.org/x/sys/unix"
|
||||||
)
|
)
|
||||||
@@ -358,9 +359,9 @@ func Openat(dir *os.File, path string, flags int, mode uint32) (*os.File, error)
|
|||||||
}
|
}
|
||||||
flags |= unix.O_CLOEXEC
|
flags |= unix.O_CLOEXEC
|
||||||
|
|
||||||
fd, err := unix.Openat(dirFd, path, flags, mode)
|
fd, err := linux.Openat(dirFd, path, flags, mode)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, &os.PathError{Op: "openat", Path: path, Err: err}
|
return nil, err
|
||||||
}
|
}
|
||||||
return os.NewFile(uintptr(fd), dir.Name()+"/"+path), nil
|
return os.NewFile(uintptr(fd), dir.Name()+"/"+path), nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -14,6 +14,7 @@ import (
|
|||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
securejoin "github.com/cyphar/filepath-securejoin"
|
securejoin "github.com/cyphar/filepath-securejoin"
|
||||||
|
"github.com/opencontainers/runc/internal/linux"
|
||||||
"github.com/opencontainers/runtime-spec/specs-go"
|
"github.com/opencontainers/runtime-spec/specs-go"
|
||||||
libseccomp "github.com/seccomp/libseccomp-golang"
|
libseccomp "github.com/seccomp/libseccomp-golang"
|
||||||
"github.com/sirupsen/logrus"
|
"github.com/sirupsen/logrus"
|
||||||
@@ -124,7 +125,7 @@ func handleNewMessage(sockfd int) (uintptr, string, error) {
|
|||||||
func readArgString(pid uint32, offset int64) (string, error) {
|
func readArgString(pid uint32, offset int64) (string, error) {
|
||||||
buffer := make([]byte, 4096) // PATH_MAX
|
buffer := make([]byte, 4096) // PATH_MAX
|
||||||
|
|
||||||
memfd, err := unix.Open(fmt.Sprintf("/proc/%d/mem", pid), unix.O_RDONLY, 0o777)
|
memfd, err := linux.Open(fmt.Sprintf("/proc/%d/mem", pid), unix.O_RDONLY, 0o777)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user