Commit d70f5bbf authored by Hubert Denkmair's avatar Hubert Denkmair
Browse files

optimize read method

parent 16ef5861
Loading
Loading
Loading
Loading
+21 −19
Original line number Diff line number Diff line
@@ -5,6 +5,11 @@
#include <msgpack.hpp>
#include <iostream>

TcpProtocol::TcpProtocol()
{
	_buf.resize(BUFFER_SIZE);
}

void TcpProtocol::SetMessageReceivedCallback(TcpProtocol::MessageReceivedCallback callback)
{
	_messageReceivedCallback = callback;
@@ -12,40 +17,37 @@ void TcpProtocol::SetMessageReceivedCallback(TcpProtocol::MessageReceivedCallbac

bool TcpProtocol::Read(int socket)
{
	std::array<char, 8192> readbuf;
	ssize_t bytesRead = read(socket, readbuf.data(), readbuf.size());
	ssize_t bytesRead = read(socket, &_buf[_bufTail], _buf.size()-_bufTail);

	if (bytesRead<=0) { return false; }
	_buf.insert(_buf.end(), &readbuf[0], &readbuf[static_cast<size_t>(bytesRead)]);
	_bufTail += static_cast<size_t>(bytesRead);

	while (true)
	{
		if ((_awaitedSize==0) && (_buf.size() >= 4))
	while ((_bufTail - _bufHead)>=4)
	{
			_awaitedSize = ntohl(*(reinterpret_cast<uint32_t*>(&_buf[0])));
			_buf.erase(_buf.begin(), _buf.begin()+4);
		}
		else if ((_awaitedSize>0) && (_buf.size() >= _awaitedSize))
		size_t size = 4 + ntohl(*(reinterpret_cast<uint32_t*>(&_buf[_bufHead])));
		if (size <= (_bufTail - _bufHead))
		{
			std::vector<char> v(_buf.begin(), _buf.begin()+_awaitedSize);
			OnMessageReceived(v);
			_buf.erase(_buf.begin(), _buf.begin()+_awaitedSize);
			_awaitedSize = 0;
			OnMessageReceived(&_buf[_bufHead+4], size-4);
			_bufHead += size;
		}
		else
		{
			return true;
			break;
		}
	}

	std::copy(_buf.begin()+_bufHead, _buf.begin()+_bufTail, _buf.begin());
	_bufTail -= _bufHead;
	_bufHead = 0;
	return true;
}

void TcpProtocol::OnMessageReceived(std::vector<char> &data)
void TcpProtocol::OnMessageReceived(const char* data, size_t count)
{
	_messageReceivedCallback(data);

	msgpack::object_handle obj;
	uint64_t version, message_type;

	msgpack::unpack(obj, data.data(), data.size());
	msgpack::unpack(obj, data, count);
	if (obj.get().type != msgpack::type::ARRAY) { return; }

	auto arr = obj.get().via.array;
+7 −4
Original line number Diff line number Diff line
@@ -15,6 +15,9 @@ class TcpProtocol
{
	public:
		typedef std::function<void(std::vector<char>&)> MessageReceivedCallback;
		static constexpr const size_t BUFFER_SIZE = 1024*1024;

		TcpProtocol();
		void SetMessageReceivedCallback(MessageReceivedCallback callback);
		bool Read(int socket);

@@ -27,18 +30,18 @@ class TcpProtocol

		typedef SpatialMap<SnakeSegmentItem, SPATIAL_MAP_TILES_X, SPATIAL_MAP_TILES_Y> SnakeSegmentMap;


		size_t _awaitedSize = 0;
		std::vector<char> _buf;
		MessageReceivedCallback _messageReceivedCallback;
		size_t _bufHead=0;
		size_t _bufTail=0;

		MessageReceivedCallback _messageReceivedCallback;
		std::unique_ptr<FoodMap> _food;
		MsgPackProtocol::GameInfoMessage _gameInfo;

		std::vector<BotItem> _bots;
		std::unique_ptr<SnakeSegmentMap> _segments;

		void OnMessageReceived(std::vector<char>& data);
		void OnMessageReceived(const char *data, size_t count);

		void OnGameInfoReceived(const MsgPackProtocol::GameInfoMessage& msg);
		void OnWorldUpdateReceived(const MsgPackProtocol::WorldUpdateMessage& msg);