diff options
| author | Tobias Klauser <tklauser@distanz.ch> | 2022-03-04 09:49:32 +0100 |
|---|---|---|
| committer | Tobias Klauser <tobias.klauser@gmail.com> | 2022-03-05 08:36:13 +0000 |
| commit | 55a60cadc3f5d01f76ac9435da2ed941e194a29b (patch) | |
| tree | 9867ff3e90013113d6ed05b0c58cf1e92be365e4 /src/syscall/exec_libc2.go | |
| parent | bf97c99b62fe7d6652cc8c807dbc91998d488a01 (diff) | |
| download | go-55a60cadc3f5d01f76ac9435da2ed941e194a29b.tar.xz | |
syscall: use dup3 in forkAndExecInChild on OpenBSD
Use dup3(oldfd, newfd, O_CLOEXEC) to atomically duplicate the file
descriptor and mark is as close-on-exec instead of dup2 & fcntl.
The dup3 system call first appeared in OpenBSD 5.7.
Change-Id: Ic06c2c7089dcdbd931ee24e5e8c316879d81474e
Reviewed-on: https://go-review.googlesource.com/c/go/+/389974
Trust: Tobias Klauser <tobias.klauser@gmail.com>
Run-TryBot: Tobias Klauser <tobias.klauser@gmail.com>
Reviewed-by: Ian Lance Taylor <iant@golang.org>
Diffstat (limited to 'src/syscall/exec_libc2.go')
| -rw-r--r-- | src/syscall/exec_libc2.go | 23 |
1 files changed, 19 insertions, 4 deletions
diff --git a/src/syscall/exec_libc2.go b/src/syscall/exec_libc2.go index b05f053bbf..91a39ba1b8 100644 --- a/src/syscall/exec_libc2.go +++ b/src/syscall/exec_libc2.go @@ -8,6 +8,7 @@ package syscall import ( "internal/abi" + "runtime" "unsafe" ) @@ -180,11 +181,18 @@ func forkAndExecInChild(argv0 *byte, argv, envv []*byte, chroot, dir *byte, attr // Pass 1: look for fd[i] < i and move those up above len(fd) // so that pass 2 won't stomp on an fd it needs later. if pipe < nextfd { - _, _, err1 = rawSyscall(abi.FuncPCABI0(libc_dup2_trampoline), uintptr(pipe), uintptr(nextfd), 0) + if runtime.GOOS == "openbsd" { + _, _, err1 = rawSyscall(dupTrampoline, uintptr(pipe), uintptr(nextfd), O_CLOEXEC) + } else { + _, _, err1 = rawSyscall(dupTrampoline, uintptr(pipe), uintptr(nextfd), 0) + if err1 != 0 { + goto childerror + } + _, _, err1 = rawSyscall(abi.FuncPCABI0(libc_fcntl_trampoline), uintptr(nextfd), F_SETFD, FD_CLOEXEC) + } if err1 != 0 { goto childerror } - rawSyscall(abi.FuncPCABI0(libc_fcntl_trampoline), uintptr(nextfd), F_SETFD, FD_CLOEXEC) pipe = nextfd nextfd++ } @@ -193,11 +201,18 @@ func forkAndExecInChild(argv0 *byte, argv, envv []*byte, chroot, dir *byte, attr if nextfd == pipe { // don't stomp on pipe nextfd++ } - _, _, err1 = rawSyscall(abi.FuncPCABI0(libc_dup2_trampoline), uintptr(fd[i]), uintptr(nextfd), 0) + if runtime.GOOS == "openbsd" { + _, _, err1 = rawSyscall(dupTrampoline, uintptr(fd[i]), uintptr(nextfd), O_CLOEXEC) + } else { + _, _, err1 = rawSyscall(dupTrampoline, uintptr(fd[i]), uintptr(nextfd), 0) + if err1 != 0 { + goto childerror + } + _, _, err1 = rawSyscall(abi.FuncPCABI0(libc_fcntl_trampoline), uintptr(nextfd), F_SETFD, FD_CLOEXEC) + } if err1 != 0 { goto childerror } - rawSyscall(abi.FuncPCABI0(libc_fcntl_trampoline), uintptr(nextfd), F_SETFD, FD_CLOEXEC) fd[i] = nextfd nextfd++ } |
