Left over junk, not needed.

This commit is contained in:
HikikoMarmy
2025-04-14 08:05:36 +01:00
committed by GitHub
parent 665a114d71
commit d005bfbf5d
13 changed files with 0 additions and 1341 deletions

View File

@@ -1 +0,0 @@
#pragma once

View File

@@ -1,53 +0,0 @@
#pragma once
/*
#include "../network/socket.h"
#include "../network/packet.h"
#include "../misc/ByteStream.h"
class GenericRequest
{
public:
uint16_t ProtocolID;
uint32_t EventID;
uint32_t State;
ByteStream stream;
public:
GenericRequest()
{
ProtocolID = 0;
EventID = 0;
State = 0;
}
~GenericRequest()
{
};
GenericRequest( sptr_packet request )
{
ProtocolID = request->read_u16();
EventID = request->read_u32();
State = request->read_u32();
stream = ByteStream( request->raw );
}
GenericRequest( ByteStream stream )
{
ProtocolID = stream.read_u16();
EventID = stream.read_u32();
State = stream.read_u32();
this->stream = stream;
}
GenericRequest( const GenericRequest & ) = delete;
GenericRequest &operator=( const GenericRequest & ) = delete;
virtual void unpack() = 0;
virtual void process( sptr_socket s, sptr_packet r ) = 0;
};
typedef std::shared_ptr< GenericRequest > sptr_request;
*/

View File

@@ -1,32 +0,0 @@
#pragma once
#include "../misc/ByteStream.h"
#include "../network/packet.h"
class GenericResponse
{
public:
uint16_t ProtocolID;
uint32_t EventID;
uint32_t State;
ByteStream stream;
public:
GenericResponse()
{
ProtocolID = 0;
EventID = 0;
State = 0;
}
~GenericResponse()
{
}
virtual void pack()
{
};
};
typedef std::shared_ptr< GenericResponse > sptr_response;

View File

