OpenClonk
C4Network2IODiscoverClient Class Referenceabstract

#include <C4Network2Discover.h>

Inheritance diagram for C4Network2IODiscoverClient:
[legend]
Collaboration diagram for C4Network2IODiscoverClient:
[legend]

Public Types

typedef EndpointAddress addr_t
 

Public Member Functions

 C4Network2IODiscoverClient ()
 
int getDiscoverCount () const
 
const C4NetIO::addr_tgetDiscover (int i)
 
void Clear ()
 
bool Init (uint16_t iPort=C4NetIO::addr_t::IPPORT_NONE) override
 
bool StartDiscovery ()
 
bool PopDiscover (C4NetIO::addr_t &Discover)
 
virtual bool InitBroadcast (addr_t *pBroadcastAddr)
 
bool Close () override
 
bool Close (const addr_t &addr) override
 
virtual bool CloseBroadcast ()
 
bool Execute (int iMaxTime=TO_INF, pollfd *=nullptr) override
 
bool Send (const C4NetIOPacket &rPacket) override
 
virtual bool Send (const class C4NetIOPacket &rPacket)=0
 
bool Broadcast (const C4NetIOPacket &rPacket) override
 
virtual bool Broadcast (const class C4NetIOPacket &rPacket)=0
 
virtual void UnBlock ()
 
void GetFDs (std::vector< struct pollfd > &FDs) override
 
bool Connect (const addr_t &addr) override
 
bool SetBroadcast (const addr_t &addr, bool fSet=true) override
 
bool GetStatistic (int *pBroadcastRate) override
 
bool GetConnStatistic (const addr_t &addr, int *pIRate, int *pORate, int *pLoss) override
 
void ClearStatistic () override
 
void SetCallback (CBClass *pnCallback) override
 
virtual void SetCallback (CBClass *pnCallback)=0
 
bool IsNotify () override
 
virtual const char * GetError () const
 
void ResetError ()
 
bool ExecuteUntil (int iTimeout=-1)
 
virtual C4TimeMilliseconds GetNextTick (C4TimeMilliseconds tNow)
 
bool IsSignaled ()
 
virtual bool IsLowPriority ()
 
virtual uint32_t TimerInterval ()
 

Static Public Member Functions

static std::vector< HostAddressGetLocalAddresses ()
 

Static Public Attributes

static const int TO_INF = -1
 

Protected Member Functions

void OnPacket (const class C4NetIOPacket &rPacket, C4NetIO *pNetIO) override
 
const addr_tgetMCAddr () const
 
bool SetMCLoopback (int fLoopback)
 
bool getMCLoopback () const
 
void SetReUseAddress (bool fAllow)
 
bool InitIPv6Socket (SOCKET socket)
 
void SetError (const char *strnError, bool fSockErr=false)
 
void Changed ()
 

Protected Attributes

StdCopyStrBuf Error
 

Private Member Functions

virtual bool OnConn (const addr_t &AddrPeer, const addr_t &AddrConnect, const addr_t *pOwnAddr, C4NetIO *pNetIO)
 
virtual void OnDisconn (const addr_t &AddrPeer, C4NetIO *pNetIO, const char *szReason)
 

Detailed Description

Definition at line 48 of file C4Network2Discover.h.

Member Typedef Documentation

◆ addr_t

typedef EndpointAddress C4NetIO::addr_t
inherited

Definition at line 212 of file C4NetIO.h.

Constructor & Destructor Documentation

◆ C4Network2IODiscoverClient()

C4Network2IODiscoverClient::C4Network2IODiscoverClient ( )
inline

Definition at line 51 of file C4Network2Discover.h.

References C4Network2IODiscover::OnPacket(), and C4NetIOSimpleUDP::SetCallback().

void SetCallback(CBClass *pnCallback) override
Definition: C4NetIO.h:589
Here is the call graph for this function:

Member Function Documentation

◆ Broadcast() [1/2]

virtual bool C4NetIO::Broadcast ( const class C4NetIOPacket rPacket)
pure virtualinherited

Referenced by C4NetIO::IsNotify().

Here is the caller graph for this function:

◆ Broadcast() [2/2]

bool C4NetIOSimpleUDP::Broadcast ( const C4NetIOPacket rPacket)
overrideinherited

Definition at line 2200 of file C4NetIO.cpp.

References C4NetIOPacket::getRef(), INFINITE, C4NetIOSimpleUDP::Send(), C4NetIO::SetError(), SOCKET_ERROR, C4NetIO::TO_INF, and C4NetIOSimpleUDP::UnBlock().

Referenced by C4NetIOUDP::DoLoopbackTest(), and C4NetIOUDP::InitBroadcast().

2201 {
2202  // just set broadcast address and send
2203  return C4NetIOSimpleUDP::Send(C4NetIOPacket(rPacket.getRef(), MCAddr));
2204 }
bool Send(const C4NetIOPacket &rPacket) override
Definition: C4NetIO.cpp:2180
C4NetIOPacket getRef() const
Definition: C4NetIO.h:324
Here is the call graph for this function:
Here is the caller graph for this function:

◆ Changed()

void StdSchedulerProc::Changed ( )
protectedinherited

Definition at line 108 of file StdScheduler.cpp.

References s.

Referenced by C4NetIOTCP::Accept(), C4NetIOTCP::AddConnectWait(), C4NetIOUDP::AddPeer(), StdScheduler::IsInManualLoop(), C4NetIOTCP::Listen(), and CStdTimerProc::SetDelay().

