From 6c5e9e37e06d9e216ce2a8bd7040c2ca06cd5943 Mon Sep 17 00:00:00 2001 From: "Ignacio R. Morelle" Date: Tue, 24 Jun 2014 20:29:17 -0400 Subject: [PATCH 1/6] campaignd: Print the destination IP in the send_error() call --- src/campaign_server/campaign_server.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/campaign_server/campaign_server.cpp b/src/campaign_server/campaign_server.cpp index 9082593e698b..bab5bf618ef1 100644 --- a/src/campaign_server/campaign_server.cpp +++ b/src/campaign_server/campaign_server.cpp @@ -238,7 +238,7 @@ void server::send_error(const std::string& msg, network::connection sock) { config cfg; cfg.add_child("error")["message"] = msg; - LOG_CS << "ERROR: " << msg << '\n'; + LOG_CS << "ERROR [" << network::ip_address(sock) << "]: " << msg << '\n'; network::send_data(cfg, sock); } From 6b8e42dfe277846ef6fadd03469de0552bd15ec6 Mon Sep 17 00:00:00 2001 From: "Ignacio R. Morelle" Date: Tue, 24 Jun 2014 20:30:25 -0400 Subject: [PATCH 2/6] campaignd: Add a typedef for the handlers map --- src/campaign_server/campaign_server.hpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/campaign_server/campaign_server.hpp b/src/campaign_server/campaign_server.hpp index cc4e64cd179e..c2b7c4d841c0 100644 --- a/src/campaign_server/campaign_server.hpp +++ b/src/campaign_server/campaign_server.hpp @@ -84,6 +84,7 @@ class server : private boost::noncopyable }; typedef boost::function request_handler; + typedef std::map request_handlers_table; config cfg_; const std::string cfg_file_; @@ -94,7 +95,7 @@ class server : private boost::noncopyable boost::scoped_ptr input_; /**< Server control socket. */ std::map hooks_; - std::map handlers_; + request_handlers_table handlers_; std::string feedback_url_format_; From df54918c362998fce482fd6b72f5739d9a774215 Mon Sep 17 00:00:00 2001 From: "Ignacio R. Morelle" Date: Tue, 24 Jun 2014 20:31:07 -0400 Subject: [PATCH 3/6] campaignd: Use find() to locate a request handler Makes it so for each request received we use request_handlers_table::find() instead of a plain linear search to find the handler, using the tag name of the first WML child node we can find, instead of trying to locate one with a known handler id. In theory this allows taking advantage of the request_handlers_table type's (currently a std::map) own lookup mechanism. --- src/campaign_server/campaign_server.cpp | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/src/campaign_server/campaign_server.cpp b/src/campaign_server/campaign_server.cpp index bab5bf618ef1..9454c142f844 100644 --- a/src/campaign_server/campaign_server.cpp +++ b/src/campaign_server/campaign_server.cpp @@ -278,13 +278,18 @@ void server::run() while((sock = network::receive_data(data, 0)) != network::null_connection) { - typedef std::pair rh_table_entry; - BOOST_FOREACH(const rh_table_entry& rh, handlers_) - { - const config& req_body = data.child(rh.first); + config::all_children_iterator i = data.ordered_begin(); - if(req_body) { - rh.second(request(rh.first, req_body, sock)); + if(i != data.ordered_end()) { + // We only handle the first child. + const config::any_child& c = *i; + + request_handlers_table::const_iterator j + = handlers_.find(c.key); + + if(j != handlers_.end()) { + // Call the handler. + j->second(request(c.key, c.cfg, sock)); } } } From efcf8f7b6aa4e25c0ed5cbd80597e2d894658d95 Mon Sep 17 00:00:00 2001 From: "Ignacio R. Morelle" Date: Tue, 24 Jun 2014 20:36:27 -0400 Subject: [PATCH 4/6] campaignd: Reject bad requests with an [error] block This can be used to signal campaignd clients in the future about features that aren't yet implemented. As with the previous change to using find() to locate a request handler, this only applies to the first WML child of the request's root node. Other nodes continue to be ignored. --- src/campaign_server/campaign_server.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/campaign_server/campaign_server.cpp b/src/campaign_server/campaign_server.cpp index 9454c142f844..2e5336c0340e 100644 --- a/src/campaign_server/campaign_server.cpp +++ b/src/campaign_server/campaign_server.cpp @@ -290,6 +290,9 @@ void server::run() if(j != handlers_.end()) { // Call the handler. j->second(request(c.key, c.cfg, sock)); + } else { + send_error("Unrecognized [" + c.key + "] request.", + sock); } } } From 46815ee0084101d28dbdea335680a13384945dad Mon Sep 17 00:00:00 2001 From: "Ignacio R. Morelle" Date: Tue, 24 Jun 2014 20:44:26 -0400 Subject: [PATCH 5/6] campaignd: Document send_message/send_error's WML output and side-effects --- src/campaign_server/campaign_server.hpp | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/src/campaign_server/campaign_server.hpp b/src/campaign_server/campaign_server.hpp index c2b7c4d841c0..31c3702cc231 100644 --- a/src/campaign_server/campaign_server.hpp +++ b/src/campaign_server/campaign_server.hpp @@ -177,10 +177,22 @@ class server : private boost::noncopyable // Generic responses. // - /** Send a client an informational message. */ + /** + * Send a client an informational message. + * + * The WML sent consists of a document containing a single @p [message] + * child with a @a message attribute holding the value of @a msg. + */ void send_message(const std::string& msg, network::connection sock); - /** Send a client an error message. */ + /** + * Send a client an error message. + * + * The WML sent consists of a document containing a single @p [error] child + * with a @a message attribute holding the value of @a msg. In addition to + * sending the error to the client, a line with the client IP and message + * is recorded to the server log. + */ void send_error(const std::string& msg, network::connection sock); }; From 6629fdf64e7db529db574f2f8f6600ebd797d5ff Mon Sep 17 00:00:00 2001 From: "Ignacio R. Morelle" Date: Tue, 24 Jun 2014 20:47:58 -0400 Subject: [PATCH 6/6] wesnothd: Only reset the commands FIFO stream when reloading if needed May or may not fix the issue noted in commit 62eb55a5a712b3e2157cf7fc0bb12873c4f0a574 regarding the SIGHUP handler, which is in charge of scheduling load_config() to run. Rather unfortunately, I'm unable to reproduce the issue on my own machine, so I'll have to take this to production and test it live. --- src/server/server.cpp | 8 ++++++-- src/server/server.hpp | 1 + 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/src/server/server.cpp b/src/server/server.cpp index d73cb324488b..3b88494157e4 100644 --- a/src/server/server.cpp +++ b/src/server/server.cpp @@ -333,6 +333,7 @@ server::server(int port, const std::string& config_file, size_t min_threads, not_logged_in_(), rooms_(players_), input_(), + input_path_(), config_file_(config_file), cfg_(read_config()), accepted_versions_(), @@ -499,8 +500,11 @@ void server::load_config() { # endif #endif const std::string fifo_path = (cfg_["fifo_path"].empty() ? std::string(FIFODIR) + "/socket" : std::string(cfg_["fifo_path"])); - input_.reset(); - input_.reset(new input_stream(fifo_path)); + // Reset (replace) the input stream only if the FIFO path changed. + if(fifo_path != input_path_) { + input_.reset(new input_stream(fifo_path)); + } + input_path_ = fifo_path; save_replays_ = cfg_["save_replays"].to_bool(); replay_save_path_ = cfg_["replay_save_path"].str(); diff --git a/src/server/server.hpp b/src/server/server.hpp index 5987c10d7779..a4c3f3121d6d 100644 --- a/src/server/server.hpp +++ b/src/server/server.hpp @@ -106,6 +106,7 @@ class server /** server socket/fifo. */ boost::scoped_ptr input_; + std::string input_path_; const std::string config_file_; config cfg_;