]> git.proxmox.com Git - ceph.git/blob - ceph/src/log/Log.h
import quincy beta 17.1.0
[ceph.git] / ceph / src / log / Log.h
1 // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*-
2 // vim: ts=8 sw=2 smarttab
3
4 #ifndef __CEPH_LOG_LOG_H
5 #define __CEPH_LOG_LOG_H
6
7 #include <boost/circular_buffer.hpp>
8
9 #include <condition_variable>
10 #include <memory>
11 #include <mutex>
12 #include <queue>
13 #include <string>
14 #include <string_view>
15
16 #include "common/Thread.h"
17 #include "common/likely.h"
18
19 #include "log/Entry.h"
20
21 struct uuid_d;
22
23 namespace ceph {
24 namespace logging {
25
26 class Graylog;
27 class JournaldLogger;
28 class SubsystemMap;
29
30 class Log : private Thread
31 {
32 using EntryRing = boost::circular_buffer<ConcreteEntry>;
33 using EntryVector = std::vector<ConcreteEntry>;
34
35 static const std::size_t DEFAULT_MAX_NEW = 100;
36 static const std::size_t DEFAULT_MAX_RECENT = 10000;
37
38 Log **m_indirect_this;
39
40 const SubsystemMap *m_subs;
41
42 std::mutex m_queue_mutex;
43 std::mutex m_flush_mutex;
44 std::condition_variable m_cond_loggers;
45 std::condition_variable m_cond_flusher;
46
47 pthread_t m_queue_mutex_holder;
48 pthread_t m_flush_mutex_holder;
49
50 EntryVector m_new; ///< new entries
51 EntryRing m_recent; ///< recent (less new) entries we've already written at low detail
52 EntryVector m_flush; ///< entries to be flushed (here to optimize heap allocations)
53
54 std::string m_log_file;
55 int m_fd = -1;
56 uid_t m_uid = 0;
57 gid_t m_gid = 0;
58
59 int m_fd_last_error = 0; ///< last error we say writing to fd (if any)
60
61 int m_syslog_log = -2, m_syslog_crash = -2;
62 int m_stderr_log = -1, m_stderr_crash = -1;
63 int m_graylog_log = -3, m_graylog_crash = -3;
64 int m_journald_log = -3, m_journald_crash = -3;
65
66 std::string m_log_stderr_prefix;
67
68 std::shared_ptr<Graylog> m_graylog;
69 std::unique_ptr<JournaldLogger> m_journald;
70
71 std::vector<char> m_log_buf;
72
73 bool m_stop = false;
74
75 std::size_t m_max_new = DEFAULT_MAX_NEW;
76 std::size_t m_max_recent = DEFAULT_MAX_RECENT;
77
78 bool m_inject_segv = false;
79
80 void *entry() override;
81
82 void _log_safe_write(std::string_view sv);
83 void _flush_logbuf();
84 void _flush(EntryVector& q, bool crash);
85
86 void _log_message(std::string_view s, bool crash);
87
88 public:
89 using Thread::is_started;
90
91 Log(const SubsystemMap *s);
92 ~Log() override;
93
94 void set_flush_on_exit();
95
96 void set_coarse_timestamps(bool coarse);
97 void set_max_new(std::size_t n);
98 void set_max_recent(std::size_t n);
99 void set_log_file(std::string_view fn);
100 void reopen_log_file();
101 void chown_log_file(uid_t uid, gid_t gid);
102 void set_log_stderr_prefix(std::string_view p);
103
104 void flush();
105
106 void dump_recent();
107
108 void set_syslog_level(int log, int crash);
109 void set_stderr_level(int log, int crash);
110 void set_graylog_level(int log, int crash);
111
112 void start_graylog(const std::string& host,
113 const uuid_d& fsid);
114 void stop_graylog();
115
116 void set_journald_level(int log, int crash);
117
118 void start_journald_logger();
119 void stop_journald_logger();
120
121 std::shared_ptr<Graylog> graylog() { return m_graylog; }
122
123 void submit_entry(Entry&& e);
124
125 void start();
126 void stop();
127
128 /// true if the log lock is held by our thread
129 bool is_inside_log_lock();
130
131 /// induce a segv on the next log event
132 void inject_segv();
133 void reset_segv();
134 };
135
136 }
137 }
138
139 #endif