@@ -1,263 +0,0 @@
/*
#include "../global_define.h"
PacketBuffer::PacketBuffer( uint16_t command, uint32_t event_seq, uint32_t hint_size )
{
if( hint_size < PACKET_HEADER_SIZE ) hint_size = PACKET_HEADER_SIZE;
buffer.resize( Math::round_up( hint_size, 0x02 ) );
write_position = PACKET_HEADER_SIZE;
read_position = PACKET_HEADER_SIZE;
*( PacketHeader * )&buffer[ 0 ] = { PACKET_HEADER_SIZE, htons( command ), event_seq, 0 };
}
PacketBuffer::PacketBuffer( std::vector< uint8_t > &data, size_t length )
{
buffer.resize( length );
std::copy( data.begin(), data.begin() + length, buffer.begin() );
write_position = length;
read_position = PACKET_HEADER_SIZE;
}
template < typename T >
void PacketBuffer::write( const T i )
{
if( ( write_position + sizeof( T ) ) >= buffer.size() )
{
buffer.resize( Math::round_up( ( write_position + sizeof( T ) ) + 1, 1024 ) );
}
memcpy( &buffer.data()[ write_position ], &i, sizeof( i ) );
write_position += sizeof( i );
}
void PacketBuffer::skip( const uint32_t size )
{
write_position += size;
read_position += size;
}
void PacketBuffer::write_buffer( const uint8_t *in_buffer, size_t size )
{
resize( size );
memcpy( &buffer.data()[ write_position ], &in_buffer[ 0 ], size );
write_position += size;
}
void PacketBuffer::write_u8( const uint8_t i )
{
write<uint8_t>( i );
}
void PacketBuffer::write_u16( const uint16_t i )
{
write<uint16_t>( i );
}
void PacketBuffer::write_u32( const uint32_t i )
{
write<uint32_t>( i );
}
void PacketBuffer::write_float( const float f )
{
write<float_t>( f );
}
void PacketBuffer::write_utf8( std::string s )
{
auto length = static_cast< int16_t >( s.length() );
write_u32( length );
if( ( write_position + length ) >= buffer.size() )
{
buffer.resize( Math::round_up( ( write_position + length ) + 1, 1024 ) );
}
memcpy( &buffer.data()[ write_position ], &s.data()[ 0 ], s.length() );
write_position += length;
}
void PacketBuffer::write_sz_utf8( std::string s )
{
auto length = static_cast< int16_t >( s.length() );
if( ( write_position + length ) >= buffer.size() )
{
buffer.resize( Math::round_up( ( write_position + length ) + 1, 1024 ) );
}
memcpy( &buffer.data()[ write_position ], &s.data()[ 0 ], s.length() );
write_position += length;
// Null-Terminator
write_u8( 0 );
}
void PacketBuffer::write_utf16( std::wstring ws )
{
auto length = ws.length();
write_u32( length );
length = length * sizeof( std::wstring::value_type );
if( ( write_position + length ) >= buffer.size() )
{
buffer.resize( Math::round_up( ( write_position + length ) + 1, 1024 ) );
}
memcpy( &buffer.data()[ write_position ], &ws.data()[ 0 ], length );
write_position += length;
write_u16( 0 );
}
void PacketBuffer::write_sz_utf16( std::wstring ws )
{
auto length = ws.length() * sizeof( std::wstring::value_type );
if( ( write_position + length ) >= buffer.size() )
{
buffer.resize( Math::round_up( ( write_position + length ) + 1, 1024 ) );
}
memcpy( &buffer.data()[ write_position ], &ws.data()[ 0 ], length );
write_position += length;
// Null-Terminator
write_u16( 0 );
}
template<typename T>
T PacketBuffer::read()
{
T ret = *( T * )&buffer.data()[ read_position ];
read_position += sizeof( T );
return ret;
}
uint8_t PacketBuffer::read_u8()
{
return read< uint8_t >();
}
uint16_t PacketBuffer::read_u16()
{
return read< uint16_t >();
}
uint32_t PacketBuffer::read_u32()
{
return read< uint32_t >();
}
float_t PacketBuffer::read_float()
{
return read< float_t >();
}
std::string PacketBuffer::read_utf8( size_t forced_size )
{
uint32_t length = read_u32();
if( forced_size != ~0 )
{
length = forced_size;
}
auto l = buffer.begin() + read_position;
auto r = buffer.begin() + ( read_position += length );
return std::string( l, r );
}
std::string PacketBuffer::read_sz_utf8()
{
std::string str;
while( auto c = read_u8() )
{
str.push_back( c );
read_position++;
}
read_position++;
return str;
}
std::wstring PacketBuffer::read_utf16( size_t forced_size )
{
//std::wstring wstr; wstr.resize( length + 1 );
//memcpy( &wstr[ 0 ], &buffer.data()[ write_position ], length * sizeof( wchar_t ) );
//write_position += length * sizeof( wchar_t );
uint32_t length = read_u32() * 2;
if( forced_size != ~0 )
{
length = forced_size * 2;
}
auto l = buffer.begin() + read_position;
auto r = buffer.begin() + ( read_position += length );
return std::wstring( l, r );
}
std::wstring PacketBuffer::read_sz_utf16()
{
std::wstring wstr;
while( auto c = read_u16() )
{
wstr.push_back( c );
read_position += 2;
}
read_position += 2;
return wstr;
}
sptr_packet make_packet( uint16_t command, uint32_t event_id, uint32_t hint_size )
{
auto p = std::make_shared< PacketBuffer >( command, event_id, hint_size );
return p;
}
sptr_packet make_packet( sptr_packet request )
{
auto p = std::make_shared< PacketBuffer >( request->get_command(), request->get_event_id() );
return p;
}
void process_networking()
{
sptr_socket s;
sptr_packet p;
if( !socket_manager->get_message( s, p ) )
{
return;
}
switch( s->channel )
{
case RealmChannelType::GATEWAY:
{
Protocol::Gateway::process_request( s, p );
break;
}
case RealmChannelType::GAME:
{
Protocol::Game::process_request( s, p );
break;
}
}
}
*/

View File

@@ -1,88 +0,0 @@
#pragma once
/*
#include <memory>
#include "socket.h"
#pragma pack( push, 2 )
struct PacketHeader
{
uint32_t length; // The length of the buffer + header
uint16_t command; // The command protocol ID
uint32_t event_id; // The event ID that we must respond to (this is assigned by the client).
uint32_t state; // Connection State (Must be 0, else force reconnect to gateway server)
};
#pragma pack(pop)
constexpr int32_t PACKET_HEADER_SIZE = 14;
static_assert( sizeof( PacketHeader ) == PACKET_HEADER_SIZE, "PacketHeader size mismatch" );
class PacketBuffer
{
public:
PacketBuffer( uint16_t command, uint32_t event_seq, uint32_t hint_size = 0x4000 );
PacketBuffer( std::vector< uint8_t > &data, size_t length );
~PacketBuffer()
{
}
uint16_t get_command()
{
return ntohs( ( ( PacketHeader * )&buffer[ 0 ] )->command );
}
uint32_t get_event_id()
{
return ( ( PacketHeader * )&buffer[ 0 ] )->event_id;
}
// Resizes buffer buffer to nearest 1024 when needed
inline void resize( size_t write_size )
{
if( write_position + write_size > buffer.size() )
{
buffer.resize( Math::round_up( write_position + write_size + 1, 1024 ) );
}
}
// Write Data
template < typename T >
void write( const T i );
void write_buffer( const uint8_t *buffer, size_t size );
void write_u8( const uint8_t i );
void write_u16( const uint16_t i );
void write_u32( const uint32_t i );
void write_float( const float f );
void write_utf8( std::string s );
void write_sz_utf8( std::string s );
void write_utf16( std::wstring ws );
void write_sz_utf16( std::wstring ws );
// Read Data
template < typename T >
T read();
uint8_t read_u8();
uint16_t read_u16();
uint32_t read_u32();
float_t read_float();
std::string read_utf8( size_t forced_size = ~0 );
std::string read_sz_utf8();
std::wstring read_utf16( size_t forced_size = ~0 );
std::wstring read_sz_utf16();
void skip( uint32_t size );
std::vector< uint8_t > buffer;
uint32_t write_position;
uint32_t read_position;
};
*/
//typedef std::shared_ptr< PacketBuffer > sptr_packet;
/*
sptr_packet make_packet( uint16_t command, uint32_t event_id, uint32_t hint_size );
sptr_packet make_packet( sptr_packet request );
void process_networking();
*/

