Esempio n. 1
0
void C4Network2IO::SendConnPackets()
{
    CStdLock ConnListLock(&ConnListCSec);

    // exlusive conn?
    if (fExclusiveConn)
        // find a live connection
        for (C4Network2IOConnection *pConn = pConnList; pConn; pConn = pConn->pNext)
            if (pConn->isAccepted() || (!pConn->isClosed() && pConn->isConnSent()))
                // do not sent additional conn packets - no other connection should succeed
                return;

    // sent pending welcome packet(s)
    for (C4Network2IOConnection *pConn = pConnList; pConn; pConn = pConn->pNext)
        if (pConn->isOpen() && !pConn->isConnSent())
        {
            // make packet
            CStdLock LCCoreLock(&LCCoreCSec);
            C4NetIOPacket Pkt = MkC4NetIOPacket(PID_Conn, C4PacketConn(LCCore, pConn->getID(), pConn->getPassword()));
            LCCoreLock.Clear();
            // send
            if (!pConn->Send(Pkt))
                pConn->Close();
            else
            {
                // set flag
                pConn->SetConnSent();
                // only one conn packet at a time
                if (fExclusiveConn)
                    return;
            }
        }

}
Esempio n. 2
0
// C4NetIO interface
bool C4Network2IO::OnConn(const C4NetIO::addr_t &PeerAddr, const C4NetIO::addr_t &ConnectAddr, const C4NetIO::addr_t *pOwnAddr, C4NetIO *pNetIO)
{
    // puncher answer? We just make sure here a connection /can/ be established, so close it instantly.
    if (pNetIO == pNetIO_UDP)
        if (PuncherAddr.sin_addr.s_addr && AddrEqual(PuncherAddr, ConnectAddr))
        {
            // got an address?
            if (pOwnAddr)
                OnPunch(*pOwnAddr);
            // this is only a test connection - close it instantly
            return false;
        }
#if(C4NET2IO_DUMP_LEVEL > 1)
    Application.InteractiveThread.ThreadLogS("OnConn: %s %s",
            C4TimeMilliseconds::Now().AsString().getData(),
            getNetIOName(pNetIO));
#endif
    // search connection
    C4Network2IOConnection *pConn = NULL;
    if (ConnectAddr.sin_addr.s_addr)
        pConn = GetConnectionByConnAddr(ConnectAddr, pNetIO);
    // not found?
    if (!pConn)
    {
        // allow connect?
        if (!fAllowConnect) return false;
        // create new connection object
        uint32_t iConnID = iNextConnID++;
        pConn = new C4Network2IOConnection();
        pConn->Set(pNetIO, getNetIOProt(pNetIO), PeerAddr, ConnectAddr, CS_Connected, NULL, iConnID);
        // add to list
        AddConnection(pConn);
    }
    else
    {
        // already closed this connection (attempt)?
        if (pConn->isClosed())
            return false;
        if (!pConn->isOpen())
        {
            // change status
            pConn->SetStatus(CS_Connected);
            pConn->SetPeerAddr(PeerAddr);
        }
    }
    // send welcome packet, if appropriate
    SendConnPackets();
#if(C4NET2IO_DUMP_LEVEL > 0)
    // log
    Application.InteractiveThread.ThreadLogS("Network: got %s connection from %s:%d", getNetIOName(pNetIO), inet_ntoa(PeerAddr.sin_addr), htons(PeerAddr.sin_port));
#endif
    // do event (disabled - unused)
    // pConn->AddRef(); PushNetEv(NE_Conn, pConn);
    // ok
    return true;
}
Esempio n. 3
0
void C4Network2IO::BeginBroadcast(bool fSelectAll)
{
    // lock
    BroadcastCSec.Enter();
    // reset all broadcast flags
    CStdLock ConnListLock(&ConnListCSec);
    for (C4Network2IOConnection *pConn = pConnList; pConn; pConn = pConn->pNext)
        if (pConn->isOpen())
            pConn->SetBroadcastTarget(fSelectAll);
}
Esempio n. 4
0
bool C4Network2IO::Broadcast(const C4NetIOPacket &rPkt)
{
    bool fSuccess = true;
    // There is no broadcasting atm, emulate it
    CStdLock ConnListLock(&ConnListCSec);
    for (C4Network2IOConnection *pConn = pConnList; pConn; pConn = pConn->pNext)
        if (pConn->isOpen() && pConn->isBroadcastTarget())
            fSuccess &= pConn->Send(rPkt);
    if(!fSuccess)
        Log("Network: Warning! Broadcast failed.");
    return fSuccess;
}
Esempio n. 5
0
void C4Network2Client::CloseConns(const char *szMsg) {
  C4PacketConnRe Pkt(false, false, szMsg);
  C4Network2IOConnection *pConn;
  while (pConn = pMsgConn) {
    // send packet, close
    if (pConn->isOpen()) {
      pConn->Send(MkC4NetIOPacket(PID_ConnRe, Pkt));
      pConn->Close();
    }
    // remove
    RemoveConn(pConn);
  }
}
Esempio n. 6
0
bool C4Network2IO::Ping()
{
    bool fSuccess = true;
    // ping all connections
    for (C4Network2IOConnection *pConn = pConnList; pConn; pConn = pConn->pNext)
        if (pConn->isOpen())
        {
            C4PacketPing Ping(pConn->getInPacketCounter(), pConn->getOutPacketCounter());
            fSuccess &= pConn->Send(MkC4NetIOPacket(PID_Ping, Ping));
            pConn->OnPing();
        }
    return fSuccess;
}
Esempio n. 7
0
void C4Network2IO::GenerateStatistics(int iInterval)
{
    int iTCPIRateSum = 0, iTCPORateSum = 0, iUDPIRateSum = 0, iUDPORateSum = 0;

    // acquire lock, get connection statistics
    CStdLock ConnListLock(&ConnListCSec);
    for (C4Network2IOConnection *pConn = pConnList; pConn; pConn = pConn->pNext)
        if (pConn->isOpen())
        {
            bool fTCP = pConn->getNetClass() == pNetIO_TCP;
            pConn->DoStatistics(iInterval, fTCP ? &iTCPIRateSum : &iUDPIRateSum,
                                fTCP ? &iTCPORateSum : &iUDPORateSum);
        }
    ConnListLock.Clear();

    // get broadcast statistics
    int inTCPBCRate = 0, inUDPBCRate = 0;
    if (pNetIO_TCP) pNetIO_TCP->GetStatistic(&inTCPBCRate);
    if (pNetIO_UDP) pNetIO_UDP->GetStatistic(&inUDPBCRate);

    // normalize everything
    iTCPIRateSum = iTCPIRateSum * 1000 / iInterval;
    iTCPORateSum = iTCPORateSum * 1000 / iInterval;
    iUDPIRateSum = iUDPIRateSum * 1000 / iInterval;
    iUDPORateSum = iUDPORateSum * 1000 / iInterval;
    inTCPBCRate = inTCPBCRate * 1000 / iInterval;
    inUDPBCRate = inUDPBCRate * 1000 / iInterval;

    // clear
    if (pNetIO_TCP) pNetIO_TCP->ClearStatistic();
    if (pNetIO_UDP) pNetIO_UDP->ClearStatistic();

    // save back
    iTCPIRate = iTCPIRateSum;
    iTCPORate = iTCPORateSum;
    iTCPBCRate = inTCPBCRate;
    iUDPIRate = iUDPIRateSum;
    iUDPORate = iUDPORateSum;
    iUDPBCRate = inUDPBCRate;
}