mirror of
https://github.com/rwinkhart/sys.git
synced 2026-09-03 23:57:32 -04:00
unix: make solaris syscall tests less flaky
Fixes golang/go#58259 Change-Id: I1e8a83ed6ee3be8165c771b81a3cbdd474216c02 Reviewed-on: https://go-review.googlesource.com/c/sys/+/465055 Auto-Submit: Ian Lance Taylor <iant@google.com> Run-TryBot: Ian Lance Taylor <iant@google.com> Auto-Submit: Bryan Mills <bcmills@google.com> Run-TryBot: Bryan Mills <bcmills@google.com> Reviewed-by: Bryan Mills <bcmills@google.com> TryBot-Result: Gopher Robot <gobot@golang.org> Reviewed-by: Ian Lance Taylor <iant@google.com>
This commit is contained in:
committed by
Gopher Robot
parent
ff18efa0a3
commit
d0781cc69b
@@ -18,6 +18,40 @@ import (
|
||||
"golang.org/x/sys/unix"
|
||||
)
|
||||
|
||||
// getOneRetry wraps EventPort.GetOne which in turn wraps a syscall that can be
|
||||
// interrupted causing us to receive EINTR.
|
||||
// To prevent our tests from flaking, we retry the syscall until it works
|
||||
// rather than get unexpected results in our tests.
|
||||
func getOneRetry(t *testing.T, p *unix.EventPort, timeout *unix.Timespec) (e *unix.PortEvent, err error) {
|
||||
t.Helper()
|
||||
for {
|
||||
e, err = p.GetOne(timeout)
|
||||
if err != unix.EINTR {
|
||||
break
|
||||
}
|
||||
}
|
||||
return e, err
|
||||
}
|
||||
|
||||
// getRetry wraps EventPort.Get which in turn wraps a syscall that can be
|
||||
// interrupted causing us to receive EINTR.
|
||||
// To prevent our tests from flaking, we retry the syscall until it works
|
||||
// rather than get unexpected results in our tests.
|
||||
func getRetry(t *testing.T, p *unix.EventPort, s []unix.PortEvent, min int, timeout *unix.Timespec) (n int, err error) {
|
||||
t.Helper()
|
||||
for {
|
||||
n, err = p.Get(s, min, timeout)
|
||||
if err != unix.EINTR {
|
||||
break
|
||||
}
|
||||
// If we did get EINTR, make sure we got 0 events
|
||||
if n != 0 {
|
||||
t.Fatalf("EventPort.Get returned events on EINTR.\ngot: %d\nexpected: 0", n)
|
||||
}
|
||||
}
|
||||
return n, err
|
||||
}
|
||||
|
||||
func TestStatvfs(t *testing.T) {
|
||||
if err := unix.Statvfs("", nil); err == nil {
|
||||
t.Fatal(`Statvfs("") expected failure`)
|
||||
@@ -84,13 +118,13 @@ func TestBasicEventPort(t *testing.T) {
|
||||
bs := []byte{42}
|
||||
tmpfile.Write(bs)
|
||||
timeout := new(unix.Timespec)
|
||||
timeout.Sec = 1
|
||||
pevent, err := port.GetOne(timeout)
|
||||
timeout.Nsec = 100
|
||||
pevent, err := getOneRetry(t, port, timeout)
|
||||
if err == unix.ETIME {
|
||||
t.Errorf("GetOne timed out: %v", err)
|
||||
}
|
||||
if err != nil {
|
||||
t.Errorf("GetOne failed: %v", err)
|
||||
t.Fatalf("GetOne failed: %v", err)
|
||||
}
|
||||
if pevent.Path != path {
|
||||
t.Errorf("Path mismatch: %v != %v", pevent.Path, path)
|
||||
@@ -135,13 +169,13 @@ func TestEventPortFds(t *testing.T) {
|
||||
t.Errorf("Pending() failed: %v, %v", n, err)
|
||||
}
|
||||
timeout := new(unix.Timespec)
|
||||
timeout.Sec = 1
|
||||
pevent, err := port.GetOne(timeout)
|
||||
timeout.Nsec = 100
|
||||
pevent, err := getOneRetry(t, port, timeout)
|
||||
if err == unix.ETIME {
|
||||
t.Errorf("GetOne timed out: %v", err)
|
||||
}
|
||||
if err != nil {
|
||||
t.Errorf("GetOne failed: %v", err)
|
||||
t.Fatalf("GetOne failed: %v", err)
|
||||
}
|
||||
if pevent.Fd != fd {
|
||||
t.Errorf("Fd mismatch: %v != %v", pevent.Fd, fd)
|
||||
@@ -181,10 +215,8 @@ func TestEventPortErrors(t *testing.T) {
|
||||
}
|
||||
timeout := new(unix.Timespec)
|
||||
timeout.Nsec = 1
|
||||
_, err = port.GetOne(timeout)
|
||||
_, err = getOneRetry(t, port, timeout)
|
||||
if err != unix.ETIME {
|
||||
// See https://go.dev/issue/58259
|
||||
// Perhaps we sometimes get EINTR ???
|
||||
t.Errorf("port.GetOne(%v) returned error %v, want %v", timeout, err, unix.ETIME)
|
||||
}
|
||||
err = port.DissociateFd(uintptr(0))
|
||||
@@ -192,15 +224,15 @@ func TestEventPortErrors(t *testing.T) {
|
||||
t.Errorf("unexpected success dissociating unassociated fd")
|
||||
}
|
||||
events := make([]unix.PortEvent, 4)
|
||||
_, err = port.Get(events, 5, nil)
|
||||
_, err = getRetry(t, port, events, 5, nil)
|
||||
if err == nil {
|
||||
t.Errorf("unexpected success calling Get with min greater than len of slice")
|
||||
}
|
||||
_, err = port.Get(nil, 1, nil)
|
||||
_, err = getRetry(t, port, nil, 1, nil)
|
||||
if err == nil {
|
||||
t.Errorf("unexpected success calling Get with nil slice")
|
||||
}
|
||||
_, err = port.Get(nil, 0, nil)
|
||||
_, err = getRetry(t, port, nil, 0, nil)
|
||||
if err == nil {
|
||||
t.Errorf("unexpected success calling Get with nil slice")
|
||||
}
|
||||
@@ -232,7 +264,13 @@ func ExamplePortEvent() {
|
||||
w.Write(bs)
|
||||
timeout := new(unix.Timespec)
|
||||
timeout.Sec = 1
|
||||
pevent, err := port.GetOne(timeout)
|
||||
var pevent *unix.PortEvent
|
||||
for {
|
||||
pevent, err = port.GetOne(timeout)
|
||||
if err != unix.EINTR {
|
||||
break
|
||||
}
|
||||
}
|
||||
if err != nil {
|
||||
fmt.Printf("didn't get the expected event: %v\n", err)
|
||||
}
|
||||
@@ -278,7 +316,7 @@ func TestPortEventSlices(t *testing.T) {
|
||||
timeout := new(unix.Timespec)
|
||||
timeout.Nsec = 1
|
||||
events := make([]unix.PortEvent, 4)
|
||||
n, err = port.Get(events, 3, timeout)
|
||||
n, err = getRetry(t, port, events, 3, timeout)
|
||||
if err != nil {
|
||||
t.Errorf("Get failed: %v", err)
|
||||
}
|
||||
@@ -291,7 +329,7 @@ func TestPortEventSlices(t *testing.T) {
|
||||
t.Errorf("unexpected event. got %v, expected %v", p.Events, unix.FILE_DELETE)
|
||||
}
|
||||
}
|
||||
n, err = port.Get(events, 3, timeout)
|
||||
n, err = getRetry(t, port, events, 3, timeout)
|
||||
if err != unix.ETIME {
|
||||
t.Errorf("unexpected error. got %v, expected %v", err, unix.ETIME)
|
||||
}
|
||||
@@ -314,7 +352,7 @@ func TestPortEventSlices(t *testing.T) {
|
||||
bs := []byte{41}
|
||||
w.Write(bs)
|
||||
|
||||
n, err = port.Get(events, 1, timeout)
|
||||
n, err = getRetry(t, port, events, 1, timeout)
|
||||
if err != nil {
|
||||
t.Errorf("Get failed: %v", err)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user