mirror of
https://github.com/aria2/aria2.git
synced 2025-04-04 21:17:41 +03:00
Rewritten SharedHandle. Now copy constructor taking raw pointer has keyword explicit and SharedHandle's default constructor initializes its internal obj to null, old implementation initializes it using obj's default constructor. To assign null, write SharedHandle<T> x(...); x.reset(); TODO: test/SharedHandleTest.cc needs more tests. * src/SharedHandle.h
194 lines
5.1 KiB
C++
194 lines
5.1 KiB
C++
#include "DHTRoutingTableSerializer.h"
|
|
#include "Exception.h"
|
|
#include "Util.h"
|
|
#include "DHTNode.h"
|
|
#include "array_fun.h"
|
|
#include "DHTConstants.h"
|
|
#include "PeerMessageUtil.h"
|
|
#include "a2netcompat.h"
|
|
#include <cstring>
|
|
#include <sstream>
|
|
#include <iostream>
|
|
#include <cppunit/extensions/HelperMacros.h>
|
|
|
|
namespace aria2 {
|
|
|
|
class DHTRoutingTableSerializerTest:public CppUnit::TestFixture {
|
|
|
|
CPPUNIT_TEST_SUITE(DHTRoutingTableSerializerTest);
|
|
CPPUNIT_TEST(testSerialize);
|
|
CPPUNIT_TEST_SUITE_END();
|
|
public:
|
|
void setUp() {}
|
|
|
|
void tearDown() {}
|
|
|
|
void testSerialize();
|
|
};
|
|
|
|
|
|
CPPUNIT_TEST_SUITE_REGISTRATION(DHTRoutingTableSerializerTest);
|
|
|
|
void DHTRoutingTableSerializerTest::testSerialize()
|
|
{
|
|
SharedHandle<DHTNode> localNode(new DHTNode());
|
|
|
|
SharedHandle<DHTNode> nodesSrc[3];
|
|
for(size_t i = 0; i < arrayLength(nodesSrc); ++i) {
|
|
nodesSrc[i].reset(new DHTNode());
|
|
nodesSrc[i]->setIPAddress("192.168.0."+Util::uitos(i+1));
|
|
nodesSrc[i]->setPort(6881+i);
|
|
}
|
|
nodesSrc[1]->setIPAddress("non-numerical-name");
|
|
std::deque<SharedHandle<DHTNode> > nodes(&nodesSrc[0], &nodesSrc[arrayLength(nodesSrc)]);
|
|
|
|
DHTRoutingTableSerializer s;
|
|
s.setLocalNode(localNode);
|
|
s.setNodes(nodes);
|
|
|
|
std::stringstream ss;
|
|
s.serialize(ss);
|
|
|
|
char zero[16];
|
|
memset(zero, 0, sizeof(zero));
|
|
|
|
char buf[20];
|
|
// header
|
|
ss.read(buf, 8);
|
|
// magic
|
|
CPPUNIT_ASSERT((char)0xa1 == buf[0]);
|
|
CPPUNIT_ASSERT((char)0xa2 == buf[1]);
|
|
// format ID
|
|
CPPUNIT_ASSERT((char)0x02 == buf[2]);
|
|
// reserved
|
|
CPPUNIT_ASSERT((char)0x00 == buf[3]);
|
|
CPPUNIT_ASSERT((char)0x00 == buf[4]);
|
|
CPPUNIT_ASSERT((char)0x00 == buf[5]);
|
|
// version
|
|
CPPUNIT_ASSERT((char)0x00 == buf[6]);
|
|
CPPUNIT_ASSERT((char)0x02 == buf[7]);
|
|
|
|
// time
|
|
ss.read(buf, 4);
|
|
time_t time = ntohl(*reinterpret_cast<uint32_t*>(buf));
|
|
std::cerr << time << std::endl;
|
|
// 4bytes reserved
|
|
ss.read(buf, 4);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 4) == 0);
|
|
|
|
// localnode
|
|
// 8bytes reserved
|
|
ss.read(buf, 8);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 8) == 0);
|
|
// localnode ID
|
|
ss.read(buf, DHT_ID_LENGTH);
|
|
CPPUNIT_ASSERT(memcmp(localNode->getID(), buf, DHT_ID_LENGTH) == 0);
|
|
// 4bytes reserved
|
|
ss.read(buf, 4);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 4) == 0);
|
|
|
|
// number of nodes saved
|
|
ss.read(buf, 4);
|
|
uint32_t numNodes = ntohl(*reinterpret_cast<uint32_t*>(buf));
|
|
CPPUNIT_ASSERT_EQUAL((uint32_t)3, numNodes);
|
|
// 4bytes reserved
|
|
ss.read(buf, 4);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 4) == 0);
|
|
|
|
// node[0]
|
|
// 1byte compatc peer format length
|
|
{
|
|
uint8_t len;
|
|
ss >> len;
|
|
CPPUNIT_ASSERT_EQUAL((uint8_t)6, len);
|
|
}
|
|
// 7bytes reserved
|
|
ss.read(buf, 7);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 7) == 0);
|
|
// 6bytes compact peer info
|
|
ss.read(buf, 6);
|
|
{
|
|
std::pair<std::string, uint16_t> peer =
|
|
PeerMessageUtil::unpackcompact(reinterpret_cast<const unsigned char*>(buf));
|
|
CPPUNIT_ASSERT_EQUAL(std::string("192.168.0.1"), peer.first);
|
|
CPPUNIT_ASSERT_EQUAL((uint16_t)6881, peer.second);
|
|
}
|
|
// 2bytes reserved
|
|
ss.read(buf, 2);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 2) == 0);
|
|
// 16bytes reserved
|
|
ss.read(buf, 16);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 16) == 0);
|
|
// localnode ID
|
|
ss.read(buf, DHT_ID_LENGTH);
|
|
CPPUNIT_ASSERT(memcmp(nodes[0]->getID(), buf, DHT_ID_LENGTH) == 0);
|
|
// 4bytes reserved
|
|
ss.read(buf, 4);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 4) == 0);
|
|
|
|
// node[1]
|
|
// 1byte compatc peer format length
|
|
{
|
|
uint8_t len;
|
|
ss >> len;
|
|
CPPUNIT_ASSERT_EQUAL((uint8_t)6, len);
|
|
}
|
|
// 7bytes reserved
|
|
ss.read(buf, 7);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 7) == 0);
|
|
// 6bytes compact peer info
|
|
ss.read(buf, 6);
|
|
// zero filled because node[1]'s hostname is not numerical form
|
|
// deserializer should skip this entry
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 6) == 0);
|
|
// 2bytes reserved
|
|
ss.read(buf, 2);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 2) == 0);
|
|
// 16bytes reserved
|
|
ss.read(buf, 16);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 16) == 0);
|
|
// localnode ID
|
|
ss.read(buf, DHT_ID_LENGTH);
|
|
CPPUNIT_ASSERT(memcmp(nodes[1]->getID(), buf, DHT_ID_LENGTH) == 0);
|
|
// 4bytes reserved
|
|
ss.read(buf, 4);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 4) == 0);
|
|
|
|
// node[2]
|
|
// 1byte compatc peer format length
|
|
{
|
|
uint8_t len;
|
|
ss >> len;
|
|
CPPUNIT_ASSERT_EQUAL((uint8_t)6, len);
|
|
}
|
|
// 7bytes reserved
|
|
ss.read(buf, 7);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 7) == 0);
|
|
// 6bytes compact peer info
|
|
ss.read(buf, 6);
|
|
{
|
|
std::pair<std::string, uint16_t> peer =
|
|
PeerMessageUtil::unpackcompact(reinterpret_cast<const unsigned char*>(buf));
|
|
CPPUNIT_ASSERT_EQUAL(std::string("192.168.0.3"), peer.first);
|
|
CPPUNIT_ASSERT_EQUAL((uint16_t)6883, peer.second);
|
|
}
|
|
// 2bytes reserved
|
|
ss.read(buf, 2);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 2) == 0);
|
|
// 16bytes reserved
|
|
ss.read(buf, 16);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 16) == 0);
|
|
// localnode ID
|
|
ss.read(buf, DHT_ID_LENGTH);
|
|
CPPUNIT_ASSERT(memcmp(nodes[2]->getID(), buf, DHT_ID_LENGTH) == 0);
|
|
// 4bytes reserved
|
|
ss.read(buf, 4);
|
|
CPPUNIT_ASSERT(memcmp(zero, buf, 4) == 0);
|
|
|
|
// check to see stream ends
|
|
ss.read(buf, 1);
|
|
CPPUNIT_ASSERT_EQUAL((std::streamsize)0, ss.gcount());
|
|
CPPUNIT_ASSERT(ss.eof());
|
|
}
|
|
|
|
} // namespace aria2
|