View File

@@ -1,49 +0,0 @@
/*
#include "../global_define.h"
#include "protocol_broker.h"
using namespace Protocol::Broker;
typedef void( *FunctionPointer )( sptr_socket, sptr_packet );
const std::map< uint16_t, FunctionPointer > BROKER_PROTOCOL =
{
};
void Protocol::Broker::process_request( sptr_socket socket, sptr_packet request )
{
if( request->get_command() == 0xFFFF )
{
process_notice( socket, request );
return;
}
auto protocol_iter = BROKER_PROTOCOL.find( request->get_command() );
if( protocol_iter == BROKER_PROTOCOL.end() )
{
Log::Error( "UNDEFINED PROTOCOL: %02X", request->get_command() );
logging.packet( request->buffer, false );
return;
}
( *protocol_iter->second )( socket, request );
}
void Protocol::Broker::process_notice( sptr_socket s, sptr_packet r )
{
SocketNotice notice_id = ( SocketNotice )r->read_u32();
sptr_client client;
switch( notice_id )
{
case SocketNotice::NEW_CONNECTION:
{
} break;
case SocketNotice::DISCONNECTED:
{
} break;
}
}
*/

View File

@@ -1,15 +0,0 @@
#pragma once
// ╔═╗╦ ╦╔═╗╔╦╗╔═╗╦╔═╗╔╗╔╔═╗
// ║ ╠═╣╠═╣║║║╠═╝║║ ║║║║╚═╗
// ╚═╝╩ ╩╩ ╩╩ ╩╩ ╩╚═╝╝╚╝╚═╝
// ╔╗ ╦═╗╔═╗╦╔═╔═╗╦═╗ ╔═╗╦═╗╔═╗╔╦╗╔═╗╔═╗╔═╗╦
// ╠╩╗╠╦╝║ ║╠╩╗║╣ ╠╦╝ ╠═╝╠╦╝║ ║ ║ ║ ║║ ║ ║║
// ╚═╝╩╚═╚═╝╩ ╩╚═╝╩╚═ ╩ ╩╚═╚═╝ ╩ ╚═╝╚═╝╚═╝╩═╝
/*
namespace Protocol::Broker
{
void process_request( sptr_socket socket, sptr_packet r ); // Process incoming packets
void process_notice( sptr_socket socket, sptr_packet r ); // Process socket notices
}*/

View File

