mirror of
https://github.com/netbirdio/gvisor.git
synced 2026-05-22 17:12:49 -07:00
Fix socket_ip_tcp_generic_loopback_test_runsc_ptrace_hostnet
This was mostly a matter of allowing more get/setsockopts. Also had to support getsockopt with a null option, because apparantly Linux allows that. PiperOrigin-RevId: 508460614
This commit is contained in:
committed by
gVisor bot
parent
89cc675c29
commit
c0a18ec43b
@@ -222,7 +222,11 @@ func accept4(fd int, addr *byte, addrlen *uint32, flags int) (int, error) {
|
||||
|
||||
func getsockopt(fd int, level, name int, opt []byte) ([]byte, error) {
|
||||
optlen32 := int32(len(opt))
|
||||
_, _, errno := unix.Syscall6(unix.SYS_GETSOCKOPT, uintptr(fd), uintptr(level), uintptr(name), uintptr(firstBytePtr(opt)), uintptr(unsafe.Pointer(&optlen32)), 0)
|
||||
var optPtr uintptr
|
||||
if optlen32 > 0 {
|
||||
optPtr = uintptr(firstBytePtr(opt))
|
||||
}
|
||||
_, _, errno := unix.Syscall6(unix.SYS_GETSOCKOPT, uintptr(fd), uintptr(level), uintptr(name), optPtr, uintptr(unsafe.Pointer(&optlen32)), 0)
|
||||
if errno != 0 {
|
||||
return nil, errno
|
||||
}
|
||||
|
||||
@@ -50,6 +50,8 @@ type SockOpt struct {
|
||||
|
||||
// SockOpts are the socket options supported by hostinet.
|
||||
var SockOpts = []SockOpt{
|
||||
{linux.SOL_IP, linux.IP_MULTICAST_LOOP, sizeofInt32, true, true},
|
||||
{linux.SOL_IP, linux.IP_MULTICAST_TTL, sizeofInt32, true, true},
|
||||
{linux.SOL_IP, linux.IP_PKTINFO, sizeofInt32, true, true},
|
||||
{linux.SOL_IP, linux.IP_RECVERR, sizeofInt32, true, true},
|
||||
{linux.SOL_IP, linux.IP_RECVORIGDSTADDR, sizeofInt32, true, true},
|
||||
@@ -70,21 +72,28 @@ var SockOpts = []SockOpt{
|
||||
|
||||
{linux.SOL_SOCKET, linux.SO_ACCEPTCONN, sizeofInt32, true, true},
|
||||
{linux.SOL_SOCKET, linux.SO_BROADCAST, sizeofInt32, true, true},
|
||||
{linux.SOL_SOCKET, linux.SO_ERROR, sizeofInt32, false, true},
|
||||
{linux.SOL_SOCKET, linux.SO_ERROR, sizeofInt32, true, false},
|
||||
{linux.SOL_SOCKET, linux.SO_KEEPALIVE, sizeofInt32, true, true},
|
||||
{linux.SOL_SOCKET, linux.SO_LINGER, linux.SizeOfLinger, true, true},
|
||||
{linux.SOL_SOCKET, linux.SO_OOBINLINE, sizeofInt32, true, true},
|
||||
{linux.SOL_SOCKET, linux.SO_RCVBUF, sizeofInt32, true, true},
|
||||
{linux.SOL_SOCKET, linux.SO_REUSEADDR, sizeofInt32, true, true},
|
||||
{linux.SOL_SOCKET, linux.SO_SNDBUF, sizeofInt32, true, true},
|
||||
{linux.SOL_SOCKET, linux.SO_TIMESTAMP, sizeofInt32, true, true},
|
||||
{linux.SOL_SOCKET, linux.SO_TYPE, sizeofInt32, false, true},
|
||||
{linux.SOL_SOCKET, linux.SO_TYPE, sizeofInt32, true, false},
|
||||
|
||||
{linux.SOL_TCP, linux.TCP_CONGESTION, 0 /* string */, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_CORK, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_DEFER_ACCEPT, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_INFO, uint64(linux.SizeOfTCPInfo), true, false},
|
||||
{linux.SOL_TCP, linux.TCP_INQ, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_KEEPCNT, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_KEEPIDLE, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_KEEPINTVL, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_LINGER2, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_MAXSEG, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_NODELAY, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_QUICKACK, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_SYNCNT, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_USER_TIMEOUT, sizeofInt32, true, true},
|
||||
{linux.SOL_TCP, linux.TCP_WINDOW_CLAMP, sizeofInt32, true, true},
|
||||
@@ -139,6 +148,9 @@ func (s *Socket) GetSockOpt(t *kernel.Task, level, name int, optValAddr hostarch
|
||||
if !ok {
|
||||
return nil, syserr.ErrProtocolNotAvailable
|
||||
}
|
||||
if !sockOpt.AllowGet {
|
||||
return nil, syserr.ErrInvalidArgument
|
||||
}
|
||||
var opt []byte
|
||||
if sockOpt.Size > 0 {
|
||||
// Validate size of input buffer.
|
||||
@@ -206,6 +218,9 @@ func (s *Socket) SetSockOpt(t *kernel.Task, level, name int, opt []byte) *syserr
|
||||
// seems dangerous, but it's what netstack does...
|
||||
return nil
|
||||
}
|
||||
if !sockOpt.AllowSet {
|
||||
return syserr.ErrInvalidArgument
|
||||
}
|
||||
if sockOpt.Size > 0 {
|
||||
if uint64(len(opt)) < sockOpt.Size {
|
||||
return syserr.ErrInvalidArgument
|
||||
|
||||
@@ -734,6 +734,7 @@ syscall_test(
|
||||
|
||||
syscall_test(
|
||||
size = "large",
|
||||
add_hostinet = True,
|
||||
shard_count = most_shards,
|
||||
test = "//test/syscalls/linux:socket_ip_tcp_generic_loopback_test",
|
||||
)
|
||||
|
||||
@@ -958,7 +958,7 @@ TEST_P(AllSocketPairTest, GetSocketRcvbufOption) {
|
||||
SyscallSucceeds());
|
||||
ASSERT_EQ(opt_len, sizeof(opt));
|
||||
|
||||
if (IsRunningOnGvisor()) {
|
||||
if (IsRunningOnGvisor() && !IsRunningWithHostinet()) {
|
||||
// Minimum buffer size in gVisor is 4KiB.
|
||||
const int minRcvBufSizeGvisor = 4096;
|
||||
EXPECT_EQ(opt, minRcvBufSizeGvisor);
|
||||
@@ -991,7 +991,7 @@ TEST_P(AllSocketPairTest, GetSetSocketRcvlowatOption) {
|
||||
SyscallSucceeds());
|
||||
ASSERT_EQ(opt_len, sizeof(opt));
|
||||
|
||||
if (IsRunningOnGvisor()) {
|
||||
if (IsRunningOnGvisor() && !IsRunningWithHostinet()) {
|
||||
// TODO(b/226603727): Add support for setting SO_RCVLOWAT option in gVisor.
|
||||
EXPECT_EQ(opt, defaultSz);
|
||||
} else {
|
||||
|
||||
@@ -1273,7 +1273,7 @@ TEST_P(TCPSocketPairTest, SetAndGetLingerOption) {
|
||||
// Linux returns a different value as it uses HZ to convert the seconds to
|
||||
// jiffies which overflows for negative values. We want to be compatible with
|
||||
// linux for getsockopt return value.
|
||||
if (IsRunningOnGvisor()) {
|
||||
if (IsRunningOnGvisor() && !IsRunningWithHostinet()) {
|
||||
EXPECT_EQ(sl.l_linger, got_linger.l_linger);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user