LCOV - code coverage report
Current view: top level - media/webrtc/trunk/webrtc/base - logging.h (source / functions) Hit Total Coverage
Test: output.info Lines: 0 10 0.0 %
Date: 2017-07-14 16:53:18 Functions: 0 10 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*
       2             :  *  Copyright 2004 The WebRTC Project Authors. All rights reserved.
       3             :  *
       4             :  *  Use of this source code is governed by a BSD-style license
       5             :  *  that can be found in the LICENSE file in the root of the source
       6             :  *  tree. An additional intellectual property rights grant can be found
       7             :  *  in the file PATENTS.  All contributing project authors may
       8             :  *  be found in the AUTHORS file in the root of the source tree.
       9             :  */
      10             : 
      11             : //   LOG(...) an ostream target that can be used to send formatted
      12             : // output to a variety of logging targets, such as debugger console, stderr,
      13             : // or any LogSink.
      14             : //   The severity level passed as the first argument to the LOGging
      15             : // functions is used as a filter, to limit the verbosity of the logging.
      16             : //   Static members of LogMessage documented below are used to control the
      17             : // verbosity and target of the output.
      18             : //   There are several variations on the LOG macro which facilitate logging
      19             : // of common error conditions, detailed below.
      20             : 
      21             : // LOG(sev) logs the given stream at severity "sev", which must be a
      22             : //     compile-time constant of the LoggingSeverity type, without the namespace
      23             : //     prefix.
      24             : // LOG_V(sev) Like LOG(), but sev is a run-time variable of the LoggingSeverity
      25             : //     type (basically, it just doesn't prepend the namespace).
      26             : // LOG_F(sev) Like LOG(), but includes the name of the current function.
      27             : // LOG_T(sev) Like LOG(), but includes the this pointer.
      28             : // LOG_T_F(sev) Like LOG_F(), but includes the this pointer.
      29             : // LOG_GLE(M)(sev [, mod]) attempt to add a string description of the
      30             : //     HRESULT returned by GetLastError.  The "M" variant allows searching of a
      31             : //     DLL's string table for the error description.
      32             : // LOG_ERRNO(sev) attempts to add a string description of an errno-derived
      33             : //     error. errno and associated facilities exist on both Windows and POSIX,
      34             : //     but on Windows they only apply to the C/C++ runtime.
      35             : // LOG_ERR(sev) is an alias for the platform's normal error system, i.e. _GLE on
      36             : //     Windows and _ERRNO on POSIX.
      37             : // (The above three also all have _EX versions that let you specify the error
      38             : // code, rather than using the last one.)
      39             : // LOG_E(sev, ctx, err, ...) logs a detailed error interpreted using the
      40             : //     specified context.
      41             : // LOG_CHECK_LEVEL(sev) (and LOG_CHECK_LEVEL_V(sev)) can be used as a test
      42             : //     before performing expensive or sensitive operations whose sole purpose is
      43             : //     to output logging data at the desired level.
      44             : // Lastly, PLOG(sev, err) is an alias for LOG_ERR_EX.
      45             : 
      46             : #ifndef WEBRTC_BASE_LOGGING_H_
      47             : #define WEBRTC_BASE_LOGGING_H_
      48             : 
      49             : #include <errno.h>
      50             : 
      51             : #include <list>
      52             : #include <sstream>
      53             : #include <string>
      54             : #include <utility>
      55             : 
      56             : #if defined(WEBRTC_MAC) && !defined(WEBRTC_IOS)
      57             : #include <CoreServices/CoreServices.h>
      58             : #endif
      59             : 
      60             : #include "webrtc/base/basictypes.h"
      61             : #include "webrtc/base/constructormagic.h"
      62             : #include "webrtc/base/thread_annotations.h"
      63             : 
      64             : namespace rtc {
      65             : 
      66             : ///////////////////////////////////////////////////////////////////////////////
      67             : // ConstantLabel can be used to easily generate string names from constant
      68             : // values.  This can be useful for logging descriptive names of error messages.
      69             : // Usage:
      70             : //   const ConstantLabel LIBRARY_ERRORS[] = {
      71             : //     KLABEL(SOME_ERROR),
      72             : //     KLABEL(SOME_OTHER_ERROR),
      73             : //     ...
      74             : //     LASTLABEL
      75             : //   }
      76             : //
      77             : //   int err = LibraryFunc();
      78             : //   LOG(LS_ERROR) << "LibraryFunc returned: "
      79             : //                 << ErrorName(err, LIBRARY_ERRORS);
      80             : 
      81             : struct ConstantLabel { int value; const char * label; };
      82             : #define KLABEL(x) { x, #x }
      83             : #define TLABEL(x, y) { x, y }
      84             : #define LASTLABEL { 0, 0 }
      85             : 
      86             : const char* FindLabel(int value, const ConstantLabel entries[]);
      87             : std::string ErrorName(int err, const ConstantLabel* err_table);
      88             : 
      89             : #if defined(WEBRTC_MAC) && !defined(WEBRTC_IOS)
      90             : // Returns a UTF8 description from an OS X Status error.
      91             : std::string DescriptionFromOSStatus(OSStatus err);
      92             : #endif
      93             : 
      94             : //////////////////////////////////////////////////////////////////////
      95             : 
      96             : // Note that the non-standard LoggingSeverity aliases exist because they are
      97             : // still in broad use.  The meanings of the levels are:
      98             : //  LS_SENSITIVE: Information which should only be logged with the consent
      99             : //   of the user, due to privacy concerns.
     100             : //  LS_VERBOSE: This level is for data which we do not want to appear in the
     101             : //   normal debug log, but should appear in diagnostic logs.
     102             : //  LS_INFO: Chatty level used in debugging for all sorts of things, the default
     103             : //   in debug builds.
     104             : //  LS_WARNING: Something that may warrant investigation.
     105             : //  LS_ERROR: Something that should not have occurred.
     106             : //  LS_NONE: Don't log.
     107             : enum LoggingSeverity {
     108             :   LS_SENSITIVE,
     109             :   LS_VERBOSE,
     110             :   LS_INFO,
     111             :   LS_WARNING,
     112             :   LS_ERROR,
     113             :   LS_NONE,
     114             :   INFO = LS_INFO,
     115             :   WARNING = LS_WARNING,
     116             :   LERROR = LS_ERROR
     117             : };
     118             : 
     119             : // LogErrorContext assists in interpreting the meaning of an error value.
     120             : enum LogErrorContext {
     121             :   ERRCTX_NONE,
     122             :   ERRCTX_ERRNO,     // System-local errno
     123             :   ERRCTX_HRESULT,   // Windows HRESULT
     124             :   ERRCTX_OSSTATUS,  // MacOS OSStatus
     125             : 
     126             :   // Abbreviations for LOG_E macro
     127             :   ERRCTX_EN = ERRCTX_ERRNO,     // LOG_E(sev, EN, x)
     128             :   ERRCTX_HR = ERRCTX_HRESULT,   // LOG_E(sev, HR, x)
     129             :   ERRCTX_OS = ERRCTX_OSSTATUS,  // LOG_E(sev, OS, x)
     130             : };
     131             : 
     132             : // Virtual sink interface that can receive log messages.
     133             : class LogSink {
     134             :  public:
     135           0 :   LogSink() {}
     136           0 :   virtual ~LogSink() {}
     137             :   virtual void OnLogMessage(const std::string& message) = 0;
     138             : };
     139             : 
     140             : class LogMessage {
     141             :  public:
     142             :   LogMessage(const char* file, int line, LoggingSeverity sev,
     143             :              LogErrorContext err_ctx = ERRCTX_NONE, int err = 0,
     144             :              const char* module = NULL);
     145             : 
     146             :   LogMessage(const char* file,
     147             :              int line,
     148             :              LoggingSeverity sev,
     149             :              const std::string& tag);
     150             : 
     151             :   ~LogMessage();
     152             : 
     153           0 :   static inline bool Loggable(LoggingSeverity sev) { return (sev >= min_sev_); }
     154           0 :   std::ostream& stream() { return print_stream_; }
     155             : 
     156             :   // Returns the time at which this function was called for the first time.
     157             :   // The time will be used as the logging start time.
     158             :   // If this is not called externally, the LogMessage ctor also calls it, in
     159             :   // which case the logging start time will be the time of the first LogMessage
     160             :   // instance is created.
     161             :   static int64_t LogStartTime();
     162             : 
     163             :   // Returns the wall clock equivalent of |LogStartTime|, in seconds from the
     164             :   // epoch.
     165             :   static uint32_t WallClockStartTime();
     166             : 
     167             :   //  LogThreads: Display the thread identifier of the current thread
     168             :   static void LogThreads(bool on = true);
     169             : 
     170             :   //  LogTimestamps: Display the elapsed time of the program
     171             :   static void LogTimestamps(bool on = true);
     172             : 
     173             :   // These are the available logging channels
     174             :   //  Debug: Debug console on Windows, otherwise stderr
     175             :   static void LogToDebug(LoggingSeverity min_sev);
     176           0 :   static LoggingSeverity GetLogToDebug() { return dbg_sev_; }
     177             : 
     178             :   // Sets whether logs will be directed to stderr in debug mode.
     179             :   static void SetLogToStderr(bool log_to_stderr);
     180             : 
     181             :   //  Stream: Any non-blocking stream interface.  LogMessage takes ownership of
     182             :   //   the stream. Multiple streams may be specified by using AddLogToStream.
     183             :   //   LogToStream is retained for backwards compatibility; when invoked, it
     184             :   //   will discard any previously set streams and install the specified stream.
     185             :   //   GetLogToStream gets the severity for the specified stream, of if none
     186             :   //   is specified, the minimum stream severity.
     187             :   //   RemoveLogToStream removes the specified stream, without destroying it.
     188             :   static int GetLogToStream(LogSink* stream = NULL);
     189             :   static void AddLogToStream(LogSink* stream, LoggingSeverity min_sev);
     190             :   static void RemoveLogToStream(LogSink* stream);
     191             : 
     192             :   // Testing against MinLogSeverity allows code to avoid potentially expensive
     193             :   // logging operations by pre-checking the logging level.
     194           0 :   static int GetMinLogSeverity() { return min_sev_; }
     195             : 
     196             :   // Parses the provided parameter stream to configure the options above.
     197             :   // Useful for configuring logging from the command line.
     198             :   static void ConfigureLogging(const char* params);
     199             : 
     200             :  private:
     201             :   typedef std::pair<LogSink*, LoggingSeverity> StreamAndSeverity;
     202             :   typedef std::list<StreamAndSeverity> StreamList;
     203             : 
     204             :   // Updates min_sev_ appropriately when debug sinks change.
     205             :   static void UpdateMinLogSeverity();
     206             : 
     207             :   // These write out the actual log messages.
     208             :   static void OutputToDebug(const std::string& msg,
     209             :                             LoggingSeverity severity,
     210             :                             const std::string& tag);
     211             : 
     212             :   // The ostream that buffers the formatted message before output
     213             :   std::ostringstream print_stream_;
     214             : 
     215             :   // The severity level of this message
     216             :   LoggingSeverity severity_;
     217             : 
     218             :   // The Android debug output tag.
     219             :   std::string tag_;
     220             : 
     221             :   // String data generated in the constructor, that should be appended to
     222             :   // the message before output.
     223             :   std::string extra_;
     224             : 
     225             :   // dbg_sev_ is the thresholds for those output targets
     226             :   // min_sev_ is the minimum (most verbose) of those levels, and is used
     227             :   //  as a short-circuit in the logging macros to identify messages that won't
     228             :   //  be logged.
     229             :   // ctx_sev_ is the minimum level at which file context is displayed
     230             :   static LoggingSeverity min_sev_, dbg_sev_, ctx_sev_;
     231             : 
     232             :   // The output streams and their associated severities
     233             :   static StreamList streams_;
     234             : 
     235             :   // Flags for formatting options
     236             :   static bool thread_, timestamp_;
     237             : 
     238             :   // Determines if logs will be directed to stderr in debug mode.
     239             :   static bool log_to_stderr_;
     240             : 
     241             :   RTC_DISALLOW_COPY_AND_ASSIGN(LogMessage);
     242             : };
     243             : 
     244             : //////////////////////////////////////////////////////////////////////
     245             : // Logging Helpers
     246             : //////////////////////////////////////////////////////////////////////
     247             : 
     248             : class LogMultilineState {
     249             :  public:
     250             :   size_t unprintable_count_[2];
     251             :   LogMultilineState() {
     252             :     unprintable_count_[0] = unprintable_count_[1] = 0;
     253             :   }
     254             : };
     255             : 
     256             : // When possible, pass optional state variable to track various data across
     257             : // multiple calls to LogMultiline.  Otherwise, pass NULL.
     258             : void LogMultiline(LoggingSeverity level, const char* label, bool input,
     259             :                   const void* data, size_t len, bool hex_mode,
     260             :                   LogMultilineState* state);
     261             : 
     262             : #ifndef LOG
     263             : 
     264             : // The following non-obvious technique for implementation of a
     265             : // conditional log stream was stolen from google3/base/logging.h.
     266             : 
     267             : // This class is used to explicitly ignore values in the conditional
     268             : // logging macros.  This avoids compiler warnings like "value computed
     269             : // is not used" and "statement has no effect".
     270             : 
     271             : class LogMessageVoidify {
     272             :  public:
     273           0 :   LogMessageVoidify() { }
     274             :   // This has to be an operator with a precedence lower than << but
     275             :   // higher than ?:
     276           0 :   void operator&(std::ostream&) { }
     277             : };
     278             : 
     279             : #define LOG_SEVERITY_PRECONDITION(sev) \
     280             :   !(rtc::LogMessage::Loggable(sev)) \
     281             :     ? (void) 0 \
     282             :     : rtc::LogMessageVoidify() &
     283             : 
     284             : #define LOG(sev) \
     285             :   LOG_SEVERITY_PRECONDITION(rtc::sev) \
     286             :     rtc::LogMessage(__FILE__, __LINE__, rtc::sev).stream()
     287             : 
     288             : // The _V version is for when a variable is passed in.  It doesn't do the
     289             : // namespace concatination.
     290             : #define LOG_V(sev) \
     291             :   LOG_SEVERITY_PRECONDITION(sev) \
     292             :     rtc::LogMessage(__FILE__, __LINE__, sev).stream()
     293             : 
     294             : // The _F version prefixes the message with the current function name.
     295             : #if (defined(__GNUC__) && !defined(NDEBUG)) || defined(WANT_PRETTY_LOG_F)
     296             : #define LOG_F(sev) LOG(sev) << __PRETTY_FUNCTION__ << ": "
     297             : #define LOG_T_F(sev) LOG(sev) << this << ": " << __PRETTY_FUNCTION__ << ": "
     298             : #else
     299             : #define LOG_F(sev) LOG(sev) << __FUNCTION__ << ": "
     300             : #define LOG_T_F(sev) LOG(sev) << this << ": " << __FUNCTION__ << ": "
     301             : #endif
     302             : 
     303             : #define LOG_CHECK_LEVEL(sev) \
     304             :   rtc::LogCheckLevel(rtc::sev)
     305             : #define LOG_CHECK_LEVEL_V(sev) \
     306             :   rtc::LogCheckLevel(sev)
     307             : 
     308           0 : inline bool LogCheckLevel(LoggingSeverity sev) {
     309           0 :   return (LogMessage::GetMinLogSeverity() <= sev);
     310             : }
     311             : 
     312             : #define LOG_E(sev, ctx, err, ...) \
     313             :   LOG_SEVERITY_PRECONDITION(rtc::sev) \
     314             :     rtc::LogMessage(__FILE__, __LINE__, rtc::sev, \
     315             :                           rtc::ERRCTX_ ## ctx, err , ##__VA_ARGS__) \
     316             :         .stream()
     317             : 
     318             : #define LOG_T(sev) LOG(sev) << this << ": "
     319             : 
     320             : #define LOG_ERRNO_EX(sev, err) \
     321             :   LOG_E(sev, ERRNO, err)
     322             : #define LOG_ERRNO(sev) \
     323             :   LOG_ERRNO_EX(sev, errno)
     324             : 
     325             : #if defined(WEBRTC_WIN)
     326             : #define LOG_GLE_EX(sev, err) \
     327             :   LOG_E(sev, HRESULT, err)
     328             : #define LOG_GLE(sev) \
     329             :   LOG_GLE_EX(sev, GetLastError())
     330             : #define LOG_GLEM(sev, mod) \
     331             :   LOG_E(sev, HRESULT, GetLastError(), mod)
     332             : #define LOG_ERR_EX(sev, err) \
     333             :   LOG_GLE_EX(sev, err)
     334             : #define LOG_ERR(sev) \
     335             :   LOG_GLE(sev)
     336             : #define LAST_SYSTEM_ERROR \
     337             :   (::GetLastError())
     338             : #elif defined(__native_client__) && __native_client__
     339             : #define LOG_ERR_EX(sev, err) \
     340             :   LOG(sev)
     341             : #define LOG_ERR(sev) \
     342             :   LOG(sev)
     343             : #define LAST_SYSTEM_ERROR \
     344             :   (0)
     345             : #elif defined(WEBRTC_POSIX)
     346             : #define LOG_ERR_EX(sev, err) \
     347             :   LOG_ERRNO_EX(sev, err)
     348             : #define LOG_ERR(sev) \
     349             :   LOG_ERRNO(sev)
     350             : #define LAST_SYSTEM_ERROR \
     351             :   (errno)
     352             : #endif  // WEBRTC_WIN
     353             : 
     354             : #define LOG_TAG(sev, tag) \
     355             :   LOG_SEVERITY_PRECONDITION(sev) \
     356             :     rtc::LogMessage(NULL, 0, sev, tag).stream()
     357             : 
     358             : #define PLOG(sev, err) \
     359             :   LOG_ERR_EX(sev, err)
     360             : 
     361             : // TODO(?): Add an "assert" wrapper that logs in the same manner.
     362             : 
     363             : #endif  // LOG
     364             : 
     365             : }  // namespace rtc
     366             : 
     367             : #endif  // WEBRTC_BASE_LOGGING_H_

Generated by: LCOV version 1.13