Implement SO_NO_CHECK socket option.

SO_NO_CHECK is used to skip the UDP checksum generation on a TX socket
(UDP checksum is optional on IPv4).

Test:
 - TestNoChecksum
 - SoNoCheckOffByDefault (UdpSocketTest)
 - SoNoCheck (UdpSocketTest)

Fixes #3055

PiperOrigin-RevId: 318575215
This commit is contained in:
gVisor bot
2020-06-26 17:51:04 -07:00
parent aed7183976
commit 8dbeac53ce
7 changed files with 173 additions and 49 deletions
+19
View File
@@ -1169,6 +1169,17 @@ func getSockOptSocket(t *kernel.Task, s socket.SocketOps, ep commonEndpoint, fam
return int32(v), nil
case linux.SO_NO_CHECK:
if outLen < sizeOfInt32 {
return nil, syserr.ErrInvalidArgument
}
v, err := ep.GetSockOptBool(tcpip.NoChecksumOption)
if err != nil {
return nil, syserr.TranslateNetstackError(err)
}
return boolToInt32(v), nil
default:
socket.GetSockOptEmitUnimplementedEvent(t, name)
}
@@ -1720,6 +1731,14 @@ func setSockOptSocket(t *kernel.Task, s socket.SocketOps, ep commonEndpoint, nam
return syserr.TranslateNetstackError(ep.SetSockOpt(tcpip.OutOfBandInlineOption(v)))
case linux.SO_NO_CHECK:
if len(optVal) < sizeOfInt32 {
return syserr.ErrInvalidArgument
}
v := usermem.ByteOrder.Uint32(optVal)
return syserr.TranslateNetstackError(ep.SetSockOptBool(tcpip.NoChecksumOption, v != 0))
case linux.SO_LINGER:
if len(optVal) < linux.SizeOfLinger {
return syserr.ErrInvalidArgument