PongHandler.cpp

Go to the documentation of this file.
00001 /*
00002 
00003 Copyright (C) 2006-2007 by Peter Dimov.
00004 
00005 This file is part of Calitko (http://www.calitko.org).
00006 
00007 Calitko is free software; you can redistribute it and/or modify
00008 it under the terms of the GNU General Public License as published by
00009 the Free Software Foundation; either version 2 of the License, or
00010 (at your option) any later version.
00011 
00012 Calitko is distributed in the hope that it will be useful,
00013 but WITHOUT ANY WARRANTY; without even the implied warranty of
00014 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00015 GNU General Public License for more details.
00016 
00017 You should have received a copy of the GNU General Public License
00018 along with Calitko; if not, write to the Free Software
00019 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
00020 
00021 */
00022 
00023 #include "Qt.h"
00024 #include "PongHandler.h"
00025 #include "NodeCache.h"
00026 #include "UdpHostCache.h"
00027 #include "Imports.cpp"
00028 
00029 using namespace Gnutella::Bootstrapping;
00030 
00031 PongHandler::PongHandler (LocalPeer *localPeer)
00032  :  d()
00033 {
00034     d.nodeCache     = localPeer->nodeCache();
00035     d.udpHostCache  = localPeer->udpHostCache();
00036 }
00037 
00038 PongHandler::~PongHandler()
00039 {
00040 }
00041 
00042 void PongHandler::processPong (const Pong &pong)
00043 {
00044     NodeInfo nodeInfo;
00045     nodeInfo.address = NodeAddress (pong.ipAddress(), pong.port());
00046     NodeCache::NodeAvailability availability = NodeCache::UnknownAvailability;
00047     // Distinguish between pongs that are surely connectable, s.a. directly
00048     //connected neighbors and such that are merely forwarded by a neighbor.
00049     // \todo Does the above make sence now when the UDP pongs are also
00050     // flowed through here?
00051     if (pong.hops() == 0)
00052         availability = NodeCache::NodeAvailable;
00053 
00054     using Gnutella::Packets::Extensions::Ggeps::DailyUptime;
00055     const DailyUptime *ggepDailyUptime = DailyUptime::findIn (pong.ggepBlock());
00056     if (ggepDailyUptime != 0) {
00057         nodeInfo.dailyUptime = ggepDailyUptime->dailyUptime();
00058     }
00059 
00060     using Gnutella::Packets::Extensions::Ggeps::Ultrapeer;
00061     const Ultrapeer *ultrapeer = Ultrapeer::findIn (pong.ggepBlock());
00062     if (ultrapeer != 0) {
00063         nodeInfo.type = TypeUltrapeer;
00064         nodeInfo.freeUltrapeerSlots = ultrapeer->ultrapeerSlots();
00065         nodeInfo.freeLeafSlots = ultrapeer->leafSlots();
00066         nodeInfo.serventVersion = Utils::Version (ultrapeer->version());
00067     }
00068 
00069     using Gnutella::Packets::Extensions::Ggeps::VendorCode;
00070     const VendorCode *vendorCode = VendorCode::findIn (pong.ggepBlock());
00071     if (vendorCode != 0) {
00072         nodeInfo.vendorCode = vendorCode->vendorCode();
00073         nodeInfo.serventVersion = Version (vendorCode->version());
00074     }
00075 
00076     using Gnutella::Packets::Extensions::Ggeps::IpPort;
00077     const IpPort *ipPort = IpPort::findIn (pong.ggepBlock());
00078     if (ipPort != 0) {
00079         foreach (NodeAddress address, ipPort->addresses()) {
00080             if (address == NodeAddress::Null)
00081                 continue;
00082             NodeInfo nodeInfo;
00083             nodeInfo.type = TypeUltrapeer; // \todo depends on the SCP we sent!
00084             nodeInfo.address = address;
00085             d.nodeCache->addNode (nodeInfo, NodeCache::UnknownAvailability);
00086         }
00087     }
00088 
00089     using Gnutella::Packets::Extensions::Ggeps::PackedHostCaches;
00090     const PackedHostCaches *phc = PackedHostCaches::findIn (pong.ggepBlock());
00091     if (phc != 0) {
00092         foreach (NodeAddress address, phc->addresses()) {
00093             qDebug () << "PHC " << address.hostAddress().toString()
00094                       << pong.port() << address.hostPort();
00095             d.udpHostCache->addCache (address);
00096         }
00097     }
00098 
00099     using Gnutella::Packets::Extensions::Ggeps::UdpHostCache;
00100     const UdpHostCache *udphc = UdpHostCache::findIn (pong.ggepBlock());
00101     // The pong is either for a normal host or an UdpHostCache
00102     if (udphc != 0) {
00103         // \todo Add to udp host cache
00104         qDebug () << "UDPHC " << pong.ipAddress().toString()
00105                   << pong.port() << udphc->hostName();
00106         NodeAddress uhcAddress;
00107         uhcAddress.setHostName (udphc->hostName());
00108         uhcAddress.setHostPort (pong.port());
00109         d.udpHostCache->addCache (uhcAddress);
00110     } else if (nodeInfo.address != NodeAddress::Null) {
00111         d.nodeCache->addNode (nodeInfo, availability);
00112     }
00113 }