109 {
110  auto s = scheduler;
111  if (s)
112  s->Changed(this);
113 }
#define s
Here is the caller graph for this function:

◆ Clear()

void C4Network2IODiscoverClient::Clear ( )
inline

Definition at line 63 of file C4Network2Discover.h.

References C4NetMaxDiscover, C4Network2IODiscover::Init(), and C4NetIO::EndpointAddress::IPPORT_NONE.

63 { iDiscoverCount = 0; }
Here is the call graph for this function:

◆ ClearStatistic()

void C4NetIOSimpleUDP::ClearStatistic ( )
inlineoverridevirtualinherited

Implements C4NetIO.

Reimplemented in C4NetIOUDP.

Definition at line 546 of file C4NetIO.h.

References SOCKET.

546 { assert(false); }

◆ Close() [1/2]

bool C4NetIOSimpleUDP::Close ( )
overridevirtualinherited

Implements C4NetIO.

Reimplemented in C4NetIOUDP.

Definition at line 2041 of file C4NetIO.cpp.

References C4NetIOSimpleUDP::CloseBroadcast(), closesocket, INVALID_SOCKET, and C4NetIO::ResetError().

Referenced by C4NetIOUDP::Close(), C4NetIOSimpleUDP::Init(), C4NetIOSimpleUDP::~C4NetIOSimpleUDP(), and C4StartupNetDlg::~C4StartupNetDlg().

2042 {
2043  // should be initialized
2044  if (!fInit) return true;
2045 
2046  ResetError();
2047 
2048  // deactivate multicast
2049  if (fMultiCast)
2050  CloseBroadcast();
2051 
2052  // close sockets
2053  if (sock != INVALID_SOCKET)
2054  {
2055  closesocket(sock);
2056  sock = INVALID_SOCKET;
2057  }
2058 
2059 #ifdef STDSCHEDULER_USE_EVENTS
2060  // close event
2061  if (hEvent != nullptr)
2062  {
2063  WSACloseEvent(hEvent);
2064  hEvent = nullptr;
2065  }
2066 #else
2067  // close pipes
2068  close(Pipe[0]);
2069  close(Pipe[1]);
2070 #endif
2071 
2072 #ifdef HAVE_WINSOCK
2073  // release winsock
2074  ReleaseWinSock();
2075 #endif
2076 
2077  // ok
2078  fInit = false;
2079  return false;
2080 }
void ResetError()
Definition: C4NetIO.h:286
#define INVALID_SOCKET
Definition: C4NetIO.h:36
virtual bool CloseBroadcast()
Definition: C4NetIO.cpp:2082
#define closesocket
Definition: C4NetIO.cpp:46
Here is the call graph for this function:
Here is the caller graph for this function:

◆ Close() [2/2]

bool C4NetIOSimpleUDP::Close ( const addr_t addr)
inlineoverridevirtualinherited

Implements C4NetIO.

Reimplemented in C4NetIOUDP.

Definition at line 539 of file C4NetIO.h.

539 { assert(false); return false; }

◆ CloseBroadcast()

bool C4NetIOSimpleUDP::CloseBroadcast ( )
virtualinherited

Reimplemented in C4NetIOUDP.

Definition at line 2082 of file C4NetIO.cpp.

References C4NetIO::SetError(), and SOCKET_ERROR.

Referenced by C4NetIOSimpleUDP::Close(), C4NetIOUDP::CloseBroadcast(), C4NetIOSimpleUDP::InitBroadcast(), and C4NetIOUDP::InitBroadcast().

2083 {
2084  // multicast not active?
2085  if (!fMultiCast) return true;
2086 
2087  // leave multicast group
2088  if (setsockopt(sock, IPPROTO_IPV6, IPV6_DROP_MEMBERSHIP,
2089  reinterpret_cast<const char *>(&MCGrpInfo), sizeof(MCGrpInfo)) == SOCKET_ERROR)
2090  {
2091  SetError("could not leave multicast group"); // to do: more error information
2092  return false;
2093  }
2094 
2095  // ok
2096  fMultiCast = false;
2097  return true;
2098 }
void SetError(const char *strnError, bool fSockErr=false)
Definition: C4NetIO.cpp:750
#define SOCKET_ERROR
Definition: C4NetIO.cpp:47
Here is the call graph for this function:
Here is the caller graph for this function:

◆ Connect()

bool C4NetIOSimpleUDP::Connect ( const addr_t addr)
inlineoverridevirtualinherited

Implements C4NetIO.

Reimplemented in C4NetIOUDP.

Definition at line 538 of file C4NetIO.h.

538 { assert(false); return false; }

◆ Execute()

bool C4NetIOSimpleUDP::Execute ( int  iMaxTime = TO_INF,
pollfd *  = nullptr 
)
overridevirtualinherited

Implements C4NetIO.

Reimplemented in C4NetIOUDP.

Definition at line 2100 of file C4NetIO.cpp.

References C4NetIO::HostAddress::GetFamily(), GetSocketErrorMsg(), HaveConnResetError(), ioctlsocket, StdBuf::New(), C4NetIO::CBClass::OnDisconn(), C4NetIO::CBClass::OnPacket(), C4NetIO::ResetError(), C4NetIOPacket::SetAddr(), C4NetIO::SetError(), StdBuf::SetSize(), SOCKET_ERROR, and C4NetIO::HostAddress::UnknownFamily.

Referenced by C4NetIOUDP::DoLoopbackTest(), C4NetIOUDP::Execute(), C4NetIOUDP::InitBroadcast(), and C4StartupNetDlg::OnSec1Timer().

