diff mbox series

libgo patch committed: Update BSD socket code

Message ID CAOyqgcXBAkoTBFm93V+XMPqJWzVX=2MPi=+nU2n4JSNhaE78_w@mail.gmail.com
State New
Headers show
Series libgo patch committed: Update BSD socket code | expand

Commit Message

Ian Lance Taylor Oct. 21, 2020, 11:58 p.m. UTC
This libgo patch by Nikhil Benesch imports the  upstream code for BSD
sockets and sysctls into the syscall package.  This code is
sufficiently different that it doesn't get merged by the scripts.
Bootstrapped and ran Go testsuite on x86_64-pc-linux-gnu.  Committed
to mainline.

Ian
d031aa7b3be4155bf83ed55d43da6900f091cb80
diff mbox series

Patch

diff --git a/gcc/go/gofrontend/MERGE b/gcc/go/gofrontend/MERGE
index fb7aa3e6eae..aedaf4664d5 100644
--- a/gcc/go/gofrontend/MERGE
+++ b/gcc/go/gofrontend/MERGE
@@ -1,4 +1,4 @@ 
-b2be94556bbc98f565fc277e30a038c742bf28a4
+64c25b2365f7125a32b3146618b627f26a78c1fc
 
 The first line of this file holds the git revision number of the last
 merge done from the gofrontend repository.
diff --git a/libgo/go/syscall/route_bsd.go b/libgo/go/syscall/route_bsd.go
index b364eeaba5d..0c32594783c 100644
--- a/libgo/go/syscall/route_bsd.go
+++ b/libgo/go/syscall/route_bsd.go
@@ -18,7 +18,7 @@  var (
 
 // Round the length of a raw sockaddr up to align it properly.
 func rsaAlignOf(salen int) int {
-	salign := sizeofPtr
+	salign := int(sizeofPtr)
 	if darwin64Bit {
 		// Darwin kernels require 32-bit aligned access to
 		// routing facilities.
diff --git a/libgo/go/syscall/socket_bsd.go b/libgo/go/syscall/socket_bsd.go
index 40637bc7818..b230a3212e6 100644
--- a/libgo/go/syscall/socket_bsd.go
+++ b/libgo/go/syscall/socket_bsd.go
@@ -13,6 +13,7 @@  import "unsafe"
 const SizeofSockaddrInet4 = 16
 const SizeofSockaddrInet6 = 28
 const SizeofSockaddrUnix = 110
+const SizeofSockaddrDatalink = 20
 
 type RawSockaddrInet4 struct {
 	Len    uint8
@@ -76,6 +77,46 @@  func (sa *RawSockaddrUnix) adjustAbstract(sl Socklen_t) Socklen_t {
 	return sl
 }
 
+type SockaddrDatalink struct {
+	Len    uint8
+	Family uint8
+	Index  uint16
+	Type   uint8
+	Nlen   uint8
+	Alen   uint8
+	Slen   uint8
+	Data   [12]int8
+	raw    RawSockaddrDatalink
+}
+
+func (sa *SockaddrDatalink) sockaddr() (*RawSockaddrAny, Socklen_t, error) {
+	if sa.Index == 0 {
+		return nil, 0, EINVAL
+	}
+	sa.raw.Len = sa.Len
+	sa.raw.Family = AF_LINK
+	sa.raw.Index = sa.Index
+	sa.raw.Type = sa.Type
+	sa.raw.Nlen = sa.Nlen
+	sa.raw.Alen = sa.Alen
+	sa.raw.Slen = sa.Slen
+	for i := 0; i < len(sa.raw.Data); i++ {
+		sa.raw.Data[i] = sa.Data[i]
+	}
+	return (*RawSockaddrAny)(unsafe.Pointer(&sa.raw)), SizeofSockaddrDatalink, nil
+}
+
+type RawSockaddrDatalink struct {
+	Len    uint8
+	Family uint8
+	Index  uint16
+	Type   uint8
+	Nlen   uint8
+	Alen   uint8
+	Slen   uint8
+	Data   [12]int8
+}
+
 type RawSockaddr struct {
 	Len    uint8
 	Family uint8
diff --git a/libgo/go/syscall/syscall_netbsd.go b/libgo/go/syscall/syscall_netbsd.go
index c67550a011d..bbc6799e3e6 100644
--- a/libgo/go/syscall/syscall_netbsd.go
+++ b/libgo/go/syscall/syscall_netbsd.go
@@ -17,3 +17,64 @@  func direntReclen(buf []byte) (uint64, bool) {
 func direntNamlen(buf []byte) (uint64, bool) {
 	return readInt(buf, unsafe.Offsetof(Dirent{}.Namlen), unsafe.Sizeof(Dirent{}.Namlen))
 }
+
+func sysctlNodes(mib []_C_int) (nodes []Sysctlnode, err error) {
+	var olen uintptr
+
+	// Get a list of all sysctl nodes below the given MIB by performing
+	// a sysctl for the given MIB with CTL_QUERY appended.
+	mib = append(mib, CTL_QUERY)
+	qnode := Sysctlnode{Flags: SYSCTL_VERS_1}
+	qp := (*byte)(unsafe.Pointer(&qnode))
+	sz := unsafe.Sizeof(qnode)
+	if err = sysctl(mib, nil, &olen, qp, sz); err != nil {
+		return nil, err
+	}
+
+	// Now that we know the size, get the actual nodes.
+	nodes = make([]Sysctlnode, olen/sz)
+	np := (*byte)(unsafe.Pointer(&nodes[0]))
+	if err = sysctl(mib, np, &olen, qp, sz); err != nil {
+		return nil, err
+	}
+
+	return nodes, nil
+}
+
+func nametomib(name string) (mib []_C_int, err error) {
+	// Split name into components.
+	var parts []string
+	last := 0
+	for i := 0; i < len(name); i++ {
+		if name[i] == '.' {
+			parts = append(parts, name[last:i])
+			last = i + 1
+		}
+	}
+	parts = append(parts, name[last:])
+
+	// Discover the nodes and construct the MIB OID.
+	for partno, part := range parts {
+		nodes, err := sysctlNodes(mib)
+		if err != nil {
+			return nil, err
+		}
+		for _, node := range nodes {
+			n := make([]byte, 0)
+			for i := range node.Name {
+				if node.Name[i] != 0 {
+					n = append(n, byte(node.Name[i]))
+				}
+			}
+			if string(n) == part {
+				mib = append(mib, _C_int(node.Num))
+				break
+			}
+		}
+		if len(mib) != partno+1 {
+			return nil, EINVAL
+		}
+	}
+
+	return mib, nil
+}