#include "inetworkserver.h" #include "tier1/utlmutex.h" #include "tier1/utlvector.h" class CLocalNetworkServer; static CLocalNetworkServer *s_pLocalServers[128]; class CLocalNetworkServer: public INetworkBase { public: CLocalNetworkServer( uint16_t uPort ); virtual ~CLocalNetworkServer() override; virtual void NetThink() override; virtual void SetCallback( NetCallbackFn fnCallback ) override; virtual uint32_t BHasUpdates() override; virtual NetPacket_t RecievePacket() override; virtual NetPacket_t PeekPacket() override; virtual void SendPacket( NetPacket_t stPacket ) override; virtual bool BIsActive() override; virtual uint64_t GetSteamID() override; virtual const char *GetIP() override; virtual uint16_t GetPort() override; CUtlLock m_lock; CUtlVector m_packets; CUtlVector m_clientPackets; CUtlVector m_freedPackets; NetCallbackFn m_fnCallback; const uint16_t m_uPort; }; CLocalNetworkServer::CLocalNetworkServer( uint16_t uPort ) : m_uPort(uPort) { s_pLocalServers[uPort] = this; } CLocalNetworkServer::~CLocalNetworkServer() { s_pLocalServers[m_uPort] = NULL; } void CLocalNetworkServer::SetCallback( NetCallbackFn fnCallback ) { m_fnCallback = fnCallback; } void CLocalNetworkServer::NetThink() { for ( auto p: m_freedPackets) { V_free(p); } m_freedPackets = {}; } uint32_t CLocalNetworkServer::BHasUpdates() { return m_clientPackets.GetSize(); } NetPacket_t CLocalNetworkServer::RecievePacket() { if (!BHasUpdates()) return {}; NetPacket_t p = m_clientPackets[0]; m_clientPackets.RemoveHead(1); m_freedPackets.AppendTail(p.pData); return p; } NetPacket_t CLocalNetworkServer::PeekPacket() { if (!BHasUpdates()) return {}; NetPacket_t p = m_clientPackets[0]; return p; } void CLocalNetworkServer::SendPacket( NetPacket_t stPacket ) { NetPacket_t stSavedPacked; stSavedPacked.uSize = stPacket.uSize; stSavedPacked.m_uOwner = 0; stSavedPacked.pData = V_malloc(stPacket.uSize); V_memcpy(stSavedPacked.pData, stPacket.pData, stPacket.uSize); m_packets.AppendTail(stSavedPacked); } bool CLocalNetworkServer::BIsActive() { return true; } uint64_t CLocalNetworkServer::GetSteamID() { return 0; } const char *CLocalNetworkServer::GetIP() { return NULL; } uint16_t CLocalNetworkServer::GetPort() { return m_uPort; } class CLocalNetworkClient: public INetworkBase { public: CLocalNetworkClient( uint16_t uPort ); virtual ~CLocalNetworkClient() override; virtual void NetThink() override; virtual void SetCallback( NetCallbackFn fnCallback ) override; virtual uint32_t BHasUpdates() override; virtual NetPacket_t RecievePacket() override; virtual NetPacket_t PeekPacket() override; virtual void SendPacket( NetPacket_t stPacket ) override; virtual bool BIsActive() override; virtual uint64_t GetSteamID() override; virtual const char *GetIP() override; virtual uint16_t GetPort() override; CLocalNetworkServer *m_pServer; }; bool CLocalNetworkClient::BIsActive() { return true; } CLocalNetworkClient::CLocalNetworkClient( uint16_t uPort ) { m_pServer = s_pLocalServers[uPort]; } CLocalNetworkClient::~CLocalNetworkClient() { } void CLocalNetworkClient::NetThink() { } uint32_t CLocalNetworkClient::BHasUpdates() { return m_pServer->m_packets.GetSize(); } NetPacket_t CLocalNetworkClient::RecievePacket() { if (!BHasUpdates()) return {}; NetPacket_t p = m_pServer->m_packets[0]; m_pServer->m_packets.RemoveHead(1); m_pServer->m_freedPackets.AppendTail(p.pData); return p; } NetPacket_t CLocalNetworkClient::PeekPacket() { if (!BHasUpdates()) return {}; NetPacket_t p = m_pServer->m_packets[0]; return p; } void CLocalNetworkClient::SendPacket( NetPacket_t stPacket ) { NetPacket_t stSavedPacked; stSavedPacked.uSize = stPacket.uSize; stSavedPacked.m_uOwner = 0; stSavedPacked.pData = V_malloc(stPacket.uSize); V_memcpy(stSavedPacked.pData, stPacket.pData, stPacket.uSize); m_pServer->m_clientPackets.AppendTail(stSavedPacked); } void CLocalNetworkClient::SetCallback( NetCallbackFn fnCallback ) { } uint64_t CLocalNetworkClient::GetSteamID() { return 0; } const char *CLocalNetworkClient::GetIP() { return NULL; } uint16_t CLocalNetworkClient::GetPort() { return m_pServer->m_uPort; } INetworkBase *LaunchLocalBridge( uint16_t uPort ) { INetworkBase *pBase = new CLocalNetworkServer(uPort); return pBase; } INetworkBase *ConnectByLocalBridge( uint16_t uPort ) { if (s_pLocalServers[uPort] == 0) { return NULL; } return new CLocalNetworkClient(uPort); }