Skip to content

Commit

Permalink
syscall: avoid writing to p when Pipe(p) fails
Browse files Browse the repository at this point in the history
Generally speaking Go functions make no guarantees
about what has happened to result parameters on error,
and Pipe is no exception: callers should avoid looking at
p if Pipe returns an error.

However, we had a bug in which ForkExec was using the
content of p after a failed Pipe, and others may too.
As a robustness fix, make Pipe avoid writing to p on failure.

Updates golang#50057

Change-Id: Ie8955025dbd20702fabadc9bbe1d1a5ac0f36305
Reviewed-on: https://team-review.git.corp.google.com/c/golang/go-private/+/1291271
Reviewed-by: Ian Lance Taylor <[email protected]>
Reviewed-on: https://go-review.googlesource.com/c/go/+/370577
Run-TryBot: Filippo Valsorda <[email protected]>
Trust: Russ Cox <[email protected]>
TryBot-Result: Gopher Robot <[email protected]>
Reviewed-by: Alex Rakoczy <[email protected]>
  • Loading branch information
rsc authored and FiloSottile committed Dec 9, 2021
1 parent a76511f commit 474ebb9
Show file tree
Hide file tree
Showing 9 changed files with 40 additions and 18 deletions.
6 changes: 4 additions & 2 deletions src/syscall/syscall_aix.go
Original file line number Diff line number Diff line change
Expand Up @@ -66,8 +66,10 @@ func Pipe(p []int) (err error) {
}
var pp [2]_C_int
err = pipe(&pp)
p[0] = int(pp[0])
p[1] = int(pp[1])
if err == nil {
p[0] = int(pp[0])
p[1] = int(pp[1])
}
return
}

Expand Down
6 changes: 4 additions & 2 deletions src/syscall/syscall_darwin.go
Original file line number Diff line number Diff line change
Expand Up @@ -80,8 +80,10 @@ func Pipe(p []int) (err error) {
}
var q [2]int32
err = pipe(&q)
p[0] = int(q[0])
p[1] = int(q[1])
if err == nil {
p[0] = int(q[0])
p[1] = int(q[1])
}
return
}

Expand Down
12 changes: 9 additions & 3 deletions src/syscall/syscall_dragonfly.go
Original file line number Diff line number Diff line change
Expand Up @@ -98,8 +98,11 @@ func Pipe(p []int) (err error) {
if len(p) != 2 {
return EINVAL
}
p[0], p[1], err = pipe()
return
r, w, err := pipe()
if err == nil {
p[0], p[1] = r, w
}
return err
}

//sysnb pipe2(p *[2]_C_int, flags int) (r int, w int, err error)
Expand All @@ -111,7 +114,10 @@ func Pipe2(p []int, flags int) (err error) {
var pp [2]_C_int
// pipe2 on dragonfly takes an fds array as an argument, but still
// returns the file descriptors.
p[0], p[1], err = pipe2(&pp, flags)
r, w, err := pipe2(&pp, flags)
if err == nil {
p[0], p[1] = r, w
}
return err
}

Expand Down
6 changes: 4 additions & 2 deletions src/syscall/syscall_freebsd.go
Original file line number Diff line number Diff line change
Expand Up @@ -105,8 +105,10 @@ func Pipe2(p []int, flags int) error {
}
var pp [2]_C_int
err := pipe2(&pp, flags)
p[0] = int(pp[0])
p[1] = int(pp[1])
if err == nil {
p[0] = int(pp[0])
p[1] = int(pp[1])
}
return err
}

Expand Down
6 changes: 4 additions & 2 deletions src/syscall/syscall_linux.go
Original file line number Diff line number Diff line change
Expand Up @@ -173,8 +173,10 @@ func Pipe2(p []int, flags int) error {
}
var pp [2]_C_int
err := pipe2(&pp, flags)
p[0] = int(pp[0])
p[1] = int(pp[1])
if err == nil {
p[0] = int(pp[0])
p[1] = int(pp[1])
}
return err
}

Expand Down
6 changes: 4 additions & 2 deletions src/syscall/syscall_netbsd.go
Original file line number Diff line number Diff line change
Expand Up @@ -114,8 +114,10 @@ func Pipe2(p []int, flags int) error {
}
var pp [2]_C_int
err := pipe2(&pp, flags)
p[0] = int(pp[0])
p[1] = int(pp[1])
if err == nil {
p[0] = int(pp[0])
p[1] = int(pp[1])
}
return err
}

Expand Down
6 changes: 4 additions & 2 deletions src/syscall/syscall_openbsd.go
Original file line number Diff line number Diff line change
Expand Up @@ -72,8 +72,10 @@ func Pipe2(p []int, flags int) error {
}
var pp [2]_C_int
err := pipe2(&pp, flags)
p[0] = int(pp[0])
p[1] = int(pp[1])
if err == nil {
p[0] = int(pp[0])
p[1] = int(pp[1])
}
return err
}

Expand Down
6 changes: 4 additions & 2 deletions src/syscall/syscall_plan9.go
Original file line number Diff line number Diff line change
Expand Up @@ -198,8 +198,10 @@ func Pipe(p []int) (err error) {
}
var pp [2]int32
err = pipe(&pp)
p[0] = int(pp[0])
p[1] = int(pp[1])
if err == nil {
p[0] = int(pp[0])
p[1] = int(pp[1])
}
return
}

Expand Down
4 changes: 3 additions & 1 deletion src/syscall/syscall_solaris.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,9 @@ func Pipe(p []int) (err error) {
if e1 != 0 {
err = Errno(e1)
}
p[0], p[1] = int(r0), int(w0)
if err == nil {
p[0], p[1] = int(r0), int(w0)
}
return
}

Expand Down

0 comments on commit 474ebb9

Please sign in to comment.