@@ -1,213 +0,0 @@
/*
#include "../global_define.h"
using namespace Protocol::Game;
typedef void( *FunctionPointer )( sptr_client, sptr_packet );
const std::map< uint16_t, FunctionPointer > GAME_PROTOCOL =
{
{ 0x0500, &ReqCancelGame },
{ 0x0800, &ReqCreatePrivateGame },
{ 0x0A00, &ReqCreatePublicGame },
{ 0x0D00, &ReqGetRoom },
{ 0x1600, &ReqLogin },
{ 0x2400, &ReqTouchSession },
{ 0x2500, &ReqDoClientDiscovery },
{ 0x2700, &ReqGetEncryptionKey },
{ 0x4200, &ReqGetRules },
{ 0x4400, &ReqUpdateGameData }
};
void Protocol::Game::process_request( sptr_socket socket, sptr_packet request )
{
if( request->get_command() == 0xFFFF )
{
process_notice( socket, request );
}
else
{
sptr_client client;
if( false == client_manager->get_client( socket, client ) )
{
socket->flag.disconnected = 1;
socket.reset();
return;
}
auto protocol_iter = GAME_PROTOCOL.find( request->get_command() );
if( protocol_iter == GAME_PROTOCOL.end() )
{
Log::Error( "UNDEFINED PROTOCOL: %02X", request->get_command() );
logging.packet( request->buffer, false );
return;
}
( *protocol_iter->second )( client, request );
}
}
void Protocol::Game::process_notice( sptr_socket socket, sptr_packet request )
{
SocketNotice notice_id = ( SocketNotice )request->read_u32();
sptr_client client;
switch( notice_id )
{
// A new client connected
case SocketNotice::NEW_CONNECTION:
{
if( false == client_manager->spawn_new( socket, client ) )
{
socket->flag.disconnected = 1;
socket.reset();
return;
}
} break;
// A client disconnected or a socket error occured
case SocketNotice::DISCONNECTED:
{
if( false == client_manager->get_client( socket, client ) )
{
return;
}
client_manager->remove_client( client->socket );
} break;
}
}
void Protocol::Game::ReqCancelGame( sptr_client client, sptr_packet request )
{
// TODO: here we would notify everyone else in the room, probably on the UDP socket bound to this room?
auto res = make_packet( request );
{
}
client->socket->send( res );
}
void Protocol::Game::ReqCreatePrivateGame( sptr_client client, sptr_packet request )
{
uint32_t total_size = request->read_u32() * 2;
uint32_t exp_size = request->read_u32();
request->skip( total_size - 4 );
std::wstring room_name = request->read_sz_utf16();
// TODO: Create Discovery Host and Port for the Broker Server
auto res = make_packet( request );
{
res->write_sz_utf8( ServerConfig::Get().service_ip ); // Discovery Host
res->write_u32( ServerConfig::Get().broker_port ); // Discovery Port
}
client->socket->send( res );
}
void Protocol::Game::ReqCreatePublicGame( sptr_client client, sptr_packet request )
{
}
void Protocol::Game::ReqGetRoom( sptr_client client, sptr_packet request )
{
uint32_t total_size = request->read_u32();
uint32_t exp_size = request->read_u32();
//std::array< uint8_t, 16 > game_id = request->read< std::array< uint8_t, 16 > >();
request->skip( 16 );
std::wstring room_name = request->read_utf16();
auto res = make_packet( request );
{
res->write_utf16( L"Room Name" );
res->write_utf16( L"Room Banner" );
res->write_u32( 4 ); // Num Members
res->write_utf8( "Name 1" );
res->write_utf8( "Name 2" );
res->write_utf8( "Name 3" );
res->write_utf8( "Name 4" );
res->write_u32( 4 ); // Num Moderators
res->write_utf8( "Moderator 1" );
res->write_utf8( "Moderator 2" );
res->write_utf8( "Moderator 3" );
res->write_utf8( "Moderator 4" );
}
client->socket->send( res );
}
void Protocol::Game::ReqLogin( sptr_client, sptr_packet request )
{
}
void Protocol::Game::ReqTouchSession( sptr_client client, sptr_packet request )
{
std::string session_key = request->read_utf8();
auto res = make_packet( request );
{
}
client->socket->send( res );
}
void Protocol::Game::ReqDoClientDiscovery( sptr_client client, sptr_packet request )
{
auto res = make_packet( request );
{
res->write_sz_utf8( ServerConfig::Get().service_ip );
res->write_u32( ServerConfig::Get().broker_port );
}
client->socket->send( res );
}
void Protocol::Game::ReqGetEncryptionKey( sptr_client client, sptr_packet request )
{
std::string public_key = request->read_utf8();
uint32_t unknown = request->read_u32();
Encryptor &encryptor = client->encryptor;
auto privateKey = encryptor.generatePrivateSymKey();
auto res = make_packet( request );
{
res->write_u32( 20 ); // Buffer Length (16 + 4)
res->write_u32( 0 );// encryptor.m_encryptedPrivateKey.length() );
res->write_utf8( "" );// encryptor.m_encryptedPrivateKey);
}
client->socket->send( res );
}
void Protocol::Game::ReqGetRules( sptr_client client, sptr_packet request )
{
std::wstring message = L"This is a test message sent from the server!\n\nHurray!";
auto res = make_packet( request );
{
res->write_utf16( message );
}
client->socket->send( res );
}
void Protocol::Game::ReqUpdateGameData( sptr_client client, sptr_packet request )
{
uint32_t total_size = request->read_u32() * 2;
uint32_t exp_size = request->read_u32();
request->skip( total_size - 4 );
std::string game_data = request->read_utf8(); // Seems to be one long string "1 / 4: <description> etc etc". Probably fixed length data structure.
auto res = make_packet( request );
{
}
client->socket->send( res );
}
*/

View File

