1 /* 2 * synergy -- mouse and keyboard sharing utility 3 * Copyright (C) 2012-2016 Symless Ltd. 4 * Copyright (C) 2002 Chris Schoeneman 5 * 6 * This package is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU General Public License 8 * found in the file LICENSE that should have accompanied this file. 9 * 10 * This package is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 * GNU General Public License for more details. 14 * 15 * You should have received a copy of the GNU General Public License 16 * along with this program. If not, see <http://www.gnu.org/licenses/>. 17 */ 18 19 #pragma once 20 21 #include "arch/IArchMultithread.h" 22 #include "arch/Arch.h" 23 #include "common/common.h" 24 #include "common/stdlist.h" 25 26 #include <stdarg.h> 27 28 #define CLOG (Log::getInstance()) 29 #define BYE "\nTry `%s --help' for more information." 30 31 class ILogOutputter; 32 class Thread; 33 34 //! Logging facility 35 /*! 36 The logging class; all console output should go through this class. 37 It supports multithread safe operation, several message priority levels, 38 filtering by priority, and output redirection. The macros LOG() and 39 LOGC() provide convenient access. 40 */ 41 class Log { 42 public: 43 Log(); 44 Log(Log* src); 45 Log(Log const &) =delete; 46 Log(Log &&) =delete; 47 ~Log(); 48 49 Log& operator=(Log const &) =delete; 50 Log& operator=(Log &&) =delete; 51 52 //! @name manipulators 53 //@{ 54 55 //! Add an outputter to the head of the list 56 /*! 57 Inserts an outputter to the head of the outputter list. When the 58 logger writes a message, it goes to the outputter at the head of 59 the outputter list. If that outputter's \c write() method returns 60 true then it also goes to the next outputter, as so on until an 61 outputter returns false or there are no more outputters. Outputters 62 still in the outputter list when the log is destroyed will be 63 deleted. If \c alwaysAtHead is true then the outputter is always 64 called before all outputters with \c alwaysAtHead false and the 65 return value of the outputter is ignored. 66 67 By default, the logger has one outputter installed which writes to 68 the console. 69 */ 70 void insert(ILogOutputter* adopted, 71 bool alwaysAtHead = false); 72 73 //! Remove an outputter from the list 74 /*! 75 Removes the first occurrence of the given outputter from the 76 outputter list. It does nothing if the outputter is not in the 77 list. The outputter is not deleted. 78 */ 79 void remove(ILogOutputter* orphaned); 80 81 //! Remove the outputter from the head of the list 82 /*! 83 Removes and deletes the outputter at the head of the outputter list. 84 This does nothing if the outputter list is empty. Only removes 85 outputters that were inserted with the matching \c alwaysAtHead. 86 */ 87 void pop_front(bool alwaysAtHead = false); 88 89 //! Set the minimum priority filter. 90 /*! 91 Set the filter. Messages below this priority are discarded. 92 The default priority is 4 (INFO) (unless built without NDEBUG 93 in which case it's 5 (DEBUG)). setFilter(const char*) returns 94 true if the priority \c name was recognized; if \c name is NULL 95 then it simply returns true. 96 */ 97 bool setFilter(const char* name); 98 99 //! Set the minimum priority filter (by ordinal). 100 void setFilter(int); 101 102 //@} 103 //! @name accessors 104 //@{ 105 106 //! Print a log message 107 /*! 108 Print a log message using the printf-like \c format and arguments 109 preceded by the filename and line number. If \c file is NULL then 110 neither the file nor the line are printed. 111 */ 112 void print(const char* file, int line, 113 const char* format, ...); 114 115 //! Get the minimum priority level. 116 int getFilter() const; 117 118 //! Get the filter name of the current filter level. 119 const char* getFilterName() const; 120 121 //! Get the filter name of a specified filter level. 122 const char* getFilterName(int level) const; 123 124 //! Get the singleton instance of the log 125 static Log* getInstance(); 126 127 //! Get the console filter level (messages above this are not sent to console). getConsoleMaxLevel()128 int getConsoleMaxLevel() const { return kDEBUG2; } 129 130 //@} 131 132 private: 133 void output(ELevel priority, char* msg); 134 135 private: 136 typedef std::list<ILogOutputter*> OutputterList; 137 138 static Log* s_log; 139 140 ArchMutex m_mutex; 141 OutputterList m_outputters; 142 OutputterList m_alwaysOutputters; 143 int m_maxNewlineLength; 144 int m_maxPriority; 145 }; 146 147 /*! 148 \def LOG(arg) 149 Write to the log. Because macros cannot accept variable arguments, this 150 should be invoked like so: 151 \code 152 LOG((CLOG_XXX "%d and %d are %s", x, y, x == y ? "equal" : "not equal")); 153 \endcode 154 In particular, notice the double open and close parentheses. Also note 155 that there is no comma after the \c CLOG_XXX. The \c XXX should be 156 replaced by one of enumerants in \c Log::ELevel without the leading 157 \c k. For example, \c CLOG_INFO. The special \c CLOG_PRINT level will 158 not be filtered and is never prefixed by the filename and line number. 159 160 If \c NOLOGGING is defined during the build then this macro expands to 161 nothing. If \c NDEBUG is defined during the build then it expands to a 162 call to Log::print. Otherwise it expands to a call to Log::print, 163 which includes the filename and line number. 164 */ 165 166 /*! 167 \def LOGC(expr, arg) 168 Write to the log if and only if expr is true. Because macros cannot accept 169 variable arguments, this should be invoked like so: 170 \code 171 LOGC(x == y, (CLOG_XXX "%d and %d are equal", x, y)); 172 \endcode 173 In particular, notice the parentheses around everything after the boolean 174 expression. Also note that there is no comma after the \c CLOG_XXX. 175 The \c XXX should be replaced by one of enumerants in \c Log::ELevel 176 without the leading \c k. For example, \c CLOG_INFO. The special 177 \c CLOG_PRINT level will not be filtered and is never prefixed by the 178 filename and line number. 179 180 If \c NOLOGGING is defined during the build then this macro expands to 181 nothing. If \c NDEBUG is not defined during the build then it expands 182 to a call to Log::print that prints the filename and line number, 183 otherwise it expands to a call that doesn't. 184 */ 185 186 #if defined(NOLOGGING) 187 #define LOG(_a1) 188 #define LOGC(_a1, _a2) 189 #define CLOG_TRACE 190 #elif defined(NDEBUG) 191 #define LOG(_a1) CLOG->print _a1 192 #define LOGC(_a1, _a2) if (_a1) CLOG->print _a2 193 #define CLOG_TRACE NULL, 0, 194 #else 195 #define LOG(_a1) CLOG->print _a1 196 #define LOGC(_a1, _a2) if (_a1) CLOG->print _a2 197 #define CLOG_TRACE __FILE__, __LINE__, 198 #endif 199 200 // the CLOG_* defines are line and file plus %z and an octal number (060=0, 201 // 071=9), but the limitation is that once we run out of numbers at either 202 // end, then we resort to using non-numerical chars. this still works (since 203 // to deduce the number we subtract octal \060, so '/' is -1, and ':' is 10 204 205 #define CLOG_PRINT CLOG_TRACE "%z\057" // char is '/' 206 #define CLOG_CRIT CLOG_TRACE "%z\060" // char is '0' 207 #define CLOG_ERR CLOG_TRACE "%z\061" 208 #define CLOG_WARN CLOG_TRACE "%z\062" 209 #define CLOG_NOTE CLOG_TRACE "%z\063" 210 #define CLOG_INFO CLOG_TRACE "%z\064" 211 #define CLOG_DEBUG CLOG_TRACE "%z\065" 212 #define CLOG_DEBUG1 CLOG_TRACE "%z\066" 213 #define CLOG_DEBUG2 CLOG_TRACE "%z\067" 214 #define CLOG_DEBUG3 CLOG_TRACE "%z\070" 215 #define CLOG_DEBUG4 CLOG_TRACE "%z\071" // char is '9' 216 #define CLOG_DEBUG5 CLOG_TRACE "%z\072" // char is ':' 217