-
Notifications
You must be signed in to change notification settings - Fork 3
Home
logme is a C/C++ logging library designed for real-world systems where logging is not just debugging output, but a tool for operating and diagnosing a running application.
- ⚡ Extremely low overhead
- 🔧 Runtime configurable
- 🧩 Optional startup control from environment variables
- 📄 Structured logging (JSON/XML)
- 🚀 Async file / console backend
- 📊 Built-in profiling macros
- 🧵 Thread-safe
- 🖥 Windows / Linux / macOS
- 🧰 Powerful command-line tools
- 🧯 Separate crash logging path

logme performance is measured in the separate logbench repository. The benchmark includes source code, an article, and charts.
Recent throughput results show logme above one billion completed cycles in the null benchmark, where logging calls exist but no output is produced. This scenario matters because production applications often keep detailed diagnostics compiled in while most of them remain inactive.
See Performance and Why logme is fast for the current table and explanation.
The library focuses on three things:
- low overhead when logging is disabled or filtered out
- efficient logging path when messages are actually written
- full control over logging behavior at runtime
This allows using detailed logging in production without paying the cost permanently. In this sense, logme is not only a collection of logging macros. It is a runtime-configurable logging infrastructure layer with channels, subsystems, routing, backends, tools, structured output, obfuscation, function tracing, and production-oriented file management.
No initialization is required. A program can write log messages immediately:
LogmeI("Server started on port %d", port);The same message can be written using stream-style output:
LogmeI() << "Server started on port " << port;When std::format support is enabled, the fLogme... macros use {} placeholders:
fLogmeI("Server started on port {}", port);The same public header is also used from C code:
#include <Logme/Logme.h>
LogmeI("Server started on port %d", port);See Logging Macros for the full C++ macro syntax, including channels, subsystems, overrides, _Once, _Every, and conditional logging. See Fatal Handling for LogmeC, FlushAll(), and configurable fatal policy. See Crash Logging for LogmeCrash, LogmeCrashRaw, prepared crash files, and stderr/stdout emergency output. For glog-style migration macros, see glog Compatibility.
For pure C projects, see C API.
Most logging libraries treat logging as something configured once at startup.
logme treats logging as a runtime system.
You can:
- enable or disable channels
- change log levels
- add or remove backends
- switch output formats
- apply startup control commands from environment variables when the application explicitly opts in
…without rebuilding the application, and for live control without restarting the process.
This model is useful when an application must stay quiet during normal operation but still allow deep diagnostics to be enabled for one component, one subsystem, or one output destination while the process keeps running.
The same philosophy is used by the companion tools: logmectl controls a running process, logmefmt converts readable logme text to JSON/XML, and logmeobf helps protect sensitive log data.
Logging in logme is built around a few core concepts.
A channel is the main logging entity.
It represents a logical part of the system (for example HTTP, TLS, or database).
A subsystem (SID) is an additional classification tag used for filtering inside a channel.
Messages are routed to backends, which define where logs are written or captured: console, file, debugger output, shared file, memory buffer, ring buffer, callback, or Windows Event Log.
Each log message is processed through an internal context, which handles formatting and structured output.
In addition to the default text format, logme supports structured logging in two ways.
First, it can produce JSON or XML directly at runtime.
Each message becomes a structured event suitable for real-time processing.
Second, existing logs can be converted using the logmefmt tool, allowing generation of finalized JSON or XML documents.
File logging is designed to work reliably in long-running systems.
logme supports:
- hourly, daily, weekly, and monthly time rotation;
- maximum active-file size with either truncation or archive rotation;
- archive naming with
{index},{date}, and{datetime}; - retention by archive count, age, and total archive size;
- optional gzip compression for completed archives;
- lifecycle counters for completion, archive, compression, and retention paths;
- limiting total directory size through a watchdog.
Old matching archive files are removed automatically by retention logic, while files currently owned by active FileBackend instances are protected.
File logging is performed asynchronously to avoid blocking the application.
Console output is coordinated to preserve message ordering even in multithreaded scenarios.
When logging is disabled, logme avoids unnecessary work.
The library uses a precheck mechanism that ensures formatting and argument evaluation are skipped whenever possible.
This optimization applies not only to disabled logging, but also to active logging paths, especially when using asynchronous backends.
logme works on major platforms (Windows, Linux, macOS) and supports modern C++ standards.
It provides native formatting support, allowing both printf-style usage and C++-style streaming.
Additional capabilities include:
- controlling message frequency (log once / log at most once every N milliseconds)
- collapse/aggregation for repeated messages
- recent-history capture with
RingBufferBackend - boot/early logging before configuration is loaded
- policy-aware control commands for trusted and restricted command sources
These features are built into the core and do not require external components.
Some logme capabilities use different names and live at different layers than similarly named features in other logging libraries. For example, logme does not need a separate null backend, because a channel with no backends can be rejected early. Repetition control is implemented through _Once, _Every, and override scopes rather than through a backend-side duplicate filter.
See Feature Map for a practical mapping between common logging-library terms and the corresponding logme mechanisms.
logme — flexible runtime logging system
Home · Getting Started · Architecture · Output · Backends · Configuration
GitHub: https://github.com/efmsoft/logme
- Home
- Getting Started
- Why logme?
- Core Concepts
- Logging Macros
- Fatal Handling
- Crash Logging
- glog Compatibility
- C API
- Choosing Logging Macros
- Function tracing
- Trace Points
- Override Scopes
- Advanced Features
- Collapse Logging
- Feature Map
- Overview
- Console Backend
- Debugger Backend
- File Backend
- File Rotation & Retention
- Buffer Backend
- Ring Buffer Backend
- SharedFile Backend
- Callback Backend
- Windows Event Log Backend
- Custom Backends
- Runtime Control
- Configuration
- Configuration JSON
- Control Server
- Environment Control
- Control Policies
- Trace Points
- Message Filtering