c++windowsboostservicepoco

Windows services and logging frameworks and AppVerifier


I have a Windows service that is written in C++. I recently became aware of the Microsoft Application Verifier Tool that can be used to catch not so obvious memory leaks and other such problems.

I've discovered that if I turn on all the checks in Application Verifier, my service will always crash. After a bunch of debugging, I figured out it's specifically the logging framework that is causing the crashes.

I came up with a simple reproducible example which is not a service, but just a simple application using the POCO logging framework. I also did one with Boost, just to compare.

POCO:

#include <Poco/Logger.h>
#include <Poco/ConsoleChannel.h>
#include <Poco/AutoPtr.h>
#include <Poco/FormattingChannel.h>
#include <Poco/PatternFormatter.h>

int main(int argc, char* argv[])
{
    using namespace Poco;

    // Create a formatter that shows timestamp, priority and message
    AutoPtr<PatternFormatter> formatter = new PatternFormatter;
    formatter->setProperty("pattern", "%Y-%m-%d %H:%M:%S [%p] %t");

    // Wrap the console channel in a formatting channel
    AutoPtr<FormattingChannel> formattingChannel = new FormattingChannel(formatter, new ConsoleChannel);
    formattingChannel->open();

    // Create and configure the logger
    Logger& logger = Logger::get("MainLogger");
    logger.setChannel(formattingChannel);
    logger.setLevel(Message::PRIO_INFORMATION);

    for (;;)
    {
        // Log some messages
        logger.information("This is an informational message.");
        logger.warning("This is a warning message.");
        logger.error("This is an error message.");
        Sleep(1000);
    }

    return 0;
}

Boost:

#include <iostream>
#include <boost/log/trivial.hpp>

int main(int argc, char* argv[])
{
    for (;;)
    {
        BOOST_LOG_TRIVIAL(info) << "This is an informational severity message";
        Sleep(1000);
    }
    return 0;
}

I've discovered that neither of them will run successfully with all the App Verifier tests turned on. For the POCO example, I only have to turn off the Low Resource Simulation, but for the boost example, I have to turn off both the Low Resource Simulation and Networking before it'll run reliably.

I'm not sure what this means. Should I avoid logging frameworks in order to keep my service reliable, or is this to be expected?


Solution

  • I've discovered that if I turn on all the checks in Application Verifier, my service will always crash. After a bunch of debugging, I figured out it's specifically the logging framework that is causing the crashes.

    Going by your Boost reproducer¹, and taking "if I turn on all the checks in Application Verifier" literally, I think you're seeing the obvious result of emulating low-memory conditions:

    enter image description here

    Indeed, you will note that if you use "Enable All Tests" menu item it will NOT enable this test, because it will lead to errors. In this case, Log frameworks are throwing std::bad_alloc exceptions because Heap allocations are "failing". Because you asked AppVerifier to.

    With "Low Resource Simulation"

    Without "Low Resource Simulation"


    ¹ Boost 1.86.0, MSVC (VS 17.7)