2101 {
2102  if (!fInit) { SetError("not yet initialized"); return false; }
2103  ResetError();
2104 
2105 #ifdef __APPLE__
2106  iMaxTime = fix_poll_timeout(iMaxTime);
2107 #endif
2108 
2109  // wait for socket / timeout
2110  WaitResult eWR = WaitForSocket(iMaxTime);
2111  if (eWR == WR_Error) return false;
2112 
2113  // cancelled / timeout?
2114  if (eWR == WR_Cancelled || eWR == WR_Timeout) return true;
2115  assert(eWR == WR_Readable);
2116 
2117  // read packets from socket
2118  for (;;)
2119  {
2120  // how much can be read?
2121 #ifdef _WIN32
2122  u_long iMaxMsgSize;
2123 #else
2124  // The FIONREAD ioctl call takes an int on unix
2125  int iMaxMsgSize;
2126 #endif
2127  if (::ioctlsocket(sock, FIONREAD, &iMaxMsgSize) == SOCKET_ERROR)
2128  {
2129  SetError("Could not determine the amount of data that can be read from socket", true);
2130  return false;
2131  }
2132 
2133  // nothing?
2134  if (!iMaxMsgSize)
2135  break;
2136  // alloc buffer
2137  C4NetIOPacket Pkt; Pkt.New(iMaxMsgSize);
2138  // read data (note: it is _not_ garantueed that iMaxMsgSize bytes are available)
2139  addr_t SrcAddr; socklen_t iSrcAddrLen = sizeof(sockaddr_in6);
2140  int iMsgSize = ::recvfrom(sock, getMBufPtr<char>(Pkt), iMaxMsgSize, 0, &SrcAddr, &iSrcAddrLen);
2141  // error?
2142  if (iMsgSize == SOCKET_ERROR)
2143  {
2144  if (HaveConnResetError())
2145  {
2146  // this is actually some kind of notification: an ICMP msg (unreachable)
2147  // came back, so callback and continue reading
2148  if (pCB) pCB->OnDisconn(SrcAddr, this, GetSocketErrorMsg());
2149  continue;
2150  }
2151  else
2152  {
2153  // this is the real thing, though
2154  SetError("could not receive data from socket", true);
2155  return false;
2156  }
2157  }
2158  // invalid address?
2159  if ((iSrcAddrLen != sizeof(sockaddr_in) && iSrcAddrLen != sizeof(sockaddr_in6)) || SrcAddr.GetFamily() == addr_t::UnknownFamily)
2160  {
2161  SetError("recvfrom returned an invalid address");
2162  return false;
2163  }
2164  // again: nothing?
2165  if (!iMsgSize)
2166  // docs say that the connection has been closed (whatever that means for a connectionless socket...)
2167  // let's just pretend it didn't happen, but stop reading.
2168  break;
2169  // fill in packet information
2170  Pkt.SetSize(iMsgSize);
2171  Pkt.SetAddr(SrcAddr);
2172  // callback
2173  if (pCB) pCB->OnPacket(Pkt, this);
2174  }
2175 
2176  // ok
2177  return true;
2178 }
void ResetError()
Definition: C4NetIO.h:286
const char * GetSocketErrorMsg(int iError)
Definition: C4NetIO.cpp:190
void SetError(const char *strnError, bool fSockErr=false)
Definition: C4NetIO.cpp:750
#define ioctlsocket
Definition: C4NetIO.cpp:45
bool HaveConnResetError()
Definition: C4NetIO.cpp:207
void SetSize(size_t inSize)
Definition: StdBuf.h:204
EndpointAddress addr_t
Definition: C4NetIO.h:212
void New(size_t inSize)
Definition: StdBuf.h:146
virtual void OnDisconn(const addr_t &AddrPeer, C4NetIO *pNetIO, const char *szReason)
Definition: C4NetIO.h:221
virtual void OnPacket(const class C4NetIOPacket &rPacket, C4NetIO *pNetIO)=0
void SetAddr(const C4NetIO::addr_t &naddr)
Definition: C4NetIO.h:327
#define SOCKET_ERROR
Definition: C4NetIO.cpp:47
Here is the call graph for this function:
Here is the caller graph for this function:

◆ ExecuteUntil()

bool StdSchedulerProc::ExecuteUntil ( int  iTimeout = -1)
inherited

Definition at line 33 of file StdScheduler.cpp.

References StdSchedulerProc::Execute(), and C4TimeMilliseconds::Now().

Referenced by main().

34 {
35  // Infinite?
36  if (iTimeout < 0)
37  for (;;)
38  if (!Execute())
39  return false;
40  // Calculate endpoint
41  C4TimeMilliseconds tStopTime = C4TimeMilliseconds::Now() + iTimeout;
42  for (;;)
43  {
44  // Call execute with given timeout
45  if (!Execute(std::max(iTimeout, 0)))
46  return false;
47  // Calculate timeout
49  if (tTime >= tStopTime)
50  break;
51  iTimeout = tStopTime - tTime;
52  }
53  // All ok.
54  return true;
55 }
virtual bool Execute(int iTimeout=-1, pollfd *readyfds=nullptr)=0
static C4TimeMilliseconds Now()
Here is the call graph for this function:
Here is the caller graph for this function:

◆ GetConnStatistic()

bool C4NetIOSimpleUDP::GetConnStatistic ( const addr_t addr,
int *  pIRate,
int *  pORate,
int *  pLoss 
)
inlineoverridevirtualinherited

Implements C4NetIO.

Reimplemented in C4NetIOUDP.

Definition at line 544 of file C4NetIO.h.

545  { assert(false); return false; }

