Corrade::Utility::Debug class

Debug output handler.

Provides convenient stream interface for passing data to debug output (standard output). Data are by default separated with spaces and last value is enclosed with newline character. Example usage:

// Common usage
Utility::Debug{} << "string" << 34 << 275.0f;

// Redirect debug output to string
std::ostringstream o;
Utility::Debug{&o} << "the meaning of life, universe and everything is" << 42;

// Mute debug output
Utility::Debug{nullptr} << "no one should see my ebanking password" << pwd;

// Conditional debug output (avoid inserting newline where it's not desired)
Utility::Debug d;
d << "Cannot foo";
if(bar)
    d << "because of bar.";
else
    d << "because of everything else.";
// (newline character will be written to output on object destruction)

Support for printing more types can be added by implementing an overload of operator<<(Debug&, const T&) for given type.

Printing STL types

To optimize compile times, the Corrade/Utility/Debug.h header provides only support for printing builtin types, generic iterable containers and std::pair. Printing of std::string and std::tuple is possible if you include Corrade/Utility/DebugStl.h. The support is provided in a separate header to avoid unconditional #include <string> or #include <tuple>, which significantly affect compile times. This header also provides a fallback to std::ostream operator<<() overloads, if there's no operator<<() implemented for printing given type using Debug. Note that printing std::vector or std::map containers is already possible with the generic iterable container support in Corrade/Utility/Debug.h.

On compilers that support C++17 and std::string_view, support for printing it is provided Corrade/Utility/DebugStlStringView.h. For similar reasons, it's a dedicated header to avoid unconditional #include <string_view>, but this one is even significantly heavier than the <string> etc. includes on certain implementations, so it's separate from the others as well.

Scoped output redirection

Output specified in class constructor is used for all instances created during that instance lifetime. Debug, Warning and Error classes outputs can be controlled separately:

std::ostringstream debugOut, errorOut;

Utility::Error{} << "this is printed into std::cerr";

Utility::Error redirectError{&errorOut};

{
    Utility::Debug redirectDebug{&debugOut};

    Utility::Debug{} << "this is printed into debugOut";
    Utility::Error{} << "this is printed into errorOut";
    Utility::Debug{} << "this is also printed into debugOut";
}

Utility::Debug{} << "this is printed into std::cout again";
Utility::Error{} << "this is still printed into errorOut";

Output modifiers

It's possible to modify the output behavior by calling setFlags() or setImmediateFlags(). The latter function applies given flag only to the immediately following value (and then it gets reset back) instead of all following values. For convenience, the operation of setFlags() / setImmediateFlags() can be done or by passing a special function to the output stream.

Explicit whitespace control

Sometimes you might not want to have everything separated by spaces or having newline at the end — use Flag::NoNewlineAtTheEnd or the nospace modifier:

// Prints "Value: 16, 24"
Utility::Debug{} << "Value:" << 16 << Utility::Debug::nospace << "," << 24;

// Prints "Value\n16"
Utility::Debug{} << "Value:" << Utility::Debug::newline << 16;

// Doesn't output newline at the end
Utility::Debug{Utility::Debug::Flag::NoNewlineAtTheEnd} << "Hello!";

Printing numbers in a different base

With Flag::Hex or the hex modifier, integers will be printed as hexadecimal. Pointer values are printed as hexadecimal always, cast them to an integer type to print them as decimal.

// Prints 0xc0ffee
Utility::Debug{} << Utility::Debug::hex << 0xc0ffee;

Colored output

It is possible to color the output using color(), boldColor() and invertedColor(). The color is automatically reset to previous value on destruction to avoid messing up the terminal, you can also use resetColor() to reset it explicitly.

Utility::Debug{}
    << Utility::Debug::boldColor(Utility::Debug::Color::Green) << "Success!"
    << Utility::Debug::resetColor << "Everything is fine.";
Success! Everything is fine.

