1// Copyright 2017 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.
4
5package socket
6
7import (
8	"syscall"
9	"unsafe"
10)
11
12func probeProtocolStack() int { return 4 }
13
14const (
15	sysSETSOCKOPT = 0xe
16	sysGETSOCKOPT = 0xf
17	sysSENDMSG    = 0x10
18	sysRECVMSG    = 0x11
19	sysRECVMMSG   = 0x13
20	sysSENDMMSG   = 0x14
21)
22
23func socketcall(call, a0, a1, a2, a3, a4, a5 uintptr) (uintptr, syscall.Errno)
24func rawsocketcall(call, a0, a1, a2, a3, a4, a5 uintptr) (uintptr, syscall.Errno)
25
26func getsockopt(s uintptr, level, name int, b []byte) (int, error) {
27	l := uint32(len(b))
28	_, errno := socketcall(sysGETSOCKOPT, s, uintptr(level), uintptr(name), uintptr(unsafe.Pointer(&b[0])), uintptr(unsafe.Pointer(&l)), 0)
29	return int(l), errnoErr(errno)
30}
31
32func setsockopt(s uintptr, level, name int, b []byte) error {
33	_, errno := socketcall(sysSETSOCKOPT, s, uintptr(level), uintptr(name), uintptr(unsafe.Pointer(&b[0])), uintptr(len(b)), 0)
34	return errnoErr(errno)
35}
36
37func recvmsg(s uintptr, h *msghdr, flags int) (int, error) {
38	n, errno := socketcall(sysRECVMSG, s, uintptr(unsafe.Pointer(h)), uintptr(flags), 0, 0, 0)
39	return int(n), errnoErr(errno)
40}
41
42func sendmsg(s uintptr, h *msghdr, flags int) (int, error) {
43	n, errno := socketcall(sysSENDMSG, s, uintptr(unsafe.Pointer(h)), uintptr(flags), 0, 0, 0)
44	return int(n), errnoErr(errno)
45}
46
47func recvmmsg(s uintptr, hs []mmsghdr, flags int) (int, error) {
48	n, errno := socketcall(sysRECVMMSG, s, uintptr(unsafe.Pointer(&hs[0])), uintptr(len(hs)), uintptr(flags), 0, 0)
49	return int(n), errnoErr(errno)
50}
51
52func sendmmsg(s uintptr, hs []mmsghdr, flags int) (int, error) {
53	n, errno := socketcall(sysSENDMMSG, s, uintptr(unsafe.Pointer(&hs[0])), uintptr(len(hs)), uintptr(flags), 0, 0)
54	return int(n), errnoErr(errno)
55}
56