◆ getDiscover()

const C4NetIO::addr_t& C4Network2IODiscoverClient::getDiscover ( int  i)
inline

Definition at line 61 of file C4Network2Discover.h.

61 { return Discovers[i]; }

◆ getDiscoverCount()

int C4Network2IODiscoverClient::getDiscoverCount ( ) const
inline

Definition at line 60 of file C4Network2Discover.h.

60 { return iDiscoverCount; }

◆ GetError()

virtual const char* C4NetIO::GetError ( ) const
inlinevirtualinherited

Definition at line 285 of file C4NetIO.h.

References StdStrBuf::getData().

Referenced by C4Network2IO::ConnectWithSocket(), C4NetIOUDP::DoLoopbackTest(), C4StartupNetDlg::DoRefresh(), C4DownloadDlg::GetError(), C4Network2IO::Init(), C4NetIOUDP::InitBroadcast(), C4Network2::InitLeague(), C4Game::InitNetworkFromAddress(), C4Network2::LeagueEnd(), C4Network2::LeaguePlrAuthCheck(), C4Network2::LeagueStart(), C4Network2::LeagueUpdate(), C4Network2::LeagueUpdateProcessReply(), main(), MyCBClass::OnConn(), C4ChatControl::OnConnectBtn(), MyCBClass::OnPacket(), C4StartupNetListEntry::OnReference(), C4ChatControl::ProcessInput(), C4Network2IOConnection::Send(), and C4StartupNetListEntry::SetRefQuery().

285 { return Error.getData(); }
StdCopyStrBuf Error
Definition: C4NetIO.h:282
const char * getData() const
Definition: StdBuf.h:442
Here is the call graph for this function:
Here is the caller graph for this function:

◆ GetFDs()

void C4NetIOSimpleUDP::GetFDs ( std::vector< struct pollfd > &  FDs)
overridevirtualinherited

Reimplemented from StdSchedulerProc.

Definition at line 2252 of file C4NetIO.cpp.

References INVALID_SOCKET, and C4NetIO::SetError().

2253 {
2254  // add pipe
2255  pollfd pfd = { Pipe[0], POLLIN, 0 };
2256  fds.push_back(pfd);
2257  // add socket
2258  if (sock != INVALID_SOCKET)
2259  {
2260  pollfd pfd = { sock, POLLIN, 0 };
2261  fds.push_back(pfd);
2262  }
2263 }
#define INVALID_SOCKET
Definition: C4NetIO.h:36
Here is the call graph for this function:

◆ GetLocalAddresses()

std::vector< C4NetIO::HostAddress > C4NetIO::GetLocalAddresses ( )
staticinherited

Definition at line 631 of file C4NetIO.cpp.

References C4NetIO::HostAddress::IsLoopback(), and C4NetIO::HostAddress::SetHost().

Referenced by C4Network2Client::AddLocalAddrs(), and C4NetIOUDP::InitBroadcast().

632 {
633  std::vector<HostAddress> result;
634 
635 #ifdef HAVE_WINSOCK
636  HostAddress addr;
637  const size_t BUFFER_SIZE = 16000;
638  PIP_ADAPTER_ADDRESSES addresses = nullptr;
639  for (int i = 0; i < 3; ++i)
640  {
641  addresses = (PIP_ADAPTER_ADDRESSES) realloc(addresses, BUFFER_SIZE * (i+1));
642  if (!addresses)
643  // allocation failed
644  return result;
645  ULONG bufsz = BUFFER_SIZE * (i+1);
646  DWORD rv = GetAdaptersAddresses(AF_UNSPEC,
647  GAA_FLAG_SKIP_ANYCAST|GAA_FLAG_SKIP_MULTICAST|GAA_FLAG_SKIP_DNS_SERVER|GAA_FLAG_SKIP_FRIENDLY_NAME,
648  nullptr, addresses, &bufsz);
649  if (rv == ERROR_BUFFER_OVERFLOW)
650  // too little space, try again
651  continue;
652  if (rv != NO_ERROR)
653  {
654  // Something else happened
655  free(addresses);
656  return result;
657  }
658  // All okay, add addresses
659  for (PIP_ADAPTER_ADDRESSES address = addresses; address; address = address->Next)
660  {
661  for (PIP_ADAPTER_UNICAST_ADDRESS unicast = address->FirstUnicastAddress; unicast; unicast = unicast->Next)
662  {
663  addr.SetHost(unicast->Address.lpSockaddr);
664  if (addr.IsLoopback())
665  continue;
666  result.push_back(addr);
667  }
668  }
669  }
670  free(addresses);
671 #else
672  bool have_ipv6 = false;
673 
674 #ifdef __linux__
675  // Get IPv6 addresses on Linux from procfs which allows filtering deprecated privacy addresses.
676  FILE *f = fopen("/proc/net/if_inet6", "r");
677  if (f)
678  {
679  sockaddr_in6 sa6 = sockaddr_in6();
680  sa6.sin6_family = AF_INET6;
681  auto a6 = sa6.sin6_addr.s6_addr;
682  uint8_t if_idx, plen, scope, flags;
683  char devname[20];
684  while (fscanf(f, "%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx %02hhx %02hhx %02hhx %02hhx %20s\n",
685  &a6[0], &a6[1], &a6[2], &a6[3], &a6[4], &a6[5], &a6[6], &a6[7],
686  &a6[8], &a6[9], &a6[10], &a6[11], &a6[12], &a6[13], &a6[14], &a6[15],
687  &if_idx, &plen, &scope, &flags, devname) != EOF)
688  {
689  // Skip loopback and deprecated addresses.
690  if (scope == IPV6_ADDR_LOOPBACK || flags & IFA_F_DEPRECATED)
691  continue;
692  sa6.sin6_scope_id = scope == IPV6_ADDR_LINKLOCAL ? if_idx : 0;
693  result.emplace_back((sockaddr*) &sa6);
694  }
695  have_ipv6 = result.size() > 0;
696  fclose(f);
697  }
698 #endif
699 
700  struct ifaddrs* addrs;
701  if (getifaddrs(&addrs) < 0)
702  return result;
703  for (struct ifaddrs* ifaddr = addrs; ifaddr != nullptr; ifaddr = ifaddr->ifa_next)
704  {
705  struct sockaddr* ad = ifaddr->ifa_addr;
706  if (ad == nullptr) continue;
707 
708  if ((ad->sa_family == AF_INET || (!have_ipv6 && ad->sa_family == AF_INET6)) && (~ifaddr->ifa_flags & IFF_LOOPBACK)) // Choose only non-loopback IPv4/6 devices
709  {
710  result.emplace_back(ad);
711  }
712  }
713  freeifaddrs(addrs);
714 #endif
715 
716  return result;
717 }
uint32_t DWORD
Here is the call graph for this function:
Here is the caller graph for this function:

