From f6acb8540da3bf1cfc122279f1fd4dd6a960420d Mon Sep 17 00:00:00 2001 From: Alice Ogeda Date: Mon, 13 Feb 2023 22:32:43 -0300 Subject: [PATCH 1/3] align packets in containers to 8 byte boundary; --- src/common/Network/GamePacket.h | 23 +++++++++++++++----- src/common/Network/PacketContainer.cpp | 30 +++++++++++++++++++------- 2 files changed, 40 insertions(+), 13 deletions(-) diff --git a/src/common/Network/GamePacket.h b/src/common/Network/GamePacket.h index 7de8afff..672722b8 100644 --- a/src/common/Network/GamePacket.h +++ b/src/common/Network/GamePacket.h @@ -90,11 +90,6 @@ namespace Sapphire::Network::Packets setTargetActor( targetActorId ); } - std::size_t getSize() const - { - return m_segHdr.size; - } - virtual std::vector< uint8_t > getData() const { return {}; @@ -124,6 +119,24 @@ namespace Sapphire::Network::Packets return m_segmentType; } + /** + * @brief gets current packet size + * @return packet size in bytes + */ + std::size_t getSize() const + { + return m_segHdr.size; + } + + /** + * @brief sets current packet size + * @param packet size in bytes + */ + void setSize( std::size_t packetSize ) + { + m_segHdr.size = packetSize; + } + /** * @brief Sets the source actor id for this packet. * @param actorId The source actor id. diff --git a/src/common/Network/PacketContainer.cpp b/src/common/Network/PacketContainer.cpp index 0b6fa1b1..cb308b31 100644 --- a/src/common/Network/PacketContainer.cpp +++ b/src/common/Network/PacketContainer.cpp @@ -43,14 +43,9 @@ void Network::Packets::PacketContainer::fillSendBuffer( std::vector< uint8_t >& m_ipcHdr.timestamp = tick; m_ipcHdr.unknown_20 = 1; - memcpy( &tempBuffer[ 0 ], &m_ipcHdr, sizeof( FFXIVARR_PACKET_HEADER ) ); - auto it = m_entryList.begin(); std::size_t offset = 0; - if( m_entryList.size() > 1 ) - offset = 0; - for( ; it != m_entryList.end(); ++it ) { auto pPacket = ( *it ); @@ -60,13 +55,32 @@ void Network::Packets::PacketContainer::fillSendBuffer( std::vector< uint8_t >& pPacket->setTargetActor( m_segmentTargetOverride ); } + auto validPacketDataSize = pPacket->getSize(); + + // check if packet is 8 byte aligned + auto alignCheck = validPacketDataSize % 8; + if( alignCheck != 0 ) + { + // pad packet to boundary + // resize is expensive + tempBuffer.resize( tempBuffer.size() + alignCheck, 0 ); + + pPacket->setSize( validPacketDataSize + alignCheck ); + } + + // copy packet data into buffer auto data = pPacket->getData(); - memcpy( &tempBuffer[ 0 ] + sizeof( FFXIVARR_PACKET_HEADER ) + offset, &data[ 0 ], pPacket->getSize() ); - offset += pPacket->getSize(); + memcpy( &tempBuffer[ 0 ] + sizeof( FFXIVARR_PACKET_HEADER ) + offset, &data[ 0 ], validPacketDataSize ); + + offset += validPacketDataSize + alignCheck; } - sendBuffer.assign( &tempBuffer[ 0 ], &tempBuffer[ 0 ] + m_ipcHdr.size ); + // buffer has possibly been resized for alignment + m_ipcHdr.size = tempBuffer.size(); + memcpy( &tempBuffer[ 0 ], &m_ipcHdr, sizeof( FFXIVARR_PACKET_HEADER ) ); + + sendBuffer.assign( &tempBuffer[ 0 ], &tempBuffer[ 0 ] + m_ipcHdr.size ); } std::string Network::Packets::PacketContainer::toString() From ae605d5b0da9ee1e90a15208d9ba4e9f86328636 Mon Sep 17 00:00:00 2001 From: Alice Ogeda Date: Tue, 14 Feb 2023 10:24:35 -0300 Subject: [PATCH 2/3] optimize resizing and allocating packet send buffer; --- src/common/Network/GamePacket.h | 17 +++++++++++++++++ src/common/Network/PacketContainer.cpp | 22 +++++++--------------- 2 files changed, 24 insertions(+), 15 deletions(-) diff --git a/src/common/Network/GamePacket.h b/src/common/Network/GamePacket.h index 672722b8..d74a5e93 100644 --- a/src/common/Network/GamePacket.h +++ b/src/common/Network/GamePacket.h @@ -99,6 +99,7 @@ namespace Sapphire::Network::Packets /** The segment header */ FFXIVARR_PACKET_SEGMENT_HEADER m_segHdr; uint16_t m_segmentType; + std::size_t m_alignedSize; public: virtual size_t getContentSize() @@ -128,6 +129,15 @@ namespace Sapphire::Network::Packets return m_segHdr.size; } + /** + * @brief gets aligned packet size + * @return packet size in bytes, to 8 byte % + */ + std::size_t getAlignedSize() const + { + return m_alignedSize; + } + /** * @brief sets current packet size * @param packet size in bytes @@ -182,6 +192,8 @@ namespace Sapphire::Network::Packets // The size must be the sum of the segment header and the content m_segHdr.size = static_cast< uint32_t >( sizeof( FFXIVARR_PACKET_SEGMENT_HEADER ) + getContentSize() ); m_segHdr.type = getSegmentType(); + + m_alignedSize = m_segHdr.size + ( m_segHdr.size % 8 ); } }; @@ -213,6 +225,8 @@ namespace Sapphire::Network::Packets memset( &m_ipcHdr, 0, ipcHdrSize ); m_ipcHdr.type = static_cast< WorldPackets::Server::ServerZoneIpcType >( m_data._ServerIpcType ); + + m_alignedSize = m_segHdr.size + ( m_segHdr.size % 8 ); } size_t getContentSize() override @@ -271,6 +285,7 @@ namespace Sapphire::Network::Packets m_ipcHdr.type = static_cast< WorldPackets::Server::ServerZoneIpcType >( m_data._ServerIpcType ); m_ipcHdr.timestamp = Common::Util::getTimeSeconds(); m_segHdr.size = sizeof( T ) + sizeof( FFXIVARR_IPC_HEADER ) + sizeof( FFXIVARR_PACKET_SEGMENT_HEADER ); + m_alignedSize = m_segHdr.size + ( m_segHdr.size % 8 ); }; protected: @@ -291,6 +306,7 @@ namespace Sapphire::Network::Packets { initialize(); m_segHdr.size = size; + m_alignedSize = m_segHdr.size + ( m_segHdr.size % 8 ); }; FFXIVRawPacket( char* data, uint16_t size ) : @@ -300,6 +316,7 @@ namespace Sapphire::Network::Packets memcpy( &m_data[ 0 ], data + segmentHdrSize, size - segmentHdrSize ); memcpy( &m_segHdr, data, segmentHdrSize ); + m_alignedSize = m_segHdr.size + ( m_segHdr.size % 8 ); } size_t getContentSize() override diff --git a/src/common/Network/PacketContainer.cpp b/src/common/Network/PacketContainer.cpp index cb308b31..fad6f951 100644 --- a/src/common/Network/PacketContainer.cpp +++ b/src/common/Network/PacketContainer.cpp @@ -26,13 +26,13 @@ void Network::Packets::PacketContainer::addPacket( Network::Packets::FFXIVPacket { m_entryList.push_back( entry ); - m_ipcHdr.size += static_cast< uint32_t >( entry->getSize() ); + m_ipcHdr.size += static_cast< uint32_t >( entry->getAlignedSize() ); m_ipcHdr.count++; } void Network::Packets::PacketContainer::fillSendBuffer( std::vector< uint8_t >& sendBuffer ) { - std::vector< uint8_t > tempBuffer( m_ipcHdr.size ); + std::vector< uint8_t > tempBuffer( m_ipcHdr.size, 0 ); memset( &tempBuffer[ 0 ], 0, m_ipcHdr.size ); using namespace std::chrono; @@ -55,24 +55,16 @@ void Network::Packets::PacketContainer::fillSendBuffer( std::vector< uint8_t >& pPacket->setTargetActor( m_segmentTargetOverride ); } - auto validPacketDataSize = pPacket->getSize(); + auto packetAlignedSize = pPacket->getAlignedSize(); + auto packetOriginalSize = pPacket->getSize(); - // check if packet is 8 byte aligned - auto alignCheck = validPacketDataSize % 8; - if( alignCheck != 0 ) - { - // pad packet to boundary - // resize is expensive - tempBuffer.resize( tempBuffer.size() + alignCheck, 0 ); - - pPacket->setSize( validPacketDataSize + alignCheck ); - } + pPacket->setSize( packetAlignedSize ); // copy packet data into buffer auto data = pPacket->getData(); - memcpy( &tempBuffer[ 0 ] + sizeof( FFXIVARR_PACKET_HEADER ) + offset, &data[ 0 ], validPacketDataSize ); + memcpy( &tempBuffer[ 0 ] + sizeof( FFXIVARR_PACKET_HEADER ) + offset, &data[ 0 ], packetOriginalSize ); - offset += validPacketDataSize + alignCheck; + offset += packetAlignedSize; } // buffer has possibly been resized for alignment From f761572b25b89091485f4f40de6ec2bfdc1293d8 Mon Sep 17 00:00:00 2001 From: Alice Ogeda Date: Tue, 14 Feb 2023 10:28:13 -0300 Subject: [PATCH 3/3] small fixes/removing useless code; --- src/common/Network/PacketContainer.cpp | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/src/common/Network/PacketContainer.cpp b/src/common/Network/PacketContainer.cpp index fad6f951..530faf41 100644 --- a/src/common/Network/PacketContainer.cpp +++ b/src/common/Network/PacketContainer.cpp @@ -55,9 +55,11 @@ void Network::Packets::PacketContainer::fillSendBuffer( std::vector< uint8_t >& pPacket->setTargetActor( m_segmentTargetOverride ); } + // get aligned and original packet data size for offset and copy auto packetAlignedSize = pPacket->getAlignedSize(); auto packetOriginalSize = pPacket->getSize(); + // set packet size in seg header to aligned size pPacket->setSize( packetAlignedSize ); // copy packet data into buffer @@ -67,9 +69,6 @@ void Network::Packets::PacketContainer::fillSendBuffer( std::vector< uint8_t >& offset += packetAlignedSize; } - // buffer has possibly been resized for alignment - m_ipcHdr.size = tempBuffer.size(); - memcpy( &tempBuffer[ 0 ], &m_ipcHdr, sizeof( FFXIVARR_PACKET_HEADER ) ); sendBuffer.assign( &tempBuffer[ 0 ], &tempBuffer[ 0 ] + m_ipcHdr.size );