1 // Copyright 2013 The Go Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style
3 // license that can be found in the LICENSE file.
5 // +build aix darwin dragonfly freebsd linux netbsd openbsd windows solaris
16 // runtimeNano returns the current value of the runtime clock in nanoseconds.
17 func runtimeNano() int64
19 func runtime_pollServerInit()
20 func runtime_pollOpen(fd
uintptr) (uintptr, int)
21 func runtime_pollClose(ctx
uintptr)
22 func runtime_pollWait(ctx
uintptr, mode
int) int
23 func runtime_pollWaitCanceled(ctx
uintptr, mode
int) int
24 func runtime_pollReset(ctx
uintptr, mode
int) int
25 func runtime_pollSetDeadline(ctx
uintptr, d
int64, mode
int)
26 func runtime_pollUnblock(ctx
uintptr)
28 type pollDesc
struct {
32 var serverInit sync
.Once
34 func (pd
*pollDesc
) init(fd
*netFD
) error
{
35 serverInit
.Do(runtime_pollServerInit
)
36 ctx
, errno
:= runtime_pollOpen(uintptr(fd
.sysfd
))
39 return syscall
.Errno(errno
)
45 func (pd
*pollDesc
) close() {
46 if pd
.runtimeCtx
== 0 {
49 runtime_pollClose(pd
.runtimeCtx
)
53 // Evict evicts fd from the pending list, unblocking any I/O running on fd.
54 func (pd
*pollDesc
) evict() {
55 if pd
.runtimeCtx
== 0 {
58 runtime_pollUnblock(pd
.runtimeCtx
)
61 func (pd
*pollDesc
) prepare(mode
int) error
{
62 res
:= runtime_pollReset(pd
.runtimeCtx
, mode
)
63 return convertErr(res
)
66 func (pd
*pollDesc
) prepareRead() error
{
67 return pd
.prepare('r')
70 func (pd
*pollDesc
) prepareWrite() error
{
71 return pd
.prepare('w')
74 func (pd
*pollDesc
) wait(mode
int) error
{
75 res
:= runtime_pollWait(pd
.runtimeCtx
, mode
)
76 return convertErr(res
)
79 func (pd
*pollDesc
) waitRead() error
{
83 func (pd
*pollDesc
) waitWrite() error
{
87 func (pd
*pollDesc
) waitCanceled(mode
int) {
88 runtime_pollWaitCanceled(pd
.runtimeCtx
, mode
)
91 func (pd
*pollDesc
) waitCanceledRead() {
95 func (pd
*pollDesc
) waitCanceledWrite() {
99 func convertErr(res
int) error
{
108 println("unreachable: ", res
)
112 func (fd
*netFD
) setDeadline(t time
.Time
) error
{
113 return setDeadlineImpl(fd
, t
, 'r'+'w')
116 func (fd
*netFD
) setReadDeadline(t time
.Time
) error
{
117 return setDeadlineImpl(fd
, t
, 'r')
120 func (fd
*netFD
) setWriteDeadline(t time
.Time
) error
{
121 return setDeadlineImpl(fd
, t
, 'w')
124 func setDeadlineImpl(fd
*netFD
, t time
.Time
, mode
int) error
{
125 diff
:= int64(time
.Until(t
))
126 d
:= runtimeNano() + diff
127 if d
<= 0 && diff
> 0 {
128 // If the user has a deadline in the future, but the delay calculation
129 // overflows, then set the deadline to the maximum possible value.
135 if err
:= fd
.incref(); err
!= nil {
138 runtime_pollSetDeadline(fd
.pd
.runtimeCtx
, d
, mode
)