◆ getMCAddr()

const addr_t& C4NetIOSimpleUDP::getMCAddr ( ) const
inlineprotectedinherited

Definition at line 572 of file C4NetIO.h.

Referenced by C4NetIOUDP::SendDirect().

572 { return MCAddr; }
Here is the caller graph for this function:

◆ getMCLoopback()

bool C4NetIOSimpleUDP::getMCLoopback ( ) const
inlineprotectedinherited

Definition at line 576 of file C4NetIO.h.

Referenced by C4NetIOUDP::DoLoopbackTest(), and C4NetIOUDP::InitBroadcast().

576 { return fMCLoopback; }
Here is the caller graph for this function:

◆ GetNextTick()

C4TimeMilliseconds StdSchedulerProc::GetNextTick ( C4TimeMilliseconds  tNow)
virtualinherited

Reimplemented in C4NetIOUDP, C4Network2HTTPClient, C4Network2IO, and CStdTimerProc.

Definition at line 115 of file StdScheduler.cpp.

References C4TimeMilliseconds::PositiveInfinity.

Referenced by StdSchedulerProc::GetFDs(), C4Network2HTTPClient::GetNextTick(), StdScheduler::IsInManualLoop(), and StdScheduler::ScheduleProcs().

Here is the caller graph for this function:

◆ GetStatistic()

bool C4NetIOSimpleUDP::GetStatistic ( int *  pBroadcastRate)
inlineoverridevirtualinherited

Implements C4NetIO.

Reimplemented in C4NetIOUDP.

Definition at line 543 of file C4NetIO.h.

543 { assert(false); return false; }

◆ Init()

bool C4Network2IODiscoverClient::Init ( uint16_t  iPort = C4NetIO::addr_t::IPPORT_NONE)
overridevirtual

Reimplemented from C4NetIOSimpleUDP.

Definition at line 89 of file C4Network2Discover.cpp.

References C4NetDiscoveryAddress, C4NetIOSimpleUDP::Init(), C4NetIOSimpleUDP::InitBroadcast(), C4NetIOSimpleUDP::SetCallback(), C4NetIOSimpleUDP::SetMCLoopback(), and C4NetIOSimpleUDP::SetReUseAddress().

Referenced by C4StartupNetDlg::C4StartupNetDlg().

90 {
91  // Reuse address
93  // Bind to port
94  if (!C4NetIOSimpleUDP::Init(iPort))
95  return false;
96  // Set callback
98  // Build broadcast address
99  DiscoveryAddr.SetAddress(C4NetDiscoveryAddress);
100  DiscoveryAddr.SetPort(iPort);
101  // Initialize broadcast
102  if (!C4NetIOSimpleUDP::InitBroadcast(&DiscoveryAddr))
103  return false;
104  // Enable multicast loopback
105  return C4NetIOSimpleUDP::SetMCLoopback(true);
106 }
bool SetMCLoopback(int fLoopback)
Definition: C4NetIO.cpp:2290
virtual bool InitBroadcast(addr_t *pBroadcastAddr)
Definition: C4NetIO.cpp:1986
void SetCallback(CBClass *pnCallback) override
Definition: C4NetIO.h:589
const StdStrBuf C4NetDiscoveryAddress
void SetAddress(const sockaddr *addr)
Definition: C4NetIO.cpp:364
void SetPort(uint16_t port)
Definition: C4NetIO.cpp:531
void SetReUseAddress(bool fAllow)
Definition: C4NetIO.cpp:2302
bool Init(uint16_t iPort=addr_t::IPPORT_NONE) override
Definition: C4NetIO.cpp:1898
Here is the call graph for this function:
Here is the caller graph for this function:

◆ InitBroadcast()

bool C4NetIOSimpleUDP::InitBroadcast ( addr_t pBroadcastAddr)
virtualinherited

Reimplemented in C4NetIOUDP.

Definition at line 1986 of file C4NetIO.cpp.

References C4NetIOSimpleUDP::CloseBroadcast(), C4NetIO::HostAddress::GetFamily(), C4NetIO::EndpointAddress::GetPort(), C4NetIO::HostAddress::IPv6, C4NetIO::HostAddress::IsMulticast(), C4NetIO::ResetError(), C4NetIO::SetError(), C4NetIOSimpleUDP::SetMCLoopback(), and SOCKET_ERROR.