@@ -1,26 +0,0 @@
#pragma once
// ╔═╗╦ ╦╔═╗╔╦╗╔═╗╦╔═╗╔╗╔╔═╗
// ║ ╠═╣╠═╣║║║╠═╝║║ ║║║║╚═╗
// ╚═╝╩ ╩╩ ╩╩ ╩╩ ╩╚═╝╝╚╝╚═╝
// ╔═╗╔═╗╔╦╗╔═╗ ╔═╗╦═╗╔═╗╔╦╗╔═╗╔═╗╔═╗╦
// ║ ╦╠═╣║║║║╣ ╠═╝╠╦╝║ ║ ║ ║ ║║ ║ ║║
// ╚═╝╩ ╩╩ ╩╚═╝ ╩ ╩╚═╚═╝ ╩ ╚═╝╚═╝╚═╝╩═╝
/*
namespace Protocol::Game
{
void process_request( sptr_socket s, sptr_packet r ); // Process incoming packets
void process_notice( sptr_socket s, sptr_packet r ); // Process socket notices
void ReqCancelGame( sptr_client client, sptr_packet request ); // 0500
void ReqCreatePrivateGame( sptr_client client, sptr_packet request ); // 0800
void ReqCreatePublicGame( sptr_client client, sptr_packet request ); // 0A00
void ReqGetRoom( sptr_client client, sptr_packet request ); // 0D00
void ReqLogin( sptr_client client, sptr_packet request ); // 1600
void ReqTouchSession( sptr_client client, sptr_packet request ); // 2400
void ReqDoClientDiscovery( sptr_client client, sptr_packet request ); // 2500
void ReqGetEncryptionKey( sptr_client client, sptr_packet request ); // 2700
void ReqGetRules( sptr_client client, sptr_packet request ); // 4200
void ReqUpdateGameData( sptr_client client, sptr_packet request ); // 4400
}*/

View File

@@ -1,60 +0,0 @@
/*
#include "../global_define.h"
#include "protocol_gateway.h"
#include "events/Gateway/ReqGetServerAddress.h"
using namespace Protocol::Gateway;
typedef void( *FunctionPointer )( sptr_socket, sptr_packet );
const std::map< uint16_t, FunctionPointer > GATEWAY_PROTOCOL =
{
{ 0x4300, &ReqGetServerAddress },
};
void Protocol::Gateway::process_request( sptr_socket socket, sptr_packet request )
{
if( request->get_command() == 0xFFFF )
{
process_notice( socket, request );
return;
}
auto protocol_iter = GATEWAY_PROTOCOL.find( request->get_command() );
if( protocol_iter == GATEWAY_PROTOCOL.end() )
{
Log::Error( "UNDEFINED PROTOCOL: %02X", request->get_command() );
logging.packet( request->buffer, false );
return;
}
( *protocol_iter->second )( socket, request );
}
void Protocol::Gateway::process_notice( sptr_socket s, sptr_packet r )
{
SocketNotice notice_id = ( SocketNotice )r->read_u32();
sptr_client client;
switch( notice_id )
{
case SocketNotice::NEW_CONNECTION:
{
} break;
case SocketNotice::DISCONNECTED:
{
} break;
}
}
void Protocol::Gateway::ReqGetServerAddress( sptr_socket socket, sptr_packet request )
{
auto res = std::make_shared< PacketBuffer >( 0x4300, request->get_event_id(), 64 );
{
res->write_sz_utf8( ServerConfig::Get().service_ip );
res->write_u32( ServerConfig::Get().session_port );
}
socket->send( res );
}
*/

View File

@@ -1,17 +0,0 @@
#pragma once
// ╔═╗╦ ╦╔═╗╔╦╗╔═╗╦╔═╗╔╗╔╔═╗
// ║ ╠═╣╠═╣║║║╠═╝║║ ║║║║╚═╗
// ╚═╝╩ ╩╩ ╩╩ ╩╩ ╩╚═╝╝╚╝╚═╝
// ╔═╗╔═╗╔╦╗╔═╗╦ ╦╔═╗╦ ╦ ╔═╗╦═╗╔═╗╔╦╗╔═╗╔═╗╔═╗╦
// ║ ╦╠═╣ ║ ║╣ ║║║╠═╣╚╦╝ ╠═╝╠╦╝║ ║ ║ ║ ║║ ║ ║║
// ╚═╝╩ ╩ ╩ ╚═╝╚╩╝╩ ╩ ╩ ╩ ╩╚═╚═╝ ╩ ╚═╝╚═╝╚═╝╩═╝
/*
namespace Protocol::Gateway
{
void process_request( sptr_socket socket, sptr_packet r ); // Process incoming packets
void process_notice( sptr_socket socket, sptr_packet r ); // Process socket notices
void ReqGetServerAddress( sptr_socket socket, sptr_packet r ); // 4300
}*/

View File