On POSIX the coloring is done using ANSI color escape sequences and works both when outputting to a terminal or any other stream. On Windows, by default due to a platform limitation, the colored output works only when outputting directly to a terminal without any intermediate buffer. See CORRADE_UTILITY_USE_ANSI_COLORS for possible alternative.

Note that colors make sense only when they finally appear in a terminal and not when redirecting output to file. You can control this by setting Flag::DisableColors based on value of isTty(), for example:

Utility::Debug::Flags flags = Utility::Debug::isTty() ?
    Utility::Debug::Flags{} : Utility::Debug::Flag::DisableColors;
Utility::Debug{flags}
    << Utility::Debug::boldColor(Utility::Debug::Color::Green) << "Success!";

Similarly as with scoped output redirection, colors can be also scoped:

Utility::Debug{} << "this has default color";

{
    Utility::Debug d;
    if(errorHappened) d << Utility::Debug::color(Utility::Debug::Color::Red);

    Utility::Debug{} << "if an error happened, this will be printed red";
    Utility::Debug{} << "this also"
        << Utility::Debug::boldColor(Utility::Debug::Color::Blue)
        << "and this blue";
}

Utility::Debug{} << "this has default color again";

With Flag::Color and/or the color modifier, some types can be also printed as actual 24bit colors. The operator<<(unsigned char) printer can interpret 8bit values as grayscale colors and other libraries may provide support for other types. For example, printing a container of 8bit values together with the packed modifier:

unsigned char data[] { 0, 32, 64, 96, 128, 160, 192, 224, 255 };
Utility::Debug{} << "41 shades of gray missing:"
    << Utility::Debug::packed << Utility::Debug::color
    << Containers::arrayView(data);

This prints the below output on terminals that support it. See the operator documentation for more information.

41 shades of gray missing:     ░░░░▒▒▓▓▓▓████

Source location

Similarly to the dbg! macro in Rust, on supported compilers the utility is able to print source file location and line where the debug output was executed, improving the "printf debugging" experience. By default no source location info is printed, in order to do that prefix the Debug instantiation with an exclamation mark. Additionally, an otherwise unused exclamated instantiation prints just the file + line alone (in contrast to unexclamated instantiaton, which is a no-op):

float a = 336;

!Utility::Debug{} << "the result is" << (a /= 8);
!Utility::Debug{} << "but here it's" << (a /= 8);

!Utility::Debug{};

Utility::Debug{} << "and finally, " << (a *= 8);

The above code then may print something like this:

main.cpp:10: the result is 42
main.cpp:11: the result is 5.25
main.cpp:13
and finally, 42

At the moment, this feature is available on GCC at least since version 4.8, Clang 9+ and MSVC 2019 16.6 and newer. Elsewhere it behaves like the unexclamated version. You can check for its availability using the CORRADE_SOURCE_LOCATION_BUILTINS_SUPPORTED predefined macro.

ANSI color support and UTF-8 output on Windows

See the Corrade::Main library for more information about a convenient way to support ANSI colors and UTF-8 output encoding on Windows.

Thread safety

