2007-12-11 20:43:17 -05:00
|
|
|
/*
|
|
|
|
* libretroshare/src/services: p3disc.cc
|
|
|
|
*
|
|
|
|
* Services for RetroShare.
|
|
|
|
*
|
|
|
|
* Copyright 2004-2008 by Robert Fernie.
|
|
|
|
*
|
|
|
|
* This library is free software; you can redistribute it and/or
|
|
|
|
* modify it under the terms of the GNU Library General Public
|
|
|
|
* License Version 2 as published by the Free Software Foundation.
|
|
|
|
*
|
|
|
|
* This library is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
|
|
* Library General Public License for more details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU Library General Public
|
|
|
|
* License along with this library; if not, write to the Free Software
|
|
|
|
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
|
|
|
|
* USA.
|
|
|
|
*
|
|
|
|
* Please report all bugs and problems to "retroshare@lunamutt.com".
|
|
|
|
*
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
|
|
#include "services/p3disc.h"
|
|
|
|
|
2008-01-25 02:49:28 -05:00
|
|
|
#include "pqi/p3authmgr.h"
|
|
|
|
#include "pqi/p3connmgr.h"
|
2007-12-11 20:43:17 -05:00
|
|
|
|
|
|
|
#include <iostream>
|
|
|
|
#include <errno.h>
|
|
|
|
#include <cmath>
|
|
|
|
|
|
|
|
const uint32_t AUTODISC_LDI_SUBTYPE_PING = 0x01;
|
|
|
|
const uint32_t AUTODISC_LDI_SUBTYPE_RPLY = 0x02;
|
|
|
|
|
|
|
|
#include <sstream>
|
|
|
|
#include "pqi/pqidebug.h"
|
|
|
|
|
|
|
|
const int pqidisczone = 2482;
|
|
|
|
|
|
|
|
static int convertTDeltaToTRange(double tdelta);
|
|
|
|
static int convertTRangeToTDelta(int trange);
|
|
|
|
|
|
|
|
// Operating System specific includes.
|
|
|
|
#include "pqi/pqinetwork.h"
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* DISC FLAGS */
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
const uint32_t P3DISC_FLAGS_USE_DISC = 0x0001;
|
|
|
|
const uint32_t P3DISC_FLAGS_USE_DHT = 0x0002;
|
|
|
|
const uint32_t P3DISC_FLAGS_EXTERNAL_ADDR = 0x0004;
|
|
|
|
const uint32_t P3DISC_FLAGS_PEER_ONLINE = 0x0008;
|
|
|
|
const uint32_t P3DISC_FLAGS_OWN_DETAILS = 0x0010;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
#define P3DISC_DEBUG 1
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/******************************************************************************************
|
|
|
|
****************************** NEW DISCOVERY *******************************************
|
|
|
|
******************************************************************************************
|
|
|
|
*****************************************************************************************/
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
p3disc::p3disc(p3AuthMgr *am, p3ConnectMgr *cm)
|
|
|
|
:p3Service(RS_SERVICE_TYPE_DISC), mAuthMgr(am), mConnMgr(cm)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
addSerialType(new RsDiscSerialiser());
|
|
|
|
|
|
|
|
mRemoteDisc = true;
|
|
|
|
mLocalDisc = false;
|
2007-12-11 20:43:17 -05:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
int p3disc::tick()
|
|
|
|
{
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
#ifdef P3DISC_DEBUG
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
static int count = 0;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
if (++count % 10 == 0)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
idServers();
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
return handleIncoming();
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
int p3disc::handleIncoming()
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
|
|
|
RsItem *item = NULL;
|
2008-02-03 01:29:02 -05:00
|
|
|
|
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::cerr << "p3disc::handleIncoming()";
|
|
|
|
std::cerr << std::endl;
|
|
|
|
#endif
|
2007-12-11 20:43:17 -05:00
|
|
|
|
|
|
|
// if off discard item.
|
2008-02-03 01:29:02 -05:00
|
|
|
if (!mRemoteDisc)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
|
|
|
while(NULL != (item = recvItem()))
|
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
#ifdef P3DISC_DEBUG
|
2007-12-11 20:43:17 -05:00
|
|
|
std::ostringstream out;
|
2008-02-03 01:29:02 -05:00
|
|
|
out << "p3disc::handleIncoming()";
|
2007-12-11 20:43:17 -05:00
|
|
|
out << " Deleting - Cos RemoteDisc Off!" << std::endl;
|
|
|
|
|
|
|
|
item -> print(out);
|
2008-02-03 01:29:02 -05:00
|
|
|
|
|
|
|
std::cerr << out.str() << std::endl;
|
|
|
|
#endif
|
2007-12-11 20:43:17 -05:00
|
|
|
|
|
|
|
delete item;
|
|
|
|
}
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
int nhandled = 0;
|
|
|
|
// While messages read
|
|
|
|
while(NULL != (item = recvItem()))
|
|
|
|
{
|
|
|
|
RsDiscItem *di = NULL;
|
|
|
|
RsDiscReply *dri = NULL;
|
|
|
|
|
|
|
|
if (NULL == (di = dynamic_cast<RsDiscItem *> (item)))
|
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
|
|
|
|
#ifdef P3DISC_DEBUG
|
2007-12-11 20:43:17 -05:00
|
|
|
std::ostringstream out;
|
2008-02-03 01:29:02 -05:00
|
|
|
out << "p3disc::handleIncoming()";
|
2007-12-11 20:43:17 -05:00
|
|
|
out << "Deleting Non RsDiscItem Msg" << std::endl;
|
|
|
|
item -> print(out);
|
2008-02-03 01:29:02 -05:00
|
|
|
|
|
|
|
std::cerr << out.str() << std::endl;
|
|
|
|
#endif
|
2007-12-11 20:43:17 -05:00
|
|
|
|
|
|
|
// delete and continue to next loop.
|
|
|
|
delete item;
|
|
|
|
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
nhandled++;
|
|
|
|
|
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::ostringstream out;
|
|
|
|
out << "p3disc::handleIncoming()";
|
|
|
|
out << " Received Message!" << std::endl;
|
|
|
|
di -> print(out);
|
|
|
|
|
|
|
|
std::cerr << out.str() << std::endl;
|
|
|
|
#endif
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
// if discovery reply then respond if haven't already.
|
2007-12-11 20:43:17 -05:00
|
|
|
if (NULL != (dri = dynamic_cast<RsDiscReply *> (di)))
|
|
|
|
{
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
recvPeerFriendMsg(dri);
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
else /* Ping */
|
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
recvPeerOwnMsg(di);
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
delete di;
|
|
|
|
}
|
|
|
|
return nhandled;
|
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
|
|
|
|
|
|
|
|
/************* from pqiMonitor *******************/
|
|
|
|
void p3disc::statusChange(const std::list<pqipeer> &plist)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::cerr << "p3disc::statusChange()";
|
|
|
|
std::cerr << std::endl;
|
|
|
|
#endif
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* get a list of all online peers */
|
|
|
|
std::list<std::string> onlineIds;
|
|
|
|
mConnMgr->getOnlineList(onlineIds);
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
std::list<pqipeer>::const_iterator pit;
|
|
|
|
/* if any have switched to 'connected' then we notify */
|
|
|
|
for(pit = plist.begin(); pit != plist.end(); pit++)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
if ((pit->state & RS_PEER_S_FRIEND) &&
|
|
|
|
(pit->actions & RS_PEER_CONNECTED))
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
/* send our details to them */
|
|
|
|
sendOwnDetails(pit->id);
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
void p3disc::respondToPeer(std::string id)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
/* get a peer lists */
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::cerr << "p3disc::respondToPeer() id: " << id;
|
|
|
|
std::cerr << std::endl;
|
|
|
|
#endif
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
std::list<std::string> friendIds;
|
|
|
|
std::list<std::string> onlineIds;
|
|
|
|
std::list<std::string>::iterator it;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
mConnMgr->getFriendList(friendIds);
|
|
|
|
mConnMgr->getOnlineList(onlineIds);
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* Check that they have DISC on */
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
/* get details */
|
|
|
|
peerConnectState detail;
|
|
|
|
if (!mConnMgr->getFriendNetStatus(id, detail))
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
/* major error! */
|
|
|
|
return;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
2008-02-03 01:29:02 -05:00
|
|
|
|
|
|
|
if (detail.visState & RS_VIS_STATE_NODISC)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
/* don't have DISC enabled */
|
|
|
|
return;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
2008-02-03 01:29:02 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
/* send them a list of all friend's details */
|
|
|
|
for(it = friendIds.begin(); it != friendIds.end(); it++)
|
|
|
|
{
|
|
|
|
/* get details */
|
|
|
|
peerConnectState detail;
|
|
|
|
if (!mConnMgr->getFriendNetStatus(*it, detail))
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
/* major error! */
|
|
|
|
continue;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
2008-02-03 01:29:02 -05:00
|
|
|
|
|
|
|
if (!(detail.visState & RS_VIS_STATE_NODISC))
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
sendPeerDetails(id, *it); /* (dest (to), source (cert)) */
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
}
|
2008-02-03 01:29:02 -05:00
|
|
|
|
|
|
|
/* send their details to all online peers */
|
|
|
|
for(it = onlineIds.begin(); it != onlineIds.end(); it++)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
peerConnectState detail;
|
|
|
|
if (!mConnMgr->getFriendNetStatus(*it, detail))
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
/* major error! */
|
|
|
|
continue;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
2008-02-03 01:29:02 -05:00
|
|
|
|
|
|
|
if (!(detail.visState & RS_VIS_STATE_NODISC))
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
sendPeerDetails(*it, id); /* (dest (to), source (cert)) */
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
2008-02-03 01:29:02 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/*************************************************************************************/
|
|
|
|
/* Output Network Msgs */
|
|
|
|
/*************************************************************************************/
|
|
|
|
void p3disc::sendOwnDetails(std::string to)
|
|
|
|
{
|
|
|
|
/* setup:
|
|
|
|
* IP local / external
|
|
|
|
* availability (TCP LOCAL / EXT, UDP ...)
|
|
|
|
*/
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
// Then send message.
|
|
|
|
{
|
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::ostringstream out;
|
|
|
|
out << "p3disc::sendOwnDetails()";
|
|
|
|
out << "Constructing a RsDiscItem Message!" << std::endl;
|
|
|
|
out << "Sending to: " << to;
|
|
|
|
std::cerr << out.str() << std::endl;
|
|
|
|
#endif
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
// Construct a message
|
|
|
|
RsDiscItem *di = new RsDiscItem();
|
|
|
|
|
|
|
|
/* components:
|
|
|
|
* laddr
|
|
|
|
* saddr
|
|
|
|
* contact_tf
|
|
|
|
* discFlags
|
|
|
|
*/
|
|
|
|
|
|
|
|
peerConnectState detail;
|
|
|
|
if (!mConnMgr->getOwnNetStatus(detail))
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
/* major error! */
|
|
|
|
return;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
// Fill the message
|
|
|
|
di -> PeerId(to);
|
|
|
|
di -> laddr = detail.localaddr;
|
|
|
|
di -> saddr = detail.serveraddr;
|
|
|
|
di -> contact_tf = 0;
|
|
|
|
|
|
|
|
/* construct disc flags */
|
|
|
|
if (!(detail.visState & RS_VIS_STATE_NODISC))
|
|
|
|
{
|
|
|
|
di->discFlags |= P3DISC_FLAGS_USE_DISC;
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
if (!(detail.visState & RS_VIS_STATE_NODHT))
|
|
|
|
{
|
|
|
|
di->discFlags |= P3DISC_FLAGS_USE_DHT;
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
if ((detail.netMode == RS_NET_MODE_EXT) ||
|
|
|
|
(detail.netMode & RS_NET_MODE_UPNP))
|
|
|
|
{
|
|
|
|
di->discFlags |= P3DISC_FLAGS_EXTERNAL_ADDR;
|
|
|
|
}
|
|
|
|
di->discFlags |= P3DISC_FLAGS_OWN_DETAILS;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* send msg */
|
|
|
|
sendItem(di);
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* (dest (to), source (cert)) */
|
|
|
|
void p3disc::sendPeerDetails(std::string to, std::string about)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
/* setup:
|
|
|
|
* Certificate.
|
|
|
|
* IP local / external
|
|
|
|
* availability ...
|
|
|
|
* last connect (0) if online.
|
|
|
|
*/
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* send it off */
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::ostringstream out;
|
|
|
|
out << "p3disc::sendPeerDetails()";
|
|
|
|
out << " Sending details of: " << about;
|
|
|
|
out << " to: " << to << std::endl;
|
|
|
|
std::cerr << out.str() << std::endl;
|
|
|
|
#endif
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
peerConnectState detail;
|
|
|
|
if (!mConnMgr->getFriendNetStatus(about, detail))
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
/* major error! */
|
|
|
|
return;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
// Construct a message
|
|
|
|
RsDiscReply *di = new RsDiscReply();
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
// Fill the message
|
|
|
|
// Set Target as input cert.
|
|
|
|
di -> PeerId(to);
|
|
|
|
di -> aboutId = about;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
// set the server address.
|
|
|
|
di -> laddr = detail.localaddr;
|
|
|
|
di -> saddr = detail.serveraddr;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
if (detail.state & RS_PEER_S_CONNECTED)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
di -> contact_tf = 0;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
2008-02-03 01:29:02 -05:00
|
|
|
else
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
di -> contact_tf = convertTDeltaToTRange(time(NULL) - detail.lastcontact);
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* construct disc flags */
|
|
|
|
di->discFlags = 0;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* NOTE we should not be sending packet if NODISC is set....
|
|
|
|
* checked elsewhere... so don't check.
|
|
|
|
*/
|
|
|
|
di->discFlags |= P3DISC_FLAGS_USE_DISC;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
if (!(detail.visState & RS_VIS_STATE_NODHT))
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
di->discFlags |= P3DISC_FLAGS_USE_DHT;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
if (detail.netMode == RS_NET_MODE_EXT)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
di->discFlags |= P3DISC_FLAGS_EXTERNAL_ADDR;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
if (detail.state & RS_PEER_S_CONNECTED)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
di->discFlags |= P3DISC_FLAGS_PEER_ONLINE;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
uint32_t certLen = 0;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
unsigned char **binptr = (unsigned char **) &(di -> certDER.bin_data);
|
|
|
|
mAuthMgr->SaveCertificateToBinary(about, binptr, &certLen);
|
|
|
|
if (certLen > 0)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
di -> certDER.bin_len = certLen;
|
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::cerr << "Cert Encoded(" << certLen << ")" << std::endl;
|
|
|
|
#endif
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::cerr << "Failed to Encode Cert" << std::endl;
|
|
|
|
#endif
|
|
|
|
di -> certDER.bin_len = 0;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
// Send off message
|
|
|
|
sendItem(di);
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::cerr << "Sent DI Message" << std::endl;
|
|
|
|
#endif
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/*************************************************************************************/
|
|
|
|
/* Input Network Msgs */
|
|
|
|
/*************************************************************************************/
|
|
|
|
void p3disc::recvPeerOwnMsg(RsDiscItem *item)
|
|
|
|
{
|
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::cerr << "p3disc::recvPeerOwnMsg() From: " << item->PeerId() << std::endl;
|
|
|
|
#endif
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* tells us their exact address (mConnectMgr can ignore if it looks wrong) */
|
|
|
|
uint32_t type = 0;
|
|
|
|
uint32_t flags = 0;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* translate flags */
|
|
|
|
if (item->discFlags & P3DISC_FLAGS_USE_DISC)
|
|
|
|
{
|
|
|
|
flags |= RS_NET_FLAGS_USE_DISC;
|
|
|
|
}
|
|
|
|
if (item->discFlags & P3DISC_FLAGS_USE_DHT)
|
|
|
|
{
|
|
|
|
flags |= RS_NET_FLAGS_USE_DHT;
|
|
|
|
}
|
|
|
|
if (item->discFlags & P3DISC_FLAGS_PEER_ONLINE)
|
|
|
|
{
|
|
|
|
flags |= RS_NET_FLAGS_ONLINE;
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* generate type */
|
|
|
|
type = RS_NET_CONN_TCP_LOCAL;
|
|
|
|
if (item->discFlags & P3DISC_FLAGS_EXTERNAL_ADDR)
|
|
|
|
{
|
|
|
|
type |= RS_NET_CONN_TCP_EXTERNAL;
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
mConnMgr->peerStatus(item->PeerId(), item->laddr, item->saddr,
|
|
|
|
type, flags, RS_CB_PERSON);
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* now reply with all details */
|
|
|
|
respondToPeer(item->PeerId());
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
addDiscoveryData(item->PeerId(), item->PeerId(),
|
|
|
|
item->laddr, item->saddr, item->discFlags, time(NULL));
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* cleanup (handled by caller) */
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
|
|
|
|
void p3disc::recvPeerFriendMsg(RsDiscReply *item)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::cerr << "p3disc::recvPeerFriendMsg() From: " << item->PeerId();
|
|
|
|
std::cerr << " About " << item->aboutId;
|
|
|
|
std::cerr << std::endl;
|
|
|
|
#endif
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* tells us their exact address (mConnectMgr can ignore if it looks wrong) */
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* load certificate */
|
|
|
|
std::string peerId;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
uint8_t *certptr = (uint8_t *) item->certDER.bin_data;
|
|
|
|
uint32_t len = item->certDER.bin_len;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
bool loaded = mAuthMgr->LoadCertificateFromBinary(certptr, len, peerId);
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
uint32_t type = 0;
|
|
|
|
uint32_t flags = 0;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* translate flags */
|
|
|
|
if (item->discFlags & P3DISC_FLAGS_USE_DISC)
|
|
|
|
{
|
|
|
|
flags |= RS_NET_FLAGS_USE_DISC;
|
|
|
|
}
|
|
|
|
if (item->discFlags & P3DISC_FLAGS_USE_DHT)
|
|
|
|
{
|
|
|
|
flags |= RS_NET_FLAGS_USE_DHT;
|
|
|
|
}
|
|
|
|
if (item->discFlags & P3DISC_FLAGS_PEER_ONLINE)
|
|
|
|
{
|
|
|
|
flags |= RS_NET_FLAGS_ONLINE;
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* generate type */
|
|
|
|
type = RS_NET_CONN_TCP_LOCAL;
|
|
|
|
if (item->discFlags & P3DISC_FLAGS_EXTERNAL_ADDR)
|
|
|
|
{
|
|
|
|
type |= RS_NET_CONN_TCP_EXTERNAL;
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
if (loaded)
|
|
|
|
{
|
|
|
|
mConnMgr->peerStatus(peerId, item->laddr,
|
|
|
|
item->saddr, type, flags, RS_CB_DISC);
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
addDiscoveryData(item->PeerId(), peerId, item->laddr, item->saddr, item->discFlags, time(NULL));
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* cleanup (handled by caller) */
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/*************************************************************************************/
|
|
|
|
/* Storing Network Graph */
|
|
|
|
/*************************************************************************************/
|
2007-12-11 20:43:17 -05:00
|
|
|
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
int p3disc::addDiscoveryData(std::string fromId, std::string aboutId,
|
|
|
|
struct sockaddr_in laddr, struct sockaddr_in raddr, uint32_t flags, time_t ts)
|
|
|
|
{
|
|
|
|
/* Store Network information */
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
std::map<std::string, autoneighbour>::iterator it;
|
|
|
|
if (neighbours.end() == (it = neighbours.find(aboutId)))
|
|
|
|
{
|
|
|
|
/* doesn't exist */
|
|
|
|
autoneighbour an;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* an data */
|
|
|
|
an.id = aboutId;
|
|
|
|
an.validAddrs = false;
|
|
|
|
an.discFlags = 0;
|
|
|
|
an.ts = 0;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
neighbours[aboutId] = an;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
it = neighbours.find(aboutId);
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* it always valid */
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* just update packet */
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
autoserver as;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
as.id = fromId;
|
|
|
|
as.localAddr = laddr;
|
|
|
|
as.remoteAddr = raddr;
|
|
|
|
as.discFlags = flags;
|
|
|
|
as.ts = ts;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
bool authDetails = (as.id == it->second.id);
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/* KEY decision about address */
|
|
|
|
if ((authDetails) ||
|
|
|
|
((!(it->second.authoritative)) && (as.ts > it->second.ts)))
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
/* copy details to an */
|
|
|
|
it->second.authoritative = authDetails;
|
|
|
|
it->second.ts = as.ts;
|
|
|
|
it->second.validAddrs = true;
|
|
|
|
it->second.localAddr = as.localAddr;
|
|
|
|
it->second.remoteAddr = as.remoteAddr;
|
|
|
|
it->second.discFlags = as.discFlags;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
(it->second).neighbour_of[fromId] = as;
|
|
|
|
|
|
|
|
/* do we update network address info??? */
|
|
|
|
return 1;
|
|
|
|
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
/*************************************************************************************/
|
|
|
|
/* Extracting Network Graph Details */
|
|
|
|
/*************************************************************************************/
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
bool p3disc::potentialproxies(std::string id, std::list<std::string> proxyIds)
|
|
|
|
{
|
|
|
|
/* find id -> and extract the neighbour_of ids */
|
|
|
|
std::map<std::string, autoneighbour>::iterator it;
|
|
|
|
std::map<std::string, autoserver>::iterator sit;
|
|
|
|
if (neighbours.end() == (it = neighbours.find(id)))
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
return false;
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
for(sit = it->second.neighbour_of.begin();
|
|
|
|
sit != it->second.neighbour_of.end(); sit++)
|
|
|
|
{
|
|
|
|
proxyIds.push_back(sit->first);
|
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
int p3disc::idServers()
|
|
|
|
{
|
|
|
|
std::map<std::string, autoneighbour>::iterator nit;
|
|
|
|
std::map<std::string, autoserver>::iterator sit;
|
|
|
|
int cts = time(NULL);
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
std::ostringstream out;
|
|
|
|
out << "::::AutoDiscovery Neighbours::::" << std::endl;
|
|
|
|
for(nit = neighbours.begin(); nit != neighbours.end(); nit++)
|
|
|
|
{
|
|
|
|
out << "Neighbour: " << (nit->second).id;
|
|
|
|
out << std::endl;
|
|
|
|
out << "-> LocalAddr: ";
|
|
|
|
out << inet_ntoa(nit->second.localAddr.sin_addr);
|
|
|
|
out << ":" << ntohs(nit->second.localAddr.sin_port) << std::endl;
|
|
|
|
out << "-> RemoteAddr: ";
|
|
|
|
out << inet_ntoa(nit->second.remoteAddr.sin_addr);
|
|
|
|
out << ":" << ntohs(nit->second.remoteAddr.sin_port) << std::endl;
|
|
|
|
out << " Last Contact: ";
|
|
|
|
out << cts - (nit->second.ts) << " sec ago";
|
|
|
|
out << std::endl;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
out << " -->DiscFlags: 0x" << std::hex << nit->second.discFlags;
|
|
|
|
out << std::dec << std::endl;
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
for(sit = (nit->second.neighbour_of).begin();
|
|
|
|
sit != (nit->second.neighbour_of).end(); sit++)
|
2007-12-11 20:43:17 -05:00
|
|
|
{
|
2008-02-03 01:29:02 -05:00
|
|
|
out << "\tConnected via: " << (sit->first);
|
2007-12-11 20:43:17 -05:00
|
|
|
out << std::endl;
|
2008-02-03 01:29:02 -05:00
|
|
|
out << "\t\tLocalAddr: ";
|
|
|
|
out << inet_ntoa(sit->second.localAddr.sin_addr);
|
|
|
|
out <<":"<< ntohs(sit->second.remoteAddr.sin_port);
|
2007-12-11 20:43:17 -05:00
|
|
|
out << std::endl;
|
2008-02-03 01:29:02 -05:00
|
|
|
out << "\t\tRemoteAddr: ";
|
|
|
|
out << inet_ntoa(sit->second.remoteAddr.sin_addr);
|
|
|
|
out <<":"<< ntohs(sit->second.remoteAddr.sin_port);
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
out << std::endl;
|
|
|
|
out << "\t\tLast Contact:";
|
|
|
|
out << cts - (sit->second.ts) << " sec ago";
|
|
|
|
out << std::endl;
|
|
|
|
out << "\t\tDiscFlags: 0x" << std::hex << (sit->second.discFlags);
|
|
|
|
out << std::dec << std::endl;
|
2007-12-11 20:43:17 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
#ifdef P3DISC_DEBUG
|
|
|
|
std::cerr << "p3disc::idServers()" << std::endl;
|
|
|
|
std::cerr << out.str();
|
|
|
|
std::cerr << std::endl;
|
|
|
|
#endif
|
2007-12-11 20:43:17 -05:00
|
|
|
|
2008-02-03 01:29:02 -05:00
|
|
|
return 1;
|
|
|
|
}
|
2007-12-11 20:43:17 -05:00
|
|
|
|
|
|
|
|
|
|
|
// tdelta -> trange.
|
|
|
|
// -inf...<0 0 (invalid)
|
|
|
|
// 0.. <9 1
|
|
|
|
// 9...<99 2
|
|
|
|
// 99...<999 3
|
|
|
|
// 999...<9999 4
|
|
|
|
// etc...
|
|
|
|
|
|
|
|
int convertTDeltaToTRange(double tdelta)
|
|
|
|
{
|
|
|
|
if (tdelta < 0)
|
|
|
|
return 0;
|
|
|
|
int trange = 1 + (int) log10(tdelta + 1.0);
|
|
|
|
return trange;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
// trange -> tdelta
|
|
|
|
// -inf...0 -1 (invalid)
|
|
|
|
// 1 8
|
|
|
|
// 2 98
|
|
|
|
// 3 998
|
|
|
|
// 4 9998
|
|
|
|
// etc...
|
|
|
|
|
|
|
|
int convertTRangeToTDelta(int trange)
|
|
|
|
{
|
|
|
|
if (trange <= 0)
|
|
|
|
return -1;
|
|
|
|
|
|
|
|
return (int) (pow(10.0, trange) - 1.5); // (int) xxx98.5 -> xxx98
|
|
|
|
}
|
|
|
|
|