diff options
Diffstat (limited to 'src/core')
-rw-r--r-- | src/core/Makefile.am | 6 | ||||
-rw-r--r-- | src/core/application.cc | 202 | ||||
-rw-r--r-- | src/core/application.h | 65 | ||||
-rw-r--r-- | src/core/commandbuffer.cc | 4 | ||||
-rw-r--r-- | src/core/core.h | 12 | ||||
-rw-r--r-- | src/core/cvar.cc | 2 | ||||
-rw-r--r-- | src/core/entity.h | 2 | ||||
-rw-r--r-- | src/core/func.cc | 2 | ||||
-rw-r--r-- | src/core/gameinterface.cc | 80 | ||||
-rw-r--r-- | src/core/gameinterface.h | 52 | ||||
-rw-r--r-- | src/core/gameserver.cc | 206 | ||||
-rw-r--r-- | src/core/gameserver.h | 75 | ||||
-rw-r--r-- | src/core/module.cc | 41 | ||||
-rw-r--r-- | src/core/module.h | 74 | ||||
-rw-r--r-- | src/core/netclient.cc | 1 | ||||
-rw-r--r-- | src/core/netgame.cc | 0 | ||||
-rw-r--r-- | src/core/netgame.h | 12 | ||||
-rw-r--r-- | src/core/netserver.cc | 90 | ||||
-rw-r--r-- | src/core/player.h | 4 |
19 files changed, 563 insertions, 367 deletions
diff --git a/src/core/Makefile.am b/src/core/Makefile.am index cbe1efd..6c42468 100644 --- a/src/core/Makefile.am +++ b/src/core/Makefile.am @@ -2,13 +2,13 @@ METASOURCES = AUTO INCLUDES = -I$(top_srcdir)/src libcore_la_SOURCES = application.cc commandbuffer.cc core.cc cvar.cc entity.cc \ - func.cc gameinterface.cc netclient.cc netconnection.cc netgame.cc netserver.cc \ - player.cc + func.cc gameinterface.cc gameserver.cc module.cc netclient.cc netconnection.cc \ + netserver.cc player.cc libcore_la_LDFLAGS = -avoid-version -no-undefined libcore_la_LIBADD = $(top_builddir)/src/math/libmath.la \ $(top_builddir)/src/filesystem/libfilesystem.la $(top_builddir)/src/sys/libsys.la $(top_builddir)/src/net/libnet.la noinst_LTLIBRARIES = libcore.la noinst_HEADERS = application.h commandbuffer.h core.h cvar.h entity.h func.h \ - gameinterface.h netconnection.h netgame.h player.h + gameinterface.h gameserver.h module.h netconnection.h player.h diff --git a/src/core/application.cc b/src/core/application.cc index 5d313ad..9c7620a 100644 --- a/src/core/application.cc +++ b/src/core/application.cc @@ -18,17 +18,11 @@ #include "core/cvar.h" #include "core/entity.h" #include "core/func.h" -#include "core/netserver.h" +#include "core/gameserver.h" namespace core { -// return the global application object -Application *application() -{ - return Application::instance(); -} - // --------------- engine functions ------------------------------ void func_print(std::string const &args) { @@ -61,24 +55,7 @@ void func_disconnect(std::string const &args) application()->disconnect(); } -// FIXME this is a game function -void func_say(std::string const &args) -{ - if (application()->netserver) { - std::ostringstream osstream; - osstream << "msg public " << Player::local.name() << " " << args << "\n"; - application()->netserver->broadcast(osstream.str()); - con_print << Player::local.name() << ": " << args << "\n"; - } else if (application()->netconnection.connected()) { - std::ostringstream osstream; - osstream << args << "\n"; - application()->netconnection.send(args); - } else if (game() && game()->connected) { - con_print << args << "\n"; - } else - con_print << "Not connected."; -} - +/* void func_name(std::string const &args) { std::istringstream argstream(args); std::string name; @@ -113,6 +90,7 @@ void func_name(std::string const &args) { Player::local.player_name = name; } +*/ // --------------- signal_handler ----------------------------------- @@ -151,8 +129,8 @@ Application::Application() } application_instance = this; - netserver = 0; - gameinterface_preload = 0; + application_time = 0; + application_game = 0; sys::signal(SIGHUP, signal_handler); sys::signal(SIGINT, signal_handler); @@ -163,22 +141,6 @@ Application::Application() Application::~Application() { application_instance = 0; - } - -Application *Application::instance() -{ - return application_instance; -} - -float Application::time() const -{ - return game_time; -} - -bool Application::connected() const -{ - return (Application::instance()->netconnection.connected() || - (GameInterface::instance() && GameInterface::instance()->connected)); } void Application::init() @@ -190,24 +152,11 @@ void Application::init() CommandBuffer::init(); - gameinterface_preload = core::GameInterface::gameinterface_instance; - core::GameInterface::gameinterface_instance = 0; - if (gameinterface_preload) { - con_print << " preloaded game found: " << gameinterface_preload->name() << "\n"; - } - game_time = 0; - - // dedicated server should set this to 1 + // dedicated server has set this to 1 Cvar::sv_dedicated = Cvar::get("sv_dedicated", "0", Cvar::ReadOnly); - // client can set this to 1 Cvar::sv_private = Cvar::get("sv_private", "0"); - if (Cvar::sv_dedicated->value()) - Player::local.player_name = "Console"; - else - Player::local.player_name = "Player0"; - // network settings Cvar::net_host = Cvar::get("net_host", "0.0.0.0"); Cvar::net_port = Cvar::get("net_port", "8042"); @@ -220,8 +169,7 @@ void Application::init() Func::add("connect", func_connect); Func::add("disconnect", func_disconnect); - Func::add("say", func_say); - Func::add("name", func_name); + //Func::add("name", func_name); } void Application::shutdown() @@ -231,6 +179,11 @@ void Application::shutdown() if (connected()) disconnect(); + if (application_game) { + delete application_game; + application_game = 0; + } + // remove our engine functions Func::remove("print"); Func::remove("help"); @@ -238,9 +191,7 @@ void Application::shutdown() Func::remove("connect"); Func::remove("disconnect"); - - Func::remove("say"); - Func::remove("name"); + //Func::remove("name"); CommandBuffer::shutdown(); @@ -252,48 +203,22 @@ void Application::quit(int status) sys::quit(status); } -// clear all game realted objects -void Application::clear() -{ - // remove all entities - for (std::map<unsigned int, Entity*>::iterator it = Entity::registry.begin(); it != Entity::registry.end(); it++) { - delete (*it).second; - } - Entity::registry.clear(); - - // remove all game functions - for (std::map<std::string, Func*>::iterator it = Func::registry.begin(); it != Func::registry.end(); it++) { - if ( ((*it).second->flags() & Func::Game) == Func::Game) { - delete (*it).second; - Func::registry.erase(it); - } - } - - // remove all game cvars - for (std::map<std::string, Cvar*>::iterator it = Cvar::registry.begin(); it != Cvar::registry.end(); it++) { - if ( ((*it).second->flags() & Cvar::Game) == Cvar::Game) { - delete (*it).second; - Cvar::registry.erase(it); - } - } -} void Application::connect(std::string const &host) { - if (game() && game()->connected || netconnection.connected()) { + if (connected()) { con_warn << "Connected. Disconnect first.\n"; return; } + - if (game()) { - // unload previous game - if (game() != gameinterface_preload) - delete core::GameInterface::gameinterface_instance; + if (application_game) { + delete application_game; + application_game = 0; } - - clear(); - + if (host.size()) { + /* // connect to remote core core::GameInterface::gameinterface_instance = 0; std::string remotehost(host); @@ -316,97 +241,58 @@ void Application::connect(std::string const &host) netconnection.disconnect(); con_warn << "Could not connect to '" << host << "'\n"; } + */ + con_warn << "Can not connect to remote core.... yet!\n"; } else { - // use preloaded game - core::GameInterface::gameinterface_instance = gameinterface_preload; + application_game = new GameServer(); - // reset everything - game_time = 0; - - if (game()->connected = game()->init()) { + if (application_game->running()) { con_print << "Connected.\n"; } else { + delete application_game; + application_game = 0; con_warn << "Could not connect.\n"; - return; - } - - if (!netserver && (Cvar::sv_dedicated->value() || Cvar::sv_private->value())) { - netserver = new NetServer(Cvar::net_host->str(), (unsigned int)Cvar::net_port->value()); - if (!netserver->valid()) { - delete netserver; - if (Cvar::sv_dedicated->value()) - shutdown(); - } } } } void Application::disconnect() { - if (netserver) { - delete netserver; - netserver = 0; + + if(application_game) { + delete application_game; + application_game = 0; + con_print << "Disconnected.\n"; } + /* if (netconnection.connected()) { netconnection.disconnect(); con_print << "Disconnected.\n"; return; } - - if (game()) { - if (!game()->connected) { - con_warn << "Not connected.\n"; - return; - } - - game()->shutdown(); - game()->connected = false; - game_time = 0; - - clear(); - - con_print << "Disconnected.\n"; - } + */ } void Application::frame(float seconds) { - if (seconds == 0.0f) - return; - // execute commands in the buffer CommandBuffer::exec(); - // update entities - if (connected()) { - std::map<unsigned int, Entity *>::iterator it; - for (it=Entity::registry.begin(); it != Entity::registry.end(); it++) { - Entity *entity = (*it).second; - if ((entity->type() == Entity::Controlable) || (entity->type() == Entity::Dynamic)) { - entity->frame(seconds); - } - } - } + // don't run zero lenght time frames + if (seconds == 0.0f) + return; - // netstuff - if (netconnection.connected()) { - netconnection.frame(seconds); - // TODO this should come from server - game_time += seconds; - } else { - if (netserver) { - // TODO limit netserver frames in local mode - netserver->frame(seconds); - } + application_time += seconds; - if (game() && game()->connected) { - game_time += seconds; + if (!connected()) + return; + + // run a game interface frame + application_game->frame(seconds); - game()->frame(seconds); - } - } + if (!application_game->running()) + disconnect(); } } - diff --git a/src/core/application.h b/src/core/application.h index 0f4c5fa..de0ab35 100644 --- a/src/core/application.h +++ b/src/core/application.h @@ -25,35 +25,18 @@ public: /// default destructor virtual ~Application(); - /// initialize the application - virtual void init(); - - /// shutdown the application - virtual void shutdown(); - - /// a pointer to the current application instance - static Application *instance(); - - /// time the has been connected, in seconds - float time() const; - - /// preloaded game object - GameInterface *gameinterface_preload; - - /// true if the core is connected to a game module or a remote server - bool connected() const; +/*----- inspectors ----------------------------------------------- */ - /// network server instance - NetServer *netserver; - - /// network client to server connection - NetConnection netconnection; + /// time the application has been running + inline float time() const { return application_time; } - /// global application object - static Application *application_instance; + /// true if the core is connected to a running game interface + inline bool connected() const { return (application_game && application_game->running()); } - /// quit the application without proper shutdown - virtual void quit(int status); + /// return the game interface, returns 0 if the pplication is not connected to a game + inline GameInterface *game() { return application_game; } + +/*----- mutators ------------------------------------------------- */ /// start the server or connect to remote host void connect(std::string const &host); @@ -61,20 +44,38 @@ public: /// disconnect from the game module void disconnect(); -protected: - /// clear all game related objects - void clear(); +/*----- virtual mutators ------------------------------------------ */ + /// initialize the application + virtual void init(); + + /// shutdown the application + virtual void shutdown(); + + /// quit the application without proper shutdown + virtual void quit(int status); + +/*----- static --------------------------------------------------- */ + + /// a pointer to the current application instance + static inline Application *instance() { return application_instance; } + +protected: /// run a core frame virtual void frame(float seconds); private: /// time the core has been running - float game_time; + float application_time; + GameInterface *application_game; + static Application *application_instance; }; -/// pointer to the current ApplicationInterface -Application *application(); +/// pointer to the current Application +inline Application *application() { return Application::instance(); } + +/// pointer to the current GameInterface +inline GameInterface *game() { return Application::instance()->game(); } } // namespace core diff --git a/src/core/commandbuffer.cc b/src/core/commandbuffer.cc index 8f02f71..5ab40e5 100644 --- a/src/core/commandbuffer.cc +++ b/src/core/commandbuffer.cc @@ -9,10 +9,10 @@ #include <list> #include "sys/sys.h" +#include "core/application.h" #include "core/commandbuffer.h" #include "core/func.h" #include "core/cvar.h" -#include "core/gameinterface.h" namespace core { @@ -75,7 +75,7 @@ void CommandBuffer::exec(std::string const &cmdline) args += c; } if ((f->flags() & Func::Game)) { - if (game() && game()->connected) { + if (application()->connected()) { f->exec(&Player::local, args); } } else { diff --git a/src/core/core.h b/src/core/core.h index 4e2af22..2a23d84 100644 --- a/src/core/core.h +++ b/src/core/core.h @@ -7,22 +7,22 @@ #ifndef __INCLUDED_CORE_H__ #define __INCLUDED_CORE_H__ +/// core contains the basic functionality of the engine +namespace core +{ +} + #include "core/application.h" #include "core/commandbuffer.h" #include "core/cvar.h" #include "core/entity.h" #include "core/func.h" #include "core/gameinterface.h" +#include "core/module.h" #include "core/netserver.h" #include "core/netclient.h" #include "core/netconnection.h" #include "core/player.h" -/// core contains the basic functionality of the engine -namespace core -{ - -} - #endif // __INCLUDED_CORE_H__ diff --git a/src/core/cvar.cc b/src/core/cvar.cc index dbe1d30..9419db3 100644 --- a/src/core/cvar.cc +++ b/src/core/cvar.cc @@ -159,7 +159,7 @@ void Cvar::list() else typeindicator += ' '; - con_print << std::setw(4) << (*it).second->flags() << " " << typeindicator << + con_print << " " << typeindicator << " " << (*it).first << " " << (*it).second->str() << std::endl; } con_print << registry.size() << " registered variables" << std::endl; diff --git a/src/core/entity.h b/src/core/entity.h index 7b3f200..df16075 100644 --- a/src/core/entity.h +++ b/src/core/entity.h @@ -178,14 +178,12 @@ public: virtual void frame(float seconds); /* entity_ variables can be set by the module */ - /// owner of the entity Player *entity_owner; /// current thrust float entity_thrust; /* target_ variables can be set by the client */ - /// target thrust as set by the client float target_thrust; /// target direction as set by the client diff --git a/src/core/func.cc b/src/core/func.cc index 0215ddf..ab3a404 100644 --- a/src/core/func.cc +++ b/src/core/func.cc @@ -78,7 +78,7 @@ void Func::list() typeindicator += 'G'; else typeindicator += ' '; - con_print << std::setw(4) << (*it).second->flags() << " " << typeindicator << + con_print << " " << typeindicator << " " << (*it).second->name() << std::endl; } diff --git a/src/core/gameinterface.cc b/src/core/gameinterface.cc index 38ea6fe..908ffca 100644 --- a/src/core/gameinterface.cc +++ b/src/core/gameinterface.cc @@ -7,81 +7,57 @@ #include <stdlib.h> #include <iostream> -class GameInterface; - +#include "sys/sys.h" #include "core/application.h" +#include "core/cvar.h" +#include "core/func.h" #include "core/gameinterface.h" #include "core/player.h" -#include "sys/sys.h" namespace core { -GameInterface *game() -{ - return GameInterface::instance(); -} - -GameInterface *GameInterface::gameinterface_instance = 0; - -GameInterface::GameInterface(const char *gamename) +GameInterface::GameInterface() { - gameinterface_instance = this; - connected = false; - if (gamename) - game_name.assign(gamename); + if (Cvar::sv_dedicated->value()) + local_player.player_name.assign("Console"); else - game_name.clear(); + local_player.player_name.assign("Player0"); + clear(); } GameInterface::~GameInterface() { - gameinterface_instance = 0; -} - -GameInterface *GameInterface::instance() -{ - return gameinterface_instance; + clear(); } -std::string const &GameInterface::name() +// clear all game related objects +void GameInterface::clear() { - return game_name; -} + con_debug << "Clearing game data\n"; -void message_broadcast(std::string const & message, int ignoreplayer) -{ - // send to console - con_print << message << std::endl; - - // broadcast to remote clients - if (application()->netserver) { - std::string netmessage("msg info "); - netmessage.append(message); - netmessage += '\n'; - - application()->netserver->broadcast(netmessage, ignoreplayer); + // remove all entities + for (std::map<unsigned int, Entity*>::iterator it = Entity::registry.begin(); it != Entity::registry.end(); it++) { + delete (*it).second; } -} + Entity::registry.clear(); -void message_send(Player const *player, const char *protohdr, std::string message) -{ - // send to console - if (player == &Player::local) { - con_print << message << std::endl; + // remove all game functions + for (std::map<std::string, Func*>::iterator it = Func::registry.begin(); it != Func::registry.end(); it++) { + if ( ((*it).second->flags() & Func::Game) == Func::Game) { + delete (*it).second; + Func::registry.erase(it); + } } - // send to remote clients - if (application()->netserver) { - NetClient *client = application()->netserver->find_client(player); - if (client) { - std::string netmessage("msg info "); - netmessage.append(message); - netmessage += '\n'; - - application()->netserver->send(client, message); + // remove all game cvars + for (std::map<std::string, Cvar*>::iterator it = Cvar::registry.begin(); it != Cvar::registry.end(); it++) { + if ( ((*it).second->flags() & Cvar::Game) == Cvar::Game) { + delete (*it).second; + Cvar::registry.erase(it); } } } + } // namespace core diff --git a/src/core/gameinterface.h b/src/core/gameinterface.h index 9eb6880..5e1f9be 100644 --- a/src/core/gameinterface.h +++ b/src/core/gameinterface.h @@ -12,55 +12,41 @@ namespace core { -/// broadcast a network message to all players -void message_broadcast(std::string const & message, int ignoreplayer=-1); - -/// send a message to a player -void message_send(Player &player, std::string const & message); - /// abstract interface from the core to the game-specific code class GameInterface { public: /// create a new game - GameInterface(const char *gamename = 0); + GameInterface(); + /// destroy the game virtual ~GameInterface(); - - /// a pointer to the current game instance - static GameInterface * instance(); - - /// true if the game is ready and running - bool connected; - - /// run one frame of the game - /// @param sec time since the previous frame, in seconds - virtual void frame(float seconds) = 0; - /// initialize the game - virtual bool init() = 0; +/*----- inspectors ---------------------------------------------- */ - /// shutdown the game - virtual void shutdown() = 0; + /// return the local player + inline Player *localplayer() { return &local_player; } + +/*----- virtual inspectors --------------------------------------- */ - /// is called when a player connects - virtual void player_connect(Player *player) = 0; + /// returns true if the game server can run a time frime + virtual bool running() = 0; - /// is called when a player disconnects - virtual void player_disconnect(Player *player) = 0; +/*----- mutators ------------------------------------------------- */ - static GameInterface *gameinterface_instance; + /// clear all game variables, game functions and entities + void clear(); - /// the name of the game - std::string const & name(); +/*----- virtual mutators ------------------------------------------ */ + + /// run one game time frame + /// @param sec time since the previous frame, in seconds + virtual void frame(float seconds) = 0; -private: - std::string game_name; +protected: + Player local_player; }; -/// pointer to the current GameInterface -GameInterface *game(); - } #endif // __INCLUDED_CORE_GAMEINTERFACE_H__ diff --git a/src/core/gameserver.cc b/src/core/gameserver.cc new file mode 100644 index 0000000..6c84d3e --- /dev/null +++ b/src/core/gameserver.cc @@ -0,0 +1,206 @@ +/* + core/gameserver.h + This file is part of the Osirion project and is distributed under + the terms of the GNU General Public License version 2 +*/ + +#include "sys/sys.h" +#include "core/cvar.h" +#include "core/func.h" +#include "core/gameserver.h" +#include "core/netserver.h" + +namespace core +{ + +void func_say(Player *player, std::string const &args) +{ + server()->say(player, args); +} + +GameServer *GameServer::server_instance = 0; + +GameServer::GameServer() : GameInterface() +{ + con_print << "Initializing game server...\n"; + server_instance = this; + server_network = 0; + + server_module = Module::preload(); + if (!server_module) { + con_error << "No module loaded.\n"; + abort(); + return; + } + + server_module->init(); + if (!server_module->running()) { + con_error << "Could not initialize module '" << server_module->name() << "'\n"; + abort(); + return; + } + + con_print << " module '" << server_module->name() << "'\n"; + + if ((Cvar::sv_dedicated->value() || Cvar::sv_private->value())) { + server_network = new NetServer(Cvar::net_host->str(), (unsigned int) Cvar::net_port->value()); + if (!server_network->valid()) { + delete server_network; + server_network = 0; + con_error << "Could not initialize network server\n"; + abort(); + return; + } + } else { + con_debug << "Network server disabled.\n"; + server_network = 0; + } + + Func::add("say", (GameFuncPtr) func_say); + + if (!Cvar::sv_dedicated->value()) + player_connect(localplayer()); + + server_running = true; +} + +GameServer::~GameServer() +{ + server_running = false; + + con_print << "Shutting down game server...\n"; + + if (server_network) { + delete server_network; + server_network = 0; + } + + if (!Cvar::sv_dedicated->value()) + player_disconnect(localplayer()); + + if (server_module) { + server_module->shutdown(); + + if (server_module != Module::preload()) + delete server_module; + } + + Func::remove("say"); + server_instance = 0; +} + +bool GameServer::running() +{ + return server_running; +} + +void GameServer::abort() +{ + server_running = false; +} + +void GameServer::say(Player *player, std::string const &message) +{ + // send to console + con_print <<player->name() << " " << message << "\n"; + + // broadcast to remote clients + if (server_network != 0 ) { + std::string netmessage("msg public "); + netmessage.append(player->name()); + netmessage += ' '; + netmessage.append(message); + netmessage += '\n'; + server_network->broadcast(netmessage); + } +} + +void GameServer::broadcast(std::string const & message, int ignoreplayer) +{ + // send to console + con_print << message << "\n"; + + // broadcast to remote clients + if (server_network) { + std::string netmessage("msg info "); + netmessage.append(message); + netmessage += '\n'; + server_network->broadcast(netmessage, ignoreplayer); + } +} + +void GameServer::send(Player const *player, std::string message) +{ + // send to console + if (player->id() == localplayer()->id()) { + con_print << message << "\n"; + } + + // send to remote clients + if (server_network) { + NetClient *client = server_network->find_client(player); + if (client) { + std::string netmessage("msg info "); + netmessage.append(message); + netmessage += '\n'; + server_network->send(client, netmessage); + } + } +} + +void GameServer::player_connect(Player *player) +{ + std::string message(player->name()); + message.append(" connects."); + broadcast(message, player->id()); + + // TODO transferplayer info, transfer entities + + // notify the game module + server_module->player_connect(player); +} + +void GameServer::player_disconnect(Player *player) +{ + std::string message(player->name()); + message.append(" disconnects."); + broadcast(message, player->id()); + + // notify the game module + server_module->player_disconnect(player); +} + +void GameServer::frame(float seconds) +{ + if (error()) + return; + + // process incoming network messages + if (server_network != 0 ) { + server_network->frame(seconds); + if (server_network->error()) { + abort(); + return; + } + } + + // update entities + std::map<unsigned int, Entity *>::iterator it; + for (it=Entity::registry.begin(); it != Entity::registry.end(); it++) { + Entity *entity = (*it).second; + if ((entity->type() == Entity::Controlable) || (entity->type() == Entity::Dynamic)) { + entity->frame(seconds); + } + } + + if (server_module) { + server_module->frame(seconds); + if (server_module->error()) { + abort(); + return; + } + } +} + + +} diff --git a/src/core/gameserver.h b/src/core/gameserver.h new file mode 100644 index 0000000..ba64f2e --- /dev/null +++ b/src/core/gameserver.h @@ -0,0 +1,75 @@ +/* + core/gameserver.h + This file is part of the Osirion project and is distributed under + the terms of the GNU General Public License version 2 +*/ + +#ifndef __INCLUDED_CORE_GAMESERVER_H__ +#define __INCLUDED_CORE_GAMESERVER_H__ + +#include "core/gameinterface.h" +#include "core/module.h" +#include "core/netserver.h" + +namespace core +{ + +/// the core game server +/** the core game server runs the game module. Network access is enabled + * for the dedicated server or the client with private server enabled. + */ +class GameServer : public GameInterface +{ +public: + GameServer(); + ~GameServer(); + +/*----- inspectors ------------------------------------------------ */ + + /// returns true if the game server can run a time frime + bool running(); + + /// returns true if the game server can not run a time frime + inline bool error() { return !server_running; } + +/*----- mutators -------------------------------------------------- */ + + /// is called when a player connects to the game server + void player_connect(Player *player); + + /// a caleld when a player disconnects from the game server + void player_disconnect(Player *player); + + /// run a game server time frame + void frame(float seconds); + + /// a player sends a chat message on the public channel + void say(Player *player, std::string const &args); + + /// broadcast a message to all players + void broadcast(std::string const & message, int ignoreplayer = -1); + + /// send a message to a single player + void send(Player const *player, std::string message); + +/*----- static ---------------------------------------------------- */ + + /// retuen the current game server + static inline GameServer *instance() { return server_instance; } + +protected: + /// abort runing + void abort(); +private: + bool server_running; + Module *server_module; + static GameServer *server_instance; + NetServer *server_network; + +}; + +inline GameServer *server() { return GameServer::instance(); } + +} + +#endif // __INCLUDED_CORE_GAMESERVER_H__ diff --git a/src/core/module.cc b/src/core/module.cc new file mode 100644 index 0000000..45559f2 --- /dev/null +++ b/src/core/module.cc @@ -0,0 +1,41 @@ +/* + core/module.cc + This file is part of the Osirion project and is distributed under + the terms of the GNU General Public License version 2 +*/ + +#include "core/module.h" + +namespace core +{ + +Module *Module::module_preload; + +Module::Module(const char *name) +{ + module_running = false; + module_name.assign(name); + module_preload = 0; +} + +Module::~Module() +{ + module_running = false; + module_name.clear(); +} + + +void Module::load(Module *module) +{ + module_preload = module; +} + +void Module::unload() +{ + if (module_preload) { + delete module_preload; + module_preload = 0; + } +} + +} diff --git a/src/core/module.h b/src/core/module.h new file mode 100644 index 0000000..053c9e5 --- /dev/null +++ b/src/core/module.h @@ -0,0 +1,74 @@ +/* + core/module.h + This file is part of the Osirion project and is distributed under + the terms of the GNU General Public License version 2 +*/ + +#ifndef __INCLUDED_CORE_MODULE_H__ +#define __INCLUDED_CORE_MODULE_H__ + +#include <string> +#include "core/player.h" + +namespace core +{ + +// a loadable game module +class Module +{ +public: + Module(const char *name); + virtual ~Module(); + +/*----- inspectors ------------------------------------------------ */ + /// return true if the game module can run a timeframe + inline bool running() const { return module_running; } + + /// return true if the game module can not run a timeframe + inline bool error() const { return !module_running; } + + /// return the name of the module + inline std::string const & name() const { return module_name; } + +/*----- mutators -------------------------------------------------- */ + + /// initialize the game module + virtual void init() = 0; + + /// shutdown the game module + virtual void shutdown() = 0; + + /// run one timeframe + virtual void frame(float seconds) = 0; + + /// is called when a player connects + virtual void player_connect(Player *player) = 0; + + /// is called when a player disconnects + virtual void player_disconnect(Player *player) = 0; + +/*----- static ---------------------------------------------------- */ + + /// load a game module + static void load(Module *module); + + /// unload the preloaded module + static void unload(); + + /// the preloaded module + inline static Module *preload() { return module_preload; }; + +protected: + /// set the disconnected state + void abort(); + bool module_running; + +private: + static Module *module_preload; + std::string module_name; + +}; + +} + +#endif // __INCLUDED_CORE_MODULE_H__ diff --git a/src/core/netclient.cc b/src/core/netclient.cc index 61a3e64..7b5d554 100644 --- a/src/core/netclient.cc +++ b/src/core/netclient.cc @@ -26,7 +26,6 @@ NetClient::NetClient(int clientfd, std::string host, int port) : client_host = host; client_port = port; - //con_debug << "NetClient " << fd() << ": starting." << std::endl; } NetClient::~NetClient() diff --git a/src/core/netgame.cc b/src/core/netgame.cc deleted file mode 100644 index e69de29..0000000 --- a/src/core/netgame.cc +++ /dev/null diff --git a/src/core/netgame.h b/src/core/netgame.h deleted file mode 100644 index e55e8c6..0000000 --- a/src/core/netgame.h +++ /dev/null @@ -1,12 +0,0 @@ -/* - core/netgame.h - This file is part of the Osirion project and is distributed under - the terms of the GNU General Public License version 2 -*/ - -#ifndef __INCLUDED_CORE_GAMEINTERFACE_H__ -#define __INCLUDED_CORE_GAMEINTERFACE_H__ - -#include "core/player.h" - -#endif
\ No newline at end of file diff --git a/src/core/netserver.cc b/src/core/netserver.cc index 39548dd..ba8510d 100644 --- a/src/core/netserver.cc +++ b/src/core/netserver.cc @@ -8,6 +8,7 @@ #include <sstream> #include "sys/sys.h" +#include "core/gameserver.h" #include "core/netclient.h" #include "core/netserver.h" #include "core/cvar.h" @@ -20,6 +21,7 @@ namespace core NetServer::NetServer(std::string const host, unsigned int const port) : net::TCPServer(host, port) { + //con_print << "Initializing network server..." << std::endl; FD_ZERO(&serverset); // add the listening socket to the file descriptor set FD_SET(fd(), &serverset); @@ -29,16 +31,16 @@ NetServer::NetServer(std::string const host, unsigned int const port) : NetServer::~NetServer() { - con_print << "Shutting down network..." << std::endl; + con_print << "Shutting down network server..." << std::endl; // delete all clients std::list<NetClient *>:: iterator it; for (it = clients.begin(); it != clients.end(); it++) { - // notify the game - if (game() && game()->connected) { - core::game()->player_disconnect((*it)->player()); - con_print << (*it)->player()->name() << " disconnected."<< std::endl; - } + // notify the game server + server()->player_disconnect((*it)->player()); + + con_print << " " << (*it)->host() << ":" << (*it)->port() << " disconnected.\n"; + delete (*it); } clients.clear(); @@ -48,8 +50,7 @@ void NetServer::client_connect(int const clientfd, std::string const host, int c { NetClient *client = new NetClient(clientfd, host, port); if (client->error()) { - con_warn << "Client " << client->fd() << " " << - client->host() << ":" << client->port() << " connection failed!" << std::endl; + con_warn << client->host() << ":" << client->port() << " connection failed!\n"; delete(client); return; } @@ -57,20 +58,11 @@ void NetServer::client_connect(int const clientfd, std::string const host, int c clients.push_back(client); FD_SET(client->fd(), &serverset); - // TODO send infos - con_print << client->host() << ":" << client->port() << " " << client->player()->name() << " connected."<< std::endl; + con_print << client->host() << ":" << client->port() << " connected.\n"; - // BROADCAST connect message - std::ostringstream osstream; - osstream << "msg info " << client->player()->name() << " connected."<< std::endl; - broadcast(osstream.str(), clientfd); + // notify the game server + server()->player_connect(client->player()); - // notify the game - if (game() && game()->connected) { - core::game()->player_connect(client->player()); - } else { - // TODO send disconnect message and remove client - } } // remove disconnected clients @@ -82,16 +74,9 @@ void NetServer::reap() if (client->error()) { FD_CLR(client->fd(), &serverset); - // BROADCAST disconnect message - std::ostringstream osstream; - osstream << "msg info " << client->player()->name() << " disconnected."<< std::endl; - broadcast(osstream.str()); - - // notify the game - if (core::game()) - core::game()->player_disconnect(client->player()); - - con_print << client->player()->name() << " disconnected."<< std::endl; + // notify the game server + server()->player_disconnect((*it)->player()); + con_print << client->host() << ":" << client->port() << " disconnected.\n"; // remove the client clients.erase(it); @@ -118,7 +103,7 @@ void NetServer::frame(float seconds) { if (nb == -1) { con_error << "Network error on select()" << std::endl; - perror("select"); + //perror("select"); abort(); } @@ -244,40 +229,21 @@ void NetServer::parse_incoming_message(NetClient *client, const std::string & me } // execute game functions - if (game() && game()->connected) { - Func *function = Func::find(command); - if (function ) { - std::string args; - char c; - if (msgstream >> args) - while (msgstream >> c) - args += c; - if (function ->flags() && Func::Game) { - function->exec(client->player(), args); - } else { - // instant rcon - //function->exec(args); - } + Func *function = Func::find(command); + if (function ) { + std::string args; + char c; + if (msgstream >> args) + while (msgstream >> c) + args += c; + if (function ->flags() && Func::Game) { + function->exec(client->player(), args); + } else { + // FIXME instant rcon + function->exec(args); } } -} -void NetServer::parse_client_variable(NetClient * client, const std::string varname, std::istringstream &istringstream) -{ - if (varname=="name") { - std::string name; - if (istringstream >> name) { - std::ostringstream osstream; - if (name.size() > 16) - name = name.substr(0,16); - if (name != client->player()->name()) { - osstream << "msg info " << client->player()->name() << " renamed to " << name << "\n"; - broadcast(osstream.str()); - client->player()->player_name = name; - } - } - return; - } } } diff --git a/src/core/player.h b/src/core/player.h index e19b8ae..490515d 100644 --- a/src/core/player.h +++ b/src/core/player.h @@ -30,10 +30,10 @@ public: inline std::string const &name() const { return player_name; } /// id of the player - inline unsigned int id() const { return player_id; } + inline int id() const { return player_id; } /// id of the player - unsigned int player_id; + int player_id; /// name of the player std::string player_name; |