Browse Source

send data frame for NTCP2

pull/1202/head
orignal 7 years ago
parent
commit
5bc157eb19
  1. 44
      libi2pd/NTCP2.cpp
  2. 10
      libi2pd/NTCP2.h

44
libi2pd/NTCP2.cpp

@ -20,7 +20,8 @@ namespace transport
m_Server (server), m_Socket (m_Server.GetService ()), m_Server (server), m_Socket (m_Server.GetService ()),
m_IsEstablished (false), m_IsTerminated (false), m_IsEstablished (false), m_IsTerminated (false),
m_SessionRequestBuffer (nullptr), m_SessionCreatedBuffer (nullptr), m_SessionConfirmedBuffer (nullptr), m_SessionRequestBuffer (nullptr), m_SessionCreatedBuffer (nullptr), m_SessionConfirmedBuffer (nullptr),
m_NextReceivedBuffer (nullptr), m_ReceiveSequenceNumber (0) m_NextReceivedBuffer (nullptr), m_NextSendBuffer (nullptr),
m_ReceiveSequenceNumber (0), m_SendSequenceNumber (0)
{ {
auto addr = in_RemoteRouter->GetNTCPAddress (); auto addr = in_RemoteRouter->GetNTCPAddress ();
if (addr->ntcp2) if (addr->ntcp2)
@ -38,6 +39,7 @@ namespace transport
delete[] m_SessionCreatedBuffer; delete[] m_SessionCreatedBuffer;
delete[] m_SessionConfirmedBuffer; delete[] m_SessionConfirmedBuffer;
delete[] m_NextReceivedBuffer; delete[] m_NextReceivedBuffer;
delete[] m_NextSendBuffer;
} }
void NTCP2Session::Terminate () void NTCP2Session::Terminate ()
@ -69,6 +71,12 @@ namespace transport
HMAC(EVP_sha256(), tempKey, 32, m_CK, 33, derived, &len); HMAC(EVP_sha256(), tempKey, 32, m_CK, 33, derived, &len);
} }
void NTCP2Session::CreateNonce (uint64_t seqn, uint8_t * nonce)
{
memset (nonce, 0, 4);
htole64buf (nonce + 4, seqn);
}
void NTCP2Session::KeyDerivationFunction1 (const uint8_t * rs, const uint8_t * priv, const uint8_t * pub, uint8_t * derived) void NTCP2Session::KeyDerivationFunction1 (const uint8_t * rs, const uint8_t * priv, const uint8_t * pub, uint8_t * derived)
{ {
static const uint8_t protocolNameHash[] = static const uint8_t protocolNameHash[] =
@ -378,7 +386,7 @@ namespace transport
// part1 48 bytes // part1 48 bytes
m_SessionConfirmedBuffer = new uint8_t[2048]; // TODO: actual size m_SessionConfirmedBuffer = new uint8_t[2048]; // TODO: actual size
uint8_t nonce[12]; uint8_t nonce[12];
memset (nonce, 0, 4); htole64buf (nonce + 4, 1); // set nonce to 1 CreateNonce (1, nonce);
i2p::crypto::AEADChaCha20Poly1305 (i2p::context.GetNTCP2StaticPublicKey (), 32, h, 32, m_K, nonce, m_SessionConfirmedBuffer, 48, true); // encrypt i2p::crypto::AEADChaCha20Poly1305 (i2p::context.GetNTCP2StaticPublicKey (), 32, h, 32, m_K, nonce, m_SessionConfirmedBuffer, 48, true); // encrypt
// part 2 // part 2
// update AD again // update AD again
@ -411,7 +419,16 @@ namespace transport
LogPrint (eLogDebug, "NTCP2: SessionConfirmed sent"); LogPrint (eLogDebug, "NTCP2: SessionConfirmed sent");
KeyDerivationFunctionDataPhase (); KeyDerivationFunctionDataPhase ();
memcpy (m_ReceiveIV, m_Sipkeysba + 16, 8); //Alice memcpy (m_ReceiveIV, m_Sipkeysba + 16, 8); //Alice
memcpy (m_SendIV, m_Sipkeysab + 16, 8); //Alice
ReceiveLength (); ReceiveLength ();
// TODO: remove
uint8_t pad[1024];
auto paddingLength = rand () % 1000;
RAND_bytes (pad + 3, paddingLength);
pad[0] = 254;
htobe16buf (pad + 1, paddingLength);
SendNextFrame (pad, paddingLength + 3);
} }
void NTCP2Session::HandleSessionCreatedSent (const boost::system::error_code& ecode, std::size_t bytes_transferred) void NTCP2Session::HandleSessionCreatedSent (const boost::system::error_code& ecode, std::size_t bytes_transferred)
@ -473,7 +490,7 @@ namespace transport
else else
{ {
uint8_t nonce[12]; uint8_t nonce[12];
memset (nonce, 0, 4); htole64buf (nonce + 4, m_ReceiveSequenceNumber); m_ReceiveSequenceNumber++; CreateNonce (m_ReceiveSequenceNumber, nonce); m_ReceiveSequenceNumber++;
uint8_t * decrypted = new uint8_t[m_NextReceivedLen]; uint8_t * decrypted = new uint8_t[m_NextReceivedLen];
if (i2p::crypto::AEADChaCha20Poly1305 (m_NextReceivedBuffer, m_NextReceivedLen-16, nullptr, 0, m_Kba, nonce, decrypted, m_NextReceivedLen, false)) // decrypt. assume Alice TODO: if (i2p::crypto::AEADChaCha20Poly1305 (m_NextReceivedBuffer, m_NextReceivedLen-16, nullptr, 0, m_Kba, nonce, decrypted, m_NextReceivedLen, false)) // decrypt. assume Alice TODO:
{ {
@ -509,6 +526,27 @@ namespace transport
} }
} }
void NTCP2Session::SendNextFrame (const uint8_t * payload, size_t len)
{
uint8_t nonce[12];
CreateNonce (m_SendSequenceNumber, nonce); m_SendSequenceNumber++;
m_NextSendBuffer = new uint8_t[len + 16 + 2];
i2p::crypto::AEADChaCha20Poly1305 (payload, len, nullptr, 0, m_Kab, nonce, m_NextSendBuffer + 2, len + 16, true); // encrypt. assume Alice TODO:
i2p::crypto::Siphash<8> (m_SendIV, m_SendIV, 8, m_Sipkeysab); // assume Alice TODO:
htobuf16 (m_NextSendBuffer, bufbe16toh (m_SendIV) ^ htobe16(len + 16));
LogPrint (eLogDebug, "NTCP2: sent length ", len + 16);
// send message
boost::asio::async_write (m_Socket, boost::asio::buffer (m_NextSendBuffer, len + 16 + 2), boost::asio::transfer_all (),
std::bind(&NTCP2Session::HandleNextFrameSent, shared_from_this (), std::placeholders::_1, std::placeholders::_2));
}
void NTCP2Session::HandleNextFrameSent (const boost::system::error_code& ecode, std::size_t bytes_transferred)
{
delete[] m_NextSendBuffer; m_NextSendBuffer = nullptr;
LogPrint (eLogDebug, "NTCP2: Next frame sent");
}
NTCP2Server::NTCP2Server (): NTCP2Server::NTCP2Server ():
m_IsRunning (false), m_Thread (nullptr), m_Work (m_Service) m_IsRunning (false), m_Thread (nullptr), m_Work (m_Service)
{ {

10
libi2pd/NTCP2.h

@ -31,6 +31,7 @@ namespace transport
private: private:
void MixKey (const uint8_t * inputKeyMaterial, uint8_t * derived); void MixKey (const uint8_t * inputKeyMaterial, uint8_t * derived);
void CreateNonce (uint64_t seqn, uint8_t * nonce);
void KeyDerivationFunction1 (const uint8_t * rs, const uint8_t * priv, const uint8_t * pub, uint8_t * derived); // for SessionRequest void KeyDerivationFunction1 (const uint8_t * rs, const uint8_t * priv, const uint8_t * pub, uint8_t * derived); // for SessionRequest
void KeyDerivationFunction2 (const uint8_t * priv, const uint8_t * pub, const uint8_t * sessionRequest, size_t sessionRequestLen, uint8_t * derived); // for SessionCreate void KeyDerivationFunction2 (const uint8_t * priv, const uint8_t * pub, const uint8_t * sessionRequest, size_t sessionRequestLen, uint8_t * derived); // for SessionCreate
void KeyDerivationFunction3 (const uint8_t * staticPrivKey, uint8_t * derived); // for SessionConfirmed part 2 void KeyDerivationFunction3 (const uint8_t * staticPrivKey, uint8_t * derived); // for SessionConfirmed part 2
@ -57,6 +58,9 @@ namespace transport
void HandleReceived (const boost::system::error_code& ecode, std::size_t bytes_transferred); void HandleReceived (const boost::system::error_code& ecode, std::size_t bytes_transferred);
void ProcessNextFrame (const uint8_t * frame, size_t len); void ProcessNextFrame (const uint8_t * frame, size_t len);
void SendNextFrame (const uint8_t * payload, size_t len);
void HandleNextFrameSent (const boost::system::error_code& ecode, std::size_t bytes_transferred);
private: private:
NTCP2Server& m_Server; NTCP2Server& m_Server;
@ -70,9 +74,9 @@ namespace transport
// data phase // data phase
uint8_t m_Kab[33], m_Kba[32], m_Sipkeysab[33], m_Sipkeysba[32]; uint8_t m_Kab[33], m_Kba[32], m_Sipkeysab[33], m_Sipkeysba[32];
uint16_t m_NextReceivedLen; uint16_t m_NextReceivedLen;
uint8_t * m_NextReceivedBuffer; uint8_t * m_NextReceivedBuffer, * m_NextSendBuffer;
uint8_t m_ReceiveIV[8]; uint8_t m_ReceiveIV[8], m_SendIV[8];
uint64_t m_ReceiveSequenceNumber; uint64_t m_ReceiveSequenceNumber, m_SendSequenceNumber;
}; };
class NTCP2Server class NTCP2Server

Loading…
Cancel
Save