Referenced by C4Network2IODiscover::Init(), Init(), and C4NetIOUDP::InitBroadcast().

1987 {
1988  // no error... yet
1989  ResetError();
1990 
1991  // security
1992  if (!pBroadcastAddr) return false;
1993 
1994  // Init() has to be called first
1995  if (!fInit) return false;
1996  // already activated?
1997  if (fMultiCast) CloseBroadcast();
1998 
1999  // broadcast addr valid?
2000  if (!pBroadcastAddr->IsMulticast() || pBroadcastAddr->GetFamily() != HostAddress::IPv6)
2001  {
2002  SetError("invalid broadcast address (only IPv6 multicast addresses are supported)");
2003  return false;
2004  }
2005  if (pBroadcastAddr->GetPort() != iPort)
2006  {
2007  SetError("invalid broadcast address (different port)");
2008  return false;
2009  }
2010 
2011  // set mc ttl to somewhat about "same net"
2012  int TTL = 16;
2013  if (setsockopt(sock, IPPROTO_IPV6, IPV6_MULTICAST_HOPS, reinterpret_cast<char*>(&TTL), sizeof(TTL)) == SOCKET_ERROR)
2014  {
2015  SetError("could not set mc ttl", true);
2016  return false;
2017  }
2018 
2019  // set up multicast group information
2020  this->MCAddr = *pBroadcastAddr;
2021  MCGrpInfo.ipv6mr_multiaddr = static_cast<sockaddr_in6>(MCAddr).sin6_addr;
2022  // TODO: do multicast on all interfaces?
2023  MCGrpInfo.ipv6mr_interface = 0; // default interface
2024 
2025  // join multicast group
2026  if (setsockopt(sock, IPPROTO_IPV6, IPV6_ADD_MEMBERSHIP,
2027  reinterpret_cast<const char *>(&MCGrpInfo), sizeof(MCGrpInfo)) == SOCKET_ERROR)
2028  {
2029  SetError("could not join multicast group"); // to do: more error information
2030  return false;
2031  }
2032 
2033  // (try to) disable loopback (will set fLoopback accordingly)
2034  SetMCLoopback(false);
2035 
2036  // ok
2037  fMultiCast = true;
2038  return true;
2039 }
void ResetError()
Definition: C4NetIO.h:286
bool SetMCLoopback(int fLoopback)
Definition: C4NetIO.cpp:2290
void SetError(const char *strnError, bool fSockErr=false)
Definition: C4NetIO.cpp:750
virtual bool CloseBroadcast()
Definition: C4NetIO.cpp:2082
#define SOCKET_ERROR
Definition: C4NetIO.cpp:47
Here is the call graph for this function:
Here is the caller graph for this function:

◆ InitIPv6Socket()

bool C4NetIO::InitIPv6Socket ( SOCKET  socket)
protectedinherited

Definition at line 730 of file C4NetIO.cpp.

References C4NetIO::SetError(), and SOCKET_ERROR.

Referenced by C4NetIOTCP::CreateSocket(), C4NetIOSimpleUDP::Init(), C4NetIO::IsNotify(), and C4NetIOTCP::Listen().

731 {
732  int opt = 0;
733  if (setsockopt(socket, IPPROTO_IPV6, IPV6_V6ONLY, reinterpret_cast<char*>(&opt), sizeof(opt)) == SOCKET_ERROR)
734  {
735  SetError("could not enable dual-stack socket", true);
736  return false;
737  }
738 
739 #ifdef IPV6_ADDR_PREFERENCES
740  // Prefer stable addresses. This should prevent issues with address
741  // deprecation while a match is running. No error handling - if the call
742  // fails, we just take any address.
743  opt = IPV6_PREFER_SRC_PUBLIC;
744  setsockopt(socket, IPPROTO_IPV6, IPV6_ADDR_PREFERENCES, reinterpret_cast<char*>(&opt), sizeof(opt));
745 #endif
746 
747  return true;
748 }
void SetError(const char *strnError, bool fSockErr=false)
Definition: C4NetIO.cpp:750
#define SOCKET_ERROR
Definition: C4NetIO.cpp:47
Here is the call graph for this function:
Here is the caller graph for this function:

◆ IsLowPriority()

virtual bool StdSchedulerProc::IsLowPriority ( )
inlinevirtualinherited

Definition at line 82 of file StdScheduler.h.

82 { return false; }

◆ IsNotify()

bool C4NetIO::IsNotify ( )
inlineoverridevirtualinherited

Reimplemented from StdSchedulerProc.

Definition at line 259 of file C4NetIO.h.

References C4NetIO::Broadcast(), C4NetIO::ClearStatistic(), C4NetIO::Close(), C4NetIO::Connect(), C4NetIO::GetConnStatistic(), C4NetIO::GetStatistic(), C4NetIO::InitIPv6Socket(), C4NetIO::Send(), C4NetIO::SetBroadcast(), and SOCKET.

259 { return true; }
Here is the call graph for this function:

◆ IsSignaled()

bool StdSchedulerProc::IsSignaled ( )
inherited

Referenced by StdSchedulerProc::GetFDs().

Here is the caller graph for this function:

◆ OnPacket()

void C4Network2IODiscoverClient::OnPacket ( const class C4NetIOPacket rPacket,
C4NetIO pNetIO 
)
overrideprotectedvirtual

Implements C4NetIO::CBClass.

Definition at line 73 of file C4Network2Discover.cpp.

