2
0
mirror of https://github.com/rehlds/rehlds.git synced 2024-12-27 23:25:45 +03:00

Merge pull request #581 from dreamstalker/hltv_frag_validation

Add fragments validation to hltv
This commit is contained in:
theAsmodai 2018-05-04 23:37:18 +03:00 committed by GitHub
commit 97868baf92
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
15 changed files with 238 additions and 116 deletions

View File

@ -159,7 +159,7 @@
<PrecompiledHeader>Use</PrecompiledHeader>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<PreprocessorDefinitions>HLTV;WIN32;_DEBUG;_CONSOLE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions>HLTV;HLTV_FIXES;WIN32;_DEBUG;_CONSOLE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<AdditionalIncludeDirectories>$(ProjectDir)\..\src;$(ProjectDir)\..\..\;$(ProjectDir)\..\..\..\;$(ProjectDir)\..\..\..\common;$(ProjectDir)\..\..\..\engine;$(ProjectDir)\..\..\..\public;$(ProjectDir)\..\..\..\public\rehlds;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<PrecompiledHeaderFile>precompiled.h</PrecompiledHeaderFile>
<RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
@ -190,7 +190,7 @@
<Optimization>Disabled</Optimization>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>true</IntrinsicFunctions>
<PreprocessorDefinitions>HLTV;WIN32;NDEBUG;_CONSOLE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions>HLTV;HLTV_FIXES;WIN32;NDEBUG;_CONSOLE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<AdditionalIncludeDirectories>$(ProjectDir)\..\src;$(ProjectDir)\..\..\;$(ProjectDir)\..\..\..\;$(ProjectDir)\..\..\..\common;$(ProjectDir)\..\..\..\engine;$(ProjectDir)\..\..\..\public;$(ProjectDir)\..\..\..\public\rehlds;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<PrecompiledHeaderFile>precompiled.h</PrecompiledHeaderFile>
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>

View File