@@ -1,468 +0,0 @@
/*
#include "../global_define.h"
#include "socket_manager.h"
CSocketManager::CSocketManager()
{
run_worker = true;
wait_end = true;
max_fd = 0;
dirty_read_buffer.resize( 0xFFFF );
socket_list.clear();
}
CSocketManager::~CSocketManager()
{
run_worker = false;
max_fd = 0;
while( wait_end )
{
std::this_thread::sleep_for( std::chrono::milliseconds( 100 ) );
}
socket_list.clear();
}
bool CSocketManager::initialize()
{
WORD wVersionRequest = MAKEWORD( 2, 2 );
WSADATA wsaData;
if( WSAStartup( wVersionRequest, &wsaData ) != 0 )
return false;
net_time.Start();
auto &config = ServerConfig::Get();
open_tcp_listener( config.service_ip, config.gateway_port, RealmChannelType::GATEWAY );
open_tcp_listener( config.service_ip, config.session_port, RealmChannelType::GAME );
open_udp_listener( config.service_ip, config.broker_port, RealmChannelType::DISCOVERY );
// Start network thread
std::thread socket_thread( &CSocketManager::net_worker, this );
socket_thread.detach();
return true;
}
bool CSocketManager::open_tcp_listener( std::string ip, uint16_t port, RealmChannelType channel )
{
struct sockaddr_in addr;
auto socket = std::make_shared< CRealmSocket >();
if( INVALID_SOCKET == ( socket->fd = ::socket( PF_INET, SOCK_STREAM, IPPROTO_TCP ) ) )
{
return false;
}
memset( &addr, 0, sizeof( addr ) );
addr.sin_family = AF_INET;
addr.sin_port = htons( port );
addr.sin_addr.s_addr = ( "0.0.0.0" != ip )
? inet_addr( ip.c_str() )
: htonl( INADDR_ANY );
if( bind( socket->fd, ( LPSOCKADDR )&addr, sizeof( addr ) ) != 0 )
{
Log::Error( "Could not open socket on %s:%d", ip.c_str(), port );
return false;
}
listen( socket->fd, 0xFFFF );
socket->port = port;
socket->channel = channel;
socket->type = RealmSocketType::TCP;
socket->flag.is_listener = true;
// Set the socket to non-blocking
u_long non_blocking = 1;
ioctlsocket( socket->fd, FIONBIO, &non_blocking );
socket_list.push_back( socket );
Log::Info( "Open TCP Listener on %s:%d", ip.c_str(), port );
return true;
}
bool CSocketManager::open_udp_listener( std::string ip, uint16_t port, RealmChannelType channel )
{
struct sockaddr_in addr;
auto socket = std::make_shared< CRealmSocket >();
if( INVALID_SOCKET == ( socket->fd = ::socket( PF_INET, SOCK_DGRAM, IPPROTO_UDP ) ) )
{
return false;
}
memset( &addr, 0, sizeof( addr ) );
addr.sin_family = AF_INET;
addr.sin_port = htons( port );
addr.sin_addr.s_addr = ( "0.0.0.0" != ip )
? inet_addr( ip.c_str() )
: htonl( INADDR_ANY );
if( bind( socket->fd, ( LPSOCKADDR )&addr, sizeof( addr ) ) != 0 )
{
Log::Error( "Could not open socket on %s:%d", ip.c_str(), port );
return false;
}
socket->port = port;
socket->channel = channel;
socket->type = RealmSocketType::UDP;
socket->flag.is_listener = true;
// Set the socket to non-blocking
u_long non_blocking = 1;
ioctlsocket( socket->fd, FIONBIO, &non_blocking );
socket_list.push_back( socket );
Log::Info( "Open UDP Listener on %s:%d", ip.c_str(), port );
return false;
}
bool CSocketManager::get_message( sptr_socket &s, sptr_packet &p )
{
std::pair< sptr_socket, sptr_packet > pair;
if( !pending_packets.front_and_pop( pair ) )
{
return false;
}
s = pair.first;
p = std::move( pair.second );
return true;
}
void CSocketManager::accept_new_tcp( sptr_socket from_socket )
{
struct sockaddr_in listen_in;
int listenLen = sizeof( listen_in );
SOCKET receive_socket = INVALID_SOCKET;
std::string connection_ip;
bool is_friendly_connection = false;
if( ( receive_socket = accept( from_socket->fd, ( struct sockaddr* ) &listen_in, &listenLen ) ) == -1 )
{
return;
}
connection_ip = inet_ntoa( listen_in.sin_addr );
auto new_socket = std::make_shared< CRealmSocket >();
new_socket->fd = receive_socket;
new_socket->peer_ip_address = inet_ntoa( listen_in.sin_addr );
new_socket->port = ntohs( listen_in.sin_port );
new_socket->channel = from_socket->channel;
if( from_socket->channel == RealmChannelType::GATEWAY )
{
Log::Info( "[GATEWAY] : New connection from %s", ( *new_socket ).peer_ip_address.c_str() );
}
else if( from_socket->channel == RealmChannelType::GAME )
{
Log::Info( "[GAME] : New connection from %s", ( *new_socket ).peer_ip_address.c_str() );
}
new_socket->last_recv_time = net_time.GetAppMilliTime();
new_socket->last_send_time = net_time.GetAppMilliTime();
accept_list.push_back( new_socket );
}
void CSocketManager::accept_new_udp( sptr_socket s, sockaddr_in addr )
{
auto new_socket = std::make_shared< CRealmSocket >();
new_socket->fd = s->fd;
new_socket->remote_address = addr;
new_socket->channel = s->channel;
new_socket->type = RealmSocketType::UDP;
accept_list.push_back( new_socket );
}
void CSocketManager::notify_socket( sptr_socket s, SocketNotice command )
{
auto p = std::make_unique< PacketBuffer >( 0xFFFF, 0, 18 );
p->write_u32( (int)command );
pending_packets.push( std::make_pair( s, std::move( p ) ) );
}
void CSocketManager::check_socket_problem( sptr_socket sock )
{
if( sock->flag.disconnected ) return;
if( sock->flag.is_listener ) return;
auto now_time = net_time.GetAppMilliTime();
if( ( now_time - sock->last_recv_time ) > 60000.0 )
{
sock->flag.disconnected = 1;
notify_socket( sock, SocketNotice::DISCONNECTED );
}
}
void CSocketManager::net_worker()
{
struct timeval timeout = { 0, 0 };
FD_SET readfd, writefd;
while( run_worker )
{
net_time.Tick();
max_fd = 0;
FD_ZERO( &readfd );
FD_ZERO( &writefd );
// Check for any new connections
for( auto &s : accept_list )
{
socket_list.push_back( s );
notify_socket( s, SocketNotice::NEW_CONNECTION );
}
accept_list.clear();
auto socket = socket_list.begin();
while( socket != socket_list.end() )
{
if( ( *socket )->fd == INVALID_SOCKET || ( *socket )->flag.disconnected )
{
socket = socket_list.erase( socket );
continue;
}
FD_SET( ( *socket )->fd, &readfd );
FD_SET( ( *socket )->fd, &writefd );
max_fd = std::max< SOCKET >( max_fd, ( *socket )->fd + 1 );
socket++;
}
if( select( max_fd, &readfd, &writefd, NULL, &timeout ) <= 0 )
{
std::this_thread::sleep_for( std::chrono::milliseconds( 1 ) );
continue;
}
for( auto &s : socket_list )
{
if( s->type == RealmSocketType::TCP )
{
if( FD_ISSET( s->fd, &readfd ) )
{
TCP_TryReadData( s );
}
else if( FD_ISSET( s->fd, &writefd ) )
{
TCP_TryWriteData( s );
}
}
else if( s->type == RealmSocketType::UDP )
{
if( FD_ISSET( s->fd, &readfd ) )
{
UDP_TryReadData( s );
}
else if( FD_ISSET( s->fd, &writefd ) )
{
UDP_TryWriteData( s );
}
}
}
}
}
void CSocketManager::TCP_TryReadData( sptr_socket socket )
{
// This socket is a listener, so we want to accept a connection
if( socket->flag.is_listener )
{
accept_new_tcp( socket );
return;
}
if( socket->read_buffer.size() >= MAX_READ_SIZE )
{
return;
}
int32_t read_size = 0;
if( ( read_size = recv( socket->fd, reinterpret_cast< char* >( &dirty_read_buffer[ 0 ] ), MAX_READ_SIZE, 0 ) ) <= 0 )
{
switch( WSAGetLastError() )
{
case WSAECONNRESET:
{
Log::Info( "Connection %s reset by peer.", socket->peer_ip_address.c_str() );
} break;
}
socket->flag.disconnected = 1;
notify_socket( socket, SocketNotice::DISCONNECTED );
return;
}
// TODO: Parse the data from 'dirty_read_buffer' directly if 'socket->read_buffer' is empty.
// Otherwise merge them and parse the data.
std::copy( std::begin( dirty_read_buffer ), std::begin( dirty_read_buffer ) + read_size, std::back_inserter( socket->read_buffer ) );
// Parse packets out from the incoming data.
while( !socket->read_buffer.empty() )
{
// Read the packet length from the first 4 bytes and flip it
uint32_t length = _byteswap_ulong( *( uint32_t * )&socket->read_buffer[ 0x00 ] );
if( length > socket->read_buffer.size() )
{
socket->flag.want_more_read_data = 1;
break;
}
if( length == 0x04 )
{
// This is a keep alive packet, I think.
// The client drops them as well.
socket->read_buffer.erase( socket->read_buffer.begin(), socket->read_buffer.begin() + length );
continue;
}
auto p = std::make_shared< PacketBuffer >( socket->read_buffer, length );
logging.packet( p->buffer, false );
socket->read_buffer.erase(
socket->read_buffer.begin(),
socket->read_buffer.begin() + length );
pending_packets.push( std::make_pair( socket, std::move( p ) ) );
}
socket->last_recv_time = net_time.GetAppMilliTime();
socket->latency = abs( socket->last_recv_time - socket->last_send_time );
}
void CSocketManager::TCP_TryWriteData( sptr_socket socket )
{
if( socket->write_queue.empty() )
{
return;
}
if( false == socket->write_mutex.try_lock() )
{
return;
}
size_t write_offset = 0;
while( !socket->write_queue.empty() )
{
auto &packet = socket->write_queue.front();
auto total_length = packet->write_position - socket->last_write_position;
auto chunk_size = std::min< int32_t >( total_length, MAX_TCP_SEND_SIZE );
auto write_size = send( socket->fd, reinterpret_cast< char * >( &packet->buffer[ socket->last_write_position ] ), chunk_size, 0 );
// Socket Error
if( write_size == SOCKET_ERROR )
{
socket->flag.disconnected = 1;
break;
}
// Not all data sent
if( write_size < total_length )
{
socket->flag.want_more_write_data = 1;
socket->last_write_position += write_size;
break;
}
socket->write_queue.pop_front();
socket->flag.want_more_write_data = 0;
socket->last_write_position = 0;
}
socket->write_mutex.unlock();
socket->last_send_time = net_time.GetAppMilliTime();
socket->latency = abs( socket->last_recv_time - socket->last_send_time );
}
void CSocketManager::UDP_TryReadData( sptr_socket socket )
{
if( socket->read_buffer.size() >= MAX_READ_SIZE )
{
return;
}
int32_t read_size = 0;
SOCKADDR_IN addr;
int addrLen = sizeof( addr );
read_size = recvfrom( socket->fd, reinterpret_cast< char * >( &dirty_read_buffer[ 0 ] ), MAX_READ_SIZE, 0, ( SOCKADDR * )&addr, &addrLen );
if( read_size <= 0 )
{
return;
}
if( socket->flag.is_listener )
{
accept_new_udp( socket, addr );
}
logging.packet( dirty_read_buffer, read_size, false );
auto packet = std::make_shared< PacketBuffer >( dirty_read_buffer, read_size );
logging.packet( packet->buffer, false );
pending_packets.push( std::make_pair( socket, std::move( packet ) ) );
}
void CSocketManager::UDP_TryWriteData( sptr_socket s )
{
if( s->write_queue.empty() )
{
return;
}
if( false == s->write_mutex.try_lock() )
{
return;
}
auto &packet = s->write_queue.front();
auto total_length = packet->write_position;
auto chunk_size = std::min< int32_t >( total_length, MAX_UDP_SEND_SIZE );
auto write_size = sendto( s->fd, reinterpret_cast< char * >( &packet->buffer[ 0 ] ), chunk_size, 0, ( SOCKADDR * )&s->remote_address, sizeof( s->remote_address ) );
// Socket Error
if( write_size == SOCKET_ERROR )
{
s->flag.disconnected = 1;
}
s->write_queue.pop_front();
s->write_mutex.unlock();
}
*/

