diff --git a/raknet/ReliabilityLayer.h b/raknet/ReliabilityLayer.h index e847e24..fa53c9c 100644 --- a/raknet/ReliabilityLayer.h +++ b/raknet/ReliabilityLayer.h @@ -18,6 +18,9 @@ #ifndef __RELIABILITY_LAYER_H #define __RELIABILITY_LAYER_H +// SAMPSRV +#define TEA_ENCRYPTOR + #include "SocketLayer.h" #include "MTUSize.h" #include "DS_LinkedList.h" @@ -27,7 +30,13 @@ #include "BitStream.h" #include "InternalPacket.h" #include "InternalPacketPool.h" + +#ifdef TEA_ENCRYPTOR +#include "TEABlockEncryptor.h" +#else #include "DataBlockEncryptor.h" +#endif + #include "RakNetStatistics.h" #include "SHA1.h" #include "DS_OrderedList.h" @@ -328,7 +337,12 @@ private: double availableBandwidth; bool continuousSend; +#ifdef TEA_ENCRYPTOR + TEABlockEncryptor encryptor; +#else DataBlockEncryptor encryptor; +#endif + unsigned sendPacketCount, receivePacketCount; RakNetTimeNS ackTimeIncrement; diff --git a/raknet/TEABlockEncryptor.cpp b/raknet/TEABlockEncryptor.cpp new file mode 100644 index 0000000..335041a --- /dev/null +++ b/raknet/TEABlockEncryptor.cpp @@ -0,0 +1,239 @@ +#include "TEABlockEncryptor.h" +#include "CheckSum.h" +#include "Rand.h" +#include +#include + +#ifdef _WIN32 +#include +#else +#define OutputDebugString NULL +#endif + +#define TEA_ROUNDS 32 +#define TEA_XOR_MASK 0x5E94A3CF + +unsigned int TEABlockEncryptor::initObsDelta = (0x9E3779B9 ^ TEA_XOR_MASK); + +#ifdef _DEBUG +void DumpMemory(const char *preText, const unsigned char *data, unsigned int count) +{ + return; + + char buffer[2000]; + char temp[5]; + sprintf(buffer, "%s: ", preText); + for(unsigned int i=0; i(output+i)); + unsigned int &V1 = *(reinterpret_cast(output+i+sizeof(unsigned int))); + EncryptBlock(V0, V1); + //*(reinterpret_cast(output+i)+0) = V0; + //*(reinterpret_cast(output+i)+1) = V1; + } + +#ifdef _DEBUG + DumpMemory("PostEncrypt", output, *outputLength); +#endif + +} + +bool TEABlockEncryptor::Decrypt( unsigned char *input, int inputLength, unsigned char *output, int *outputLength ) +{ + unsigned char checkSum; + unsigned int checkSumInt; + unsigned char paddingBytes; + unsigned char encodedPad; + CheckSum checkSumCalculator; + +#ifdef _DEBUG + assert( keySet ); +#endif + + if ( input == 0 || inputLength < 8 || ( inputLength % 8 ) != 0 ) + { + return false; + } + +#ifdef _DEBUG + DumpMemory("Pre Decrypt", input, inputLength); +#endif + + for(int i=0; i(input+i)); + unsigned int &V1 = *(reinterpret_cast(input+i+sizeof(unsigned int))); + DecryptBlock(V0, V1); + //*(reinterpret_cast(input+i)+0) = V0; + //*(reinterpret_cast(input+i)+1) = V1; + } + +#ifdef _DEBUG + DumpMemory("PostDecrypt", input, inputLength); +#endif + + // Read checksum + checkSum = *(output); + + // Read the pad size variable + encodedPad = *(output + sizeof( checkSum )); + + // Only care about the last 4 bits + paddingBytes = encodedPad & 0x0F; + + // Get the data length + *outputLength = inputLength - sizeof( checkSum ) - sizeof( encodedPad ) - paddingBytes; + + // Calculate the checksum on the data. + checkSumCalculator.Add( input + sizeof( checkSum ), *outputLength + sizeof( encodedPad ) + paddingBytes ); + + checkSumInt = checkSumCalculator.Get(); + checkSumInt = ( (checkSumInt << 4) ^ (checkSumInt) ) & 0xFF; + + if ( (unsigned char)checkSumInt != checkSum ) + return false; + + // Read the data + if ( input == output ) + memmove( output, input + sizeof( checkSum ) + sizeof( encodedPad ) + paddingBytes, *outputLength ); + else + memcpy( output, input + sizeof( checkSum ) + sizeof( encodedPad ) + paddingBytes, *outputLength ); + + return true; + +} + +void TEABlockEncryptor::EncryptBlock(unsigned int &V0, unsigned int &V1) +{ + unsigned int sum = 0; + + for(unsigned int i=0; i> 5) + V1) ^ (sum + key[sum & 3]); + sum += initDelta; + V1 += ((V0 << 4 ^ V0 >> 5) + V0) ^ (sum + key[sum>>11 & 3]); + } +} + +void TEABlockEncryptor::DecryptBlock(unsigned int &V0, unsigned int &V1) +{ + unsigned int sum = initSum; + + for(unsigned int i=0; i> 5) + V0) ^ (sum + key[sum>>11 & 3]); + sum -= initDelta; + V0 -= ((V1 << 4 ^ V1 >> 5) + V1) ^ (sum + key[sum & 3]); + } +} diff --git a/raknet/TEABlockEncryptor.h b/raknet/TEABlockEncryptor.h new file mode 100644 index 0000000..820bdf4 --- /dev/null +++ b/raknet/TEABlockEncryptor.h @@ -0,0 +1,36 @@ + +// Implements a TEA block encryptor for RakNet + +#ifndef __TEA_BLOCK_ENCRYPTOR_H +#define __TEA_BLOCK_ENCRYPTOR_H + +#include "DataBlockEncryptor.h" + +class TEABlockEncryptor : + public DataBlockEncryptor +{ + +public: + + TEABlockEncryptor(); + ~TEABlockEncryptor(); + + bool IsKeySet( void ) const; + void SetKey( const unsigned char key[ 16 ] ); + void UnsetKey( void ); + void Encrypt( unsigned char *input, int inputLength, unsigned char *output, int *outputLength ); + bool Decrypt( unsigned char *input, int inputLength, unsigned char *output, int *outputLength ); + +protected: + unsigned char key[ 16 ]; + unsigned int initSum; + unsigned int initDelta; + + static unsigned int initObsDelta; + + void EncryptBlock(unsigned int &V0, unsigned int &V1); + void DecryptBlock(unsigned int &V0, unsigned int &V1); + +}; + +#endif diff --git a/saco/saco.vcproj b/saco/saco.vcproj index aa17650..18e26b7 100644 --- a/saco/saco.vcproj +++ b/saco/saco.vcproj @@ -862,6 +862,12 @@ + + + +