@ -20,7 +20,7 @@ void setupToolchain(NativeBinarySpec b) {
cfg.projectInclude(project, '/..', '/../..', '/src', '/../../common', '/../../engine', '/../../public', '/../../public/rehlds', '/../../pm_shared');
cfg.projectInclude(dep_bzip2, '/include')
cfg.singleDefines 'USE_BREAKPAD_HANDLER', 'HLTV', 'CORE_MODULE'
cfg.singleDefines 'USE_BREAKPAD_HANDLER', 'HLTV', 'HLTV_FIXES', 'CORE_MODULE'
if (cfg instanceof MsvcToolchainConfig) {
cfg.compilerOptions.pchConfig = new MsvcToolchainConfig.PrecompiledHeadersConfig(

View File

@ -77,7 +77,7 @@
<PrecompiledHeader>Use</PrecompiledHeader>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<PreprocessorDefinitions>HLTV;WIN32;_DEBUG;_WINDOWS;_USRDLL;CORE_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions>HLTV;HLTV_FIXES;WIN32;_DEBUG;_WINDOWS;_USRDLL;CORE_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<SDLCheck>
</SDLCheck>
<AdditionalIncludeDirectories>$(ProjectDir)\..\src;$(ProjectDir)\..\..\;$(ProjectDir)\..\..\..\;$(ProjectDir)\..\..\..\common;$(ProjectDir)\..\..\..\engine;$(ProjectDir)\..\..\..\public;$(ProjectDir)\..\..\..\public\rehlds;$(ProjectDir)\..\..\..\pm_shared;$(ProjectDir)\..\..\..\..\dep\bzip2\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
@ -112,7 +112,7 @@
<Optimization>MaxSpeed</Optimization>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>true</IntrinsicFunctions>
<PreprocessorDefinitions>HLTV;WIN32;NDEBUG;_WINDOWS;_USRDLL;CORE_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions>HLTV;HLTV_FIXES;WIN32;NDEBUG;_WINDOWS;_USRDLL;CORE_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<SDLCheck>
</SDLCheck>
<AdditionalIncludeDirectories>$(ProjectDir)\..\src;$(ProjectDir)\..\..\;$(ProjectDir)\..\..\..\;$(ProjectDir)\..\..\..\common;$(ProjectDir)\..\..\..\engine;$(ProjectDir)\..\..\..\public;$(ProjectDir)\..\..\..\public\rehlds;$(ProjectDir)\..\..\..\pm_shared;$(ProjectDir)\..\..\..\..\dep\bzip2\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>

View File

@ -297,6 +297,14 @@ int NetSocket::GetLong(unsigned char *pData, int size)
{
m_NetSplitPacket.currentSequence = sequenceNumber;
m_NetSplitPacket.splitCount = packetCount;
#ifdef HLTV_FIXES
m_NetSplitPacket.totalSize = 0;
// clear part's sequence
for (int i = 0; i < MAX_SPLIT_FRAGMENTS; i++)
netSplitFlags[i] = -1;
#endif
}
unsigned int packetPayloadSize = size - sizeof(SPLITPACKET);
@ -310,16 +318,47 @@ int NetSocket::GetLong(unsigned char *pData, int size)
m_NetSplitPacket.totalSize = packetPayloadSize + SPLIT_SIZE * (packetCount - 1);
}
--m_NetSplitPacket.splitCount;
m_NetSplitPacket.splitCount--;
netSplitFlags[packetNumber] = sequenceNumber;
#ifdef HLTV_FIXES
if (SPLIT_SIZE * packetNumber + packetPayloadSize > MAX_UDP_PACKET)
{
m_System->DPrintf("WARNING! NetSocket::GetLong: Malformed packet size (%i, %i)\n", SPLIT_SIZE * packetNumber, packetPayloadSize);
m_NetSplitPacket.currentSequence = -1;
return -1;
}
Q_memcpy(&m_NetSplitPacket.buffer[SPLIT_SIZE * packetNumber], pHeader + 1, packetPayloadSize);
#endif
}
#ifndef HLTV_FIXES
Q_memcpy(&m_NetSplitPacket.buffer[SPLIT_SIZE * packetNumber], pHeader + 1, packetPayloadSize);
#endif
if (m_NetSplitPacket.splitCount > 0) {
return 0;
}
#ifdef HLTV_FIXES
for (unsigned int i = 0; i < packetCount; i++)
{
if (netSplitFlags[i] != m_NetSplitPacket.currentSequence)
{
m_System->DPrintf("WARNING! NetSocket::GetLong: Split packet without all %i parts, part %i had wrong sequence %i/%i\n",
packetCount,
i + 1,
netSplitFlags[i],
m_NetSplitPacket.currentSequence);
m_NetSplitPacket.currentSequence = -1;
return -1;
}
}
#endif
m_NetSplitPacket.currentSequence = -1;
if (m_NetSplitPacket.totalSize > MAX_UDP_PACKET)
{

View File

@ -252,11 +252,11 @@ protected:
int m_MaxInstanced_BaseLine;
#ifdef HOOK_HLTV
char m_Lightstyles[MAX_LIGHTSTYLES][65];
#else
#if defined(HLTV_FIXES) && !defined(HOOK_HLTV)
char m_Lightstyles[MAX_LIGHTSTYLES][64];
#endif // HOOK_HLTV
#else
char m_Lightstyles[MAX_LIGHTSTYLES][65];
#endif
movevars_t m_MoveVars;
BSPModel m_WorldModel;

View File

@ -16,7 +16,7 @@ void setupToolchain(NativeBinarySpec b) {
boolean useGcc = project.hasProperty("useGcc")
def cfg = rootProject.createToolchainConfig(b);
cfg.projectInclude(project, '/..', '/../..', '/src', '/../common', '/../../common', '/../../engine', '/../../public', '/../../public/rehlds', '/../../pm_shared');
cfg.singleDefines 'USE_BREAKPAD_HANDLER', 'HLTV', 'DEMOPLAYER_MODULE'
cfg.singleDefines 'USE_BREAKPAD_HANDLER', 'HLTV', 'HLTV_FIXES', 'DEMOPLAYER_MODULE'
if (cfg instanceof MsvcToolchainConfig) {
cfg.compilerOptions.pchConfig = new MsvcToolchainConfig.PrecompiledHeadersConfig(

View File

@ -125,7 +125,7 @@
<PrecompiledHeader>Use</PrecompiledHeader>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<PreprocessorDefinitions>HLTV;WIN32;_DEBUG;_WINDOWS;_USRDLL;DEMOPLAYER_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions>HLTV;HLTV_FIXES;WIN32;_DEBUG;_WINDOWS;_USRDLL;DEMOPLAYER_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PrecompiledHeaderFile>precompiled.h</PrecompiledHeaderFile>
<AdditionalIncludeDirectories>$(ProjectDir)\..\src;$(ProjectDir)\..\..\;$(ProjectDir)\..\..\..\;$(ProjectDir)\..\..\..\common;$(ProjectDir)\..\..\..\engine;$(ProjectDir)\..\..\..\public;$(ProjectDir)\..\..\..\public\rehlds;$(ProjectDir)\..\..\..\pm_shared;$(ProjectDir)\..\..\..\game_shared;$(ProjectDir)\..\..\..\..\dep\bzip2\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
@ -155,7 +155,7 @@
<Optimization>MaxSpeed</Optimization>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>true</IntrinsicFunctions>
<PreprocessorDefinitions>HLTV;WIN32;NDEBUG;_WINDOWS;_USRDLL;DEMOPLAYER_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitiHOOons)</PreprocessorDefinitions>
<PreprocessorDefinitions>HLTV;HLTV_FIXES;WIN32;NDEBUG;_WINDOWS;_USRDLL;DEMOPLAYER_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitiHOOons)</PreprocessorDefinitions>
<PrecompiledHeaderFile>precompiled.h</PrecompiledHeaderFile>
<AdditionalIncludeDirectories>$(ProjectDir)\..\src;$(ProjectDir)\..\..\;$(ProjectDir)\..\..\..\;$(ProjectDir)\..\..\..\common;$(ProjectDir)\..\..\..\engine;$(ProjectDir)\..\..\..\public;$(ProjectDir)\..\..\..\public\rehlds;$(ProjectDir)\..\..\..\pm_shared;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>

View File

@ -16,7 +16,7 @@ void setupToolchain(NativeBinarySpec b) {
boolean useGcc = project.hasProperty("useGcc")
def cfg = rootProject.createToolchainConfig(b);
cfg.projectInclude(project, '/..', '/../..', '/src', '/../../common', '/../../engine', '/../../public', '/../../public/rehlds', '/../../pm_shared');
cfg.singleDefines 'USE_BREAKPAD_HANDLER', 'HLTV', 'DIRECTOR_MODULE'
cfg.singleDefines 'USE_BREAKPAD_HANDLER', 'HLTV', 'HLTV_FIXES', 'DIRECTOR_MODULE'
if (cfg instanceof MsvcToolchainConfig) {
cfg.compilerOptions.pchConfig = new MsvcToolchainConfig.PrecompiledHeadersConfig(

View File

@ -76,7 +76,7 @@
<PrecompiledHeader>Use</PrecompiledHeader>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<PreprocessorDefinitions>HLTV;WIN32;_DEBUG;_WINDOWS;_USRDLL;DIRECTOR_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions>HLTV;HLTV_FIXES;WIN32;_DEBUG;_WINDOWS;_USRDLL;DIRECTOR_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<AdditionalIncludeDirectories>$(ProjectDir)\..\..\;$(ProjectDir)\..\src;$(ProjectDir)\..\..\..\common;$(ProjectDir)\..\..\..\engine;$(ProjectDir)\..\..\..\public;$(ProjectDir)\..\..\..\public\rehlds;$(ProjectDir)\..\..\..\pm_shared;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<PrecompiledHeaderFile>precompiled.h</PrecompiledHeaderFile>
<RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
@ -107,7 +107,7 @@
<Optimization>MaxSpeed</Optimization>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>true</IntrinsicFunctions>
<PreprocessorDefinitions>HLTV;WIN32;NDEBUG;_WINDOWS;_USRDLL;DIRECTOR_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions>HLTV;HLTV_FIXES;WIN32;NDEBUG;_WINDOWS;_USRDLL;DIRECTOR_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<AdditionalIncludeDirectories>$(ProjectDir)\..\..\;$(ProjectDir)\..\src;$(ProjectDir)\..\..\..\common;$(ProjectDir)\..\..\..\engine;$(ProjectDir)\..\..\..\public;$(ProjectDir)\..\..\..\public\rehlds;$(ProjectDir)\..\..\..\pm_shared;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<PrecompiledHeaderFile>precompiled.h</PrecompiledHeaderFile>
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>

View File

@ -16,11 +16,12 @@ project.ext.dep_bzip2 = project(':dep/bzip2')
void setupToolchain(NativeBinarySpec b) {
boolean useGcc = project.hasProperty("useGcc")
def cfg = rootProject.createToolchainConfig(b);
cfg.projectInclude(project, '/..', '/../..', '/src', '/../Director/src', '/../../common', '/../../engine', '/../../public', '/../../public/rehlds', '/../../pm_shared');
cfg.projectInclude(dep_bzip2, '/include')
cfg.singleDefines 'USE_BREAKPAD_HANDLER', 'HLTV', 'CORE_MODULE'
cfg.singleDefines 'USE_BREAKPAD_HANDLER', 'HLTV', 'HLTV_FIXES', 'PROXY_MODULE'
if (cfg instanceof MsvcToolchainConfig) {
cfg.compilerOptions.pchConfig = new MsvcToolchainConfig.PrecompiledHeadersConfig(

View File

@ -384,7 +384,7 @@
<PrecompiledHeader>Use</PrecompiledHeader>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<PreprocessorDefinitions>HLTV;WIN32;_DEBUG;_WINDOWS;_USRDLL;PROXY_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions>HLTV;HLTV_FIXES;WIN32;_DEBUG;_WINDOWS;_USRDLL;PROXY_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<AdditionalIncludeDirectories>$(ProjectDir)\..\src;$(ProjectDir)\..\..\;$(ProjectDir)\..\..\..\;$(ProjectDir)\..\..\Director\src;$(ProjectDir)\..\..\..\common;$(ProjectDir)\..\..\..\engine;$(ProjectDir)\..\..\..\public;$(ProjectDir)\..\..\..\public\rehlds;$(ProjectDir)\..\..\..\pm_shared;$(ProjectDir)\..\..\..\..\dep\bzip2\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<PrecompiledHeaderFile>precompiled.h</PrecompiledHeaderFile>
<RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
@ -418,7 +418,7 @@
<Optimization>MaxSpeed</Optimization>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>true</IntrinsicFunctions>
<PreprocessorDefinitions>HLTV;WIN32;NDEBUG;_WINDOWS;_USRDLL;PROXY_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions>HLTV;HLTV_FIXES;WIN32;NDEBUG;_WINDOWS;_USRDLL;PROXY_MODULE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<AdditionalIncludeDirectories>$(ProjectDir)\..\src;$(ProjectDir)\..\..\;$(ProjectDir)\..\..\..\;$(ProjectDir)\..\..\Director\src;$(ProjectDir)\..\..\..\common;$(ProjectDir)\..\..\..\engine;$(ProjectDir)\..\..\..\public;$(ProjectDir)\..\..\..\public\rehlds;$(ProjectDir)\..\..\..\pm_shared;$(ProjectDir)\..\..\..\..\dep\bzip2\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<PrecompiledHeaderFile>precompiled.h</PrecompiledHeaderFile>
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>

View File

@ -69,7 +69,7 @@ const uint32 INVBITTABLE[] =
BitBuffer::BitBuffer() : m_Data(nullptr),
m_CurByte(nullptr),
m_CurSize(0),
m_CurBit(0),
m_MaxSize(0),
m_Overflowed(false),
m_LittleEndian(false),
@ -83,7 +83,7 @@ BitBuffer::BitBuffer(void *newData, unsigned int size)
m_Data = (unsigned char *)newData;
m_CurByte = m_Data;
m_CurSize = 0;
m_CurBit = 0;
m_MaxSize = size;
m_Overflowed = false;
m_LittleEndian = true;
@ -100,7 +100,7 @@ BitBuffer::BitBuffer(unsigned int size)
m_Data = nullptr;
m_CurByte = nullptr;
m_CurSize = 0;
m_CurBit = 0;
m_MaxSize = size;
m_Overflowed = false;
m_LittleEndian = false;
@ -114,7 +114,7 @@ bool BitBuffer::Resize(unsigned int size)
Free();
m_Data = (unsigned char *)Mem_ZeroMalloc(size + 4);
m_CurSize = 0;
m_CurBit = 0;
m_Overflowed = false;
if (m_Data)
@ -139,7 +139,7 @@ void BitBuffer::Clear()
Q_memset(m_Data, 0, m_MaxSize);
m_CurByte = m_Data;
m_CurSize = 0;
m_CurBit = 0;
m_Overflowed = false;
m_LittleEndian = true;
@ -147,13 +147,13 @@ void BitBuffer::Clear()
int BitBuffer::CurrentBit()
{
return m_CurSize + 8 * (m_CurByte - m_Data);
return m_CurBit + 8 * (m_CurByte - m_Data);
}
void BitBuffer::Reset()
{
m_CurByte = m_Data;
m_CurSize = 0;
m_CurBit = 0;
m_Overflowed = false;
m_LittleEndian = true;
@ -168,7 +168,7 @@ void BitBuffer::Free()
m_Data = nullptr;
m_CurByte = nullptr;
m_CurSize = 0;
m_CurBit = 0;
m_MaxSize = 0;
m_OwnData = false;
@ -187,26 +187,26 @@ unsigned int BitBuffer::ReadBits(int numbits)
return -1;
}
int bits = m_CurSize + numbits;
int bits = m_CurBit + numbits;
if (bits <= 32)
{
result = (*(unsigned int *)m_CurByte >> m_CurSize) & ROWBITTABLE[numbits];
result = (*(unsigned int *)m_CurByte >> m_CurBit) & ROWBITTABLE[numbits];
m_CurByte += numbits >> 3;
m_CurSize += numbits & 7;
m_CurBit += numbits & 7;
if (m_CurSize > 7)
if (m_CurBit > 7)
{
m_CurSize &= 7;
m_CurBit &= 7;
m_CurByte++;
}
}
else
{
unsigned int data = *(unsigned int *)m_CurByte >> m_CurSize;
unsigned int data = *(unsigned int *)m_CurByte >> m_CurBit;
m_CurByte += 4;
result = ((ROWBITTABLE[bits & 7] & *(unsigned int *)m_CurByte) << (32 - m_CurSize)) | data;
m_CurSize = bits & 7;
result = ((ROWBITTABLE[bits & 7] & *(unsigned int *)m_CurByte) << (32 - m_CurBit)) | data;
m_CurBit = bits & 7;
}
}
else
@ -235,26 +235,26 @@ int BitBuffer::ReadBit()
{
if (m_LittleEndian)
{
if (m_CurSize == 7)
if (m_CurBit == 7)
{
m_CurSize = 0;
m_CurBit = 0;
result = (*m_CurByte++ >> 7) & 1;
}
else
{
result = ((unsigned int)*m_CurByte >> m_CurSize++) & 1;
result = ((unsigned int)*m_CurByte >> m_CurBit++) & 1;
}
}
else
{
if (m_CurSize == 7)
if (m_CurBit == 7)
{
m_CurSize = 0;
m_CurBit = 0;
result = *m_CurByte++ & 1;
}
else
{
result = ((unsigned int)*m_CurByte >> (7 - m_CurSize++)) & 1;
result = ((unsigned int)*m_CurByte >> (7 - m_CurBit++)) & 1;
}
}
}
@ -264,11 +264,11 @@ int BitBuffer::ReadBit()
unsigned int BitBuffer::PeekBits(int numbits)
{
int oldcurrentBit = m_CurSize;
int oldcurrentBit = m_CurBit;
unsigned char *oldcurrentByte = m_CurByte;
unsigned int data = ReadBits(numbits);
m_CurSize = oldcurrentBit;
m_CurBit = oldcurrentBit;
m_CurByte = oldcurrentByte;
return data;
}
@ -316,7 +316,7 @@ bool BitBuffer::ReadBuf(int iSize, void *pbuf)
return false;
}
if (m_CurSize)
if (m_CurBit)
{
int i, j;
unsigned int *p = (unsigned int *)pbuf;
@ -402,7 +402,7 @@ void BitBuffer::WriteBit(int c)
if (m_LittleEndian)
{
if (m_CurSize == 7)
if (m_CurBit == 7)
{
if (c)
{
@ -414,20 +414,20 @@ void BitBuffer::WriteBit(int c)
}
m_CurByte++;
m_CurSize = 0;
m_CurBit = 0;
}
else
{
if (c)
{
m_CurByte[0] |= BITTABLE[ m_CurSize ];
m_CurByte[0] |= BITTABLE[ m_CurBit ];
}
else
{
m_CurByte[0] &= INVBITTABLE[ m_CurSize ];
m_CurByte[0] &= INVBITTABLE[ m_CurBit ];
}
m_CurSize++;
m_CurBit++;
}
}
else
@ -436,13 +436,13 @@ void BitBuffer::WriteBit(int c)
static unsigned char inv_masks[] = { 0x7Fu, 0xBFu, 0xDFu, 0xEFu, 0xF7u, 0xFBu, 0xFDu, 0xFEu };
if (c)
m_CurByte[0] |= masks[ m_CurSize ];
m_CurByte[0] |= masks[ m_CurBit ];
else
m_CurByte[0] &= inv_masks[ m_CurSize ];
m_CurByte[0] &= inv_masks[ m_CurBit ];
if (++m_CurSize == 8)
if (++m_CurBit == 8)
{
m_CurSize = 0;
m_CurBit = 0;
m_CurByte++;
}
}
@ -461,26 +461,26 @@ void BitBuffer::WriteBits(unsigned int data, int numbits)
return;
}
int bits = numbits + m_CurSize;
int bits = numbits + m_CurBit;
if (bits <= 32)
{
*(uint32 *)m_CurByte |= (ROWBITTABLE[numbits] & data) << m_CurSize;
*(uint32 *)m_CurByte |= (ROWBITTABLE[numbits] & data) << m_CurBit;
m_CurByte = &m_CurByte[numbits >> 3];
m_CurSize = m_CurSize + (numbits & 7);
m_CurBit = m_CurBit + (numbits & 7);
if (m_CurSize > 7)
if (m_CurBit > 7)
{
m_CurSize = m_CurSize & 7;
m_CurBit = m_CurBit & 7;
m_CurByte = m_CurByte + 1;
}
}
else
{
*(uint32 *)m_CurByte |= (ROWBITTABLE[numbits] & data) << m_CurSize;
*(uint32 *)m_CurByte |= (ROWBITTABLE[numbits] & data) << m_CurBit;
int leftBits = (32 - m_CurSize);
m_CurSize = (m_CurSize + numbits) & 7;
int leftBits = (32 - m_CurBit);
m_CurBit = (m_CurBit + numbits) & 7;
m_CurByte += 4;
*(uint32 *)m_CurByte |= (ROWBITTABLE[numbits] & data) >> leftBits;
@ -581,7 +581,7 @@ void BitBuffer::WriteBuf(const void *buf, int iSize)
return;
}
if (m_CurSize)
if (m_CurBit)
{
int i, j;
unsigned int *p = (unsigned int *)buf;
@ -623,7 +623,7 @@ void BitBuffer::WriteHiresAngle(float f)
int BitBuffer::CurrentSize()
{
return (m_CurSize != 0) + m_CurByte - m_Data;
return (m_CurBit != 0) + m_CurByte - m_Data;
}
unsigned char *BitBuffer::CurrentByte()
@ -638,10 +638,10 @@ int BitBuffer::SpaceLeft()
void BitBuffer::AlignByte()
{
if (m_CurSize)
if (m_CurBit)
{
m_CurByte++;
m_CurSize = 0;
m_CurBit = 0;
}
}
@ -712,7 +712,7 @@ void BitBuffer::WriteBitString(const char *p)
void BitBuffer::StartBitMode()
{
if (m_CurSize) {
if (m_CurBit) {
m_Overflowed = true;
}
}
@ -739,7 +739,7 @@ void BitBuffer::SetBuffer(void *buffer, int size)
m_Data = (unsigned char *)buffer;
m_CurByte = (unsigned char *)buffer;
m_MaxSize = size;
m_CurSize = 0;
m_CurBit = 0;
m_OwnData = false;
m_Overflowed = false;
@ -811,22 +811,22 @@ void BitBuffer::SkipBits(int numbits)
return;
}
int bits = m_CurSize + numbits;
int bits = m_CurBit + numbits;
if (bits <= 32)
{
m_CurByte += numbits >> 3;
m_CurSize += numbits & 7;
m_CurBit += numbits & 7;
if (m_CurSize > 7)
if (m_CurBit > 7)
{
m_CurSize &= 7;
m_CurBit &= 7;
m_CurByte++;
}
}
else
{
m_CurByte += 4;
m_CurSize = bits & 7;
m_CurBit = bits & 7;
}
}
else
@ -835,14 +835,14 @@ void BitBuffer::SkipBits(int numbits)
while (d > 0)
{
--d;
if (m_CurSize == 7)
if (m_CurBit == 7)
{
m_CurByte++;
m_CurSize = 0;
m_CurBit = 0;
}
else
{
m_CurSize++;
m_CurBit++;
}
}
}
@ -870,7 +870,7 @@ void BitBuffer::FastClear()
Q_memset(m_Data, 0, iSize);
m_CurByte = m_Data;
m_CurSize = 0;
m_CurBit = 0;
m_Overflowed = false;
m_LittleEndian = true;

View File

@ -41,7 +41,6 @@ public:
unsigned char *CurrentByte();
int GetMaxSize() const { return m_MaxSize; }
unsigned int GetCurSize() const { return m_CurSize; }
unsigned char *GetData() const { return m_Data; }
bool IsOverflowed() const { return m_Overflowed; }
@ -108,7 +107,7 @@ public:
bool m_Overflowed;
unsigned char *m_Data;
unsigned char *m_CurByte;
int m_CurSize;
int m_CurBit;
int m_MaxSize;
protected:

View File

@ -310,7 +310,12 @@ void NetChannel::UpdateFlow(int stream)
void NetChannel::TransmitOutgoing()
{
#ifdef HLTV_FIXES
byte send_buf[MAX_UDP_PACKET];
#else
byte send_buf[NET_MAX_MESSAGE];
#endif
BitBuffer data(send_buf, sizeof(send_buf));
bool send_reliable;
@ -336,7 +341,7 @@ void NetChannel::TransmitOutgoing()
// check for reliable message overflow
if (m_reliableStream.IsOverflowed())
{
m_System->DPrintf("Transmit:Outgoing m_reliableStream overflow (%s)\n", m_remote_address.ToString());
m_System->DPrintf("NetChannel::Transmit:Outgoing m_reliableStream overflow (%s)\n", m_remote_address.ToString());
m_reliableStream.Clear();
return;
}
@ -344,7 +349,7 @@ void NetChannel::TransmitOutgoing()
// check for unreliable message overflow
if (m_unreliableStream.IsOverflowed())
{
m_System->DPrintf("Transmit:Outgoing m_unreliableStream overflow (%s)\n", m_remote_address.ToString());
m_System->DPrintf("NetChannel::Transmit:Outgoing m_unreliableStream overflow (%s)\n", m_remote_address.ToString());
m_unreliableStream.Clear();
}
@ -653,6 +658,46 @@ bool NetChannel::CheckForCompletion(int stream, int intotalbuffers)
return false;
}
bool NetChannel::ValidateFragments(BitBuffer &buf, bool *frag_message, unsigned int *fragid, int *frag_offset, int *frag_length)
{
for (int i = 0; i < MAX_STREAMS; i++)
{
if (!frag_message[i])
continue;
// total fragments should be <= MAX_FRAGMENTS and current fragment can't be > total fragments
if (i == FRAG_NORMAL_STREAM && FRAG_GETCOUNT(fragid[i]) > MAX_NORMAL_FRAGMENTS)
return false;
if (i == FRAG_FILE_STREAM && FRAG_GETCOUNT(fragid[i]) > MAX_FILE_FRAGMENTS)
return false;
if (FRAG_GETID(fragid[i]) > FRAG_GETCOUNT(fragid[i]))
return false;
if (!frag_length[i])
return false;
if ((size_t)frag_length[i] > FRAGMENT_MAX_SIZE || (size_t)frag_offset[i] > MAX_POSSIBLE_MSG - 1)
return false;
int frag_end = frag_offset[i] + frag_length[i];
// end of fragment is out of the packet
if (frag_end + buf.CurrentSize() > buf.GetMaxSize())
return false;
// fragment overlaps next stream's fragment or placed after it
for (int j = i + 1; j < MAX_STREAMS; j++)
{
if (frag_end > frag_offset[j] && frag_message[j]) // don't add buf.CurrentSize() for comparison
return false;
}
}
return true;
}
void NetChannel::ProcessIncoming(unsigned char *data, int size)
{
BitBuffer message(data, size);
@ -721,6 +766,11 @@ void NetChannel::ProcessIncoming(unsigned char *data, int size)
frag_length[i] = message.ReadShort();
}
}
#ifdef HLTV_FIXES
if (!ValidateFragments(message, frag_message, fragid, frag_offset, frag_length))
return;
#endif
}
sequence &= ~(1 << 31);
@ -758,7 +808,12 @@ void NetChannel::ProcessIncoming(unsigned char *data, int size)
// clear the buffer to make way for the next
if (reliable_ack == (unsigned int)m_reliable_sequence)
{
// Make sure we actually could have ack'd this message
#ifdef HLTV_FIXES
if (sequence_ack >= (unsigned)m_last_reliable_sequence)
#else
if (m_incoming_acknowledged + 1 >= m_last_reliable_sequence)
#endif
{
// it has been received
m_reliableOutSize = 0;
@ -1104,6 +1159,24 @@ void NetChannel::CopyNormalFragments()
p = n;
}
#ifdef HLTV_FIXES
if (packet->data.IsOverflowed())
{
if (packet->address.IsValid())
{
m_System->Printf("WARNING! NetChannel::CopyNormalFragments: Incoming overflowed from %s\n", packet->address.ToString());
}
else
{
m_System->Printf("WARNING! NetChannel::CopyNormalFragments: Incoming overflowed\n");
}
packet->data.Clear();
m_incomingbufs[FRAG_NORMAL_STREAM] = nullptr;
return;
}
#endif
if (*(uint32 *)packet->data.GetData() == MAKEID('B', 'Z', '2', '\0'))
{
char uncompressed[65536];

View File

@ -51,32 +51,41 @@ enum
MAX_FLOWS
};
#define MAX_LATENT 32
#define FRAGMENT_MAX_SIZE 1400 // Size of fragmentation buffer internal buffers
#define MAX_LATENT 32
#define FRAGMENT_MAX_SIZE 1400 // Size of fragmentation buffer internal buffers
#define CLIENT_FRAGMENT_SIZE_ONCONNECT 128
#define CUSTOMIZATION_MAX_SIZE 20480
#define UDP_HEADER_SIZE 28
#define MAX_RELIABLE_PAYLOAD 1200
// Client sends normal fragments only while connecting
#define MAX_NORMAL_FRAGMENTS (MAX_POSSIBLE_MSG / CLIENT_FRAGMENT_SIZE_ONCONNECT)
#define MAKE_FRAGID(id, count) (((id & 0xffff) << 16) | (count & 0xffff))
#define FRAG_GETID(fragid) ((fragid >> 16) & 0xffff)
#define FRAG_GETCOUNT(fragid) (fragid & 0xffff)
// While client is connecting it sending fragments with minimal size, also it transfers sprays with minimal fragments...
// But with sv_delayed_spray_upload it sends with cl_dlmax fragment size
#define MAX_FILE_FRAGMENTS (CUSTOMIZATION_MAX_SIZE / FRAGMENT_C2S_MIN_SIZE)
#define UDP_HEADER_SIZE 28
#define MAX_RELIABLE_PAYLOAD 1200
#define MAKE_FRAGID(id, count) (((id & 0xffff) << 16) | (count & 0xffff))
#define FRAG_GETID(fragid) ((fragid >> 16) & 0xffff)
#define FRAG_GETCOUNT(fragid) (fragid & 0xffff)
// Max length of a reliable message
#define MAX_MSGLEN 3990 // 10 reserved for fragheader?
#define MAX_POSSIBLE_MSG 65536
#define MAX_MSGLEN 3990 // 10 reserved for fragheader?
#define MAX_POSSIBLE_MSG 65536
#define MAX_ROUTEABLE_PACKET 1400
#define MIN_ROUTEABLE_PACKET 16
#define MAX_ROUTEABLE_PACKET 1400
#define MIN_ROUTEABLE_PACKET 16
#define SPLIT_SIZE (MAX_ROUTEABLE_PACKET - sizeof(SPLITPACKET))
#define SPLIT_SIZE (MAX_ROUTEABLE_PACKET - sizeof(SPLITPACKET))
// Pad this to next higher 16 byte boundary
// This is the largest packet that can come in/out over the wire, before processing the header
// bytes will be stripped by the networking channel layer
// #define NET_MAX_MESSAGE PAD_NUMBER( ( MAX_MSGLEN + HEADER_BYTES ), 16 )
// This is currently used value in the engine. TODO: define above gives 4016, check it why.
#define NET_MAX_MESSAGE 4037
#define NET_HEADER_FLAG_SPLITPACKET -2
#define NET_MAX_MESSAGE 4037
#define NET_HEADER_FLAG_SPLITPACKET -2
class IBaseSystem;
@ -116,7 +125,7 @@ public:
typedef struct flowstats_s
{
int size; // Size of message sent/received
double time; // Time that message was sent/received
double time; // Time that message was sent/received
} flowstats_t;
typedef struct flow_s
@ -134,24 +143,25 @@ public:
typedef struct fragbuf_s
{
struct fragbuf_s *next; // Next buffer in chain
int bufferId; // Id of this buffer
byte data[FRAGMENT_MAX_SIZE]; // The actual data sits here
int bufferId; // Id of this buffer
byte data[FRAGMENT_MAX_SIZE]; // The actual data sits here
int size; // Size of data to read at that offset
bool isfile; // Is this a file buffer?
bool isbuffer; // Is this file buffer from memory ( custom decal, etc. ).
int size; // Size of data to read at that offset
bool isfile; // Is this a file buffer?
bool isbuffer; // Is this file buffer from memory ( custom decal, etc. ).
char fileName[MAX_PATH]; // Name of the file to save out on remote host
int fOffset; // Offset in file from which to read data
int fOffset; // Offset in file from which to read data
} fragbuf_t;
// Waiting list of fragbuf chains
typedef struct fragbufwaiting_s
{
struct fragbufwaiting_s *next; // Next chain in waiting list
int fragbufcount; // Number of buffers in this chain
struct fragbufwaiting_s *next; // Next chain in waiting list
int fragbufcount; // Number of buffers in this chain
fragbuf_t *fragbufs; // The actual buffers
} fragbufwaiting_t;
bool ValidateFragments(BitBuffer &buf, bool *frag_message, unsigned int *fragid, int *frag_offset, int *frag_length);
bool CreateFragmentsFromFile(char *fileName);
bool CopyFileFragments();
void GetFlowStats(float *avgInKBSec, float *avgOutKBSec);
@ -179,25 +189,25 @@ public:
NetAddress m_remote_address; // Address this channel is talking to.
double m_last_received;
double m_last_send;
double m_connect_time; // Time when channel was connected.
double m_connect_time; // Time when channel was connected.
float m_timeout;
int m_max_bandwidth_rate;
double m_send_interval;
int m_updaterate; // Bandwidth choke, bytes per second
double m_cleartime; // If realtime > cleartime, free to send next packet
int m_updaterate; // Bandwidth choke, bytes per second
double m_cleartime; // If realtime > cleartime, free to send next packet
bool m_keep_alive;
bool m_crashed;
bool m_connected;
// Sequencing variables
int m_incoming_sequence; // Increasing count of sequence numbers
int m_incoming_acknowledged; // # of last outgoing message that has been ack'd.
int m_incoming_sequence; // Increasing count of sequence numbers
int m_incoming_acknowledged; // # of last outgoing message that has been ack'd.
int m_incoming_reliable_acknowledged; // Toggles T/F as reliable messages are received.
int m_incoming_reliable_sequence; // single bit, maintained local
int m_outgoing_sequence; // Message we are sending to remote
int m_reliable_sequence; // Whether the message contains reliable payload, single bit
int m_last_reliable_sequence; // Outgoing sequence number of last send that had reliable data
int m_incoming_reliable_sequence; // single bit, maintained local
int m_outgoing_sequence; // Message we are sending to remote
int m_reliable_sequence; // Whether the message contains reliable payload, single bit
int m_last_reliable_sequence; // Outgoing sequence number of last send that had reliable data
void *m_connection_status;
@ -216,11 +226,11 @@ public:
int m_reliable_fragment[MAX_STREAMS]; // Is reliable waiting buf a fragment?
size_t m_reliable_fragid[MAX_STREAMS]; // Buffer id for each waiting fragment
fragbuf_t *m_fragbufs[MAX_STREAMS]; // The current fragment being set
int m_fragbufcount[MAX_STREAMS]; // The total number of fragments in this stream
fragbuf_t *m_fragbufs[MAX_STREAMS]; // The current fragment being set
int m_fragbufcount[MAX_STREAMS]; // The total number of fragments in this stream
int16 m_frag_startpos[MAX_STREAMS]; // Position in outgoing buffer where frag data starts
int16 m_frag_length[MAX_STREAMS]; // Length of frag data in the buffer
int16 m_frag_startpos[MAX_STREAMS]; // Position in outgoing buffer where frag data starts
int16 m_frag_length[MAX_STREAMS]; // Length of frag data in the buffer
fragbuf_t *m_incomingbufs[MAX_STREAMS]; // Incoming fragments are stored here