Source file
src/syscall/syscall_unix.go
1
2
3
4
5
6
7 package syscall
8
9 import (
10 errorspkg "errors"
11 "internal/asan"
12 "internal/bytealg"
13 "internal/itoa"
14 "internal/msan"
15 "internal/oserror"
16 "internal/race"
17 "runtime"
18 "sync"
19 "unsafe"
20 )
21
22 var (
23 Stdin = 0
24 Stdout = 1
25 Stderr = 2
26 )
27
28 const (
29 darwin64Bit = (runtime.GOOS == "darwin" || runtime.GOOS == "ios") && sizeofPtr == 8
30 netbsd32Bit = runtime.GOOS == "netbsd" && sizeofPtr == 4
31 )
32
33
34 func clen(n []byte) int {
35 if i := bytealg.IndexByte(n, 0); i != -1 {
36 return i
37 }
38 return len(n)
39 }
40
41
42
43 type mmapper struct {
44 sync.Mutex
45 active map[*byte][]byte
46 mmap func(addr, length uintptr, prot, flags, fd int, offset int64) (uintptr, error)
47 munmap func(addr uintptr, length uintptr) error
48 }
49
50 func (m *mmapper) Mmap(fd int, offset int64, length int, prot int, flags int) (data []byte, err error) {
51 if length <= 0 {
52 return nil, EINVAL
53 }
54
55
56 addr, errno := m.mmap(0, uintptr(length), prot, flags, fd, offset)
57 if errno != nil {
58 return nil, errno
59 }
60
61
62 b := unsafe.Slice((*byte)(unsafe.Pointer(addr)), length)
63
64
65 p := &b[cap(b)-1]
66 m.Lock()
67 defer m.Unlock()
68 m.active[p] = b
69 return b, nil
70 }
71
72 func (m *mmapper) Munmap(data []byte) (err error) {
73 if len(data) == 0 || len(data) != cap(data) {
74 return EINVAL
75 }
76
77
78 p := &data[cap(data)-1]
79 m.Lock()
80 defer m.Unlock()
81 b := m.active[p]
82 if b == nil || &b[0] != &data[0] {
83 return EINVAL
84 }
85
86
87 if errno := m.munmap(uintptr(unsafe.Pointer(&b[0])), uintptr(len(b))); errno != nil {
88 return errno
89 }
90 delete(m.active, p)
91 return nil
92 }
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108 type Errno uintptr
109
110 func (e Errno) Error() string {
111 if 0 <= int(e) && int(e) < len(errors) {
112 s := errors[e]
113 if s != "" {
114 return s
115 }
116 }
117 return "errno " + itoa.Itoa(int(e))
118 }
119
120 func (e Errno) Is(target error) bool {
121 switch target {
122 case oserror.ErrPermission:
123 return e == EACCES || e == EPERM
124 case oserror.ErrExist:
125 return e == EEXIST || e == ENOTEMPTY
126 case oserror.ErrNotExist:
127 return e == ENOENT
128 case errorspkg.ErrUnsupported:
129 return e == ENOSYS || e == ENOTSUP || e == EOPNOTSUPP
130 }
131 return false
132 }
133
134 func (e Errno) Temporary() bool {
135 return e == EINTR || e == EMFILE || e == ENFILE || e.Timeout()
136 }
137
138 func (e Errno) Timeout() bool {
139 return e == EAGAIN || e == EWOULDBLOCK || e == ETIMEDOUT
140 }
141
142
143
144 var (
145 errEAGAIN error = EAGAIN
146 errEINVAL error = EINVAL
147 errENOENT error = ENOENT
148 )
149
150
151
152 func errnoErr(e Errno) error {
153 switch e {
154 case 0:
155 return nil
156 case EAGAIN:
157 return errEAGAIN
158 case EINVAL:
159 return errEINVAL
160 case ENOENT:
161 return errENOENT
162 }
163 return e
164 }
165
166
167
168 type Signal int
169
170 func (s Signal) Signal() {}
171
172 func (s Signal) String() string {
173 if 0 <= s && int(s) < len(signals) {
174 str := signals[s]
175 if str != "" {
176 return str
177 }
178 }
179 return "signal " + itoa.Itoa(int(s))
180 }
181
182 func Read(fd int, p []byte) (n int, err error) {
183 n, err = read(fd, p)
184 if race.Enabled {
185 if n > 0 {
186 race.WriteRange(unsafe.Pointer(&p[0]), n)
187 }
188 if err == nil {
189 race.Acquire(unsafe.Pointer(&ioSync))
190 }
191 }
192 if msan.Enabled && n > 0 {
193 msan.Write(unsafe.Pointer(&p[0]), uintptr(n))
194 }
195 if asan.Enabled && n > 0 {
196 asan.Write(unsafe.Pointer(&p[0]), uintptr(n))
197 }
198 return
199 }
200
201 func Write(fd int, p []byte) (n int, err error) {
202 if race.Enabled {
203 race.ReleaseMerge(unsafe.Pointer(&ioSync))
204 }
205 if faketime && (fd == 1 || fd == 2) {
206 n = faketimeWrite(fd, p)
207 if n < 0 {
208 n, err = 0, errnoErr(Errno(-n))
209 }
210 } else {
211 n, err = write(fd, p)
212 }
213 if race.Enabled && n > 0 {
214 race.ReadRange(unsafe.Pointer(&p[0]), n)
215 }
216 if msan.Enabled && n > 0 {
217 msan.Read(unsafe.Pointer(&p[0]), uintptr(n))
218 }
219 if asan.Enabled && n > 0 {
220 asan.Read(unsafe.Pointer(&p[0]), uintptr(n))
221 }
222 return
223 }
224
225 func Pread(fd int, p []byte, offset int64) (n int, err error) {
226 n, err = pread(fd, p, offset)
227 if race.Enabled {
228 if n > 0 {
229 race.WriteRange(unsafe.Pointer(&p[0]), n)
230 }
231 if err == nil {
232 race.Acquire(unsafe.Pointer(&ioSync))
233 }
234 }
235 if msan.Enabled && n > 0 {
236 msan.Write(unsafe.Pointer(&p[0]), uintptr(n))
237 }
238 if asan.Enabled && n > 0 {
239 asan.Write(unsafe.Pointer(&p[0]), uintptr(n))
240 }
241 return
242 }
243
244 func Pwrite(fd int, p []byte, offset int64) (n int, err error) {
245 if race.Enabled {
246 race.ReleaseMerge(unsafe.Pointer(&ioSync))
247 }
248 n, err = pwrite(fd, p, offset)
249 if race.Enabled && n > 0 {
250 race.ReadRange(unsafe.Pointer(&p[0]), n)
251 }
252 if msan.Enabled && n > 0 {
253 msan.Read(unsafe.Pointer(&p[0]), uintptr(n))
254 }
255 if asan.Enabled && n > 0 {
256 asan.Read(unsafe.Pointer(&p[0]), uintptr(n))
257 }
258 return
259 }
260
261
262
263 var SocketDisableIPv6 bool
264
265 type Sockaddr interface {
266 sockaddr() (ptr unsafe.Pointer, len _Socklen, err error)
267 }
268
269 type SockaddrInet4 struct {
270 Port int
271 Addr [4]byte
272 raw RawSockaddrInet4
273 }
274
275 type SockaddrInet6 struct {
276 Port int
277 ZoneId uint32
278 Addr [16]byte
279 raw RawSockaddrInet6
280 }
281
282 type SockaddrUnix struct {
283 Name string
284 raw RawSockaddrUnix
285 }
286
287 func Bind(fd int, sa Sockaddr) (err error) {
288 ptr, n, err := sa.sockaddr()
289 if err != nil {
290 return err
291 }
292 return bind(fd, ptr, n)
293 }
294
295 func Connect(fd int, sa Sockaddr) (err error) {
296 ptr, n, err := sa.sockaddr()
297 if err != nil {
298 return err
299 }
300 return connect(fd, ptr, n)
301 }
302
303 func Getpeername(fd int) (sa Sockaddr, err error) {
304 var rsa RawSockaddrAny
305 var len _Socklen = SizeofSockaddrAny
306 if err = getpeername(fd, &rsa, &len); err != nil {
307 return
308 }
309 return anyToSockaddr(&rsa)
310 }
311
312 func GetsockoptInt(fd, level, opt int) (value int, err error) {
313 var n int32
314 vallen := _Socklen(4)
315 err = getsockopt(fd, level, opt, unsafe.Pointer(&n), &vallen)
316 return int(n), err
317 }
318
319 func Recvfrom(fd int, p []byte, flags int) (n int, from Sockaddr, err error) {
320 var rsa RawSockaddrAny
321 var len _Socklen = SizeofSockaddrAny
322 if n, err = recvfrom(fd, p, flags, &rsa, &len); err != nil {
323 return
324 }
325 if rsa.Addr.Family != AF_UNSPEC {
326 from, err = anyToSockaddr(&rsa)
327 }
328 return
329 }
330
331 func recvfromInet4(fd int, p []byte, flags int, from *SockaddrInet4) (n int, err error) {
332 var rsa RawSockaddrAny
333 var socklen _Socklen = SizeofSockaddrAny
334 if n, err = recvfrom(fd, p, flags, &rsa, &socklen); err != nil {
335 return
336 }
337 pp := (*RawSockaddrInet4)(unsafe.Pointer(&rsa))
338 port := (*[2]byte)(unsafe.Pointer(&pp.Port))
339 from.Port = int(port[0])<<8 + int(port[1])
340 from.Addr = pp.Addr
341 return
342 }
343
344 func recvfromInet6(fd int, p []byte, flags int, from *SockaddrInet6) (n int, err error) {
345 var rsa RawSockaddrAny
346 var socklen _Socklen = SizeofSockaddrAny
347 if n, err = recvfrom(fd, p, flags, &rsa, &socklen); err != nil {
348 return
349 }
350 pp := (*RawSockaddrInet6)(unsafe.Pointer(&rsa))
351 port := (*[2]byte)(unsafe.Pointer(&pp.Port))
352 from.Port = int(port[0])<<8 + int(port[1])
353 from.ZoneId = pp.Scope_id
354 from.Addr = pp.Addr
355 return
356 }
357
358 func recvmsgInet4(fd int, p, oob []byte, flags int, from *SockaddrInet4) (n, oobn int, recvflags int, err error) {
359 var rsa RawSockaddrAny
360 n, oobn, recvflags, err = recvmsgRaw(fd, p, oob, flags, &rsa)
361 if err != nil {
362 return
363 }
364 pp := (*RawSockaddrInet4)(unsafe.Pointer(&rsa))
365 port := (*[2]byte)(unsafe.Pointer(&pp.Port))
366 from.Port = int(port[0])<<8 + int(port[1])
367 from.Addr = pp.Addr
368 return
369 }
370
371 func recvmsgInet6(fd int, p, oob []byte, flags int, from *SockaddrInet6) (n, oobn int, recvflags int, err error) {
372 var rsa RawSockaddrAny
373 n, oobn, recvflags, err = recvmsgRaw(fd, p, oob, flags, &rsa)
374 if err != nil {
375 return
376 }
377 pp := (*RawSockaddrInet6)(unsafe.Pointer(&rsa))
378 port := (*[2]byte)(unsafe.Pointer(&pp.Port))
379 from.Port = int(port[0])<<8 + int(port[1])
380 from.ZoneId = pp.Scope_id
381 from.Addr = pp.Addr
382 return
383 }
384
385 func Recvmsg(fd int, p, oob []byte, flags int) (n, oobn int, recvflags int, from Sockaddr, err error) {
386 var rsa RawSockaddrAny
387 n, oobn, recvflags, err = recvmsgRaw(fd, p, oob, flags, &rsa)
388
389 if rsa.Addr.Family != AF_UNSPEC {
390 from, err = anyToSockaddr(&rsa)
391 }
392 return
393 }
394
395 func Sendmsg(fd int, p, oob []byte, to Sockaddr, flags int) (err error) {
396 _, err = SendmsgN(fd, p, oob, to, flags)
397 return
398 }
399
400 func SendmsgN(fd int, p, oob []byte, to Sockaddr, flags int) (n int, err error) {
401 var ptr unsafe.Pointer
402 var salen _Socklen
403 if to != nil {
404 ptr, salen, err = to.sockaddr()
405 if err != nil {
406 return 0, err
407 }
408 }
409 return sendmsgN(fd, p, oob, ptr, salen, flags)
410 }
411
412 func sendmsgNInet4(fd int, p, oob []byte, to *SockaddrInet4, flags int) (n int, err error) {
413 ptr, salen, err := to.sockaddr()
414 if err != nil {
415 return 0, err
416 }
417 return sendmsgN(fd, p, oob, ptr, salen, flags)
418 }
419
420 func sendmsgNInet6(fd int, p, oob []byte, to *SockaddrInet6, flags int) (n int, err error) {
421 ptr, salen, err := to.sockaddr()
422 if err != nil {
423 return 0, err
424 }
425 return sendmsgN(fd, p, oob, ptr, salen, flags)
426 }
427
428 func sendtoInet4(fd int, p []byte, flags int, to *SockaddrInet4) (err error) {
429 ptr, n, err := to.sockaddr()
430 if err != nil {
431 return err
432 }
433 return sendto(fd, p, flags, ptr, n)
434 }
435
436 func sendtoInet6(fd int, p []byte, flags int, to *SockaddrInet6) (err error) {
437 ptr, n, err := to.sockaddr()
438 if err != nil {
439 return err
440 }
441 return sendto(fd, p, flags, ptr, n)
442 }
443
444 func Sendto(fd int, p []byte, flags int, to Sockaddr) (err error) {
445 var (
446 ptr unsafe.Pointer
447 salen _Socklen
448 )
449 if to != nil {
450 ptr, salen, err = to.sockaddr()
451 if err != nil {
452 return err
453 }
454 }
455 return sendto(fd, p, flags, ptr, salen)
456 }
457
458 func SetsockoptByte(fd, level, opt int, value byte) (err error) {
459 return setsockopt(fd, level, opt, unsafe.Pointer(&value), 1)
460 }
461
462 func SetsockoptInt(fd, level, opt int, value int) (err error) {
463 var n = int32(value)
464 return setsockopt(fd, level, opt, unsafe.Pointer(&n), 4)
465 }
466
467 func SetsockoptInet4Addr(fd, level, opt int, value [4]byte) (err error) {
468 return setsockopt(fd, level, opt, unsafe.Pointer(&value[0]), 4)
469 }
470
471 func SetsockoptIPMreq(fd, level, opt int, mreq *IPMreq) (err error) {
472 return setsockopt(fd, level, opt, unsafe.Pointer(mreq), SizeofIPMreq)
473 }
474
475 func SetsockoptIPv6Mreq(fd, level, opt int, mreq *IPv6Mreq) (err error) {
476 return setsockopt(fd, level, opt, unsafe.Pointer(mreq), SizeofIPv6Mreq)
477 }
478
479 func SetsockoptICMPv6Filter(fd, level, opt int, filter *ICMPv6Filter) error {
480 return setsockopt(fd, level, opt, unsafe.Pointer(filter), SizeofICMPv6Filter)
481 }
482
483 func SetsockoptLinger(fd, level, opt int, l *Linger) (err error) {
484 return setsockopt(fd, level, opt, unsafe.Pointer(l), SizeofLinger)
485 }
486
487 func SetsockoptString(fd, level, opt int, s string) (err error) {
488 var p unsafe.Pointer
489 if len(s) > 0 {
490 p = unsafe.Pointer(&[]byte(s)[0])
491 }
492 return setsockopt(fd, level, opt, p, uintptr(len(s)))
493 }
494
495 func SetsockoptTimeval(fd, level, opt int, tv *Timeval) (err error) {
496 return setsockopt(fd, level, opt, unsafe.Pointer(tv), unsafe.Sizeof(*tv))
497 }
498
499 func Socket(domain, typ, proto int) (fd int, err error) {
500 if domain == AF_INET6 && SocketDisableIPv6 {
501 return -1, EAFNOSUPPORT
502 }
503 fd, err = socket(domain, typ, proto)
504 return
505 }
506
507 func Socketpair(domain, typ, proto int) (fd [2]int, err error) {
508 var fdx [2]int32
509 err = socketpair(domain, typ, proto, &fdx)
510 if err == nil {
511 fd[0] = int(fdx[0])
512 fd[1] = int(fdx[1])
513 }
514 return
515 }
516
517 func Sendfile(outfd int, infd int, offset *int64, count int) (written int, err error) {
518 if race.Enabled {
519 race.ReleaseMerge(unsafe.Pointer(&ioSync))
520 }
521 return sendfile(outfd, infd, offset, count)
522 }
523
524 var ioSync int64
525
View as plain text