glog_asio_sink.cc
1 // Copyright 2018, Beeri 15. All rights reserved.
2 // Author: Roman Gershman (romange@gmail.com)
3 //
4 #include "util/asio/glog_asio_sink.h"
5 #include <glog/raw_logging.h>
6 
7 namespace util {
8 using namespace ::boost;
9 using namespace ::std;
10 
11 using namespace fibers;
12 
13 GlogAsioSink::GlogAsioSink() : msg_q_(64) {
14 }
15 
16 GlogAsioSink::~GlogAsioSink() noexcept {
17 }
18 
19 void GlogAsioSink::Run() {
20  google::AddLogSink(this);
21  RAW_DLOG(INFO, "Started running");
22  run_started_.store(true, std::memory_order_seq_cst);
23  ec_.notifyAll();
24 
25  Item item;
26  while (true) {
27  channel_op_status st = msg_q_.pop(item);
28  if (st == channel_op_status::closed)
29  break;
30 
31  CHECK_EQ(channel_op_status::success, st);
32  // RAW_VLOG(1, "HandleItem : %s:%d", item.base_filename, item.line);
33  HandleItem(item);
34  }
35 
36  LOG_IF(INFO, lost_messages_ > 0) << "GlogAsioSink lost " << lost_messages_ << " lost messages ";
37 }
38 
39 void GlogAsioSink::Cancel() {
40  google::RemoveLogSink(this);
41  msg_q_.close();
42 }
43 
44 void GlogAsioSink::WaitTillRun() {
45  ec_.await([this] { return run_started_.load(std::memory_order_acquire); });
46 }
47 
48 void GlogAsioSink::send(google::LogSeverity severity, const char* full_filename,
49  const char* base_filename, int line, const struct ::tm* tm_time,
50  const char* message, size_t message_len) {
51  if (ShouldIgnore(severity, full_filename, line))
52  return;
53 
54  // string creation might have potential performance impact.
55  channel_op_status st = msg_q_.push_wait_for(
56  Item{full_filename, base_filename, severity, line, *tm_time, string{message, message_len}},
57  100us);
58 
59  if (st != channel_op_status::success) {
60  ++lost_messages_;
61  }
62  RAW_VLOG(1, "GlogAsioSink::SendExit : %d", int(st));
63 }
64 
65 void GlogAsioSink::WaitTillSent() {
66  /* Noop to reduce send latency */
67 }
68 
69 } // namespace util