References C4NetMaxDiscover, C4NetIOPacket::getAddr(), StdBuf::getData(), StdBuf::getSize(), C4NetIOPacket::getStatus(), C4Network2IODiscoverReply::Port, and C4NetIO::EndpointAddress::SetPort().

74 {
75  // discovery?
76  if (rPacket.getSize() == sizeof(C4Network2IODiscoverReply) && rPacket.getStatus() == 4)
77  {
78  // save discovered address
79  if (iDiscoverCount < C4NetMaxDiscover)
80  {
81  const C4Network2IODiscoverReply *pReply = reinterpret_cast<const C4Network2IODiscoverReply *>(rPacket.getData());
82  Discovers[iDiscoverCount] = rPacket.getAddr();
83  Discovers[iDiscoverCount].SetPort(pReply->Port);
84  iDiscoverCount++;
85  }
86  }
87 }
void SetPort(uint16_t port)
Definition: C4NetIO.cpp:531
const int C4NetMaxDiscover
Here is the call graph for this function:

◆ PopDiscover()

bool C4Network2IODiscoverClient::PopDiscover ( C4NetIO::addr_t Discover)

Definition at line 115 of file C4Network2Discover.cpp.

Referenced by C4StartupNetDlg::OnBtnRecord().

116 {
117  // Discovers left?
118  if (!getDiscoverCount())
119  return false;
120  // Return one
121  Discover = Discovers[--iDiscoverCount];
122  return true;
123 }
Here is the caller graph for this function:

◆ ResetError()

void C4NetIO::ResetError ( )
inlineinherited

Definition at line 286 of file C4NetIO.h.

References StdStrBuf::Clear(), and C4NetIO::SetCallback().

Referenced by C4NetIO::C4NetIO(), C4NetIOTCP::Close(), C4NetIOSimpleUDP::Close(), C4NetIOUDP::CloseBroadcast(), C4Network2IO::ConnectWithSocket(), C4NetIOSimpleUDP::Execute(), C4NetIOUDP::Execute(), C4NetIOSimpleUDP::Init(), C4NetIOSimpleUDP::InitBroadcast(), C4NetIOUDP::InitBroadcast(), C4Network2IOConnection::Send(), and C4NetIOSimpleUDP::Send().

286 { Error.Clear(); }
void Clear()
Definition: StdBuf.h:466
StdCopyStrBuf Error
Definition: C4NetIO.h:282
Here is the call graph for this function:
Here is the caller graph for this function:

◆ Send() [1/2]

virtual bool C4NetIO::Send ( const class C4NetIOPacket rPacket)
pure virtualinherited

Referenced by C4NetIOUDP::Peer::GetAltAddr(), C4NetIOTCP::Peer::GetORate(), C4NetIO::IsNotify(), main(), MyCBClass::OnConn(), MyCBClass::OnPacket(), C4Network2IOConnection::Send(), and C4Network2IO::SendPuncherPacket().

Here is the caller graph for this function:

◆ Send() [2/2]

bool C4NetIOSimpleUDP::Send ( const C4NetIOPacket rPacket)
overrideinherited

Definition at line 2180 of file C4NetIO.cpp.

References C4NetIOPacket::getAddr(), C4NetIO::HostAddress::GetAddrLen(), StdBuf::getSize(), HaveWouldBlockError(), C4NetIO::ResetError(), and C4NetIO::SetError().

Referenced by C4NetIOSimpleUDP::Broadcast(), and C4NetIOUDP::SendDirect().

