How to remove log debugging statements from a prog

2019-04-08 12:08发布

I am using boost::log as a logger for my C++ program. During development I often use it this way, for example:

#define LOG(severity) BOOST_LOG_SEV(boost::logger::get(), (severity))
#define LOG_ERR LOG(Severity::error)
#define LOG_INFO LOG(Severity::info)
#define LOG_DEBUG LOG(Severity::debug)

where BOOST_LOG_SEV is the facility provided by boost::log, while LOG, LOG_ERROR, LOG_INFO, LOG_DEBUG are shortcuts defined by me.

In short, BOOST_LOG_SEV dynamically compares the current debugging severity with the severity passed to the macro itself to decide whether to emit the output or not.

This is an example of a program which use the above macros for debugging purposes:

// set at compile time
#define MAX_LOG_SEVERITY Severity::debug

int main() {
   // Print all the messages with a
   // Severity <= MAX_LOG_SEVERITY defined before compiling
   boost::log::set_severity(boost::logger::get(), MAX_LOG_SEVERITY); // set_severity() is fictitious just to give you an idea

   // bool err = ...
   if (err)
      LOG_ERR << "An error occurred";
   else 
      LOG_INFO << "Okay;
   LOG_DEBUG << "main() called";
}

Now, when releasing the program for a production environment, debugging messages with a Severity::debug level do not really make sense. I could hide them from the output by simply decreasing MAX_LOG_SEVERITY to Severity::info, but the problem is that the calls made by LOG_DEBUG will not be removed from the executable code. This has a bad impact on both efficiency and object size.

The code is full of logging statements and I'd really like to preserve the simple use of operator<<().

Without touching those statements themselves, is there any better macro definition/trick for LOG_DEBUG that would make the pre-processor or the compiler (during its optimizations) "skip" or "remove" the debugging statements when MAX_LOG_SEVERITY is set to the Severity::debug constant ?

3条回答
在下西门庆
2楼-- · 2019-04-08 12:52

Turns off all optimizations in the program and speeds compilation.

/Od or boot_log_stop

查看更多
冷血范
3楼-- · 2019-04-08 12:53

While I can't make any guarantees, something like this might work. It depends on what your optimizer does and whether or not you have side effects in the parameters to operator<<.

#ifdef NO_LOG_DEBUG

static class DevNull
{
} dev_null;

template <typename T>
DevNull & operator<<(DevNull & dest, T)
{
    return dest;
}

#define LOG_DEBUG dev_null

#else

#define LOG_DEBUG LOG(Severity::debug)

#endif
查看更多
老娘就宠你
4楼-- · 2019-04-08 12:58

@MartinShobe's accepted answer works on:

  • g++ (4.7.2) with -O1 and higher
  • clang++ (3.4) with -O2 and higher
  • Visual Studio (2008) with linker flag /OPT:REF
查看更多
登录 后发表回答