View File

@@ -1,56 +0,0 @@
#pragma once
/*
#include <vector>
#include <set>
#include <thread>
#include <string>
#include <memory>
#include "packet.h"
#include "socket.h"
#include "../misc/Timer.h"
#include "../misc/threadsafe_queue.hpp"
enum class SocketNotice
{
NEW_CONNECTION = 1,
DISCONNECTED = 2,
};
class CSocketManager
{
private:
const uint32_t MAX_TCP_SEND_SIZE = 65535;
const uint32_t MAX_UDP_SEND_SIZE = 1024;
const uint32_t MAX_READ_SIZE = 65535;
const uint32_t MAX_SOCKETS = 1024;
CTimer net_time;
std::vector< uint8_t > dirty_read_buffer;
std::vector< sptr_socket > accept_list;
std::vector< sptr_socket > socket_list;
threadsafe_queue< std::pair< sptr_socket, sptr_packet > > pending_packets;
bool run_worker, wait_end;
SOCKET max_fd;
public:
CSocketManager();
~CSocketManager();
bool initialize();
bool open_tcp_listener( std::string ip, uint16_t port, RealmChannelType channel );
bool open_udp_listener( std::string ip, uint16_t port, RealmChannelType channel );
bool get_message( sptr_socket &s, sptr_packet &p );
private:
void net_worker();
void accept_new_tcp( sptr_socket s );
void accept_new_udp( sptr_socket s, sockaddr_in addr );
void notify_socket( sptr_socket s, SocketNotice notice );
void check_socket_problem( sptr_socket s );
void TCP_TryReadData( sptr_socket s );
void TCP_TryWriteData( sptr_socket s );
void UDP_TryReadData( sptr_socket s );
void UDP_TryWriteData( sptr_socket s );
};*/