2181 {
2182  if (!fInit) { SetError("not yet initialized"); return false; }
2183 
2184  // send it
2185  C4NetIO::addr_t addr = rPacket.getAddr();
2186  if (::sendto(sock, getBufPtr<char>(rPacket), rPacket.getSize(), 0,
2187  &addr, addr.GetAddrLen())
2188  != int(rPacket.getSize()) &&
2190  {
2191  SetError("socket sendto failed", true);
2192  return false;
2193  }
2194 
2195  // ok
2196  ResetError();
2197  return true;
2198 }
void ResetError()
Definition: C4NetIO.h:286
void SetError(const char *strnError, bool fSockErr=false)
Definition: C4NetIO.cpp:750
size_t getSize() const
Definition: StdBuf.h:101
bool HaveWouldBlockError()
Definition: C4NetIO.cpp:203
size_t GetAddrLen() const
Definition: C4NetIO.cpp:526
const C4NetIO::addr_t & getAddr() const
Definition: C4NetIO.h:316
Here is the call graph for this function:
Here is the caller graph for this function:

◆ SetBroadcast()

bool C4NetIOSimpleUDP::SetBroadcast ( const addr_t addr,
bool  fSet = true 
)
inlineoverridevirtualinherited

Implements C4NetIO.

Reimplemented in C4NetIOUDP.

Definition at line 541 of file C4NetIO.h.

541 { assert(false); return false; }

◆ SetCallback() [1/2]

virtual void C4NetIO::SetCallback ( CBClass pnCallback)
pure virtualinherited

Referenced by C4NetIOMan::AddIO(), C4Network2IO::Init(), and C4NetIO::ResetError().

Here is the caller graph for this function:

◆ SetCallback() [2/2]

void C4NetIOSimpleUDP::SetCallback ( CBClass *  pnCallback)
inlineoverrideinherited

Definition at line 589 of file C4NetIO.h.

Referenced by C4Network2IODiscover::C4Network2IODiscover(), C4Network2IODiscoverClient(), C4Network2IODiscover::Init(), Init(), and C4NetIOUDP::Init().

589 { pCB = pnCallback; };
Here is the caller graph for this function:

◆ SetError()

void C4NetIO::SetError ( const char *  strnError,
bool  fSockErr = false 
)
protectedinherited

Definition at line 750 of file C4NetIO.cpp.

References C4NetIOPacket::C4NetIOPacket(), StdStrBuf::Copy(), C4NetIO::Error, StdStrBuf::Format(), GetSocketErrorMsg(), and HaveSocketError().

Referenced by C4NetIOTCP::Accept(), C4NetIOTCP::Bind(), C4NetIOSimpleUDP::Broadcast(), C4NetIOSimpleUDP::CloseBroadcast(), C4NetIOTCP::Connect(), C4NetIOTCP::CreateSocket(), C4NetIOUDP::DoLoopbackTest(), C4NetIOTCP::Execute(), C4NetIOSimpleUDP::Execute(), C4NetIOUDP::Execute(), C4NetIOSimpleUDP::GetFDs(), C4NetIOTCP::Init(), C4NetIOSimpleUDP::Init(), C4NetIOSimpleUDP::InitBroadcast(), C4NetIOUDP::InitBroadcast(), C4NetIO::InitIPv6Socket(), C4NetIOTCP::Listen(), C4NetIOTCP::Peer::Send(), C4NetIOSimpleUDP::Send(), C4NetIOTCP::UnBlock(), and C4NetIOSimpleUDP::UnBlock().

751 {
752  fSockErr &= HaveSocketError();
753  if (fSockErr)
754  Error.Format("%s (%s)", strnError, GetSocketErrorMsg());
755  else
756  Error.Copy(strnError);
757 }
const char * GetSocketErrorMsg(int iError)
Definition: C4NetIO.cpp:190
StdCopyStrBuf Error
Definition: C4NetIO.h:282
void Format(const char *szFmt,...) GNUC_FORMAT_ATTRIBUTE_O
Definition: StdBuf.cpp:174
bool HaveSocketError()
Definition: C4NetIO.cpp:199
void Copy()
Definition: StdBuf.h:467
Here is the call graph for this function:
Here is the caller graph for this function:

◆ SetMCLoopback()

bool C4NetIOSimpleUDP::SetMCLoopback ( int  fLoopback)
protectedinherited

Definition at line 2290 of file C4NetIO.cpp.

References iSize, and SOCKET_ERROR.

Referenced by C4NetIOUDP::DoLoopbackTest(), C4Network2IODiscover::Init(), Init(), C4NetIOSimpleUDP::InitBroadcast(), and C4NetIOUDP::InitBroadcast().

2291 {
2292  // enable/disable MC loopback
2293  setsockopt(sock, IPPROTO_IPV6, IPV6_MULTICAST_LOOP, reinterpret_cast<char *>(&fLoopback), sizeof fLoopback);
2294  // read result
2295  socklen_t iSize = sizeof(fLoopback);
2296  if (getsockopt(sock, IPPROTO_IPV6, IPV6_MULTICAST_LOOP, reinterpret_cast<char *>(&fLoopback), &iSize) == SOCKET_ERROR)
2297  return false;
2298  fMCLoopback = !! fLoopback;
2299  return true;
2300 }
int iSize
Definition: TstC4NetIO.cpp:32
#define SOCKET_ERROR
Definition: C4NetIO.cpp:47
Here is the caller graph for this function:

◆ SetReUseAddress()

void C4NetIOSimpleUDP::SetReUseAddress ( bool  fAllow)
protectedinherited

Definition at line 2302 of file C4NetIO.cpp.

Referenced by C4Network2IODiscover::Init(), and Init().

2303 {
2304  fAllowReUse = fAllow;
2305 }
Here is the caller graph for this function:

◆ StartDiscovery()

bool C4Network2IODiscoverClient::StartDiscovery ( )

Definition at line 108 of file C4Network2Discover.cpp.

References C4Network2IODiscoverReply::c.

Referenced by C4StartupNetDlg::C4StartupNetDlg(), C4StartupNetDlg::DoRefresh(), and C4StartupNetDlg::OnSec1Timer().

109 {
110  // Multicast discovery byte
111  char c = 3;
112  return Send(C4NetIOPacket(&c, sizeof(c), false, DiscoveryAddr));
113 }
bool Send(const C4NetIOPacket &rPacket) override
Definition: C4NetIO.cpp:2180
Here is the caller graph for this function:

◆ TimerInterval()

virtual uint32_t StdSchedulerProc::TimerInterval ( )
inlinevirtualinherited

Reimplemented in CStdTimerProc.

Definition at line 84 of file StdScheduler.h.

Referenced by SCHAdditions::assignAdditionForProc:.

84 { return 0; }
Here is the caller graph for this function:

◆ UnBlock()

void C4NetIOSimpleUDP::UnBlock ( )
virtualinherited

Definition at line 2243 of file C4NetIO.cpp.

References C4NetIO::SetError().

Referenced by C4NetIOSimpleUDP::Broadcast().

2244 {
2245  // write one character to the pipe, this will unblock everything that
2246  // waits for the FD set returned by GetFDs.
2247  char c = 42;
2248  if (write(Pipe[1], &c, 1) == -1)
2249  SetError("write failed");
2250 }
void SetError(const char *strnError, bool fSockErr=false)
Definition: C4NetIO.cpp:750
Here is the call graph for this function:
Here is the caller graph for this function:

Member Data Documentation

◆ Error

StdCopyStrBuf C4NetIO::Error
protectedinherited

Definition at line 282 of file C4NetIO.h.

Referenced by C4NetIO::SetError().

◆ TO_INF


The documentation for this class was generated from the following files: