diff --git a/example/example.cpp b/example/example.cpp index c06d5a6d..462613a1 100644 --- a/example/example.cpp +++ b/example/example.cpp @@ -2,7 +2,7 @@ // #include "c11log/logger.h" -//#include "c11log/sinks/async_sink.h" +#include "c11log/sinks/async_sink.h" #include "c11log/sinks/file_sinks.h" #include "c11log/sinks/console_sinks.h" @@ -19,14 +19,12 @@ int main(int argc, char* argv[]) { if(argc || argv) {}; - const unsigned int howmany = 5000000; + const unsigned int howmany = argc <= 1 ? 1500000 :atoi(argv[1]); auto fsink = std::make_shared("log", "txt", 1024*1024*50 , 5, 0); - //auto fsink = std::make_shared("simplelog", "txt"); auto null_sink = std::make_shared(); - logger cout_logger ("cout", {null_sink, sinks::stdout_sink()}); - + logger cout_logger ("cout", {sinks::stdout_sink()}); cout_logger.info() << "Hello cout logger!"; logger my_logger ("my_logger", {null_sink}); @@ -36,9 +34,8 @@ int main(int argc, char* argv[]) auto start = system_clock::now(); for(unsigned int i = 0; i < howmany ; i++) my_logger.info() << s; - //my_logger.info() << "Hello logger " << i;; - //async->shutdown(seconds(3)); + auto delta = system_clock::now() - start; auto delta_d = duration_cast> (delta).count(); cout_logger.info() << "Total " << format(howmany); diff --git a/include/c11log/common_types.h b/include/c11log/common_types.h index 85ea8ba0..d4b1efea 100644 --- a/include/c11log/common_types.h +++ b/include/c11log/common_types.h @@ -25,14 +25,5 @@ inline const char* to_str(c11log::level::level_enum l) { return level_names[l]; } -} - -struct log_msg -{ - bufpair_t msg_buf; - log_clock::time_point msg_time; - std::size_t msg_header_size; - level::level_enum msg_level; -}; - -} +} //level +} //c11log diff --git a/include/c11log/details/line_logger.h b/include/c11log/details/line_logger.h index 04fadec4..fce5a933 100644 --- a/include/c11log/details/line_logger.h +++ b/include/c11log/details/line_logger.h @@ -72,7 +72,7 @@ public: private: logger* _callback_logger; - c11log::log_msg _log_msg; + log_msg _log_msg; details::stack_oss _oss; bool _enabled; diff --git a/include/c11log/details/os.h b/include/c11log/details/os.h index ab91284c..0e66950a 100644 --- a/include/c11log/details/os.h +++ b/include/c11log/details/os.h @@ -28,9 +28,6 @@ inline std::tm localtime() return localtime(now_t); } - - - inline bool operator==(const std::tm& tm1, const std::tm& tm2) { return (tm1.tm_sec == tm2.tm_sec && diff --git a/include/c11log/details/stack_buf.h b/include/c11log/details/stack_buf.h index f0774fb5..01d9d4f2 100644 --- a/include/c11log/details/stack_buf.h +++ b/include/c11log/details/stack_buf.h @@ -3,7 +3,7 @@ #include #include #include - +#include // Fast memory storage // stores its contents on the stack when possible, in vector otherwise diff --git a/include/c11log/logger.h b/include/c11log/logger.h index 4b303823..97b124b0 100644 --- a/include/c11log/logger.h +++ b/include/c11log/logger.h @@ -68,7 +68,7 @@ private: sinks_vector_t _sinks; std::atomic_int _logger_level; - void _log_it(const log_msg& msg); + void _log_it(const details::log_msg& msg); }; @@ -146,14 +146,13 @@ inline bool c11log::logger::should_log(c11log::level::level_enum level) const return level >= _logger_level.load(); } -inline void c11log::logger::_log_it(const log_msg& msg) +inline void c11log::logger::_log_it(const details::log_msg& msg) { for (auto &sink : _sinks) sink->log(msg); } // Static factory function - inline c11log::logger& c11log::get_logger(const std::string& name) { return *(c11log::details::factory::instance().get_logger(name)); diff --git a/include/c11log/sinks/async_sink.h b/include/c11log/sinks/async_sink.h index 4eba5b2b..fb92733b 100644 --- a/include/c11log/sinks/async_sink.h +++ b/include/c11log/sinks/async_sink.h @@ -7,7 +7,10 @@ #include "base_sink.h" #include "../logger.h" #include "../details/blocking_queue.h" +#include "../details/log_msg.h" + +using namespace std; namespace c11log { namespace sinks @@ -16,7 +19,9 @@ namespace sinks class async_sink : public base_sink { public: - using size_type = c11log::details::blocking_queue::size_type; + + using queue_t = c11log::details::blocking_queue>; + using size_type = queue_t::size_type; explicit async_sink(const size_type max_queue_size); ~async_sink(); @@ -28,13 +33,13 @@ public: protected: - void _sink_it(const bufpair_t& msg) override; + void _sink_it(const details::log_msg& msg) override; void _thread_loop(); private: c11log::logger::sinks_vector_t _sinks; std::atomic _active; - c11log::details::blocking_queue _q; + queue_t _q; std::thread _back_thread; //Clear all remaining messages(if any), stop the _back_thread and join it void _shutdown(); @@ -46,7 +51,7 @@ private: // async_sink class implementation /////////////////////////////////////////////////////////////////////////////// -inline c11log::sinks::async_sink::async_sink(const std::size_t max_queue_size) +inline c11log::sinks::async_sink::async_sink(const size_type max_queue_size) :_sinks(), _active(true), _q(max_queue_size), @@ -57,27 +62,33 @@ inline c11log::sinks::async_sink::~async_sink() { _shutdown(); } -inline void c11log::sinks::async_sink::_sink_it(const bufpair_t& msg) +inline void c11log::sinks::async_sink::_sink_it(const details::log_msg& msg) { - std::string s {msg.first, msg.first+msg.second}; - _q.push(s); + //re allocate on the heap the (stack based) message + auto new_msg = new details::log_msg(); + *new_msg = msg; + auto msg_size = msg.msg_buf.second; + char *buf = new char[msg_size]; + std::memcpy(buf, msg.msg_buf.first, msg_size); + new_msg->msg_buf = bufpair_t(buf, msg_size); + auto new_shared = std::shared_ptr(new_msg, [](details::log_msg* msg_to_delete) + { + delete []msg_to_delete->msg_buf.first; + }); + _q.push(new_shared); } inline void c11log::sinks::async_sink::_thread_loop() { static std::chrono::seconds pop_timeout { 1 }; - std::string msg; - while (_active) { + std::shared_ptr msg; if (_q.pop(msg, pop_timeout)) { - bufpair_t buf(msg.data(), msg.size()); for (auto &sink : _sinks) { - sink->log(buf, level::INFO); - if (!_active) - return; + sink->log(*msg); } } } diff --git a/include/c11log/sinks/base_sink.h b/include/c11log/sinks/base_sink.h index b5e4a93d..b2a6b9f0 100644 --- a/include/c11log/sinks/base_sink.h +++ b/include/c11log/sinks/base_sink.h @@ -5,6 +5,7 @@ #include "../formatter.h" #include "../common_types.h" +#include "../details/log_msg.h" namespace c11log { @@ -19,7 +20,7 @@ public: base_sink(const base_sink&) = delete; base_sink& operator=(const base_sink&) = delete; - void log(const log_msg& msg) + void log(const details::log_msg& msg) { if (_enabled) { @@ -38,14 +39,14 @@ public: } protected: - virtual void _sink_it(const log_msg& msg) = 0; + virtual void _sink_it(const details::log_msg& msg) = 0; std::atomic _enabled; }; class null_sink:public base_sink { protected: - void _sink_it(const log_msg&) override + void _sink_it(const details::log_msg&) override { } }; diff --git a/include/c11log/sinks/console_sinks.h b/include/c11log/sinks/console_sinks.h index a8a45af8..86830207 100644 --- a/include/c11log/sinks/console_sinks.h +++ b/include/c11log/sinks/console_sinks.h @@ -19,7 +19,7 @@ public: virtual ~console_sink() = default; protected: - virtual void _sink_it(const log_msg& msg) override + virtual void _sink_it(const details::log_msg& msg) override { std::lock_guard lock(_mutex); _ostream.write(msg.msg_buf.first, msg.msg_buf.second); diff --git a/include/c11log/sinks/file_sinks.h b/include/c11log/sinks/file_sinks.h index 1d227fb5..0b345321 100644 --- a/include/c11log/sinks/file_sinks.h +++ b/include/c11log/sinks/file_sinks.h @@ -6,6 +6,7 @@ #include #include "base_sink.h" #include "../details/flush_helper.h" +#include "../details/blocking_queue.h" namespace c11log { @@ -27,7 +28,7 @@ public: { } protected: - void _sink_it(const log_msg& msg) override + void _sink_it(const details::log_msg& msg) override { std::lock_guard lock(_mutex); _flush_helper.write(msg.msg_buf, _ofstream); @@ -60,7 +61,7 @@ public: } protected: - void _sink_it(const log_msg& msg) override + void _sink_it(const details::log_msg& msg) override { std::lock_guard lock(_mutex); @@ -134,7 +135,7 @@ public: } protected: - void _sink_it(const log_msg& msg) override + void _sink_it(const details::log_msg& msg) override { std::lock_guard lock(_mutex); if (std::chrono::system_clock::now() >= _midnight_tp)