/** ** File ......... MyHandler.cpp ** Published .... 2004-04-18 ** Author ....... grymse@alhem.net **/ /* Copyright (C) 2004 Anders Hedstrom This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program 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 General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ #ifdef _WIN32 #pragma warning(disable:4786) #endif //#include #include #include "MyTcpSocket.h" #include "config.h" #include "MyHandler.h" #ifdef _WIN32 //#define random rand #endif #define DEB(x) MyHandler::MyHandler() :SocketHandler() { } MyHandler::~MyHandler() { } void MyHandler::CheckTimeout() { bool ok = true; for (app_m::iterator it = m_app.begin(); it != m_app.end() && ok; it++) for (host_v::iterator i2 = (*it).second.begin(); i2 != (*it).second.end() && ok; i2++) { HOST *p = *i2; if (p) { if (time(NULL) - p -> t > 15 * 60 + 10) { unreg_host( (*it).first, p -> id,p -> ip,p -> port,p -> ip); ok = false; } } } } HOST * MyHandler::reg_host(const std::string& app,const std::string& id,ipaddr_t ip,port_t port,ipaddr_t ip_minion,unsigned long& hostid,long hid_from_host) { for (host_v::iterator it = m_app[app].begin(); it != m_app[app].end(); it++) { HOST *p = *it; if (!strcmp(id.c_str(),p -> id.c_str()) && p -> ip == ip && p -> port == port) { hostid = p -> host_id; p -> t = time(NULL); return p; } } HOST *p = new HOST(id,ip,port); if (hid_from_host) { p -> host_id = hostid = hid_from_host; } else { p -> host_id = hostid = atol(config["next_host_id"].c_str()); //m_host_id++; config["next_host_id"] = Utility::l2string(hostid + 1); write_config(); } p -> t = time(NULL); if (ip != ip_minion) p -> behind_firewall = true; m_app[app].push_back(p); ViewHosts(); return p; } void MyHandler::unreg_host(const std::string& app,const std::string& id,ipaddr_t ip,port_t port,ipaddr_t ip_minion) { for (host_v::iterator it = m_app[app].begin(); it != m_app[app].end(); it++) { HOST *p = *it; if (!strcmp(id.c_str(),p -> id.c_str()) && p -> ip == ip && p -> port == port) { delete p; m_app[app].erase(it); ViewHosts(); break; } } } HOST* MyHandler::GetRandomHOST(const std::string& app,bool must) { if (must) { int q = 0; for (host_v::iterator it = m_app[app].begin(); it != m_app[app].end(); it++) { HOST *p = *it; if (p -> connectable) { q++; break; } } if (q) { #ifdef _WIN32 int x = rand() % m_app[app].size(); #else int x = random() % m_app[app].size(); #endif HOST *p = m_app[app][x]; while (!p -> connectable) { #ifdef _WIN32 x = rand() % m_app[app].size(); #else x = random() % m_app[app].size(); #endif p = m_app[app][x]; } return p; } } else { if (m_app[app].size()) { #ifdef _WIN32 return m_app[app][rand() % m_app[app].size()]; #else return m_app[app][random() % m_app[app].size()]; #endif } } return NULL; } void MyHandler::reset_sent(const std::string& app) { for (host_v::iterator it = m_app[app].begin(); it != m_app[app].end(); it++) { HOST *p = *it; p -> sent = false; } } #define DEB(x) x void MyHandler::ViewHosts() { DEB( printf("Current minion list\n");) for (app_m::iterator it = m_app.begin(); it != m_app.end(); it++) { DEB( printf(" %s\n",(*it).first.c_str());) for (host_v::iterator i2 = (*it).second.begin(); i2 != (*it).second.end(); i2++) { HOST *p = *i2; DEB( printf(" %ld %08x:%d %s%s%s\n", p -> host_id,p -> ip,p -> port,p -> id.c_str(), p -> behind_firewall ? " (nat)" : "", p -> connectable ? " Connectable" : "");) } } }