Browse Source

account for timeout

lizzie/refactor-networking-12
lizzie 6 days ago
parent
commit
757cfdc7fd
  1. 12
      src/core/internal_network/network.cpp
  2. 10
      src/core/internal_network/socket_icmp.cpp
  3. 2
      src/core/internal_network/socket_icmp.h
  4. 6
      src/core/internal_network/socket_types.h

12
src/core/internal_network/network.cpp

@ -1059,6 +1059,18 @@ Errno Socket::SetSockOpt(Network::SocketLevel level, Network::OptName optname, s
return GetAndLogLastError(CallType::Other); return GetAndLogLastError(CallType::Other);
} }
return Errno::INVAL; return Errno::INVAL;
} else if (optname == Network::OptName::RCVTIMEO || optname == Network::OptName::SNDTIMEO) {
if (optval.size() >= sizeof(Network::Timeval)) {
Network::Timeval guest_tv{};
std::memcpy(&guest_tv, optval.data(), sizeof(guest_tv));
struct timeval tv{};
tv.tv_sec = guest_tv.tv_sec;
tv.tv_usec = guest_tv.tv_usec;
if (setsockopt(fd, native_level, native_optname, reinterpret_cast<const char*>(&tv), sizeof(tv)) != SOCKET_ERROR)
return Errno::SUCCESS;
return GetAndLogLastError(CallType::Other);
}
return Errno::INVAL;
} }
if (setsockopt(fd, native_level, native_optname, reinterpret_cast<const char*>(optval.data()), socklen_t(optval.size())) != SOCKET_ERROR) if (setsockopt(fd, native_level, native_optname, reinterpret_cast<const char*>(optval.data()), socklen_t(optval.size())) != SOCKET_ERROR)
return Errno::SUCCESS; return Errno::SUCCESS;

10
src/core/internal_network/socket_icmp.cpp

@ -42,6 +42,11 @@ IcmpSocket::~IcmpSocket() {
Errno IcmpSocket::SetSockOpt(Network::SocketLevel level, Network::OptName optname, std::span<const u8> optval) { Errno IcmpSocket::SetSockOpt(Network::SocketLevel level, Network::OptName optname, std::span<const u8> optval) {
LOG_WARNING(Network, "(stubbed) level={},optname={},optval={}", level, optname, optval.size()); LOG_WARNING(Network, "(stubbed) level={},optname={},optval={}", level, optname, optval.size());
if (optname == Network::OptName::RCVTIMEO) {
if (optval.size() < sizeof(Network::Timeval))
return Errno::INVAL;
std::memcpy(&rcv_timeo, optval.data(), sizeof(rcv_timeo));
}
return Errno::SUCCESS; return Errno::SUCCESS;
} }
@ -99,10 +104,11 @@ std::pair<s32, Errno> IcmpSocket::RecvFrom(int flags, std::span<u8> message, Net
return {0, Errno::SUCCESS}; return {0, Errno::SUCCESS};
// PLEASE DON'T KILL ME, I SWEAR THIS IS LEGITIMATELY THE BEST WAY TO DO IT // PLEASE DON'T KILL ME, I SWEAR THIS IS LEGITIMATELY THE BEST WAY TO DO IT
// IF YOU OPEN socket() GOOGLE WILL STRAIGHT UP IP BAN YOU AFTER 2 HOURS // IF YOU OPEN socket() GOOGLE WILL STRAIGHT UP IP BAN YOU AFTER 2 HOURS
auto const rcv_timeout = std::max<u64>(rcv_timeo.tv_sec, 0);
#ifdef __FreeBSD__ #ifdef __FreeBSD__
auto const cmd = fmt::format("ping -t 3 -o {}.{}.{}.{}", addr->ip[0], addr->ip[1], addr->ip[2], addr->ip[3]);
auto const cmd = fmt::format("ping -t {} -o {}.{}.{}.{}", rcv_timeout, addr->ip[0], addr->ip[1], addr->ip[2], addr->ip[3]);
#elif defined(__linux__) #elif defined(__linux__)
auto const cmd = fmt::format("ping -c 1 -W 3 {}.{}.{}.{}", addr->ip[0], addr->ip[1], addr->ip[2], addr->ip[3]);
auto const cmd = fmt::format("ping -c 1 -W {} {}.{}.{}.{}", rcv_timeout, addr->ip[0], addr->ip[1], addr->ip[2], addr->ip[3]);
#endif #endif
if (::system(cmd.c_str()) == 0) { if (::system(cmd.c_str()) == 0) {
std::vector<u8> data{ std::vector<u8> data{

2
src/core/internal_network/socket_icmp.h

@ -4,6 +4,7 @@
#pragma once #pragma once
#include <span> #include <span>
#include "core/internal_network/socket_types.h"
#include "core/internal_network/sockets.h" #include "core/internal_network/sockets.h"
namespace Network { namespace Network {
@ -32,6 +33,7 @@ public:
Errno SetNonBlock(bool enable) override; Errno SetNonBlock(bool enable) override;
std::vector<u32> seq_ident; std::vector<u32> seq_ident;
Network::Timeval rcv_timeo;
}; };
} // namespace Network } // namespace Network

6
src/core/internal_network/socket_types.h

@ -348,6 +348,12 @@ struct Linger {
}; };
static_assert(sizeof(Linger) == 8); static_assert(sizeof(Linger) == 8);
struct Timeval {
u64 tv_sec;
u64 tv_usec;
};
static_assert(sizeof(Timeval) == 16);
/// @brief Cross-platform addrinfo structure (not guest) /// @brief Cross-platform addrinfo structure (not guest)
struct AddrInfo { struct AddrInfo {
Domain family; Domain family;

Loading…
Cancel
Save