summaryrefslogtreecommitdiffstats
path: root/xbmc/utils/log.h
diff options
context:
space:
mode:
authormanuel <manuel@mausz.at>2020-10-19 00:52:24 +0200
committermanuel <manuel@mausz.at>2020-10-19 00:52:24 +0200
commitbe933ef2241d79558f91796cc5b3a161f72ebf9c (patch)
treefe3ab2f130e20c99001f2d7a81d610c78c96a3f4 /xbmc/utils/log.h
parent5f8335c1e49ce108ef3481863833c98efa00411b (diff)
downloadkodi-pvr-build-be933ef2241d79558f91796cc5b3a161f72ebf9c.tar.gz
kodi-pvr-build-be933ef2241d79558f91796cc5b3a161f72ebf9c.tar.bz2
kodi-pvr-build-be933ef2241d79558f91796cc5b3a161f72ebf9c.zip
sync with upstream
Diffstat (limited to 'xbmc/utils/log.h')
-rw-r--r--xbmc/utils/log.h217
1 files changed, 217 insertions, 0 deletions
diff --git a/xbmc/utils/log.h b/xbmc/utils/log.h
new file mode 100644
index 0000000..7287918
--- /dev/null
+++ b/xbmc/utils/log.h
@@ -0,0 +1,217 @@
1/*
2 * Copyright (C) 2005-2018 Team Kodi
3 * This file is part of Kodi - https://kodi.tv
4 *
5 * SPDX-License-Identifier: GPL-2.0-or-later
6 * See LICENSES/README.md for more information.
7 */
8
9#pragma once
10
11// spdlog specific defines
12#define SPDLOG_LEVEL_NAMES {"TRACE", "DEBUG", "INFO", "WARNING", "ERROR", "FATAL", "OFF"};
13
14#include "commons/ilog.h"
15#include "settings/lib/ISettingCallback.h"
16#include "settings/lib/ISettingsHandler.h"
17#include "settings/lib/SettingDefinitions.h"
18#include "utils/IPlatformLog.h"
19#include "utils/StringUtils.h"
20#include "utils/logtypes.h"
21
22#include <string>
23#include <vector>
24
25#include <spdlog/spdlog.h>
26
27namespace spdlog
28{
29namespace sinks
30{
31template<typename Mutex>
32class basic_file_sink;
33
34template<typename Mutex>
35class dist_sink;
36} // namespace sinks
37} // namespace spdlog
38
39class CLog : public ISettingsHandler, public ISettingCallback
40{
41public:
42 CLog();
43 ~CLog() = default;
44
45 // implementation of ISettingsHandler
46 void OnSettingsLoaded() override;
47
48 // implementation of ISettingCallback
49 void OnSettingChanged(std::shared_ptr<const CSetting> setting) override;
50
51 void Initialize(const std::string& path);
52 void Uninitialize();
53
54 void SetLogLevel(int level);
55 int GetLogLevel() { return m_logLevel; }
56 bool IsLogLevelLogged(int loglevel);
57
58 bool CanLogComponent(uint32_t component) const;
59 static void SettingOptionsLoggingComponentsFiller(std::shared_ptr<const CSetting> setting,
60 std::vector<IntegerSettingOption>& list,
61 int& current,
62 void* data);
63
64 Logger GetLogger(const std::string& loggerName);
65
66 template<typename Char, typename... Args>
67 static inline void Log(int level, const Char* format, Args&&... args)
68 {
69 Log(MapLogLevel(level), format, std::forward<Args>(args)...);
70 }
71
72 template<typename Char, typename... Args>
73 static inline void Log(int level, uint32_t component, const Char* format, Args&&... args)
74 {
75 if (!GetInstance().CanLogComponent(component))
76 return;
77
78 Log(level, format, std::forward<Args>(args)...);
79 }
80
81 template<typename Char, typename... Args>
82 static inline void Log(spdlog::level::level_enum level, const Char* format, Args&&... args)
83 {
84 GetInstance().FormatAndLogInternal(level, format, std::forward<Args>(args)...);
85 }
86
87 template<typename Char, typename... Args>
88 static inline void Log(spdlog::level::level_enum level,
89 uint32_t component,
90 const Char* format,
91 Args&&... args)
92 {
93 if (!GetInstance().CanLogComponent(component))
94 return;
95
96 Log(level, format, std::forward<Args>(args)...);
97 }
98
99 template<typename Char, typename... Args>
100 static inline void LogFunction(int level,
101 const char* functionName,
102 const Char* format,
103 Args&&... args)
104 {
105 LogFunction(MapLogLevel(level), functionName, format, std::forward<Args>(args)...);
106 }
107
108 template<typename Char, typename... Args>
109 static inline void LogFunction(
110 int level, const char* functionName, uint32_t component, const Char* format, Args&&... args)
111 {
112 if (!GetInstance().CanLogComponent(component))
113 return;
114
115 LogFunction(level, functionName, format, std::forward<Args>(args)...);
116 }
117
118 template<typename Char, typename... Args>
119 static inline void LogFunction(spdlog::level::level_enum level,
120 const char* functionName,
121 const Char* format,
122 Args&&... args)
123 {
124 if (functionName == nullptr || strlen(functionName) == 0)
125 GetInstance().FormatAndLogInternal(level, format, std::forward<Args>(args)...);
126 else
127 GetInstance().FormatAndLogFunctionInternal(level, functionName, format,
128 std::forward<Args>(args)...);
129 }
130
131 template<typename Char, typename... Args>
132 static inline void LogFunction(spdlog::level::level_enum level,
133 const char* functionName,
134 uint32_t component,
135 const Char* format,
136 Args&&... args)
137 {
138 if (!GetInstance().CanLogComponent(component))
139 return;
140
141 LogFunction(level, functionName, format, std::forward<Args>(args)...);
142 }
143
144#define LogF(level, format, ...) LogFunction((level), __FUNCTION__, (format), ##__VA_ARGS__)
145#define LogFC(level, component, format, ...) \
146 LogFunction((level), __FUNCTION__, (component), (format), ##__VA_ARGS__)
147
148private:
149 static CLog& GetInstance();
150
151 static spdlog::level::level_enum MapLogLevel(int level);
152
153 template<typename... Args>
154 static inline void FormatAndLogFunctionInternal(spdlog::level::level_enum level,
155 const char* functionName,
156 const char* format,
157 Args&&... args)
158 {
159 GetInstance().FormatAndLogInternal(
160 level, StringUtils::Format("{0:s}: {1:s}", functionName, format).c_str(),
161 std::forward<Args>(args)...);
162 }
163
164 template<typename... Args>
165 static inline void FormatAndLogFunctionInternal(spdlog::level::level_enum level,
166 const char* functionName,
167 const wchar_t* format,
168 Args&&... args)
169 {
170 GetInstance().FormatAndLogInternal(
171 level, StringUtils::Format(L"{0:s}: {1:s}", functionName, format).c_str(),
172 std::forward<Args>(args)...);
173 }
174
175 template<typename Char, typename... Args>
176 inline void FormatAndLogInternal(spdlog::level::level_enum level,
177 const Char* format,
178 Args&&... args)
179 {
180 // TODO: for now we manually format the messages to support both python- and printf-style formatting.
181 // this can be removed once all log messages have been adjusted to python-style formatting
182 auto logString = StringUtils::Format(format, std::forward<Args>(args)...);
183
184 // fixup newline alignment, number of spaces should equal prefix length
185 StringUtils::Replace(logString, "\n", "\n ");
186
187 m_defaultLogger->log(level, std::move(logString));
188 }
189
190 Logger CreateLogger(const std::string& loggerName);
191
192 void SetComponentLogLevel(const std::vector<CVariant>& components);
193
194 std::unique_ptr<IPlatformLog> m_platform;
195 std::shared_ptr<spdlog::sinks::dist_sink<std::mutex>> m_sinks;
196 Logger m_defaultLogger;
197
198 std::shared_ptr<spdlog::sinks::basic_file_sink<std::mutex>> m_fileSink;
199
200 int m_logLevel;
201
202 bool m_componentLogEnabled;
203 uint32_t m_componentLogLevels;
204};
205
206namespace XbmcUtils
207{
208class LogImplementation : public XbmcCommons::ILogger
209{
210public:
211 ~LogImplementation() override = default;
212 inline void log(int logLevel, IN_STRING const char* message) override
213 {
214 CLog::Log(logLevel, "{0:s}", message);
215 }
216};
217} // namespace XbmcUtils