If Corrade is compiled with CORRADE_BUILD_MULTITHREADED enabled (the default), scoped output redirection and coloring is done thread-locally. This might cause some performance penalties — if you are sure that you will never need to handle these per-thread (and won't need any other functionality enabled by this option either), build Corrade with the option disabled.

Derived classes

class Error
Error output handler.
class Warning
Warning output handler.

Public types

enum class Flag: unsigned short { NoNewlineAtTheEnd = 1 << 0, DisableColors = 1 << 1, NoSpace = 1 << 2, Packed = 1 << 3, Color = 1 << 4, Hex = 1 << 7 new in Git master } new in 2019.10
Debug output flag.
using Flags = Containers::EnumSet<Flag> new in 2019.10
Debug output flags.

Public static functions

static auto defaultOutput() -> std::ostream* new in 2019.10
Default debug output stream.
static auto output() -> std::ostream*
Current debug output stream.
static auto isTty(std::ostream* output) -> bool
Whether given output stream is a TTY.
static auto isTty() -> bool
Whether current debug output is a TTY.

Constructors, destructors, conversion operators

Debug(Flags flags = {}) explicit
Default constructor.
Debug(std::ostream* output, Flags flags = {}) explicit
Constructor.
Debug(const Debug&) deleted
Copying is not allowed.
Debug(Debug&&) defaulted
Move constructor.
~Debug()
Destructor.

Public functions

auto operator=(const Debug&) -> Debug& deleted
Copying is not allowed.
auto operator=(Debug&&) -> Debug& deleted
Move assignment is not allowed.
auto flags() const -> Flags new in 2019.10
Flags applied for all following values.
void setFlags(Flags flags) new in 2019.10
Set flags applied for all following values.
auto immediateFlags() const -> Flags new in 2019.10
Flags applied for the immediately following value.
void setImmediateFlags(Flags flags) new in 2019.10
Set flags to be applied for the immediately following value.
auto operator<<(const char* value) -> Debug&
Print string to debug output.
auto operator<<(Containers::StringView value) -> Debug& new in Git master
auto operator<<(Containers::MutableStringView value) -> Debug& new in Git master
auto operator<<(const Containers::String& value) -> Debug& new in Git master
auto operator<<(const void* value) -> Debug&
Print a pointer value to debug output.
auto operator<<(bool value) -> Debug&
Print a boolean value to debug output.
auto operator<<(char value) -> Debug&
Print char to debug output.
auto operator<<(unsigned char value) -> Debug&
Print unsigned char to debug output.
auto operator<<(int value) -> Debug&
auto operator<<(long value) -> Debug&
auto operator<<(long long value) -> Debug&
auto operator<<(unsigned value) -> Debug&
auto operator<<(unsigned long value) -> Debug&
auto operator<<(unsigned long long value) -> Debug&
auto operator<<(float value) -> Debug&
Print float value to debug output.
auto operator<<(double value) -> Debug&
Print double value to debug output.
auto operator<<(long double value) -> Debug&
Print long double value to debug output.
auto operator<<(char32_t value) -> Debug&
Print UTF-32 character to debug output.
auto operator<<(const char32_t* value) -> Debug&
Print UTF-32 character literal to debug output.
auto operator<<(std::nullptr_t) -> Debug&
Print a nullptr to debug output.

Output modifiers

See Output modifiers for more information.

enum class Color: char { Black = 0, Red = 1, Green = 2, Yellow = 3, Blue = 4, Magenta = 5, Cyan = 6, White = 7, Default = 9 }
Output color.
using Modifier = void(*)(Debug&)
Debug output modifier.
static void nospace(Debug& debug)
Don't put space before next value.
static void newline(Debug& debug)
Output a newline.
static void space(Debug& debug) new in 2020.06
Output a space.
static auto color(Color color) -> Modifier
Set output color.
static auto boldColor(Color color) -> Modifier
Set bold output color.
static auto invertedColor(Color color) -> Modifier new in Git master
Set inverted output color.
static void resetColor(Debug& debug)
Reset output color.
static void packed(Debug& debug) new in 2019.10
Print the next value in a packed form.
static void color(Debug& debug) new in 2019.10
Print the next value as a color.
static void hex(Debug& debug) new in Git master
Print the next value as hexadecimal.
auto operator<<(Modifier f) -> Debug&
Debug output modification.

Enum documentation

enum class Corrade::Utility::Debug::Flag: unsigned short new in 2019.10

Debug output flag.

Enumerators
NoNewlineAtTheEnd

Don't put newline at the end on destruction

DisableColors

Disable colored output in color(), boldColor() and resetColor().

NoSpace

Print without spaces between values.

Packed

Print complex values (such as containers) in a packed form.

Color

Print colored values as colored squares in the terminal.

Hex new in Git master

Print integer values as lowercase hexadecimal prefixed with 0x, e.g. 0xc0ffee instead of 12648430.

enum class Corrade::Utility::Debug::Color: char

Output color.

Enumerators
Black

Black

Red

Red

Green

Green

Yellow

Yellow

Blue

Blue

Magenta

Magenta

Cyan

Cyan

White

White

Default

Default (implementation/style-defined)

Typedef documentation

typedef Containers::EnumSet<Flag> Corrade::Utility::Debug::Flags new in 2019.10

Debug output flags.

typedef void(*Corrade::Utility::Debug::Modifier)(Debug&)

Debug output modifier.

Function documentation

static std::ostream* Corrade::Utility::Debug::defaultOutput() new in 2019.10

Default debug output stream.

Debug output when no output redirection happens. A pointer to std::cout.

static std::ostream* Corrade::Utility::Debug::output()

Current debug output stream.

Debug output constructed with the Debug(Flags) constructor will be using this output stream.

static bool Corrade::Utility::Debug::isTty(std::ostream* output)

Whether given output stream is a TTY.

Useful for deciding whether to use ANSI colored output using Flag::DisableColors. Returns true if output is a pointer to std::cout / std::cerr and the stream is not redirected to a file, false otherwise. Calls isatty() on Unix-like systems and Windows with CORRADE_UTILITY_USE_ANSI_COLORS enabled, calls Windows APIs if CORRADE_UTILITY_USE_ANSI_COLORS is disabled. On platforms without isatty() equivalent returns always false.

static bool Corrade::Utility::Debug::isTty()

Whether current debug output is a TTY.

Calls isTty(std::ostream*) with output of enclosing Debug instance or with std::cerr if there isn't any.

Corrade::Utility::Debug::Debug(Flags flags = {}) explicit

Default constructor.

Parameters
flags Output flags

Uses output of enclosing Debug instance or uses std::cout if there isn't any.

Corrade::Utility::Debug::Debug(std::ostream* output, Flags flags = {}) explicit

Constructor.

Parameters
output Stream where to put debug output. If set to nullptr, no debug output will be written anywhere.
flags Output flags

All new instances created using the default Debug() constructor during lifetime of this instance will inherit the output set in output.

Corrade::Utility::Debug::~Debug()

Destructor.

Resets the output redirection back to the output of enclosing scope. If there was any output, adds newline at the end. Also resets output color modifier, if there was any.

Flags Corrade::Utility::Debug::flags() const new in 2019.10

Flags applied for all following values.

void Corrade::Utility::Debug::setFlags(Flags flags) new in 2019.10

Set flags applied for all following values.

Flags Corrade::Utility::Debug::immediateFlags() const new in 2019.10

Flags applied for the immediately following value.

Returned value is a combination of flags() and immediate flags. The immediate part gets reset after a value is printed.

void Corrade::Utility::Debug::setImmediateFlags(Flags flags) new in 2019.10

Set flags to be applied for the immediately following value.

Unlike flags set with setFlags(), these get applied only to the immediately following value and reset after.

Debug& Corrade::Utility::Debug::operator<<(const char* value)

Print string to debug output.

If there is already something in the output, puts a space before the value, unless nospace was set immediately before.

Debug& Corrade::Utility::Debug::operator<<(Containers::StringView value) new in Git master

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Debug& Corrade::Utility::Debug::operator<<(Containers::MutableStringView value) new in Git master

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Debug& Corrade::Utility::Debug::operator<<(const Containers::String& value) new in Git master

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Debug& Corrade::Utility::Debug::operator<<(const void* value)

Print a pointer value to debug output.

The value is printed in lowercase hexadecimal prefixed with 0x, for example 0xdeadbeef. Equivalent to enabling Flag::Hex or using the hex modifier and printing reinterpret_cast<std::uintptr_t>(value) instead of value.

Debug& Corrade::Utility::Debug::operator<<(bool value)

Print a boolean value to debug output.

The value is printed as literal true or false.

Debug& Corrade::Utility::Debug::operator<<(char value)

Print char to debug output.

Printed as a numeric value.

Debug& Corrade::Utility::Debug::operator<<(unsigned char value)

Print unsigned char to debug output.

If Flag::Color is enabled or color was set immediately before, prints the value as a grayscale ANSI 24bit color escape sequence using two successive Unicode block characters (to have it roughly square). To preserve at least some information when text is copied, the square consists of one of the five ░▒▓█ shades, however the color is set for both foreground and background so the actual block character is indistinguishable when seen on a terminal. See the class documentation for more information.

If Flag::Color is enabled and Flag::DisableColors is set, only the shaded character is used, without any ANSI color escape sequence.

If Flag::Color is not enabled, the value is printed as a number.

Debug& Corrade::Utility::Debug::operator<<(int value)

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Debug& Corrade::Utility::Debug::operator<<(long value)

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Debug& Corrade::Utility::Debug::operator<<(long long value)

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Debug& Corrade::Utility::Debug::operator<<(unsigned value)

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Debug& Corrade::Utility::Debug::operator<<(unsigned long value)

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Debug& Corrade::Utility::Debug::operator<<(unsigned long long value)

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Debug& Corrade::Utility::Debug::operator<<(float value)

Print float value to debug output.

Prints the value with 6 significant digits.

Debug& Corrade::Utility::Debug::operator<<(double value)

Print double value to debug output.

Prints the value with 15 significant digits.

Debug& Corrade::Utility::Debug::operator<<(long double value)

Print long double value to debug output.

Prints the value with 18 significant digits on platforms with 80-bit long double and 15 digits on platforms where it is 64-bit.

Debug& Corrade::Utility::Debug::operator<<(char32_t value)

Print UTF-32 character to debug output.

Prints the value as Unicode codepoint, i.e. U+0061.

Debug& Corrade::Utility::Debug::operator<<(const char32_t* value)

Print UTF-32 character literal to debug output.

Prints the value as list of Unicode codepoints, i.e. {U+0061, U+0062, U+0063}.

Debug& Corrade::Utility::Debug::operator<<(std::nullptr_t)

Print a nullptr to debug output.

Prints the value as nullptr.

static void Corrade::Utility::Debug::nospace(Debug& debug)

Don't put space before next value.

Debug output by default separates values with space, this disables it for the immediately following value. The default behavior is then restored. The following line outputs Value: 16, 24:

Utility::Debug{} << "Value:" << 16 << Utility::Debug::nospace << "," << 24;

static void Corrade::Utility::Debug::newline(Debug& debug)

Output a newline.

Puts a newline (not surrounded by spaces) to the output. The following two lines are equivalent:

Utility::Debug{} << "Value:" << Utility::Debug::newline << 16;
Utility::Debug{} << "Value:" << Utility::Debug::nospace << "\n"
    << Utility::Debug::nospace << 16;

and their output is

Value:
16

static void Corrade::Utility::Debug::space(Debug& debug) new in 2020.06

Output a space.

Puts a space (not surrounded by additional spaces) to the output. Useful for adding an explicit leading space or for delimiting values with spaces when Flag::NoSpace is set. The last two lines are equivalent:

Utility::Debug{} << "Value:";

Utility::Debug{} << "" << 16;
Utility::Debug{} << Utility::Debug::space << 16;

and the output is

Value:
 16

static Modifier Corrade::Utility::Debug::color(Color color)

Set output color.

Resets previous color(), boldColor() or invertedColor() setting. The color is also automatically reset on object destruction to a value that was active in outer scope. If Flag::DisableColors was set, this function does nothing.

static Modifier Corrade::Utility::Debug::boldColor(Color color)

Set bold output color.

Resets previous color(), boldColor() or invertedColor() setting. The color is also automatically reset on object destruction to a value that was active in outer scope. If Flag::DisableColors was set, this function does nothing.

static Modifier Corrade::Utility::Debug::invertedColor(Color color) new in Git master

Set inverted output color.

The color is used for background while foreground is rendered with the terminal background color instead. Resets previous color(), boldColor() or invertedColor() setting. The color is also automatically reset on object destruction to a value that was active in outer scope. If Flag::DisableColors was set, this function does nothing.

static void Corrade::Utility::Debug::resetColor(Debug& debug)

Reset output color.

Resets any previous color(), boldColor() or invertedColor() setting to a value that was active in outer scope. The same is also automatically done on object destruction. If the color was not changed by this instance or Flag::DisableColors was set, this function does nothing.

static void Corrade::Utility::Debug::packed(Debug& debug) new in 2019.10

Print the next value in a packed form.

Enables a more compact output for types that support it (such as iterable containers).

static void Corrade::Utility::Debug::color(Debug& debug) new in 2019.10

Print the next value as a color.

Prints color-like values as actual 24bit ANSI color sequences.

static void Corrade::Utility::Debug::hex(Debug& debug) new in Git master

Print the next value as hexadecimal.

If the next value is integer, it's printed as lowercase hexadecimal prefixed with 0x e.g. 0xc0ffee instead of 12648430.

Debug& Corrade::Utility::Debug::operator<<(Modifier f)

Debug output modification.

See Output modifiers for more information.

Debug& operator<<(Debug& debug, Debug::Color value)

Debug output operator.

Debug& operator<<(Debug& debug, Debug::Flag value)

Debug output operator.

Debug& operator<<(Debug& debug, Debug::Flags value)

Debug output operator.

Debug& operator!(Implementation::DebugSourceLocation debug) new in 2020.06

Prefix the output with source location.

Only on supported compilers, does nothing otherwise. See Source location for more information.

template<class T>
Debug& operator<<(Debug& debug, const T& value)

Operator for printing custom types to debug output.

Parameters
debug Debug class
value Value to be printed

Support for printing custom types (i.e. those not handled by std::iostream) can be added by implementing this function for given type.

The function should convert the type to one of supported types (such as the builtin types or std::string) and then call Debug::operator<<() with it. You can also use Debug::nospace and Debug::newline.

template<class Iterable>
Debug& operator<<(Debug& debug, const Iterable& value)

Operator for printing iterable types to debug output.

Prints the value as {a, b, …}. If the type contains a nested iterable type, the values are separated by newlines. Specifying Debug::Flag::Packed or using Debug::packed will print the values tightly-packed without commas and spaces in between.

template<class T, class U>
Debug& operator<<(Debug& debug, const std::pair<T, U>& value)

Print a std::pair to debug output.

Prints the value as (first, second). Unlike operator<<(Debug& debug, const Iterable& value), the output is not affected by Debug::Flag::Packed / Debug::packed.

Debug& operator<<(Debug& debug, const std::string& value)

Print a std::string to debug output.

For types that are only convertible to a std::string this overload is picked only if the type doesn't also provide a std::ostream operator<<() overload. In that case the value is printed directly to the stream instead, assuming it's a cheaper operation than conversion to a std::string. This is for example a case with std::filesystem::path.

template<class T>
std::enable_if<!std::is_same<T, char>::value, Debug&>::type operator<<(Debug& debug, const std::basic_string<T>& value)

Print a std::basic_string to debug output.

All other types than exactly std::string are printed as containers.

template<class ... Args>
Debug& operator<<(Debug& debug, const std::tuple<Args...>& value)

Print a std::tuple to debug output.

Prints the value as (first, second, third...). Unlike operator<<(Debug& debug, const Iterable& value), the output is not affected by Debug::Flag::Packed / Debug::packed.

template<class T>
Debug& operator<<(Debug& debug, std::basic_string_view<T> value) new in Git master

Print a std::basic_string_view to debug output.

All other types than exactly std::string_view are printed as containers.