# # # patch "administrator.cc" # from [df93336d3ff1e1ef1d441d84ed1e243937d9bd6d] # to [2089d74452a2aa045e3a2089202722fd3939f5fb] # # patch "channel.cc" # from [74dcb51d9ec09c7163c9a35f4c1e6051681af55b] # to [52453ded4583458cee87bd5d1dcc9351e8a9a900] # # patch "channel.hh" # from [5ab9c1f07c07884cb05aa4a5bedc451d19881e05] # to [e7c35bd545765f9aa0908a1b955132bb3ba69802] # # patch "server.cc" # from [f713179678ccaaeb5fb6e91e311de1ea8bd1a92a] # to [c9ba01a8e9a4abf884f5fd02b803c831dd0efee1] # # patch "server_manager.cc" # from [0ac40f5d2df7553d9e72ab336d68cabec0711a4a] # to [14db3fb2467a58c5e363d956bad71385f7c6836e] # # patch "server_manager.hh" # from [edc251e468e963f6b4fe1a1c038457b10e3d4e9c] # to [9aa2f2417967bc2d7b360c320f2eec6a54aac602] # # patch "usher.cc" # from [57d4235ae9446846b8d1ca456b8dc9b5f8165079] # to [f7c55b6b4e14aee45046b58b6990a223b3dec322] # ============================================================ --- administrator.cc df93336d3ff1e1ef1d441d84ed1e243937d9bd6d +++ administrator.cc 2089d74452a2aa045e3a2089202722fd3939f5fb @@ -1,5 +1,4 @@ #include "administrator.hh" -#include "server.hh" #include "err.hh" #include "io.hh" @@ -57,74 +56,77 @@ std::ostringstream oss; if (srv.empty()) { serverstate ss; - ss.num = manager.total_connections; - if (manager.connections_allowed) { - if (manager.total_connections) + ss.num = manager.get_total_connections(); + if (manager.get_connections_allowed()) { + if (ss.num) ss.state = serverstate::active; else ss.state = serverstate::waiting; } else { - if (manager.total_connections) + if (ss.num) ss.state = serverstate::shuttingdown; else ss.state = serverstate::shutdown; } oss< >::iterator i; - i = manager.by_name.find(srv); - if (i != manager.by_name.end()) - oss<second->get_state()<<"\n"; - else - oss<<"No such server.\n"; + try + { + oss<>srv; std::ostringstream oss; - map >::iterator i; - i = manager.by_name.find(srv); - if (i != manager.by_name.end()) { - i->second->enabled = true; - oss<second->get_state()<<"\n"; - } else - oss<<"No such server.\n"; + try + { + manager.start_stop_server(srv, true); + } + catch (errstr &e) + { + oss<>srv; std::ostringstream oss; - map >::iterator i; - i = manager.by_name.find(srv); - if (i != manager.by_name.end()) { - i->second->enabled = false; - i->second->maybekill(); - oss<second->get_state()<<"\n"; - } else - oss<<"No such server.\n"; + try + { + manager.start_stop_server(srv, false); + } + catch (errstr &e) + { + oss<>state; - map >::iterator i; - for (i = manager.by_name.begin(); - i != manager.by_name.end(); ++i) { - if (state.empty() || i->second->get_state() == state) - cs.buf += (cs.buf.empty()?"":" ") + i->first; - } + set servers = manager.list_servers(state); + for (set::iterator i = servers.begin(); + i != servers.end(); ++i) + { + cs.buf += (cs.buf.empty()?"":" ") + *i; + } cs.buf += "\n"; } else if (cmd == "SHUTDOWN") { - manager.connections_allowed = false; + manager.allow_connections(false); manager.kill_old_servers(); cs.buf = "ok\n"; } else if (cmd == "CONNECTIONS") { - cs.buf = lexical_cast(manager.total_connections) + "\n"; + cs.buf = lexical_cast(manager.get_total_connections()) + "\n"; } else if (cmd == "RELOAD") { reload_conffile(); cs.buf = "ok\n"; } else if (cmd == "STARTUP") { - manager.connections_allowed = true; + manager.allow_connections(true); cs.buf = "ok\n"; } else { return true; ============================================================ --- channel.cc 74dcb51d9ec09c7163c9a35f4c1e6051681af55b +++ channel.cc 52453ded4583458cee87bd5d1dcc9351e8a9a900 @@ -32,8 +32,8 @@ channel::~channel() { - if (who && !no_server) - who->disconnect(); + if (srv && !no_server) + manager.disconnect_from_server(srv); } bool @@ -99,7 +99,6 @@ if (extract_reply(cbuf, reply_srv, reply_pat)) { try { serversock ss = manager.connect_to_server(reply_srv, reply_pat); - who = ss.srv; srv = ss; have_routed = true; s = srv; ============================================================ --- channel.hh 5ab9c1f07c07884cb05aa4a5bedc451d19881e05 +++ channel.hh e7c35bd545765f9aa0908a1b955132bb3ba69802 @@ -1,9 +1,9 @@ #ifndef __CHANNEL_HH_ #define __CHANNEL_HH_ #include "sock.hh" #include "buffer.hh" -#include "server.hh" +#include "server_manager.hh" #include using boost::shared_ptr; @@ -17,12 +17,11 @@ static int counter; int num; sock cli; - sock srv; + serversock srv; bool have_routed; bool no_server; buffer cbuf; buffer sbuf; - shared_ptr who; server_manager &manager; channel(sock & c, server_manager &sm); ~channel(); ============================================================ --- server.cc f713179678ccaaeb5fb6e91e311de1ea8bd1a92a +++ server.cc c9ba01a8e9a4abf884f5fd02b803c831dd0efee1 @@ -104,8 +104,8 @@ { serverstate ss; ss.num = connection_count; - if (!manager.connections_allowed) { - if (!manager.total_connections) + if (!manager.get_connections_allowed()) { + if (!manager.get_total_connections()) ss.state = serverstate::shutdown; else ss.state = serverstate::shuttingdown; @@ -231,7 +231,8 @@ return; int difftime = time(0) - last_conn_time; if (!connection_count - && (difftime > server_idle_timeout || !manager.connections_allowed)) + && (difftime > server_idle_timeout + || !manager.get_connections_allowed())) yeskill(); else if (waitpid(pid, 0, WNOHANG) > 0) { pid = -1; ============================================================ --- server_manager.cc 0ac40f5d2df7553d9e72ab336d68cabec0711a4a +++ server_manager.cc 14db3fb2467a58c5e363d956bad71385f7c6836e @@ -9,6 +9,8 @@ #include +#include + serversock::serversock(sock const &o) : sock(o) { @@ -181,7 +183,10 @@ { sock s = srv->connect(); serversock ss(s); - ss.srv = srv; + map, serverdata>::iterator i = servers.find(srv); + if (i == servers.end()) + throw errstr("server_manager is inconsistent"); + ss.srv = i->second.name; ++total_connections; if (srv->local && srv->connection_count == 1) { @@ -195,21 +200,56 @@ void server_manager::disconnect_from_server(serversock const &s) { - s.srv->disconnect(); - if (s.srv->local && s.srv->pid == -1) - live.erase(s.srv); + map >::iterator i = by_name.find(s.srv); + if (i == by_name.end()) + return; + i->second->disconnect(); + if (i->second->local && i->second->pid == -1) + live.erase(i->second); --total_connections; } -serverstate +string server_manager::get_server_state(string const &name) { map >::iterator i = by_name.find(name); if (i != by_name.end()) - return i->second->get_state(); + return boost::lexical_cast(i->second->get_state()); throw errstr("No such server."); } +set +server_manager::list_servers(string const &state) +{ + set out; + for (map >::iterator i = by_name.begin(); + i != by_name.end(); ++i) + { + if (state.empty() || i->second->get_state() == state) + out.insert(i->first); + } + return out; +} + void +server_manager::allow_connections(bool allow) +{ + connections_allowed = allow; +} + +string +server_manager::start_stop_server(string const &srv, bool start) +{ + map >::iterator i = by_name.find(srv); + if (i != by_name.end()) { + i->second->enabled = start; + if (!start) + i->second->maybekill(); + return boost::lexical_cast(i->second->get_state()); + } else + throw errstr("No such server."); +} + +void server_manager::kill_old_servers() { set >::iterator i; ============================================================ --- server_manager.hh edc251e468e963f6b4fe1a1c038457b10e3d4e9c +++ server_manager.hh 9aa2f2417967bc2d7b360c320f2eec6a54aac602 @@ -18,11 +18,12 @@ struct serversock : public sock { - shared_ptr srv; + string srv; serversock(sock const &o); + operator bool() {return !srv.empty();} }; -struct server_manager +class server_manager { struct serverdata { @@ -51,15 +52,21 @@ int total_connections; serverlist_reader &reader; - server_manager(serverlist_reader &r); - void add_replace_server(shared_ptr srv, serverdata const &dat); void delist_server(shared_ptr srv); + +public: + server_manager(serverlist_reader &r); + bool get_connections_allowed() {return connections_allowed;} + int get_total_connections() {return total_connections;} + void allow_connections(bool allow=true); + string start_stop_server(string const &srv, bool start); void reload_servers(); serversock connect_to_server(string const &host, string const &pattern); void disconnect_from_server(serversock const &s); - serverstate get_server_state(string const &name); + string get_server_state(string const &name); + set list_servers(string const &state); void kill_old_servers(); }; ============================================================ --- usher.cc 57d4235ae9446846b8d1ca456b8dc9b5f8165079 +++ usher.cc f7c55b6b4e14aee45046b58b6990a223b3dec322 @@ -190,7 +190,7 @@ memset(&client_address, 0, l); sock cli = tosserr(accept(h, (struct sockaddr *) &client_address, &l), "accept()"); - if (manager.connections_allowed) + if (manager.get_connections_allowed()) newchan = new channel(cli, manager); else { char * dat;