// // client.cpp // ~~~~~~~~~~ // // Copyright (c) 2003-2016 Christopher M. Kohlhoff (chris at kohlhoff dot com) // // Distributed under the Boost Software License, Version 1.0. (See accompanying // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) // #include #include #include #include #include // #include #include #include #include #include #include #include #include #include #include "config.h" #include "logging.h" #include "session.h" // #define BOOST_ASIO_ENABLE_HANDLER_TRACKING // std::map CONFIG; // #include #include #include /* boost log linking - undefined reference to `void boost::log::v2_mt_posix::init_from_stream https://github.com/boostorg/log/issues/46 */ void init_logging(void) { // because TimeStamp is missing by default. boost::log::add_common_attributes(); // "proxy-%Y-%m-%d.log" std::string log_filename = "proxy.log"; if (CONFIG.contains("log_file")) log_filename = json_str(CONFIG["log_file"]); // "%I:%M:%S.%f %p" std::string log_timeformat = "%H:%M:%S.%f"; if (CONFIG.contains("log_timeformat")) log_timeformat = json_str(CONFIG["log_timeformat"]); // from_config("log_timeformat", "%H:%M:%S.%f"); bool log_autoflush = false; if (CONFIG.contains("log_autoflush")) { log_autoflush = json_bool(CONFIG["log_autoflush"]); } int log_level = 2; if (CONFIG.contains("log_level")) { log_level = json_int(CONFIG["log_level"]); } bool console = false; if (CONFIG.contains("log_console")) { console = json_bool(CONFIG["log_console"]); } std::cout << "Logging to: "; if (console) std::cout << "console + "; std::cout << log_filename << " level: " << log_level << " flush: " << log_autoflush << " format: " << log_timeformat << std::endl; if (console) boost::log::add_console_log( std::clog, boost::log::keywords::auto_flush = log_autoflush, boost::log::keywords::format = (boost::log::expressions::stream << boost::log::expressions::format_date_time< boost::posix_time::ptime>("TimeStamp", log_timeformat) << " " << std::setw(8) << boost::log::trivial::severity << " " << boost::log::expressions::smessage)); boost::log::add_file_log( boost::log::keywords::file_name = log_filename, // This appends to the logfile (instead of overwrite) boost::log::keywords::open_mode = std::ios_base::out | std::ios_base::app, boost::log::keywords::auto_flush = log_autoflush, // boost::log::keywords::format = "[%TimeStamp%] %Severity% : %Message%" boost::log::keywords::format = (boost::log::expressions::stream << boost::log::expressions::format_date_time< boost::posix_time::ptime>("TimeStamp", log_timeformat) << " " << std::setw(8) << boost::log::trivial::severity << " " << boost::log::expressions::smessage)); auto core = boost::log::core::get(); core->set_filter(boost::log::trivial::severity >= log_level); } int main(int argc, char *argv[]) { if (argc != 2) { std::cerr << "Usage: twproxy " << std::endl; return EXIT_FAILURE; } { std::ifstream fin(argv[1]); CONFIG = json::parse(fin); // YAML::LoadFile(argv[1]); } init_logging(); bool config_ok = true; // for (const char *key : {"server", "host", "port"}) { for (auto key : {"server", "host", "port", "basename"}) { if (!CONFIG.contains(key)) { config_ok = false; std::cout << "Config file missing: " << key << std::endl; BUGZ_LOG(fatal) << "Config file missing: " << key; } // The leaks are reported here, because this is the first usage of the // BOOST_LOG_TRIVIAL()! Comment these out, and the leaks are reported at the // next logging usage instance. std::string value = json_str(CONFIG[key]); BUGZ_LOG(info) << "Config: " << key << " : " << value; } if (!config_ok) return EXIT_FAILURE; int listen_port = json_int(CONFIG["server"]); #define BURN #ifndef BURN try { #endif bool telnet = false; if (CONFIG.contains("server_telnet")) { telnet = true; BUGZ_LOG(fatal) << "Connect to server via TELNET"; } boost::asio::io_service io_service; boost::asio::ip::tcp::endpoint endpoint(boost::asio::ip::tcp::v4(), listen_port); // connect to the game server std::string host = json_str(CONFIG["host"]); std::string port = json_str(CONFIG["port"]); BUGZ_LOG(fatal) << "host: " << host << " port: " << port; Server serve(io_service, endpoint, host, port, telnet); io_service.run(); #ifndef BURN } catch (std::exception &e) { BUGZ_LOG(fatal) << "Exception: " << e.what(); std::cerr << "Exception: " << e.what() << "\n"; } #endif return EXIT_SUCCESS; }