Source file
src/net/net_fake.go
1
2
3
4
5
6
7
8
9 package net
10
11 import (
12 "context"
13 "internal/poll"
14 "io"
15 "os"
16 "sync"
17 "syscall"
18 "time"
19
20 "golang.org/x/net/dns/dnsmessage"
21 )
22
23 var listenersMu sync.Mutex
24 var listeners = make(map[string]*netFD)
25
26 var portCounterMu sync.Mutex
27 var portCounter = 0
28
29 func nextPort() int {
30 portCounterMu.Lock()
31 defer portCounterMu.Unlock()
32 portCounter++
33 return portCounter
34 }
35
36
37 type netFD struct {
38 r *bufferedPipe
39 w *bufferedPipe
40 incoming chan *netFD
41
42 closedMu sync.Mutex
43 closed bool
44
45
46 listener bool
47 family int
48 sotype int
49 net string
50 laddr Addr
51 raddr Addr
52
53
54 pfd poll.FD
55 isConnected bool
56 }
57
58
59
60 func socket(ctx context.Context, net string, family, sotype, proto int, ipv6only bool, laddr, raddr sockaddr, ctrlCtxFn func(context.Context, string, string, syscall.RawConn) error) (*netFD, error) {
61 fd := &netFD{family: family, sotype: sotype, net: net}
62
63 if laddr != nil && raddr == nil {
64 l := laddr.(*TCPAddr)
65 fd.laddr = &TCPAddr{
66 IP: l.IP,
67 Port: nextPort(),
68 Zone: l.Zone,
69 }
70 fd.listener = true
71 fd.incoming = make(chan *netFD, 1024)
72 listenersMu.Lock()
73 listeners[fd.laddr.(*TCPAddr).String()] = fd
74 listenersMu.Unlock()
75 return fd, nil
76 }
77
78 fd.laddr = &TCPAddr{
79 IP: IPv4(127, 0, 0, 1),
80 Port: nextPort(),
81 }
82 fd.raddr = raddr
83 fd.r = newBufferedPipe(65536)
84 fd.w = newBufferedPipe(65536)
85
86 fd2 := &netFD{family: fd.family, sotype: sotype, net: net}
87 fd2.laddr = fd.raddr
88 fd2.raddr = fd.laddr
89 fd2.r = fd.w
90 fd2.w = fd.r
91 listenersMu.Lock()
92 l, ok := listeners[fd.raddr.(*TCPAddr).String()]
93 if !ok {
94 listenersMu.Unlock()
95 return nil, syscall.ECONNREFUSED
96 }
97 l.incoming <- fd2
98 listenersMu.Unlock()
99
100 return fd, nil
101 }
102
103 func (fd *netFD) Read(p []byte) (n int, err error) {
104 return fd.r.Read(p)
105 }
106
107 func (fd *netFD) Write(p []byte) (nn int, err error) {
108 return fd.w.Write(p)
109 }
110
111 func (fd *netFD) Close() error {
112 fd.closedMu.Lock()
113 if fd.closed {
114 fd.closedMu.Unlock()
115 return nil
116 }
117 fd.closed = true
118 fd.closedMu.Unlock()
119
120 if fd.listener {
121 listenersMu.Lock()
122 delete(listeners, fd.laddr.String())
123 close(fd.incoming)
124 fd.listener = false
125 listenersMu.Unlock()
126 return nil
127 }
128
129 fd.r.Close()
130 fd.w.Close()
131 return nil
132 }
133
134 func (fd *netFD) closeRead() error {
135 fd.r.Close()
136 return nil
137 }
138
139 func (fd *netFD) closeWrite() error {
140 fd.w.Close()
141 return nil
142 }
143
144 func (fd *netFD) accept() (*netFD, error) {
145 c, ok := <-fd.incoming
146 if !ok {
147 return nil, syscall.EINVAL
148 }
149 return c, nil
150 }
151
152 func (fd *netFD) SetDeadline(t time.Time) error {
153 fd.r.SetReadDeadline(t)
154 fd.w.SetWriteDeadline(t)
155 return nil
156 }
157
158 func (fd *netFD) SetReadDeadline(t time.Time) error {
159 fd.r.SetReadDeadline(t)
160 return nil
161 }
162
163 func (fd *netFD) SetWriteDeadline(t time.Time) error {
164 fd.w.SetWriteDeadline(t)
165 return nil
166 }
167
168 func newBufferedPipe(softLimit int) *bufferedPipe {
169 p := &bufferedPipe{softLimit: softLimit}
170 p.rCond.L = &p.mu
171 p.wCond.L = &p.mu
172 return p
173 }
174
175 type bufferedPipe struct {
176 softLimit int
177 mu sync.Mutex
178 buf []byte
179 closed bool
180 rCond sync.Cond
181 wCond sync.Cond
182 rDeadline time.Time
183 wDeadline time.Time
184 }
185
186 func (p *bufferedPipe) Read(b []byte) (int, error) {
187 p.mu.Lock()
188 defer p.mu.Unlock()
189
190 for {
191 if p.closed && len(p.buf) == 0 {
192 return 0, io.EOF
193 }
194 if !p.rDeadline.IsZero() {
195 d := time.Until(p.rDeadline)
196 if d <= 0 {
197 return 0, os.ErrDeadlineExceeded
198 }
199 time.AfterFunc(d, p.rCond.Broadcast)
200 }
201 if len(p.buf) > 0 {
202 break
203 }
204 p.rCond.Wait()
205 }
206
207 n := copy(b, p.buf)
208 p.buf = p.buf[n:]
209 p.wCond.Broadcast()
210 return n, nil
211 }
212
213 func (p *bufferedPipe) Write(b []byte) (int, error) {
214 p.mu.Lock()
215 defer p.mu.Unlock()
216
217 for {
218 if p.closed {
219 return 0, syscall.ENOTCONN
220 }
221 if !p.wDeadline.IsZero() {
222 d := time.Until(p.wDeadline)
223 if d <= 0 {
224 return 0, os.ErrDeadlineExceeded
225 }
226 time.AfterFunc(d, p.wCond.Broadcast)
227 }
228 if len(p.buf) <= p.softLimit {
229 break
230 }
231 p.wCond.Wait()
232 }
233
234 p.buf = append(p.buf, b...)
235 p.rCond.Broadcast()
236 return len(b), nil
237 }
238
239 func (p *bufferedPipe) Close() {
240 p.mu.Lock()
241 defer p.mu.Unlock()
242
243 p.closed = true
244 p.rCond.Broadcast()
245 p.wCond.Broadcast()
246 }
247
248 func (p *bufferedPipe) SetReadDeadline(t time.Time) {
249 p.mu.Lock()
250 defer p.mu.Unlock()
251
252 p.rDeadline = t
253 p.rCond.Broadcast()
254 }
255
256 func (p *bufferedPipe) SetWriteDeadline(t time.Time) {
257 p.mu.Lock()
258 defer p.mu.Unlock()
259
260 p.wDeadline = t
261 p.wCond.Broadcast()
262 }
263
264 func sysSocket(family, sotype, proto int) (int, error) {
265 return 0, syscall.ENOSYS
266 }
267
268 func (fd *netFD) readFrom(p []byte) (n int, sa syscall.Sockaddr, err error) {
269 return 0, nil, syscall.ENOSYS
270
271 }
272 func (fd *netFD) readFromInet4(p []byte, sa *syscall.SockaddrInet4) (n int, err error) {
273 return 0, syscall.ENOSYS
274 }
275
276 func (fd *netFD) readFromInet6(p []byte, sa *syscall.SockaddrInet6) (n int, err error) {
277 return 0, syscall.ENOSYS
278 }
279
280 func (fd *netFD) readMsg(p []byte, oob []byte, flags int) (n, oobn, retflags int, sa syscall.Sockaddr, err error) {
281 return 0, 0, 0, nil, syscall.ENOSYS
282 }
283
284 func (fd *netFD) readMsgInet4(p []byte, oob []byte, flags int, sa *syscall.SockaddrInet4) (n, oobn, retflags int, err error) {
285 return 0, 0, 0, syscall.ENOSYS
286 }
287
288 func (fd *netFD) readMsgInet6(p []byte, oob []byte, flags int, sa *syscall.SockaddrInet6) (n, oobn, retflags int, err error) {
289 return 0, 0, 0, syscall.ENOSYS
290 }
291
292 func (fd *netFD) writeMsgInet4(p []byte, oob []byte, sa *syscall.SockaddrInet4) (n int, oobn int, err error) {
293 return 0, 0, syscall.ENOSYS
294 }
295
296 func (fd *netFD) writeMsgInet6(p []byte, oob []byte, sa *syscall.SockaddrInet6) (n int, oobn int, err error) {
297 return 0, 0, syscall.ENOSYS
298 }
299
300 func (fd *netFD) writeTo(p []byte, sa syscall.Sockaddr) (n int, err error) {
301 return 0, syscall.ENOSYS
302 }
303
304 func (fd *netFD) writeToInet4(p []byte, sa *syscall.SockaddrInet4) (n int, err error) {
305 return 0, syscall.ENOSYS
306 }
307
308 func (fd *netFD) writeToInet6(p []byte, sa *syscall.SockaddrInet6) (n int, err error) {
309 return 0, syscall.ENOSYS
310 }
311
312 func (fd *netFD) writeMsg(p []byte, oob []byte, sa syscall.Sockaddr) (n int, oobn int, err error) {
313 return 0, 0, syscall.ENOSYS
314 }
315
316 func (fd *netFD) dup() (f *os.File, err error) {
317 return nil, syscall.ENOSYS
318 }
319
320 func (r *Resolver) lookup(ctx context.Context, name string, qtype dnsmessage.Type, conf *dnsConfig) (dnsmessage.Parser, string, error) {
321 panic("unreachable")
322 }
323
View as plain text