25#ifndef DCCLLOGGER20121009H
26#define DCCLLOGGER20121009H
37#include "thread_safety.h"
51 ALL = DEBUG3 | (DEBUG3 - 1),
52 WARN_PLUS = WARN | (WARN - 1),
53 INFO_PLUS = INFO | (INFO - 1),
54 DEBUG1_PLUS = DEBUG1 | (DEBUG1 - 1),
55 DEBUG2_PLUS = DEBUG2 | (DEBUG2 - 1),
56 DEBUG3_PLUS = DEBUG3 | (DEBUG3 - 1),
69void to_ostream(
const std::string& msg, dccl::logger::Verbosity vrb, dccl::logger::Group grp,
70 std::ostream* os,
bool add_timestamp);
83 template <
typename Slot>
void connect(
int verbosity_mask, Slot slot)
85 enabled_verbosities_ |= verbosity_mask;
86 if (verbosity_mask & logger::WARN)
87 warn_signal.emplace_back(slot);
88 if (verbosity_mask & logger::INFO)
89 info_signal.emplace_back(slot);
90 if (verbosity_mask & logger::DEBUG1)
91 debug1_signal.emplace_back(slot);
92 if (verbosity_mask & logger::DEBUG2)
93 debug2_signal.emplace_back(slot);
94 if (verbosity_mask & logger::DEBUG3)
95 debug3_signal.emplace_back(slot);
98 void disconnect(
int verbosity_mask)
100 enabled_verbosities_ &= ~verbosity_mask;
101 if (verbosity_mask & logger::WARN)
103 if (verbosity_mask & logger::INFO)
105 if (verbosity_mask & logger::DEBUG1)
106 debug1_signal.clear();
107 if (verbosity_mask & logger::DEBUG2)
108 debug2_signal.clear();
109 if (verbosity_mask & logger::DEBUG3)
110 debug3_signal.clear();
114 void set_verbosity(logger::Verbosity verbosity) { verbosity_.push(verbosity); }
116 void set_group(logger::Group group) { group_.push(group); }
118 bool contains(logger::Verbosity verbosity)
const {
return verbosity & enabled_verbosities_; }
127 int overflow(
int c = EOF)
override;
129 void display(
const std::string& s)
131 if (verbosity() & logger::WARN)
133 for (
auto& slot : warn_signal) slot(s, logger::WARN, group());
135 if (verbosity() & logger::INFO)
137 for (
auto& slot : info_signal) slot(s, logger::INFO, group());
139 if (verbosity() & logger::DEBUG1)
141 for (
auto& slot : debug1_signal) slot(s, logger::DEBUG1, group());
143 if (verbosity() & logger::DEBUG2)
145 for (
auto& slot : debug2_signal) slot(s, logger::DEBUG2, group());
147 if (verbosity() & logger::DEBUG3)
149 for (
auto& slot : debug3_signal) slot(s, logger::DEBUG3, group());
153 logger::Verbosity verbosity()
155 return verbosity_.empty() ? logger::UNKNOWN : verbosity_.top();
157 logger::Group group() {
return group_.empty() ? logger::GENERAL : group_.top(); }
160 std::stack<logger::Verbosity> verbosity_;
161 std::stack<logger::Group> group_;
162 std::deque<std::string> buffer_;
163 int enabled_verbosities_;
165 using LogSignal = std::vector<
166 std::function<void(
const std::string& msg, logger::Verbosity vrb, logger::Group grp)>>;
168 LogSignal warn_signal, info_signal, debug1_signal, debug2_signal, debug3_signal;
176 Logger() : std::ostream(&buf_) {}
180 bool check(logger::Verbosity verbosity) {
return buf_.contains(verbosity); }
191 bool is(logger::Verbosity verbosity, logger::Group group = logger::GENERAL)
193 if (!buf_.contains(verbosity))
199#if DCCL_THREAD_SUPPORT
203 buf_.set_group(group);
213 template <
typename Slot>
void connect(
int verbosity_mask, Slot slot)
216 buf_.
connect(verbosity_mask, slot);
225 template <
typename Obj>
227 void (Obj::*mem_func)(const std::string& msg, logger::Verbosity vrb,
231 connect(verbosity_mask, [obj, mem_func](
const std::string& msg, logger::Verbosity vrb,
232 logger::Group grp) { (obj->*mem_func)(msg, vrb, grp); });
240 void connect(
int verbosity_mask, std::ostream* os,
bool add_timestamp =
true)
243 buf_.
connect(verbosity_mask, [os, add_timestamp](
const std::string& msg,
244 logger::Verbosity vrb, logger::Group grp) {
245 to_ostream(msg, vrb, grp, os, add_timestamp);
253 buf_.disconnect(verbosity_mask);
262inline std::string hash_as_string(std::size_t hash)
264 std::stringstream hash_stream;
265 hash_stream <<
"0x" << std::setfill(
'0') << std::setw(
sizeof(std::size_t) * 2) << std::hex
267 return hash_stream.str();
The DCCL Logger class. Do not instantiate this class directly. Rather, use the dccl::dlog object.
bool is(logger::Verbosity verbosity, logger::Group group=logger::GENERAL)
Indicates the verbosity of the Logger until the next std::flush or std::endl. The boolean return is u...
bool check(logger::Verbosity verbosity)
Same as is() but doesn't set the verbosity or lock the mutex.
void disconnect(int verbosity_mask)
Disconnect all slots for one or more given verbosities.
void connect(int verbosity_mask, Obj *obj, void(Obj::*mem_func)(const std::string &msg, logger::Verbosity vrb, logger::Group grp))
Connect the output of one or more given verbosities to a member function.
void connect(int verbosity_mask, Slot slot)
Connect the output of one or more given verbosities to a slot (function pointer or similar)
void connect(int verbosity_mask, std::ostream *os, bool add_timestamp=true)
Connect the output of one or more given verbosities to a std::ostream.
void connect(int verbosity_mask, Slot slot)
connect a signal to a slot (function pointer or similar)
void set_verbosity(logger::Verbosity verbosity)
sets the verbosity level until the next sync()
Dynamic Compact Control Language namespace.