//////////////////////////////////////////////////////////////////////
// This file is part of Remere's Map Editor
//////////////////////////////////////////////////////////////////////
// Remere's Map Editor is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Remere's Map Editor is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see .
//////////////////////////////////////////////////////////////////////
#include "main.h"
#include "net_connection.h"
NetworkMessage::NetworkMessage()
{
clear();
}
void NetworkMessage::clear()
{
buffer.resize(4);
position = 4;
size = 0;
}
void NetworkMessage::expand(const size_t length)
{
if(position + length >= buffer.size()) {
buffer.resize(position + length + 1);
}
size += length;
}
template<> std::string NetworkMessage::read()
{
const uint16_t length = read();
char* strBuffer = reinterpret_cast(&buffer[position]);
position += length;
return std::string(strBuffer, length);
}
template<> Position NetworkMessage::read()
{
Position position;
position.x = read();
position.y = read();
position.z = read();
return position;
}
template<> void NetworkMessage::write(const std::string& value)
{
const size_t length = value.length();
write(length);
expand(length);
memcpy(&buffer[position], &value[0], length);
position += length;
}
template<> void NetworkMessage::write(const Position& value)
{
write(value.x);
write(value.y);
write(value.z);
}
// NetworkConnection
NetworkConnection::NetworkConnection() :
service(nullptr), thread(), stopped(false)
{
//
}
NetworkConnection::~NetworkConnection()
{
stop();
}
NetworkConnection& NetworkConnection::getInstance()
{
static NetworkConnection connection;
return connection;
}
bool NetworkConnection::start()
{
if(thread.joinable()) {
if(stopped) {
return false;
}
return true;
}
stopped = false;
if(!service) {
service = new asio::io_service;
}
thread = std::thread([this]() -> void {
asio::io_service& serviceRef = *service;
try {
while(!stopped) {
serviceRef.run_one();
serviceRef.reset();
}
} catch (std::exception& e) {
std::cout << e.what() << std::endl;
}
});
return true;
}
void NetworkConnection::stop()
{
if(!service) {
return;
}
service->stop();
stopped = true;
thread.join();
delete service;
service = nullptr;
}
asio::io_service& NetworkConnection::get_service()
{
return *service;
}