[syscall/zx] Remove syscall/zx/mxerror

Change-Id: I37da4810b59310e1f1eeef9fd0dd7c63a6b44c24
diff --git a/src/go/build/deps_test.go b/src/go/build/deps_test.go
index 9db279f..cfd2f30 100644
--- a/src/go/build/deps_test.go
+++ b/src/go/build/deps_test.go
@@ -165,10 +165,9 @@
 	"syscall/zx/fidl/bindingstest": {"L0"},
 	"syscall/zx/io":                {"L0"},
 	"syscall/zx/mem":               {"L0"},
-	"syscall/zx/mxerror":           {"L0", "fmt"},
 	"syscall/zx/mxnet":             {"L0"},
 	"syscall/zx/net":               {"L0"},
-	"syscall/zx/zxsocket":          {"L0", "syscall", "syscall/zx/mxerror"},
+	"syscall/zx/zxsocket":          {"L0", "syscall"},
 	"syscall/zx/zxwait":            {"L0"},
 
 	"internal/syscall/unix":             {"L0", "syscall"},
diff --git a/src/internal/poll/fd_fuchsia.go b/src/internal/poll/fd_fuchsia.go
index 152e6ca..89b703d 100644
--- a/src/internal/poll/fd_fuchsia.go
+++ b/src/internal/poll/fd_fuchsia.go
@@ -214,18 +214,16 @@
 		code, err := s.Accept(0)
 		if code == syscall.EAGAIN {
 			// TODO: non-blocking support, pass this to the poller
-			obs, err := s.Wait(mxnet.MXSIO_SIGNAL_INCOMING|zx.SignalSocketPeerClosed, zx.TimensecInfinite)
-			if err != nil {
+			if obs, err := s.Wait(mxnet.MXSIO_SIGNAL_INCOMING|zx.SignalSocketPeerClosed, zx.TimensecInfinite); err != nil {
 				return nil, err
-			}
-			if obs&zx.SignalSocketPeerClosed != 0 {
+			} else if obs&zx.SignalSocketPeerClosed != 0 {
 				return nil, &zx.Error{Status: zx.ErrPeerClosed, Text: "zxsocket"}
-			}
-			if obs&mxnet.MXSIO_SIGNAL_INCOMING != 0 {
-				code, err = s.Accept(0)
+			} else if obs&mxnet.MXSIO_SIGNAL_INCOMING != 0 {
+				// fallthrough
 			} else {
 				panic("unreachable")
 			}
+			code, err = s.Accept(0)
 		}
 		if err != nil {
 			return nil, err
diff --git a/src/net/ipsock_fuchsia.go b/src/net/ipsock_fuchsia.go
index e2503af..53b06ac 100644
--- a/src/net/ipsock_fuchsia.go
+++ b/src/net/ipsock_fuchsia.go
@@ -69,10 +69,8 @@
 	socketProvider.mu.Lock()
 	defer socketProvider.mu.Unlock()
 	if socketProvider.h == zx.HandleInvalid {
-		c0, c1, err := zx.NewChannel(0)
-		if err == nil {
-			err = fdio.ServiceConnect("/svc/"+zxnet.SocketProviderName, zx.Handle(c0))
-			if err == nil {
+		if c0, c1, err := zx.NewChannel(0); err == nil {
+			if err := fdio.ServiceConnect("/svc/"+zxnet.SocketProviderName, zx.Handle(c0)); err == nil {
 				socketProvider.h = zx.Handle(c1)
 			}
 		}
@@ -157,19 +155,17 @@
 		b = b[:addrlen]
 		code, err := fd.sock.Connect(b)
 		if code == syscall.EINPROGRESS {
-			obs, err := fd.sock.Wait(mxnet.MXSIO_SIGNAL_OUTGOING|zx.SignalSocketPeerClosed, zx.TimensecInfinite)
-			if err != nil {
+			if obs, err := fd.sock.Wait(mxnet.MXSIO_SIGNAL_OUTGOING|zx.SignalSocketPeerClosed, zx.TimensecInfinite); err != nil {
 				return nil, err
-			}
-			if obs&zx.SignalSocketPeerClosed != 0 {
+			} else if obs&zx.SignalSocketPeerClosed != 0 {
 				return nil, &zx.Error{Status: zx.ErrPeerClosed, Text: "zxsocket"}
-			}
-			if obs&mxnet.MXSIO_SIGNAL_OUTGOING != 0 {
-				// Call connect again to learn the result.
-				code, err = fd.sock.Connect(b)
+			} else if obs&mxnet.MXSIO_SIGNAL_OUTGOING != 0 {
+				// fallthrough
 			} else {
 				panic("unreachable")
 			}
+			// Call connect again to learn the result.
+			code, err = fd.sock.Connect(b)
 		}
 		if err != nil {
 			return nil, err
diff --git a/src/os/error_fuchsia.go b/src/os/error_fuchsia.go
index 0b89e7c..e3a655a 100644
--- a/src/os/error_fuchsia.go
+++ b/src/os/error_fuchsia.go
@@ -13,8 +13,7 @@
 
 func isExist(err error) bool {
 	err = underlyingError(err)
-	switch err := err.(type) {
-	case *zx.Error:
+	if err, ok := err.(*zx.Error); ok {
 		return err.Status == zx.ErrAlreadyExists
 	}
 	return err == syscall.EEXIST || err == syscall.ENOTEMPTY || err == ErrExist
@@ -22,8 +21,7 @@
 
 func isNotExist(err error) bool {
 	err = underlyingError(err)
-	switch err := err.(type) {
-	case *zx.Error:
+	if err, ok := err.(*zx.Error); ok {
 		return err.Status == zx.ErrNotFound
 	}
 	return err == syscall.ENOENT || err == ErrNotExist
@@ -31,8 +29,7 @@
 
 func isPermission(err error) bool {
 	err = underlyingError(err)
-	switch err := err.(type) {
-	case *zx.Error:
+	if err, ok := err.(*zx.Error); ok {
 		return err.Status == zx.ErrAccessDenied
 	}
 	return err == syscall.EACCES || err == syscall.EPERM || err == ErrPermission
diff --git a/src/syscall/syscall_fuchsia.go b/src/syscall/syscall_fuchsia.go
index b087473..c473b5f 100644
--- a/src/syscall/syscall_fuchsia.go
+++ b/src/syscall/syscall_fuchsia.go
@@ -440,18 +440,14 @@
 	return 0, EINVAL
 }
 
-func Seek(fd int, offset int64, whence int) (off int64, err error) {
+func Seek(fd int, offset int64, whence int) (int64, error) {
 	fdsMu.Lock()
 	f := fds[fd-fdsOff]
 	fdsMu.Unlock()
-	off, err = f.Seek(offset, whence)
-	if err != nil {
-		if status, isStatus := err.(*zx.Error); isStatus {
-			if status.Status == zx.ErrNotSupported {
-				if _, isPipe := f.(*fdio.Pipe); isPipe {
-					return off, ESPIPE
-				}
-			}
+	off, err := f.Seek(offset, whence)
+	if err, ok := err.(*zx.Error); ok && err.Status == zx.ErrNotSupported {
+		if _, ok := f.(*fdio.Pipe); ok {
+			return off, ESPIPE
 		}
 	}
 	return off, err
diff --git a/src/syscall/zx/dispatch/dispatcher.go b/src/syscall/zx/dispatch/dispatcher.go
index e607ae6..0652a08 100644
--- a/src/syscall/zx/dispatch/dispatcher.go
+++ b/src/syscall/zx/dispatch/dispatcher.go
@@ -181,9 +181,9 @@
 
 		// If we fail to re-arm, notify the handler of what happened.
 		if err != nil {
-			zxErr := err.(*zx.Error)
-			result = wc.callback(d, zxErr.Status, nil)
-			assertWaitResult(result, zxErr.Status)
+			status := err.(*zx.Error).Status
+			result = wc.callback(d, status, nil)
+			assertWaitResult(result, status)
 		}
 	case WaitFinished:
 		d.mu.Lock()
diff --git a/src/syscall/zx/fdio/pipe.go b/src/syscall/zx/fdio/pipe.go
index 03724b1..d8468198 100644
--- a/src/syscall/zx/fdio/pipe.go
+++ b/src/syscall/zx/fdio/pipe.go
@@ -68,34 +68,32 @@
 	return nil, nil, &zx.Error{Status: zx.ErrNotSupported, Text: "fdio.Pipe"}
 }
 
-func (f *Pipe) Read(data []byte) (n int, err error) {
+func (f *Pipe) Read(data []byte) (int, error) {
 	for {
-		n, err = f.s.Read(data, 0)
-		if err == nil {
-			return n, nil
-		}
-		mxerr, ok := err.(*zx.Error)
-		if !ok {
-			return n, err
-		}
-		switch mxerr.Status {
-		case zx.ErrPeerClosed:
-			return 0, zx.EOF
-		case zx.ErrShouldWait:
-			pending, err := f.Wait(zx.SignalSocketReadable|zx.SignalSocketPeerClosed, zx.TimensecInfinite)
-			if err != nil {
-				return 0, err
+		n, err := f.s.Read(data, 0)
+		if err != nil {
+			if err, ok := err.(*zx.Error); ok {
+				switch err.Status {
+				case zx.ErrPeerClosed:
+					return 0, zx.EOF
+				case zx.ErrShouldWait:
+					pending, err := f.Wait(zx.SignalSocketReadable|zx.SignalSocketPeerClosed, zx.TimensecInfinite)
+					if err != nil {
+						return 0, err
+					}
+					if pending&zx.SignalSocketReadable != 0 {
+						continue
+					}
+					if pending&zx.SignalSocketPeerClosed != 0 {
+						return 0, zx.EOF
+					}
+					// impossible
+					return 0, &zx.Error{Status: zx.ErrInternal, Text: "fdio.Pipe"}
+				}
 			}
-			if pending&zx.SignalSocketReadable != 0 {
-				continue
-			}
-			if pending&zx.SignalSocketPeerClosed != 0 {
-				return 0, zx.EOF
-			}
-			// impossible
-			return 0, &zx.Error{Status: zx.ErrInternal, Text: "fdio.Pipe"}
+			return 0, err
 		}
-		return 0, err
+		return n, nil
 	}
 }
 
@@ -103,34 +101,32 @@
 	return 0, &zx.Error{Status: zx.ErrNotSupported, Text: "fdio.Pipe"}
 }
 
-func (f *Pipe) Write(data []byte) (n int, err error) {
+func (f *Pipe) Write(data []byte) (int, error) {
 	for {
-		n, err = f.s.Write(data, 0)
-		if err == nil {
-			return n, nil
-		}
-		mxerr, ok := err.(*zx.Error)
-		if !ok {
-			return n, err
-		}
-		switch mxerr.Status {
-		case zx.ErrPeerClosed:
-			return 0, zx.EPIPE
-		case zx.ErrShouldWait:
-			pending, err := f.Wait(zx.SignalSocketWritable|zx.SignalSocketPeerClosed, zx.TimensecInfinite)
-			if err != nil {
-				return 0, err
+		n, err := f.s.Write(data, 0)
+		if err != nil {
+			if err, ok := err.(*zx.Error); ok {
+				switch err.Status {
+				case zx.ErrPeerClosed:
+					return 0, zx.EPIPE
+				case zx.ErrShouldWait:
+					pending, err := f.Wait(zx.SignalSocketWritable|zx.SignalSocketPeerClosed, zx.TimensecInfinite)
+					if err != nil {
+						return 0, err
+					}
+					if pending&zx.SignalSocketWritable != 0 {
+						continue
+					}
+					if pending&zx.SignalSocketPeerClosed != 0 {
+						return 0, zx.EPIPE
+					}
+					// impossible
+					return 0, &zx.Error{Status: zx.ErrInternal, Text: "fdio.Pipe"}
+				}
 			}
-			if pending&zx.SignalSocketWritable != 0 {
-				continue
-			}
-			if pending&zx.SignalSocketPeerClosed != 0 {
-				return 0, zx.EPIPE
-			}
-			// impossible
-			return 0, &zx.Error{Status: zx.ErrInternal, Text: "fdio.Pipe"}
+			return 0, err
 		}
-		return 0, err
+		return n, nil
 	}
 }
 
diff --git a/src/syscall/zx/fidl/bindings.go b/src/syscall/zx/fidl/bindings.go
index 978e3ed..85b074d 100644
--- a/src/syscall/zx/fidl/bindings.go
+++ b/src/syscall/zx/fidl/bindings.go
@@ -138,8 +138,7 @@
 
 	nb, nh, err := b.Channel.Read(respb, resph, 0)
 	if err != nil {
-		zxErr, ok := err.(*zx.Error)
-		if ok && zxErr.Status == zx.ErrShouldWait {
+		if err, ok := err.(*zx.Error); ok && err.Status == zx.ErrShouldWait {
 			return true, nil
 		}
 		return false, err
@@ -198,11 +197,10 @@
 // called with the binding's mutex set.
 func (b *Binding) close() error {
 	if err := d.CancelWait(*b.id); err != nil {
-		zxErr, ok := err.(*zx.Error)
 		// If it just says that the ID isn't found, there are cases where this is
 		// a reasonable error (particularly when we're in the middle of handling
 		// a signal from the dispatcher).
-		if !ok || zxErr.Status != zx.ErrNotFound {
+		if err, ok := err.(*zx.Error); !ok || err.Status != zx.ErrNotFound {
 			// Attempt to close the channel if we hit a more serious error.
 			b.Channel.Close()
 			return err
diff --git a/src/syscall/zx/handle.go b/src/syscall/zx/handle.go
index 5e77328..a832c0b 100644
--- a/src/syscall/zx/handle.go
+++ b/src/syscall/zx/handle.go
@@ -43,26 +43,25 @@
 	return (*Handle)(s)
 }
 
-func (s *Socket) Read(data []byte, flags uint32) (n int, err error) {
-	var actual uint
-	var p unsafe.Pointer
+func bytesPtr(data []byte) unsafe.Pointer {
 	if len(data) > 0 {
-		p = unsafe.Pointer(&data[0])
+		return unsafe.Pointer(&data[0])
 	}
-	status := sys_socket_read(Handle(*s), flags, p, uint(len(data)), &actual)
+	return unsafe.Pointer(uintptr(0))
+}
+
+func (s *Socket) Read(data []byte, flags uint32) (int, error) {
+	var actual uint
+	status := sys_socket_read(Handle(*s), flags, bytesPtr(data), uint(len(data)), &actual)
 	if status != ErrOk {
 		return int(actual), &Error{Status: status, Text: "zx.Socket.Read"}
 	}
 	return int(actual), nil
 }
 
-func (s *Socket) Write(data []byte, flags uint32) (n int, err error) {
-	var p unsafe.Pointer
-	if len(data) > 0 {
-		p = unsafe.Pointer(&data[0])
-	}
+func (s *Socket) Write(data []byte, flags uint32) (int, error) {
 	var actual uint
-	status := sys_socket_write(Handle(*s), flags, p, uint(len(data)), &actual)
+	status := sys_socket_write(Handle(*s), flags, bytesPtr(data), uint(len(data)), &actual)
 	if status != ErrOk {
 		return int(actual), &Error{Status: status, Text: "zx.Socket.Write"}
 	}
@@ -90,7 +89,7 @@
 	return err
 }
 
-func (s *Socket) Shutdown(flags uint32) (err error) {
+func (s *Socket) Shutdown(flags uint32) error {
 	status := Sys_socket_shutdown(Handle(*s), flags)
 	if status != ErrOk {
 		return &Error{Status: status, Text: "zx.Socket.Shutdown"}
@@ -98,7 +97,7 @@
 	return nil
 }
 
-func NewSocket(flags uint32) (s0, s1 Socket, err error) {
+func NewSocket(flags uint32) (Socket, Socket, error) {
 	var h0, h1 Handle
 	if status := sys_socket_create(flags, &h0, &h1); status != ErrOk {
 		return Socket(HandleInvalid), Socket(HandleInvalid), &Error{Status: status, Text: "zx.Socket"}
@@ -108,7 +107,7 @@
 
 type Event Handle
 
-func NewEvent(options uint32) (e Event, err error) {
+func NewEvent(options uint32) (Event, error) {
 	var h Handle
 	if status := Sys_event_create(options, &h); status != ErrOk {
 		return Event(HandleInvalid), &Error{Status: status, Text: "zx.Event"}
@@ -166,34 +165,27 @@
 	return nil
 }
 
-func (h *Handle) GetInfo(topic uint32, data []byte) (actual, avail uint, err error) {
+func (h *Handle) GetInfo(topic uint32, data []byte) (actual, avail uint, _ error) {
 	dataBytes := uint(len(data))
-	var dataPtr unsafe.Pointer
-	if dataBytes > 0 {
-		dataPtr = unsafe.Pointer(&data[0])
+	if status := Sys_object_get_info(*h, topic, bytesPtr(data), dataBytes, &actual, &avail); status != ErrOk {
+		return 0, 0, &Error{Status: status, Text: "zx.Handle.GetInfo"}
 	}
-	if status := Sys_object_get_info(*h, topic, dataPtr, dataBytes, &actual, &avail); status != ErrOk {
-		err = &Error{Status: status, Text: "zx.Handle.GetInfo"}
-	}
-	return
+	return actual, avail, nil
 }
 
-func (h *Handle) GetInfoHandleBasic() (info InfoHandleBasic, err error) {
+func (h *Handle) GetInfoHandleBasic() (InfoHandleBasic, error) {
+	var info InfoHandleBasic
 	dataBytes := uint(unsafe.Sizeof(info))
 	dataPtr := unsafe.Pointer(&info)
 	if status := Sys_object_get_info(*h, ObjectInfoHandleBasic, dataPtr, dataBytes, nil, nil); status != ErrOk {
-		err = &Error{Status: status, Text: "zx.Handle.GetInfoHandleBasic"}
+		return info, &Error{Status: status, Text: "zx.Handle.GetInfoHandleBasic"}
 	}
-	return
+	return info, nil
 }
 
 func (h *Handle) GetProperty(property uint32, data []byte) error {
 	var numBytes = uint(len(data))
-	var dataPtr unsafe.Pointer
-	if numBytes > 0 {
-		dataPtr = unsafe.Pointer(&data[0])
-	}
-	if status := Sys_object_get_property(*h, property, dataPtr, numBytes); status != ErrOk {
+	if status := Sys_object_get_property(*h, property, bytesPtr(data), numBytes); status != ErrOk {
 		return &Error{Status: status, Text: "zx.Handle.GetProperty"}
 	}
 	return nil
@@ -201,11 +193,7 @@
 
 func (h *Handle) SetProperty(property uint32, data []byte) error {
 	var numBytes = uint(len(data))
-	var dataPtr unsafe.Pointer
-	if numBytes > 0 {
-		dataPtr = unsafe.Pointer(&data[0])
-	}
-	if status := Sys_object_set_property(*h, property, dataPtr, numBytes); status != ErrOk {
+	if status := Sys_object_set_property(*h, property, bytesPtr(data), numBytes); status != ErrOk {
 		return &Error{Status: status, Text: "zx.Handle.SetProperty"}
 	}
 	return nil
@@ -216,7 +204,11 @@
 }
 
 func WaitMany(items []WaitItem, timeout Time) error {
-	if status := sys_object_wait_many(&items[0], uint(len(items)), timeout); status != ErrOk {
+	var ptr *WaitItem
+	if len(items) > 0 {
+		ptr = &items[0]
+	}
+	if status := sys_object_wait_many(ptr, uint(len(items)), timeout); status != ErrOk {
 		return &Error{Status: status, Text: "zx.Handle.WaitMany"}
 	}
 	return nil
@@ -240,75 +232,48 @@
 	return err
 }
 
-func (c *Channel) Read(data []byte, handles []Handle, flags uint32) (numBytes, numHandles uint32, err error) {
+func handlePtr(data []Handle) *Handle {
+	if len(data) > 0 {
+		return &data[0]
+	}
+	return nil
+}
+
+func (c *Channel) Read(data []byte, handles []Handle, flags uint32) (numBytes, numHandles uint32, _ error) {
 	numBytes = uint32(len(data))
 	numHandles = uint32(len(handles))
-	var dataPtr unsafe.Pointer
-	if len(data) > 0 {
-		dataPtr = unsafe.Pointer(&data[0])
+	if status := sys_channel_read(Handle(*c), flags, bytesPtr(data), handlePtr(handles), numBytes, numHandles, &numBytes, &numHandles); status != ErrOk {
+		return 0, 0, &Error{Status: status, Text: "zx.Channel.Read"}
 	}
-	var handlePtr *Handle
-	if len(handles) > 0 {
-		handlePtr = &handles[0]
-	}
-	if status := sys_channel_read(Handle(*c), flags, dataPtr, handlePtr, numBytes, numHandles, &numBytes, &numHandles); status != ErrOk {
-		err = &Error{Status: status, Text: "zx.Channel.Read"}
-	}
-	return numBytes, numHandles, err
+	return numBytes, numHandles, nil
 }
 
 func (c *Channel) Write(data []byte, handles []Handle, flags uint32) error {
-	var dataPtr unsafe.Pointer
-	if len(data) > 0 {
-		dataPtr = unsafe.Pointer(&data[0])
-	}
-	var handlePtr *Handle
-	if len(handles) > 0 {
-		handlePtr = &handles[0]
-	}
-	status := sys_channel_write(Handle(*c), flags, dataPtr, uint32(len(data)), handlePtr, uint32(len(handles)))
-	if status != ErrOk {
+	if status := sys_channel_write(Handle(*c), flags, bytesPtr(data), uint32(len(data)), handlePtr(handles), uint32(len(handles))); status != ErrOk {
 		return &Error{Status: status, Text: "zx.Channel.Write"}
 	}
 	return nil
 }
 
-func (c *Channel) Call(flags uint32, deadline Time, wData []byte, wHandles []Handle, rData []byte, rHandles []Handle) (actualBytes, actualHandles uint32, err error) {
-	var writeDataPtr uintptr
-	if len(wData) > 0 {
-		writeDataPtr = uintptr(unsafe.Pointer(&wData[0]))
-	}
-	var writeHandlePtr *Handle
-	if len(wHandles) > 0 {
-		writeHandlePtr = &wHandles[0]
-	}
-	var readDataPtr uintptr
-	if len(rData) > 0 {
-		readDataPtr = uintptr(unsafe.Pointer(&rData[0]))
-	}
-	var readHandlePtr *Handle
-	if len(rHandles) > 0 {
-		readHandlePtr = &rHandles[0]
-	}
+func (c *Channel) Call(flags uint32, deadline Time, wData []byte, wHandles []Handle, rData []byte, rHandles []Handle) (actualBytes, actualHandles uint32, _ error) {
 	args := &ChannelCallArgs{
-		WriteBytes:      writeDataPtr,
-		WriteHandles:    writeHandlePtr,
-		ReadBytes:       readDataPtr,
-		ReadHandles:     readHandlePtr,
+		WriteBytes:      bytesPtr(wData),
+		WriteHandles:    handlePtr(wHandles),
+		ReadBytes:       bytesPtr(rData),
+		ReadHandles:     handlePtr(rHandles),
 		WriteNumBytes:   uint32(len(wData)),
 		WriteNumHandles: uint32(len(wHandles)),
 		ReadNumBytes:    uint32(len(rData)),
 		ReadNumHandles:  uint32(len(rHandles)),
 	}
 
-	status := Sys_channel_call(Handle(*c), flags, deadline, args, &actualBytes, &actualHandles)
-	if status != ErrOk {
-		err = &Error{Status: status, Text: "zx.Channel.Call"}
+	if status := Sys_channel_call(Handle(*c), flags, deadline, args, &actualBytes, &actualHandles); status != ErrOk {
+		return 0, 0, &Error{Status: status, Text: "zx.Channel.Call"}
 	}
-	return actualBytes, actualHandles, err
+	return actualBytes, actualHandles, nil
 }
 
-func NewChannel(flags uint32) (c0, c1 Channel, err error) {
+func NewChannel(flags uint32) (Channel, Channel, error) {
 	var h0, h1 Handle
 	if status := sys_channel_create(flags, &h0, &h1); status != ErrOk {
 		return Channel(HandleInvalid), Channel(HandleInvalid), &Error{Status: status, Text: "zx.Channel"}
@@ -436,14 +401,14 @@
 }
 
 func (vmo *VMO) Read(b []byte, offset uint64) error {
-	if status := sys_vmo_read(Handle(*vmo), unsafe.Pointer(&b[0]), offset, uint(len(b))); status != ErrOk {
+	if status := sys_vmo_read(Handle(*vmo), bytesPtr(b), offset, uint(len(b))); status != ErrOk {
 		return &Error{Status: status, Text: "zx.VMO.Read"}
 	}
 	return nil
 }
 
 func (vmo *VMO) Write(b []byte, offset uint64) error {
-	if status := sys_vmo_write(Handle(*vmo), unsafe.Pointer(&b[0]), offset, uint(len(b))); status != ErrOk {
+	if status := sys_vmo_write(Handle(*vmo), bytesPtr(b), offset, uint(len(b))); status != ErrOk {
 		return &Error{Status: status, Text: "zx.VMO.Write"}
 	}
 	return nil
@@ -465,7 +430,7 @@
 }
 
 func (vmo *VMO) OpRange(op uint32, offset, size uint64, b []byte) error {
-	if status := sys_vmo_op_range(Handle(*vmo), op, offset, size, unsafe.Pointer(&b[0]), uint(len(b))); status != ErrOk {
+	if status := sys_vmo_op_range(Handle(*vmo), op, offset, size, bytesPtr(b), uint(len(b))); status != ErrOk {
 		return &Error{Status: status, Text: "zx.VMO.OpRange"}
 	}
 	return nil
@@ -495,40 +460,32 @@
 	return nil
 }
 
-var mapErr error = &Error{Status: 1, Text: "zx.VMAR.Map"}
-
-func (v VMAR) Map(vmarOffset uint64, vmo VMO, vmoOffset, len uint64, flags VMFlag) (addr uintptr, err error) {
-	status := Sys_vmar_map(Handle(v), flags, uint64(vmarOffset), Handle(vmo), vmoOffset, uint64(len), (*Vaddr)(&addr))
-	if status != ErrOk {
-		println("zx.VMAR.Map failed: status: ", status)
-		return 0, mapErr
+func (v VMAR) Map(vmarOffset uint64, vmo VMO, vmoOffset, len uint64, flags VMFlag) (Vaddr, error) {
+	var addr Vaddr
+	if status := Sys_vmar_map(Handle(v), flags, uint64(vmarOffset), Handle(vmo), vmoOffset, uint64(len), &addr); status != ErrOk {
+		return 0, &Error{Status: status, Text: "zx.VMAR.Map"}
 	}
 	return addr, nil
 }
 
-var unmapErr error = &Error{Status: 1, Text: "zx.VMAR.Unmap"}
-
-func (v VMAR) Unmap(addr uintptr, len uint64) error {
-	status := Sys_vmar_unmap(Handle(v), Vaddr(addr), uint64(len))
-	if status != ErrOk {
-		println(status)
-		return unmapErr
+func (v VMAR) Unmap(addr Vaddr, len uint64) error {
+	if status := Sys_vmar_unmap(Handle(v), addr, uint64(len)); status != ErrOk {
+		return &Error{Status: status, Text: "zx.VMAR.Unmap"}
 	}
 	return nil
 }
 
-func (v VMAR) Protect(addr uintptr, len uint64, flags VMFlag) error {
-	status := Sys_vmar_protect(Handle(v), flags, Vaddr(addr), uint64(len))
-	if status != ErrOk {
+func (v VMAR) Protect(addr Vaddr, len uint64, flags VMFlag) error {
+	if status := Sys_vmar_protect(Handle(v), flags, addr, uint64(len)); status != ErrOk {
 		return &Error{Status: status, Text: "zx.VMAR.Protect"}
 	}
 	return nil
 }
 
-func NewVMAR(parent VMAR, offset, size uint64, flags VMFlag) (child VMAR, addr uintptr, err error) {
+func NewVMAR(parent VMAR, offset, size uint64, flags VMFlag) (VMAR, Vaddr, error) {
 	var childHandle Handle
-	status := sys_vmar_allocate(Handle(parent), flags, uint64(offset), uint64(size), &childHandle, (*Vaddr)(&addr))
-	if status != ErrOk {
+	var addr Vaddr
+	if status := sys_vmar_allocate(Handle(parent), flags, uint64(offset), uint64(size), &childHandle, &addr); status != ErrOk {
 		return 0, 0, &Error{Status: status, Text: "zx.NewVMAR"}
 	}
 	return VMAR(childHandle), addr, nil
@@ -549,36 +506,29 @@
 	return (*Handle)(l)
 }
 
-func (l Log) Write(b []byte) (n int, err error) {
-	var p unsafe.Pointer
-	if len(b) > 0 {
-		p = unsafe.Pointer(&b[0])
-	}
-
-	status := Sys_debuglog_write(Handle(l), 0, p, uint(len(b)))
-	if status != ErrOk {
+func (l Log) Write(b []byte) (int, error) {
+	if status := Sys_debuglog_write(Handle(l), 0, bytesPtr(b), uint(len(b))); status != ErrOk {
 		return 0, &Error{Status: status, Text: "zx.Log.Write"}
 	}
 	return len(b), nil
 }
 
-func (l Log) Read(b []byte) (n int, err error) {
-	status := Sys_debuglog_read(Handle(l), 0, unsafe.Pointer(&b[0]), uint(len(b)))
-	if status != ErrOk {
+func (l Log) Read(b []byte) (int, error) {
+	if status := Sys_debuglog_read(Handle(l), 0, bytesPtr(b), uint(len(b))); status != ErrOk {
 		return 0, &Error{Status: status, Text: "zx.Log.Read"}
 	}
 	return len(b), nil
 }
 
-func (l *Log) Close() (err error) {
+func (l *Log) Close() error {
 	h := Handle(*l)
-	err = h.Close()
+	err := h.Close()
 	*l = Log(HandleInvalid)
 	return err
 }
 
 func RandRead(b []byte) {
-	Sys_cprng_draw(unsafe.Pointer(&b[0]), uint(len(b)))
+	Sys_cprng_draw(bytesPtr(b), uint(len(b)))
 }
 
 // Error is a Status with associated error text.
diff --git a/src/syscall/zx/mxerror/mxerror.go b/src/syscall/zx/mxerror/mxerror.go
deleted file mode 100644
index 64422c0..0000000
--- a/src/syscall/zx/mxerror/mxerror.go
+++ /dev/null
@@ -1,23 +0,0 @@
-// Copyright 2017 The Go Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style
-// license that can be found in the LICENSE file.
-
-// +build fuchsia
-
-package mxerror
-
-import (
-	"syscall/zx"
-)
-
-// Status extracts an zx.Status from an error.
-func Status(err error) zx.Status {
-	if err == nil {
-		return zx.ErrOk
-	}
-	switch err := err.(type) {
-	case *zx.Error:
-		return err.Status
-	}
-	return zx.ErrInternal
-}
diff --git a/src/syscall/zx/types.go b/src/syscall/zx/types.go
index ecb34af..02fd558 100644
--- a/src/syscall/zx/types.go
+++ b/src/syscall/zx/types.go
@@ -141,9 +141,9 @@
 func (*RrecIOPort) rrec() {}
 
 type ChannelCallArgs struct {
-	WriteBytes      uintptr
+	WriteBytes      unsafe.Pointer
 	WriteHandles    *Handle
-	ReadBytes       uintptr
+	ReadBytes       unsafe.Pointer
 	ReadHandles     *Handle
 	WriteNumBytes   uint32
 	WriteNumHandles uint32
diff --git a/src/syscall/zx/zxsocket/socket.go b/src/syscall/zx/zxsocket/socket.go
index f9d5345..e320759 100644
--- a/src/syscall/zx/zxsocket/socket.go
+++ b/src/syscall/zx/zxsocket/socket.go
@@ -12,7 +12,6 @@
 	"syscall/zx"
 	"syscall/zx/fdio"
 	fidlIo "syscall/zx/io"
-	"syscall/zx/mxerror"
 	"syscall/zx/mxnet"
 	"syscall/zx/net"
 	"syscall/zx/zxwait"
@@ -34,7 +33,7 @@
 	}
 }
 
-func (s *Socket) Wait(signals zx.Signals, timeout zx.Time) (observed zx.Signals, err error) {
+func (s *Socket) Wait(signals zx.Signals, timeout zx.Time) (zx.Signals, error) {
 	return zxwait.Wait(zx.Handle(s.Socket), signals, timeout)
 }
 
@@ -99,32 +98,36 @@
 		n = copy(data, b)
 		return n, err
 	}
-	// c.f. mxsio_read_stream in zircon/system/ulib/fdio/remoteio.c
+	// c.f. zxs_recvmsg_stream in zircon/system/ulib/zxs/zxs.cpp
 	for {
-		n, err = s.Socket.Read(data, 0)
-		switch mxerror.Status(err) {
-		case zx.ErrOk:
-			return n, nil
-		case zx.ErrPeerClosed:
-			return 0, io.EOF
-		case zx.ErrShouldWait:
-			obs, err := s.Wait(zx.SignalSocketReadable|zx.SignalSocketPeerClosed, zx.TimensecInfinite)
-			switch mxerror.Status(err) {
-			case zx.ErrOk:
-				switch {
-				case obs&zx.SignalSocketReadable != 0:
-					continue
-				case obs&zx.SignalSocketPeerClosed != 0:
+		n, err := s.Socket.Read(data, 0)
+		if err != nil {
+			if err, ok := err.(*zx.Error); ok {
+				switch err.Status {
+				case zx.ErrPeerClosed:
 					return 0, io.EOF
+				case zx.ErrShouldWait:
+					obs, err := s.Wait(zx.SignalSocketReadable|zx.SignalSocketPeerClosed, zx.TimensecInfinite)
+					if err != nil {
+						if err, ok := err.(*zx.Error); ok {
+							switch err.Status {
+							case zx.ErrBadHandle, zx.ErrCanceled:
+								return 0, io.EOF
+							}
+						}
+						return 0, err
+					}
+					switch {
+					case obs&zx.SignalSocketReadable != 0:
+						continue
+					case obs&zx.SignalSocketPeerClosed != 0:
+						return 0, io.EOF
+					}
 				}
-			case zx.ErrBadHandle, zx.ErrCanceled:
-				return 0, io.EOF
-			default:
-				return 0, err
 			}
-		default:
 			return 0, err
 		}
+		return n, nil
 	}
 }
 
@@ -140,32 +143,33 @@
 		return n, err
 	}
 
-	// c.f. zxsio_write_stream
+	// c.f. zxsio_sendmsg_stream
 	var total int
 	for {
 		n, err := s.Socket.Write(data, 0)
 		total += n
-
-		switch mxerror.Status(err) {
-		case zx.ErrOk:
-			return total, nil
-		case zx.ErrShouldWait:
-			obs, err := s.Wait(zx.SignalSocketWritable|zx.SignalSocketPeerClosed|zx.SignalSocketWriteDisabled, zx.TimensecInfinite)
-			if err != nil {
-				return total, err
+		if err != nil {
+			if err, ok := err.(*zx.Error); ok {
+				switch err.Status {
+				case zx.ErrShouldWait:
+					obs, err := s.Wait(zx.SignalSocketWritable|zx.SignalSocketPeerClosed|zx.SignalSocketWriteDisabled, zx.TimensecInfinite)
+					if err != nil {
+						return total, err
+					}
+					if obs&zx.SignalSocketPeerClosed != 0 || obs&zx.SignalSocketWriteDisabled != 0 {
+						return total, &zx.Error{Status: zx.ErrPeerClosed, Text: "zxsocket.Socket.Write"}
+					}
+					if obs&zx.SignalSocketWritable != 0 {
+						data = data[n:]
+						continue
+					}
+					// This case should be impossible:
+					return total, &zx.Error{Status: zx.ErrInternal, Text: "zxsocket.Socket.Write(impossible state)"}
+				}
 			}
-			if obs&zx.SignalSocketPeerClosed != 0 || obs&zx.SignalSocketWriteDisabled != 0 {
-				return total, &zx.Error{Status: zx.ErrPeerClosed, Text: "zxsocket.Socket.Write"}
-			}
-			if obs&zx.SignalSocketWritable != 0 {
-				data = data[n:]
-				continue
-			}
-			// This case should be impossible:
-			return total, &zx.Error{Status: zx.ErrInternal, Text: "zxsocket.Socket.Write(impossible state)"}
-		default:
 			return total, err
 		}
+		return total, nil
 	}
 }
 
@@ -232,28 +236,29 @@
 func (s *Socket) recvMsg(data []byte) (int, error) {
 	for {
 		n, err := s.Socket.Read(data, 0)
-		switch mxerror.Status(err) {
-		case zx.ErrOk:
-			return n, err
-		case zx.ErrShouldWait:
-			if n != 0 {
-				return n, &zx.Error{Status: zx.ErrInternal, Text: "zsocket.Socket.recvMsg(datagram short-read)"}
+		if err != nil {
+			if err, ok := err.(*zx.Error); ok {
+				switch err.Status {
+				case zx.ErrShouldWait:
+					if n != 0 {
+						return n, &zx.Error{Status: zx.ErrInternal, Text: "zsocket.Socket.recvMsg(datagram short-read)"}
+					}
+					obs, err := s.Wait(zx.SignalSocketReadable|zx.SignalSocketPeerClosed|zx.SignalSocketReadDisabled, zx.TimensecInfinite)
+					if err != nil {
+						return n, err
+					}
+					if obs&zx.SignalSocketReadable != 0 {
+						continue
+					}
+					if obs&zx.SignalSocketPeerClosed != 0 || obs&zx.SignalSocketReadDisabled != 0 {
+						return n, &zx.Error{Status: zx.ErrPeerClosed, Text: "zxsocket.Socket.recvMsg"}
+					}
+					return n, &zx.Error{Status: zx.ErrInternal, Text: "zxsocket.Socket.recvMsg(impossible state))"}
+				}
 			}
-
-			obs, err := s.Wait(zx.SignalSocketReadable|zx.SignalSocketPeerClosed|zx.SignalSocketReadDisabled, zx.TimensecInfinite)
-			if err != nil {
-				return n, err
-			}
-			if obs&zx.SignalSocketReadable != 0 {
-				continue
-			}
-			if obs&zx.SignalSocketPeerClosed != 0 || obs&zx.SignalSocketReadDisabled != 0 {
-				return n, &zx.Error{Status: zx.ErrPeerClosed, Text: "zxsocket.Socket.recvMsg"}
-			}
-			return n, &zx.Error{Status: zx.ErrInternal, Text: "zxsocket.Socket.recvMsg"}
-		default:
 			return n, err
 		}
+		return n, nil
 	}
 }
 
@@ -267,31 +272,33 @@
 
 	for {
 		n, err := s.Socket.Write(data, 0)
-		switch mxerror.Status(err) {
-		case zx.ErrOk:
-			return len(b), nil
-		case zx.ErrShouldWait:
-			if n != 0 {
-				return n, &zx.Error{Status: zx.ErrInternal, Text: "zxsocket.Socket.SendMsg(datagram short-write)"}
-			}
+		if err != nil {
+			if err, ok := err.(*zx.Error); ok {
+				switch err.Status {
+				case zx.ErrShouldWait:
+					if n != 0 {
+						return n, &zx.Error{Status: zx.ErrInternal, Text: "zxsocket.Socket.SendMsg(datagram short-write)"}
+					}
 
-			obs, err := s.Wait(zx.SignalSocketWritable|zx.SignalSocketPeerClosed|zx.SignalSocketWriteDisabled, zx.TimensecInfinite)
-			if err != nil {
-				return 0, err
+					obs, err := s.Wait(zx.SignalSocketWritable|zx.SignalSocketPeerClosed|zx.SignalSocketWriteDisabled, zx.TimensecInfinite)
+					if err != nil {
+						return 0, err
+					}
+					if obs&zx.SignalSocketWritable != 0 {
+						continue
+					}
+					if obs&zx.SignalSocketPeerClosed != 0 || obs&zx.SignalSocketWriteDisabled != 0 {
+						return 0, &zx.Error{Status: zx.ErrPeerClosed, Text: "zxsocket.Socket.SendMsg"}
+					}
+					return 0, &zx.Error{Status: zx.ErrInternal, Text: "zxsocket.Socket.SendMsg(impossible state)"}
+				}
 			}
-			if obs&zx.SignalSocketWritable != 0 {
-				continue
-			}
-			if obs&zx.SignalSocketPeerClosed != 0 || obs&zx.SignalSocketWriteDisabled != 0 {
-				return 0, &zx.Error{Status: zx.ErrPeerClosed, Text: "zxsocket.Socket.SendMsg"}
-			}
-			return 0, &zx.Error{Status: zx.ErrInternal, Text: "zxsocket.Socket.SendMsg(impossible state)"}
-		default:
 			if n != 0 {
 				return n, &zx.Error{Status: zx.ErrInternal, Text: "zxsocket.Socket.SendMsg(datagram short-write)"}
 			}
 			return 0, err
 		}
+		return len(b), nil
 	}
 }
 
@@ -300,54 +307,3 @@
 func (s *Socket) SetDgram() {
 	s.dgram = true
 }
-
-func ReadControl(s zx.Socket, data []byte) (n int, err error) {
-	// c.f. zxsocket._read_control in zircon/system/ulib/fdio/remoteio.c
-	for {
-		n, err = s.Read(data, zx.SocketControl)
-		switch mxerror.Status(err) {
-		case zx.ErrOk:
-			return n, nil
-		case zx.ErrPeerClosed:
-			return 0, io.EOF
-		case zx.ErrShouldWait:
-			obs, err := zxwait.Wait(
-				zx.Handle(s),
-				zx.SignalSocketControlReadable|zx.SignalSocketPeerClosed,
-				zx.TimensecInfinite,
-			)
-			switch mxerror.Status(err) {
-			case zx.ErrOk:
-				switch {
-				case obs&zx.SignalSocketControlReadable != 0:
-					continue
-				case obs&zx.SignalSocketPeerClosed != 0:
-					return 0, io.EOF
-				}
-			case zx.ErrBadHandle, zx.ErrCanceled:
-				return 0, io.EOF
-			default:
-				return 0, err
-			}
-		default:
-			return 0, err
-		}
-	}
-}
-
-func WriteControl(s zx.Socket, data []byte) (int, error) {
-	// c.f. zxsocket._write_control
-	for {
-		n, err := s.Write(data, zx.SocketControl)
-		switch mxerror.Status(err) {
-		case zx.ErrOk:
-			return n, nil
-		case zx.ErrShouldWait:
-			_, err := zxwait.Wait(zx.Handle(s), zx.SignalSocketControlWriteable, zx.TimensecInfinite)
-			if err != nil {
-				return n, err
-			}
-			continue
-		}
-	}
-}
diff --git a/src/syscall/zx/zxwait/zxwait.go b/src/syscall/zx/zxwait/zxwait.go
index de286eb..6647ad9 100644
--- a/src/syscall/zx/zxwait/zxwait.go
+++ b/src/syscall/zx/zxwait/zxwait.go
@@ -26,9 +26,10 @@
 // Semantically it is equivalent to calling the WaitOne method on a zx.Handle.
 // However it is not implemented with zx_object_wait_one, instead it uses
 // zx_object_wait_async and a port to wait for signals.
-func Wait(handle zx.Handle, signals zx.Signals, timeout zx.Time) (observed zx.Signals, err error) {
+func Wait(handle zx.Handle, signals zx.Signals, timeout zx.Time) (zx.Signals, error) {
 	// TODO: support finite timeouts.
 	if timeout != zx.TimensecInfinite {
+		var observed zx.Signals
 		if status := zx.Sys_object_wait_one(handle, signals, timeout, &observed); status != zx.ErrOk {
 			return observed, &zx.Error{Status: status, Text: "zxwait.Wait"}
 		}
@@ -118,7 +119,7 @@
 // Wait waits for signals on handle.
 //
 // See the package function Wait for more commentary.
-func (w *waiter) Wait(handle zx.Handle, signals zx.Signals) (observed zx.Signals, err error) {
+func (w *waiter) Wait(handle zx.Handle, signals zx.Signals) (zx.Signals, error) {
 	var waiting *waitingG
 
 	w.mu.Lock()
@@ -138,7 +139,7 @@
 	pkt.Signal().Trigger = signals
 
 	const ZX_WAIT_ASYNC_ONCE = 0
-	if err = w.port.WaitAsync(handle, pkt.Hdr.Key, signals, ZX_WAIT_ASYNC_ONCE); err != nil {
+	if err := w.port.WaitAsync(handle, pkt.Hdr.Key, signals, ZX_WAIT_ASYNC_ONCE); err != nil {
 		return 0, err
 	}