lokinet/llarp/link_intro.cpp

165 lines
3.6 KiB
C++
Raw Normal View History

2018-06-01 14:08:54 +00:00
#include <llarp/bencode.h>
2018-08-30 18:48:43 +00:00
#include <llarp/router_contact.hpp>
2018-06-01 14:08:54 +00:00
#include <llarp/messages/link_intro.hpp>
#include "logger.hpp"
2018-07-03 13:13:56 +00:00
#include "router.hpp"
2018-06-01 14:08:54 +00:00
namespace llarp
{
LinkIntroMessage::~LinkIntroMessage()
{
}
bool
LinkIntroMessage::DecodeKey(llarp_buffer_t key, llarp_buffer_t* buf)
{
2018-09-04 19:15:06 +00:00
if(llarp_buffer_eq(key, "a"))
{
llarp_buffer_t strbuf;
if(!bencode_read_string(buf, &strbuf))
return false;
if(strbuf.sz != 1)
return false;
return *strbuf.cur == 'i';
}
2018-09-06 11:46:19 +00:00
if(llarp_buffer_eq(key, "n"))
{
if(N.BDecode(buf))
return true;
llarp::LogWarn("failed to decode nonce in LIM");
return false;
}
if(llarp_buffer_eq(key, "p"))
{
return bencode_read_integer(buf, &P);
}
2018-06-01 14:08:54 +00:00
if(llarp_buffer_eq(key, "r"))
{
2018-09-06 11:46:19 +00:00
if(rc.BDecode(buf))
return true;
llarp::LogWarn("failed to decode RC in LIM");
llarp::DumpBuffer(*buf);
return false;
2018-06-01 14:08:54 +00:00
}
else if(llarp_buffer_eq(key, "v"))
{
if(!bencode_read_integer(buf, &version))
2018-06-01 14:08:54 +00:00
return false;
if(version != LLARP_PROTO_VERSION)
{
2018-07-17 04:37:50 +00:00
llarp::LogWarn("llarp protocol version missmatch ", version,
" != ", LLARP_PROTO_VERSION);
2018-06-01 14:08:54 +00:00
return false;
}
llarp::LogDebug("LIM version ", version);
2018-06-01 14:08:54 +00:00
return true;
}
else if(llarp_buffer_eq(key, "z"))
{
return Z.BDecode(buf);
}
2018-06-01 14:08:54 +00:00
else
{
llarp::LogWarn("invalid LIM key: ", *key.cur);
2018-06-01 14:08:54 +00:00
return false;
}
}
bool
LinkIntroMessage::BEncode(llarp_buffer_t* buf) const
{
if(!bencode_start_dict(buf))
return false;
if(!bencode_write_bytestring(buf, "a", 1))
return false;
if(!bencode_write_bytestring(buf, "i", 1))
return false;
if(!bencode_write_bytestring(buf, "n", 1))
return false;
if(!N.BEncode(buf))
return false;
if(!bencode_write_bytestring(buf, "p", 1))
return false;
if(!bencode_write_uint64(buf, P))
return false;
if(!bencode_write_bytestring(buf, "r", 1))
return false;
if(!rc.BEncode(buf))
return false;
2018-06-01 14:08:54 +00:00
if(!bencode_write_version_entry(buf))
return false;
if(!bencode_write_bytestring(buf, "z", 1))
return false;
if(!Z.BEncode(buf))
return false;
2018-06-01 14:08:54 +00:00
return bencode_end(buf);
}
LinkIntroMessage&
LinkIntroMessage::operator=(const LinkIntroMessage& msg)
{
version = msg.version;
Z = msg.Z;
rc = msg.rc;
N = msg.N;
P = msg.P;
return *this;
}
2018-06-01 14:08:54 +00:00
bool
LinkIntroMessage::HandleMessage(llarp_router* router) const
{
if(!Verify(&router->crypto))
return false;
return session->GotLIM(this);
2018-06-01 14:08:54 +00:00
}
bool
LinkIntroMessage::Sign(llarp_crypto* c, const SecretKey& k)
{
Z.Zero();
byte_t tmp[MaxSize] = {0};
auto buf = llarp::StackBuffer< decltype(tmp) >(tmp);
if(!BEncode(&buf))
return false;
buf.sz = buf.cur - buf.base;
buf.cur = buf.base;
return c->sign(Z, k, buf);
}
bool
LinkIntroMessage::Verify(llarp_crypto* c) const
{
LinkIntroMessage copy;
copy = *this;
copy.Z.Zero();
byte_t tmp[MaxSize] = {0};
auto buf = llarp::StackBuffer< decltype(tmp) >(tmp);
if(!copy.BEncode(&buf))
return false;
buf.sz = buf.cur - buf.base;
buf.cur = buf.base;
// outer signature
if(!c->verify(rc.pubkey, buf, Z))
{
llarp::LogError("outer signature failure");
return false;
}
2018-10-15 12:02:32 +00:00
// verify RC
if(!rc.Verify(c))
{
2018-10-15 12:02:32 +00:00
llarp::LogError("invalid RC in link intro");
return false;
}
return true;
}
2018-07-03 13:13:56 +00:00
} // namespace llarp