From 2e728963c7ba39cf585bd463f579354010abbbd9 Mon Sep 17 00:00:00 2001 From: Olaf Rempel Date: Sun, 5 Mar 2006 02:28:19 +0100 Subject: [PATCH] daily work --- Makefile | 3 + config.cpp | 24 ++++---- config.h | 10 +-- gamelist.cpp | 12 +++- gamelist.h | 25 ++------ gameparser.cpp | 8 +-- gameparser.h | 6 +- gamescanner.cpp | 8 +-- gamescanner.h | 6 +- hlswmaster.cpp | 12 ++-- hlswserver.cpp | 57 ++++++----------- hlswserver.h | 16 ++--- logging.cpp | 4 +- mod_d3engine.cpp | 10 +-- mod_d3engine.h | 4 +- mod_gamespy1.cpp | 3 +- mod_gamespy1.h | 4 +- mod_gamespy2.cpp | 3 +- mod_gamespy2.h | 4 +- mod_halflife.cpp | 7 ++- mod_halflife.h | 4 +- mod_q3engine.cpp | 24 ++++---- mod_q3engine.h | 4 +- module.h | 7 +-- multisock.cpp | 155 ++++++----------------------------------------- multisock.h | 38 ++---------- netpkt.cpp | 71 ++++++++-------------- netpkt.h | 23 ++++--- recvqueue.cpp | 4 -- recvqueue.h | 4 +- semaphore.h | 2 +- thread.cpp | 6 +- 32 files changed, 186 insertions(+), 382 deletions(-) diff --git a/Makefile b/Makefile index eb5cebc..55b378c 100644 --- a/Makefile +++ b/Makefile @@ -16,6 +16,9 @@ hlswmaster: $(OBJS) %.d: %.cpp $(CXX) $(CFLAGS) -MM -c $< -o $@ +dist: + git-tar-tree HEAD hlswmaster-ng | gzip -9 -c > hlswmaster-ng.tar.gz + clean: rm -f hlswmaster *.d *.o *.log diff --git a/config.cpp b/config.cpp index ba67a95..ba395cb 100644 --- a/config.cpp +++ b/config.cpp @@ -43,7 +43,7 @@ bool Config::Section::addTupel(const char* name, const char* value) Tupel* t = new Tupel(name, value); tupelList.addTail(t); - + return true; } @@ -51,12 +51,12 @@ void Config::Section::show() const { Iterator* it = tupelList.createIterator(); LogSystem::log(LOG_INFO, "[%s]", name); - + while (it->hasNext()) { Tupel* t = it->next(); LogSystem::log(LOG_INFO, " %s = %s", t->name, t->value); } - + delete it; } @@ -71,7 +71,7 @@ const char* Config::Section::getTupelValue(const char* name) const break; } } - + delete it; return retval; } @@ -132,18 +132,18 @@ bool Config::parseFile(const char* name) int i = 0; char *row, *tok, *tok2; bool ret = true; - + row = new char[BUFSIZE]; if (!row) { LogSystem::log(LOG_ERROR, "config_parse(): out of memory()"); return false; } - + if (!(fz = fopen(name, "r"))) { LogSystem::log(LOG_ERROR, "config_parse(): can not open %s", name); return false; } - + while (fgets(row, BUFSIZE, fz)) { i++; @@ -168,7 +168,7 @@ bool Config::parseFile(const char* name) ret = false; break; } - + /* option */ if ((tok = strtok(row, " \n"))) { while ((tok2 = strtok(NULL, " \n"))) { @@ -177,10 +177,10 @@ bool Config::parseFile(const char* name) } } } - + fclose(fz); delete row; - + return ret; } @@ -206,7 +206,7 @@ Config::Section* Config::getSection(const char* name) const break; } } - + delete it; return retval; } @@ -250,7 +250,7 @@ Iterator* Config::createIterator(const char* section, const char* name) return new NullIterator(); - } else { + } else { return new Config::Section::SectionIterator(s, name); } } diff --git a/config.h b/config.h index 31c5ea4..54e93b5 100644 --- a/config.h +++ b/config.h @@ -18,14 +18,14 @@ public: private: class Tupel { - public: + public: Tupel(const char* name, const char* value); ~Tupel(); const char* name; const char* value; }; - + class Section { public: class SectionIterator : public Iterator { @@ -35,20 +35,20 @@ private: bool hasNext(); char* next(); void reset(); - + private: Iterator* it; Tupel* nexttup; const char* name; }; - + Section(const char* name); ~Section(); bool addTupel(const char* name, const char* option); const char* getTupelValue(const char* name) const; void show() const; - + const char* name; private: diff --git a/gamelist.cpp b/gamelist.cpp index c3ebd15..6926b54 100644 --- a/gamelist.cpp +++ b/gamelist.cpp @@ -3,6 +3,10 @@ #define DEFAULT_TIMEOUT 180 +/* +** TODO: replace list with sorted list, or even better with a hash +*/ + GameList::GameList(Config& conf) : lastUpdate(0) { @@ -12,6 +16,8 @@ GameList::GameList(Config& conf) GameList::~GameList() { + while (!glist.isEmpty()) + delete glist.get(); } void GameList::cleanup() @@ -29,11 +35,11 @@ Iterator* GameList::createIterator() return glist.createIterator(); } -void GameList::addGame(int gameid, NetPkt* pkt) +void GameList::addGame(int gameid, NetPkt* pkt, int port2) { char buf[64]; pkt->show(buf, sizeof(buf)); - LogSystem::log(LOG_NOTICE, "Adding Game %d: %s", gameid, buf); - + LogSystem::log(LOG_NOTICE, "Adding Game %d: %s %d", gameid, buf, port2); + glist.add(new GameEntry()); } diff --git a/gamelist.h b/gamelist.h index b654099..d071c5c 100644 --- a/gamelist.h +++ b/gamelist.h @@ -2,25 +2,10 @@ #define _GAMELIST_H_ #include "config.h" -#include "list.h" #include "netpkt.h" +#include "gameentry.h" #include "timerservice.h" - -class GameEntry { -public: - GameEntry() {}; - ~GameEntry() {}; - - struct in_addr addr; - int port1; - int port2; - int gameid; - -protected: - GameEntry(const GameEntry& ge); - GameEntry& operator=(const GameEntry& ge); -}; - +#include "list.h" class GameList { public: @@ -28,7 +13,7 @@ public: ~GameList(); void cleanup(); - void addGame(int gameid, NetPkt* pkt); + void addGame(int gameid, NetPkt* pkt, int port2 = 0); long getLastUpdate(); Iterator* createIterator(); @@ -43,10 +28,10 @@ private: CleanupEvent(GameList& gl) : gl(gl) {} ~CleanupEvent() {} void execute() { gl.cleanup(); } - + private: GameList& gl; - }; + }; List glist; long lastUpdate; diff --git a/gameparser.cpp b/gameparser.cpp index 75d6a0c..2f57cd5 100644 --- a/gameparser.cpp +++ b/gameparser.cpp @@ -7,10 +7,6 @@ GameParser::GameParser(RecvQueue& rxQueue, ModuleList& modList, GameList& gameLi { } -GameParser::~GameParser() -{ -} - int GameParser::execute(void* arg) { while (1) { @@ -25,10 +21,10 @@ int GameParser::execute(void* arg) case PARSE_ACCEPT: delete pkt; - + case PARSE_ACCEPT_FREED: break; - } + } } return 0; } diff --git a/gameparser.h b/gameparser.h index 8330ff5..a519475 100644 --- a/gameparser.h +++ b/gameparser.h @@ -10,10 +10,10 @@ class GameParser : public Thread { public: GameParser(RecvQueue& rxQueue, ModuleList& modlist, GameList& gameList); - ~GameParser(); - + ~GameParser() {}; + int execute(void* arg); - + protected: GameParser(const GameParser& rp); GameParser& operator=(const GameParser& rp); diff --git a/gamescanner.cpp b/gamescanner.cpp index 7f51983..57ff083 100644 --- a/gamescanner.cpp +++ b/gamescanner.cpp @@ -9,7 +9,7 @@ GameScanner::GameScanner(Config& conf, ModuleList& modList, RecvQueue& rxQueue) : modList(modList), rxQueue(rxQueue) { msock = new MultiSock(conf); - + int interval = conf.getInteger("global", "scan_interval", DEFAULT_SCAN_INTERVAL); TimerService::registerTimer(new Timer(new ScanEvent(*this), interval)); } @@ -22,9 +22,9 @@ GameScanner::~GameScanner() int GameScanner::execute(void* arg) { while (1) { - int fd = msock->waitOnSocket(); - NetPkt* pkt = NetPkt::createFromSocket(fd); - rxQueue.addPkt(pkt); + NetPkt* pkt = msock->recv(); + if (pkt) + rxQueue.addPkt(pkt); } return 0; } diff --git a/gamescanner.h b/gamescanner.h index e224ef3..7153fbf 100644 --- a/gamescanner.h +++ b/gamescanner.h @@ -13,7 +13,7 @@ class GameScanner : public Thread { public: GameScanner(Config& conf, ModuleList& modList, RecvQueue& rxQueue); ~GameScanner(); - + int execute(void* arg); void scan(); @@ -27,10 +27,10 @@ private: ScanEvent(GameScanner& gs) : gs(gs) {} ~ScanEvent() {} void execute() { gs.scan(); } - + private: GameScanner& gs; - }; + }; ModuleList& modList; RecvQueue& rxQueue; diff --git a/hlswmaster.cpp b/hlswmaster.cpp index a388a16..df4cd48 100644 --- a/hlswmaster.cpp +++ b/hlswmaster.cpp @@ -66,7 +66,7 @@ int main(int argc, char *argv[]) break; } } - + Config conf; conf.parseFile(configfile); @@ -78,7 +78,7 @@ int main(int argc, char *argv[]) } else { LogSystem::init(logprio, new StdErrLog()); } - + LogSystem::log(LOG_EVERYTIME, "hlswmaster-ng startup (pid:%d)", getpid()); conf.show(); @@ -91,11 +91,11 @@ int main(int argc, char *argv[]) HlswServer server(conf, gameList); // modList.reg(new ModHalfLife()); -// modList.reg(new ModQ3Engine()); + modList.reg(new ModQ3Engine()); // modList.reg(new ModD3Engine()); // modList.reg(new ModGameSpy1()); // modList.reg(new ModGameSpy2()); - + server.start(); parser.start(); scanner.start(); @@ -108,12 +108,12 @@ int main(int argc, char *argv[]) LogSystem::log(LOG_CRIT, "Scanner aborted!"); break; } - + if (!parser.isRunning()) { LogSystem::log(LOG_CRIT, "RecvParser aborted!"); break; } - + if (!server.isRunning()) { LogSystem::log(LOG_CRIT, "HlswServer aborted!"); break; diff --git a/hlswserver.cpp b/hlswserver.cpp index 88b9393..969a2be 100644 --- a/hlswserver.cpp +++ b/hlswserver.cpp @@ -22,10 +22,10 @@ struct hlsw_entry { } __attribute__ ((packed)); HlswServer::HlswPacket::HlswPacket(HlswPacket* next) -: next(next), count(0) +: NetPkt(1418), next(next) { - memcpy(data, hlsw_header, sizeof(hlsw_header)); - memset(data + sizeof(hlsw_header), 0, sizeof(data) - sizeof(hlsw_header)); + memcpy((void*)data, hlsw_header, sizeof(hlsw_header)); + used = sizeof(hlsw_header); } HlswServer::HlswPacket::~HlswPacket() @@ -36,39 +36,31 @@ HlswServer::HlswPacket::~HlswPacket() bool HlswServer::HlswPacket::addGame(GameEntry* ge) { - if (count >= 140) + if (used >= 1418) return false; - + struct hlsw_entry tmp; tmp.gameid = ge->gameid; tmp.ip = ge->addr.s_addr; tmp.port1 = ge->port1; tmp.port2 = ge->port2; - memcpy(data + sizeof(hlsw_header) + count * 10, &tmp, sizeof(tmp)); - count++; + memcpy((void*)(data + used), &tmp, sizeof(tmp)); + used += sizeof(tmp); return true; } -void HlswServer::HlswPacket::send(int socket, struct sockaddr_in* dst) +void HlswServer::HlswPacket::send(Socket* socket, struct sockaddr_in* dst) { if (next) next->send(socket, dst); - if (sendto(socket, data, sizeof(hlsw_header) + count * 10, 0, - (struct sockaddr *)dst, sizeof(*dst)) < 0) { - LogSystem::log(LOG_WARN, "HlswPacket::send()"); - } + socket->sendto(this, dst); } HlswServer::HlswServer(Config& conf, GameList& glist) : lastUpdate(0) { - if ((sock = socket(PF_INET, SOCK_DGRAM, 0)) < 0) { - LogSystem::log(LOG_CRIT, "HlswServer(): socket()"); - return; - } - const char *ip = conf.getString("global", "master_ip", "0.0.0.0"); LogSystem::log(LOG_NOTICE, "HlswServer listen on %s:%d", ip, HLSW_MASTER_PORT); @@ -76,44 +68,33 @@ HlswServer::HlswServer(Config& conf, GameList& glist) dst.sin_family = AF_INET; dst.sin_port = htons(HLSW_MASTER_PORT); inet_aton(ip, &dst.sin_addr); - - if (bind(sock, (struct sockaddr *)&dst, sizeof(dst)) < 0) { - LogSystem::log(LOG_ERROR, "HlswServer(): bind()"); - return; - } + socket = Socket::createSocket(&dst); int interval = conf.getInteger("global", "rebuild_interval", DEFAULT_REBUILD_INTERVAL); TimerService::registerTimer(new Timer(new RebuildEvent(*this, glist), interval)); - + pktlist = new HlswPacket(NULL); } HlswServer::~HlswServer() { - close(sock); delete pktlist; + delete socket; } int HlswServer::execute(void* arg) { - struct sockaddr_in src; - unsigned char buf[32]; - socklen_t len; - int ret; - while (1) { - /* auf clientanfrage warten */ - len = sizeof(src); - ret = recvfrom(sock, buf, sizeof(buf), 0, (struct sockaddr *)&src, &len); - - if (memcmp(buf, hlsw_header, sizeof(hlsw_header))) { + NetPkt* pkt = socket->recv(); + if (!pkt->compare(0, hlsw_header, sizeof(hlsw_header))) { LogSystem::log(LOG_NOTICE, "HlswServer: not a hlsw packet"); continue; } mutex.lock(); - pktlist->send(sock, &src); + pktlist->send(socket, pkt->getAddress()); mutex.unlock(); + } return 0; } @@ -122,7 +103,7 @@ int HlswServer::execute(void* arg) void HlswServer::rebuild(GameList& glist) { if (glist.getLastUpdate() > lastUpdate) { HlswPacket* newlist = new HlswPacket(NULL); - + Iterator* it = glist.createIterator(); while (it->hasNext()) { GameEntry* d = it->next(); @@ -133,12 +114,12 @@ void HlswServer::rebuild(GameList& glist) { } lastUpdate = glist.getLastUpdate(); delete it; - + mutex.lock(); HlswPacket* oldlist = pktlist; pktlist = newlist; mutex.unlock(); - + delete oldlist; } } diff --git a/hlswserver.h b/hlswserver.h index 9d13c49..b645133 100644 --- a/hlswserver.h +++ b/hlswserver.h @@ -6,6 +6,8 @@ #include "thread.h" #include "config.h" #include "gamelist.h" +#include "netpkt.h" +#include "socket.h" #include "mutex.h" class HlswServer : public Thread { @@ -16,7 +18,7 @@ public: int execute(void* arg); void rebuild(GameList& gl); - + protected: HlswServer(const HlswServer& hs); HlswServer& operator=(const HlswServer& hs); @@ -27,29 +29,27 @@ private: RebuildEvent(HlswServer& hs, GameList& gl) : hs(hs), gl(gl) {} ~RebuildEvent() {} void execute() { hs.rebuild(gl); } - + private: HlswServer& hs; GameList& gl; }; - - class HlswPacket { + + class HlswPacket : private NetPkt { public: HlswPacket(HlswPacket* next); ~HlswPacket(); bool addGame(GameEntry* ge); - void send(int socket, struct sockaddr_in* dst); + void send(Socket* socket, struct sockaddr_in* dst); private: HlswPacket* next; - int count; - char data[1418]; }; + Socket* socket; HlswPacket* pktlist; Mutex mutex; - int sock; long lastUpdate; }; diff --git a/logging.cpp b/logging.cpp index 1d9fcfe..70b46e8 100644 --- a/logging.cpp +++ b/logging.cpp @@ -48,7 +48,7 @@ void LogSystem::init(const char* prio, LogOutput* out) else if (!strcasecmp(prio, "INFO")) init(LOG_INFO, out); - + else if (!strcasecmp(prio, "NOTICE")) init(LOG_NOTICE, out); @@ -57,7 +57,7 @@ void LogSystem::init(const char* prio, LogOutput* out) else if (!strcasecmp(prio, "ERROR")) init(LOG_ERROR, out); - + else if (!strcasecmp(prio, "CRIT")) init(LOG_CRIT, out); diff --git a/mod_d3engine.cpp b/mod_d3engine.cpp index 398174b..f458c86 100644 --- a/mod_d3engine.cpp +++ b/mod_d3engine.cpp @@ -1,5 +1,6 @@ #include #include "netpkt.h" +#include "modhelper.h" #include "mod_d3engine.h" static struct game_ports port_arr[] = { @@ -13,16 +14,17 @@ static const char replyhead[] = "\xff\xffinfoResponse"; void ModD3Engine::scan(MultiSock* msock) { - msock->send(port_arr, scanmsg, strlen(scanmsg)); + ModHelper::send(msock, port_arr, scanmsg, strlen(scanmsg)); } int ModD3Engine::parse(NetPkt* pkt, GameList* glist) { int gameid; - - if (!(gameid = pkt->checkPortArray(port_arr))) + + gameid = ModHelper::checkPorts(pkt, port_arr); + if (!gameid) return PARSE_REJECT; - + if (pkt->compare(0, replyhead, strlen(replyhead))) return PARSE_REJECT; diff --git a/mod_d3engine.h b/mod_d3engine.h index 21712db..9df5ff0 100644 --- a/mod_d3engine.h +++ b/mod_d3engine.h @@ -7,10 +7,10 @@ class ModD3Engine : public Module { public: ModD3Engine() {} ~ModD3Engine() {} - + void scan(MultiSock* msock); int parse(NetPkt* pkt, GameList* slist); - + const char* getName() { return "Doom3 engine"; } }; diff --git a/mod_gamespy1.cpp b/mod_gamespy1.cpp index 854cea4..f6a1fe4 100644 --- a/mod_gamespy1.cpp +++ b/mod_gamespy1.cpp @@ -1,4 +1,5 @@ #include +#include "modhelper.h" #include "mod_gamespy1.h" static struct game_ports port_arr[] = { @@ -14,7 +15,7 @@ static const char scanmsg[] = "\\status\\"; void ModGameSpy1::scan(MultiSock* msock) { - msock->send(port_arr, scanmsg, strlen(scanmsg)); + ModHelper::send(msock, port_arr, scanmsg, strlen(scanmsg)); } int ModGameSpy1::parse(NetPkt* pkt, GameList* slist) diff --git a/mod_gamespy1.h b/mod_gamespy1.h index e29ef99..f0a21b5 100644 --- a/mod_gamespy1.h +++ b/mod_gamespy1.h @@ -7,10 +7,10 @@ class ModGameSpy1 : public Module { public: ModGameSpy1() {} ~ModGameSpy1() {} - + void scan(MultiSock* msock); int parse(NetPkt* pkt, GameList* glist); - + const char* getName() { return "GameSpy 1 Protocol"; } }; diff --git a/mod_gamespy2.cpp b/mod_gamespy2.cpp index 0c430c3..293dd37 100644 --- a/mod_gamespy2.cpp +++ b/mod_gamespy2.cpp @@ -1,4 +1,5 @@ #include +#include "modhelper.h" #include "mod_gamespy2.h" static struct game_ports port_arr[] = { @@ -15,7 +16,7 @@ static const char replyhead[] = { 0x00, 0xDE, 0xAD, 0xBE, 0xEF }; void ModGameSpy2::scan(MultiSock* msock) { - msock->send(port_arr, scanmsg, sizeof(scanmsg)); + ModHelper::send(msock, port_arr, scanmsg, sizeof(scanmsg)); } int ModGameSpy2::parse(NetPkt* pkt, GameList* slist) diff --git a/mod_gamespy2.h b/mod_gamespy2.h index 9a5e0eb..77dbedc 100644 --- a/mod_gamespy2.h +++ b/mod_gamespy2.h @@ -7,10 +7,10 @@ class ModGameSpy2 : public Module { public: ModGameSpy2() {} ~ModGameSpy2() {} - + void scan(MultiSock* msock); int parse(NetPkt* pkt, GameList* glist); - + const char* getName() { return "GameSpy 2 Protocol"; } }; diff --git a/mod_halflife.cpp b/mod_halflife.cpp index 0f44d32..32b802d 100644 --- a/mod_halflife.cpp +++ b/mod_halflife.cpp @@ -1,4 +1,5 @@ #include +#include "modhelper.h" #include "mod_halflife.h" static struct game_ports port_arr[] = { @@ -12,9 +13,9 @@ static const char scanmsg3[] = "\xff\xff\xff\xff""TSource Engine Query"; void ModHalfLife::scan(MultiSock* msock) { - msock->send(port_arr, scanmsg1, strlen(scanmsg1)); - msock->send(port_arr, scanmsg2, strlen(scanmsg2)); - msock->send(port_arr, scanmsg3, strlen(scanmsg3)); + ModHelper::send(msock, port_arr, scanmsg1, strlen(scanmsg1)); + ModHelper::send(msock, port_arr, scanmsg2, strlen(scanmsg2)); + ModHelper::send(msock, port_arr, scanmsg3, strlen(scanmsg3)); } int ModHalfLife::parse(NetPkt* pkt, GameList* slist) diff --git a/mod_halflife.h b/mod_halflife.h index 73da759..6d7586c 100644 --- a/mod_halflife.h +++ b/mod_halflife.h @@ -7,10 +7,10 @@ class ModHalfLife : public Module { public: ModHalfLife() {} ~ModHalfLife() {} - + void scan(MultiSock* msock); int parse(NetPkt* pkt, GameList* glist); - + const char* getName() { return "HalfLife engine"; } }; diff --git a/mod_q3engine.cpp b/mod_q3engine.cpp index 6fa2043..8caa8c3 100644 --- a/mod_q3engine.cpp +++ b/mod_q3engine.cpp @@ -1,10 +1,9 @@ #include - -#include "logging.h" +#include "modhelper.h" #include "mod_q3engine.h" static struct game_ports port_arr[] = { - { 27960, 27969, ID_Q3A }, // q3(6), ef(7), et25), rtcw(8) + { 27960, 27960, ID_Q3A }, // q3(6), ef(7), et25), rtcw(8) // { 28070, 28070, ID_JK2 }, // jk2(12) // { 28960, 28963, ID_COD }, // cod(31), cod:uo(42), cod2(48) // { 29070, 29070, ID_JK3 }, // jk3(27) @@ -30,14 +29,15 @@ static const char reply_cod2[] = "Call of Duty 2\\"; void ModQ3Engine::scan(MultiSock* msock) { - msock->send(port_arr, scanmsg, strlen(scanmsg)); + ModHelper::send(msock, port_arr, scanmsg, strlen(scanmsg)); } int ModQ3Engine::parse(NetPkt* pkt, GameList* glist) { int gameid = 0, pos1, pos2; - - if (!pkt->checkPortArray(port_arr)) + + gameid = ModHelper::checkPorts(pkt, port_arr); + if (!gameid) return PARSE_REJECT; if (!pkt->compare(0, replyhead, strlen(replyhead))) @@ -48,36 +48,36 @@ int ModQ3Engine::parse(NetPkt* pkt, GameList* glist) pos1 += strlen(search_version); if (pkt->compare(pos1, reply_q3, strlen(reply_q3))) gameid = ID_Q3A; - + else if (pkt->compare(pos1, reply_ef, strlen(reply_ef))) gameid = ID_EF; - + else if (pkt->compare(pos1, reply_rtcw, strlen(reply_rtcw))) gameid = ID_RTCW; else if (pkt->compare(pos1, reply_et, strlen(reply_et))) gameid = ID_ET; - + else if (pkt->compare(pos1, reply_jk2, strlen(reply_jk2))) gameid = ID_JK2; else if (pkt->compare(pos1, reply_jk3, strlen(reply_jk3))) gameid = ID_JK3; } - + pos2 = pkt->find(0, search_gamename, strlen(search_gamename)); if (gameid == 0 && pos2 != -1) { pos2 += strlen(search_gamename); if (pkt->compare(pos2, reply_cod, strlen(reply_cod))) gameid = ID_COD; - + else if (pkt->compare(pos2, reply_coduo, strlen(reply_coduo))) gameid = ID_COD_UO; else if (pkt->compare(pos2, reply_cod2, strlen(reply_cod2))) gameid = ID_COD2; } - + if (gameid == 0) return PARSE_REJECT; diff --git a/mod_q3engine.h b/mod_q3engine.h index ff17f49..ff4981e 100644 --- a/mod_q3engine.h +++ b/mod_q3engine.h @@ -7,10 +7,10 @@ class ModQ3Engine : public Module { public: ModQ3Engine() {} ~ModQ3Engine() {} - + void scan(MultiSock* msock); int parse(NetPkt* pkt, GameList* glist); - + const char* getName() { return "Quake3 engine"; } }; diff --git a/module.h b/module.h index b3768b3..985c847 100644 --- a/module.h +++ b/module.h @@ -2,13 +2,10 @@ #define _MODULE_H_ #include "config.h" +#include "multisock.h" #include "netpkt.h" #include "gamelist.h" -/* avoid cyclic deps, include this later.. */ -//#include "multisock.h" -class MultiSock; - enum { ID_UNKNOWN = 0, // "Unknown" ID_HL, // "Halflife" @@ -81,6 +78,4 @@ protected: Module& operator=(const Module& m); }; -#include "multisock.h" - #endif // _MODULE_H_ diff --git a/multisock.cpp b/multisock.cpp index bae0169..cf1f856 100644 --- a/multisock.cpp +++ b/multisock.cpp @@ -17,101 +17,6 @@ #define DEVFILE "/proc/net/dev" #define BUFSIZE 1024 - -MultiSock::Socket::Socket() -{ - if ((fd = socket(PF_INET, SOCK_DGRAM, 0)) < 0) - LogSystem::log(LOG_CRIT, "Socket: socket()"); -} - -MultiSock::Socket::~Socket() -{ - close(fd); -} - -bool MultiSock::Socket::bindToDevice(const char* name) -{ - strncpy(devname, name, sizeof(devname)); - - int ret = setsockopt(fd, SOL_SOCKET, SO_BINDTODEVICE, devname, sizeof(devname)); - - if (ret < 0) { - LogSystem::log(LOG_NOTICE, "Socket: setsockopt(SO_BINDTODEVICE) %s", devname); - return false; - } - - return true; -} - -bool MultiSock::Socket::bindToPort(int port) -{ - struct ifreq ifr; - - strncpy(ifr.ifr_name, devname, sizeof(ifr.ifr_name)); - - if (ioctl(fd, SIOCGIFADDR, &ifr) != 0) { - LogSystem::log(LOG_WARN, "Socket: ioctl(SIOCGIFADDR) %s", devname); - return false; - } - - memcpy(&addr, &ifr.ifr_addr, sizeof(addr)); - addr.sin_port = htons(port); - - if (bind(fd, (struct sockaddr*)&addr, sizeof(addr)) < 0) { - LogSystem::log(LOG_WARN, "Socket: bind() %s", devname); - return false; - } - - int bcast = 1; - if (setsockopt(fd, SOL_SOCKET, SO_BROADCAST, &bcast, sizeof(bcast))) { - LogSystem::log(LOG_WARN, "Socket: setsockopt(SO_BROADCAST) %s", devname); - return false; - } - - return true; -} - - -int MultiSock::Socket::show(char* buf, int size) -{ - return snprintf(buf, size, "%s (%s:%d) ", devname, - inet_ntoa(addr.sin_addr), ntohs(addr.sin_port)); -} - -MultiSock::Socket* MultiSock::Socket::createSocket(const char* name, int port) -{ - Socket* sock = new Socket(); - - if (sock->fd < 0) { - delete sock; - return NULL; - } - - struct ifreq ifr; - strncpy(ifr.ifr_name, name, sizeof(ifr.ifr_name)); - - if (ioctl(sock->fd, SIOCGIFFLAGS, &ifr) != 0) { - LogSystem::log(LOG_WARN, "Socket: ioctl(SIOCGIFFLAGS) %s", name); - delete sock; - return NULL; - } - - if (!(ifr.ifr_flags & IFF_UP) || (ifr.ifr_flags & (IFF_LOOPBACK | IFF_POINTOPOINT))) { - delete sock; - return NULL; - } - - sock->bindToDevice(name); - - if (!sock->bindToPort(port)) { - delete sock; - return NULL; - } - - return sock; -} - - MultiSock::MultiSock(Config& conf) { char* buf = new char [BUFSIZE]; @@ -126,17 +31,17 @@ MultiSock::MultiSock(Config& conf) free(buf); return; } - + fgets(buf, BUFSIZE, fp); fgets(buf, BUFSIZE, fp); - + int port = conf.getInteger("global", "scan_port", DEFAULT_PORT); Iterator* it = conf.createIterator("global", "scan_deny_iface"); FD_ZERO(&fdsel); while (fgets(buf, BUFSIZE, fp) != NULL) { char* tok = strtok(buf, " :"); - + it->reset(); while (it->hasNext()) { if (!strcmp(it->next(), tok)) { @@ -145,21 +50,21 @@ MultiSock::MultiSock(Config& conf) break; } } - + if (tok) { Socket* sock = Socket::createSocket(tok, port); if (sock) { FD_SET(sock->getFD(), &fdsel); - + sock->show(buf, BUFSIZE); LogSystem::log(LOG_NOTICE, "adding Interface %s", buf); - + ifaceList.add(sock); } } } - delete it; + fclose(fp); delete buf; @@ -173,62 +78,36 @@ MultiSock::~MultiSock() delete ifaceList.get(); } - -int MultiSock::waitOnSocket() +NetPkt* MultiSock::recv() { fd_set fdcpy; while (1) { memcpy(&fdcpy, &fdsel, sizeof(fdcpy)); - select(FD_SETSIZE, &fdcpy, NULL, NULL, NULL); - + Iterator* it = ifaceList.createIterator(); while (it->hasNext()) { Socket* sock = it->next(); if (FD_ISSET(sock->getFD(), &fdcpy)) { delete it; - return sock->getFD(); + return sock->recv(); } } delete it; - - LogSystem::log(LOG_WARN, "waitOnSocket(): select()"); + LogSystem::log(LOG_WARN, "MultiSock::recvFrom(): select()"); } - - return -1; + return NULL; } -void MultiSock::send(struct in_addr *dstip, int dport, const char* data, int size) +int MultiSock::sendto(NetPkt* pkt, struct sockaddr_in* dst) { - struct sockaddr_in addr; - addr.sin_family = AF_INET; - addr.sin_port = htons(dport); - addr.sin_addr.s_addr = (dstip ? dstip->s_addr : 0xFFFFFFFF); - Iterator* it = ifaceList.createIterator(); while (it->hasNext()) - if (sendto(it->next()->getFD(), data, size, 0, (struct sockaddr *)&addr, sizeof(addr)) < 0) - LogSystem::log(LOG_WARN, "MultiSock::send()"); - + it->next()->sendto(pkt, dst); + delete it; - + usleep(10000); -} - -void MultiSock::send(struct game_ports* arr, const char* data, int size) -{ - while (arr && arr->portlo && arr->porthi) { - int port; - for (port = arr->portlo; port <= arr->porthi; port++) - send(NULL, port, data, size); - - arr++; - } -} - -void MultiSock::send(int* arr, const char* data, int size) -{ - while (*arr) - send(NULL, *arr++, data, size); + return 0; } diff --git a/multisock.h b/multisock.h index e674078..902f4d3 100644 --- a/multisock.h +++ b/multisock.h @@ -4,52 +4,24 @@ #include #include -#include "list.h" #include "config.h" -#include "module.h" +#include "netpkt.h" +#include "socket.h" +#include "list.h" class MultiSock { public: MultiSock(Config& conf); ~MultiSock(); - void send(struct in_addr *dstip, int dport, const char* data, int size); - void send(struct game_ports* arr, const char* data, int size); - void send(int* arr, const char* data, int size); - - int waitOnSocket(); + int sendto(NetPkt* pkt, struct sockaddr_in* dst = NULL); + NetPkt* recv(); protected: MultiSock(const MultiSock& x); MultiSock& operator=(const MultiSock& x); private: - class Socket { - public: - static Socket* createSocket(const char* name, int port); - int show(char* buf, int size); - - int getFD() { return fd; } - - ~Socket(); - - protected: - Socket(const Socket& s); - Socket& operator=(const Socket& s); - - private: - Socket(); - - bool bindToDevice(const char* name); - bool bindToPort(int port); - - int fd; - char devname[IFNAMSIZ]; - struct sockaddr_in addr; - }; - - void addIface(const char* name, int port); - List ifaceList; fd_set fdsel; }; diff --git a/netpkt.cpp b/netpkt.cpp index ed21da0..95ad3e8 100644 --- a/netpkt.cpp +++ b/netpkt.cpp @@ -13,78 +13,59 @@ #include "module.h" #include "netpkt.h" +NetPkt::NetPkt(const char* data, int size) +: data(data), used(size), size(0) +{ +} + NetPkt::NetPkt(int size) -:size(size) +: used(0), size(size) { data = new char[size]; } NetPkt::~NetPkt() { - delete data; -} - -int NetPkt::readFromSocket(int fd) -{ - socklen_t i = sizeof(struct sockaddr_in); - return recvfrom(fd, this->data, this->size, 0, (struct sockaddr *)&this->addr, &i); + if (size > 0) + delete data; } int NetPkt::show(char* buf, int size) { - return snprintf(buf, size, "(%s:%d) %d bytes", + return snprintf(buf, size, "(%s:%d) (%d/%d) bytes", inet_ntoa(this->addr.sin_addr), ntohs(this->addr.sin_port), - this->size); -} - -NetPkt* NetPkt::createFromSocket(int fd) -{ - int recvsize; - - if (ioctl(fd, FIONREAD, &recvsize) == -1) { - LogSystem::log(LOG_ERROR, "NetPkt::createFromSocket()"); - return NULL; - } - - NetPkt* retval = new NetPkt(recvsize); - retval->readFromSocket(fd); - - return retval; -} - -int NetPkt::checkPortArray(struct game_ports* portarr) -{ - int myport = ntohs(this->addr.sin_port); - while (portarr && portarr->portlo) { - int port; - for (port = portarr->portlo; port <= portarr->porthi; port++) - if (port == myport) - return portarr->gameid; - - portarr++; - } - return 0; + this->used, this->size); } bool NetPkt::compare(int offset, const char* buf, int len) { - if (offset >= this->size) + if (offset >= this->used) return false; /* nicht ueber das paket hinaus vergleichen */ - if (offset + len >= this->size) - len = this->size - offset; + if (offset + len >= this->used) + len = this->used - offset; return (memcmp(this->data + offset, buf, len) == 0); } int NetPkt::find(int offset, const char *buf, int len) { - if (offset >= this->size) + if (offset >= this->used) return -1; - void* found = memmem(this->data + offset, this->size, buf, len); - + void* found = memmem(this->data + offset, this->used, buf, len); + return (found == NULL) ? -1 : ((char*)found - this->data); } + +void NetPkt::setAddress(struct sockaddr_in *tmp) +{ + memcpy(&addr, tmp, sizeof(addr)); +} + +struct sockaddr_in * NetPkt::getAddress() +{ + return &addr; +} diff --git a/netpkt.h b/netpkt.h index 3b8a4ee..6f8b69e 100644 --- a/netpkt.h +++ b/netpkt.h @@ -8,28 +8,33 @@ #define PARSE_ACCEPT_FREED 2 #define PARSE_REJECT 4 +/* avoid cyclic deps */ +class Socket; + class NetPkt { +friend class Socket; public: + NetPkt(const char* data, int size); + NetPkt(int size); ~NetPkt(); - static NetPkt* createFromSocket(int fd); int show(char* buf, int size); - - int checkPortArray(struct game_ports* arr); bool compare(int offset, const char* buf, int len); int find(int offset, const char *buf, int len); - + + void setAddress(struct sockaddr_in *addr); + struct sockaddr_in * getAddress(); + protected: NetPkt(const NetPkt& x); NetPkt& operator=(const NetPkt& x); -private: - NetPkt(int size); - int readFromSocket(int fd); - struct sockaddr_in addr; + const char *data; + int used; + +private: int size; - char *data; }; #endif // _NETPKT_H_ diff --git a/recvqueue.cpp b/recvqueue.cpp index 707629b..0c33f17 100644 --- a/recvqueue.cpp +++ b/recvqueue.cpp @@ -1,9 +1,5 @@ #include "recvqueue.h" -RecvQueue::RecvQueue() -{ -} - RecvQueue::~RecvQueue() { while (!pktList.isEmpty()) diff --git a/recvqueue.h b/recvqueue.h index 261d58e..064af64 100644 --- a/recvqueue.h +++ b/recvqueue.h @@ -7,9 +7,9 @@ class RecvQueue { public: - RecvQueue(); + RecvQueue() {}; ~RecvQueue(); - + void addPkt(NetPkt* pkt); NetPkt* getPkt(); diff --git a/semaphore.h b/semaphore.h index 7ac016d..890cd97 100644 --- a/semaphore.h +++ b/semaphore.h @@ -10,7 +10,7 @@ public: ~Semaphore() { sem_destroy(&s); } void wait() { sem_wait(&s); } void post() { sem_post(&s); } - + protected: Semaphore(const Semaphore& s); Semaphore& operator=(const Semaphore& s); diff --git a/thread.cpp b/thread.cpp index fd22759..0dc5f96 100644 --- a/thread.cpp +++ b/thread.cpp @@ -16,10 +16,10 @@ Thread::~Thread() switch (state) { case THREAD_RUNNING: cancel(); - + case THREAD_ENDED: join(); - + case THREAD_READY: break; } @@ -31,7 +31,7 @@ int Thread::start(void* arg_) if (state != THREAD_READY) return -1; - + arg = arg_; state = THREAD_RUNNING;