A Discrete-Event Network Simulator
API
Loading...
Searching...
No Matches
log.h
Go to the documentation of this file.
1/*
2 * Copyright (c) 2006,2007 INRIA
3 *
4 * SPDX-License-Identifier: GPL-2.0-only
5 *
6 * Author: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
7 */
8
9#ifndef NS3_LOG_H
10#define NS3_LOG_H
11
12#include "log-macros-disabled.h"
13#include "log-macros-enabled.h"
14#include "node-printer.h"
15#include "time-printer.h"
16
17#include <iostream>
18#include <stdint.h>
19#include <string>
20#include <type_traits>
21#include <unordered_map>
22#include <vector>
23
24/**
25 * @file
26 * @ingroup logging
27 * Debug message logging
28 *
29 * Included by graph was not generated because of its size.
30 * @hideincludedbygraph
31 */
32
33/**
34 * @ingroup debugging
35 * @defgroup logging Logging
36 *
37 * @brief Logging functions and macros
38 *
39 * LOG functionality: macros which allow developers to
40 * send information to the \c std::clog output stream.
41 *
42 * All logging messages are disabled by default. To enable selected logging
43 * messages, use the ns3::LogComponentEnable
44 * function or use the NS_LOG environment variable
45 *
46 * Use the environment variable NS_LOG to define a ':'-separated list of
47 * logging components to enable. For example (using bash syntax),
48 * @code
49 * $ NS_LOG="OlsrAgent" ./ns3 run ...
50 * @endcode
51 * would enable one component at all log levels.
52 * @code
53 * $NS_LOG="OlsrAgent:Ipv4L3Protocol" ./ns3 run ...
54 * @endcode
55 * would enable two components, at all log levels, etc.
56 * \c NS_LOG="*" will enable all available log components at all levels.
57 *
58 * To control more selectively the log levels for each component, use
59 * this syntax:
60 * @code
61 * $ NS_LOG='Component1=func|warn:Component2=error|debug'
62 * @endcode
63 * This example would enable the \c func, and \c warn log
64 * levels for 'Component1' and the \c error and \c debug log levels
65 * for 'Component2'. The wildcard '*' can be used here as well. For example
66 * \c NS_LOG='*=level_all|prefix' would enable all log levels and prefix all
67 * prints with the component and function names.
68 *
69 * A note on NS_LOG_FUNCTION() and NS_LOG_FUNCTION_NOARGS():
70 * generally, use of (at least) NS_LOG_FUNCTION(this) is preferred,
71 * with the any function parameters added:
72 * @code
73 * NS_LOG_FUNCTION (this << arg1 << args);
74 * @endcode
75 * Use NS_LOG_FUNCTION_NOARGS() only in static functions with no arguments.
76 */
77/** @{ */
78
79namespace ns3
80{
81
82/**
83 * Logging severity classes and levels.
84 */
86{
87 LOG_NONE = 0x00000000, //!< No logging.
88
89 LOG_ERROR = 0x00000001, //!< Serious error messages only.
90 LOG_LEVEL_ERROR = 0x00000001, //!< LOG_ERROR and above.
91
92 LOG_WARN = 0x00000002, //!< Warning messages.
93 LOG_LEVEL_WARN = 0x00000003, //!< LOG_WARN and above.
94
95 LOG_INFO = 0x00000004, //!< Something happened to change state.
96 LOG_LEVEL_INFO = 0x00000007, //!< LOG_INFO and above.
97
98 LOG_FUNCTION = 0x00000008, //!< Function tracing for non-trivial function calls.
99 LOG_LEVEL_FUNCTION = 0x0000000f, //!< LOG_FUNCTION and above.
100
101 LOG_LOGIC = 0x00000010, //!< Debugging logs for key branches and decisions in a function.
102 LOG_LEVEL_LOGIC = 0x0000001f, //!< LOG_LOGIC and above.
103
104 LOG_DEBUG = 0x00000020, //!< Full voluminous logging to support debugging.
105 LOG_LEVEL_DEBUG = 0x0000003f, //!< LOG_DEBUG and above.
106
107 LOG_ALL = 0x0fffffff, //!< Print everything.
108 LOG_LEVEL_ALL = LOG_ALL, //!< Print everything.
109
110 LOG_PREFIX_FUNC = 0x80000000, //!< Prefix all trace prints with function.
111 LOG_PREFIX_TIME = 0x40000000, //!< Prefix all trace prints with simulation time.
112 LOG_PREFIX_NODE = 0x20000000, //!< Prefix all trace prints with simulation node.
113 LOG_PREFIX_LEVEL = 0x10000000, //!< Prefix all trace prints with log level (severity).
114 LOG_PREFIX_ALL = 0xf0000000 //!< All prefixes.
115};
116
117/**
118 * Enable the logging output associated with that log component.
119 *
120 * The logging output can be later disabled with a call
121 * to ns3::LogComponentDisable.
122 *
123 * Same as running your program with the NS_LOG environment
124 * variable set as NS_LOG='name=level'.
125 *
126 * @param [in] name The log component name.
127 * @param [in] level The logging level.
128 */
129void LogComponentEnable(const std::string& name, LogLevel level);
130
131/**
132 * Enable the logging output for all registered log components.
133 *
134 * Same as running your program with the NS_LOG environment
135 * variable set as NS_LOG='*=level'
136 *
137 * @param [in] level The logging level.
138 */
140
141/**
142 * Disable the logging output associated with that log component.
143 *
144 * The logging output can be later re-enabled with a call
145 * to LogComponentEnable.
146 *
147 * @param [in] name The log component name.
148 * @param [in] level The logging level.
149 */
150void LogComponentDisable(const std::string& name, LogLevel level);
151
152/**
153 * Disable all logging for all components.
154 *
155 * @param [in] level The logging level.
156 */
158
159} // namespace ns3
160
161/**
162 * Define a Log component with a specific name.
163 *
164 * This macro should be used at the top of every file in which you want
165 * to use the NS_LOG macro. This macro defines a new
166 * "log component" which can be later selectively enabled
167 * or disabled with the ns3::LogComponentEnable and
168 * ns3::LogComponentDisable functions or with the NS_LOG
169 * environment variable.
170 *
171 * LogComponent names should be simple string tokens, _i.e._,
172 * "ArfWifiManager", not "ns3::ArfWifiManager".
173 *
174 * This macro should be placed within namespace ns3. If functions
175 * outside of namespace ns3 require access to logging, the preferred
176 * solution is to add the following 'using' directive at file scope,
177 * outside of namespace ns3, and after the inclusion of
178 * NS_LOG_COMPONENT_DEFINE, such as follows:
179 * @code
180 * namespace ns3 {
181 * NS_LOG_COMPONENT_DEFINE ("...");
182 *
183 * // Definitions within the ns3 namespace
184 *
185 * } // namespace ns3
186 *
187 * using ns3::g_log;
188 *
189 * // Further definitions outside of the ns3 namespace
190 * @endcode
191 *
192 * @param [in] name The log component name.
193 */
194#define NS_LOG_COMPONENT_DEFINE(name) \
195 static ns3::LogComponent g_log = ns3::LogComponent(name, __FILE__)
196
197/**
198 * Define a logging component with a mask.
199 *
200 * See LogComponent().
201 *
202 * @param [in] name The log component name.
203 * @param [in] mask The default mask.
204 */
205#define NS_LOG_COMPONENT_DEFINE_MASK(name, mask) \
206 static ns3::LogComponent g_log = ns3::LogComponent(name, __FILE__, mask)
207
208/**
209 * Declare a reference to a Log component.
210 *
211 * This macro should be used in the declaration of template classes
212 * to allow their methods (defined in an header file) to make use of
213 * the NS_LOG_* macros. This macro should be used in the private
214 * section to prevent subclasses from using the same log component
215 * as the base class.
216 */
217#define NS_LOG_TEMPLATE_DECLARE LogComponent& g_log
218
219/**
220 * Initialize a reference to a Log component.
221 *
222 * This macro should be used in the constructor of template classes
223 * to allow their methods (defined in an header file) to make use of
224 * the NS_LOG_* macros.
225 *
226 * @param [in] name The log component name.
227 */
228#define NS_LOG_TEMPLATE_DEFINE(name) g_log(GetLogComponent(name))
229
230/**
231 * Declare and initialize a reference to a Log component.
232 *
233 * This macro should be used in static template methods to allow their
234 * methods (defined in an header file) to make use of the NS_LOG_* macros.
235 *
236 * @param [in] name The log component name.
237 */
238#define NS_LOG_STATIC_TEMPLATE_DEFINE(name) \
239 static LogComponent& g_log [[maybe_unused]] = GetLogComponent(name)
240
241/**
242 * Use \ref NS_LOG to output a message of level LOG_ERROR.
243 *
244 * @param [in] msg The message to log.
245 */
246#define NS_LOG_ERROR(msg) NS_LOG(ns3::LOG_ERROR, msg)
247
248/**
249 * Use \ref NS_LOG to output a message of level LOG_WARN.
250 *
251 * @param [in] msg The message to log.
252 */
253#define NS_LOG_WARN(msg) NS_LOG(ns3::LOG_WARN, msg)
254
255/**
256 * Use \ref NS_LOG to output a message of level LOG_DEBUG.
257 *
258 * @param [in] msg The message to log.
259 */
260#define NS_LOG_DEBUG(msg) NS_LOG(ns3::LOG_DEBUG, msg)
261
262/**
263 * Use \ref NS_LOG to output a message of level LOG_INFO.
264 *
265 * @param [in] msg The message to log.
266 */
267#define NS_LOG_INFO(msg) NS_LOG(ns3::LOG_INFO, msg)
268
269/**
270 * Use \ref NS_LOG to output a message of level LOG_LOGIC
271 *
272 * @param [in] msg The message to log.
273 */
274#define NS_LOG_LOGIC(msg) NS_LOG(ns3::LOG_LOGIC, msg)
275
276namespace ns3
277{
278
279/**
280 * Print the list of logging messages available.
281 * Same as running your program with the NS_LOG environment
282 * variable set as NS_LOG=print-list
283 */
285
286/**
287 * Set the TimePrinter function to be used
288 * to prepend log messages with the simulation time.
289 *
290 * The default is DefaultTimePrinter().
291 *
292 * @param [in] lp The TimePrinter function.
293 */
295/**
296 * Get the LogTimePrinter function currently in use.
297 * @returns The current LogTimePrinter function.
298 */
300
301/**
302 * Set the LogNodePrinter function to be used
303 * to prepend log messages with the node id.
304 *
305 * The default is DefaultNodePrinter().
306 *
307 * @param [in] np The LogNodePrinter function.
308 */
310/**
311 * Get the LogNodePrinter function currently in use.
312 * @returns The current LogNodePrinter function.
313 */
315
316/**
317 * A single log component configuration.
318 */
320{
321 public:
322 /**
323 * Constructor.
324 *
325 * @param [in] name The user-visible name for this component.
326 * @param [in] file The source code file which defined this LogComponent.
327 * @param [in] mask LogLevels blocked for this LogComponent. Blocking
328 * a log level helps prevent recursion by logging in
329 * functions which help implement the logging facility.
330 */
331 LogComponent(const std::string& name, const std::string& file, const LogLevel mask = LOG_NONE);
332
333 /**
334 * Check if this LogComponent is enabled for \c level
335 *
336 * @param [in] level The level to check for.
337 * @return \c true if we are enabled at \c level.
338 *
339 * @internal
340 * This function is defined in the header to enable inlining for better performance. See:
341 * https://gitlab.com/nsnam/ns-3-dev/-/merge_requests/2448#note_2527898962
342 */
343 bool IsEnabled(const LogLevel level) const
344 {
345 return level & m_levels;
346 }
347
348 /**
349 * Check if all levels are disabled.
350 *
351 * @return \c true if all levels are disabled.
352 */
353 bool IsNoneEnabled() const;
354 /**
355 * Enable this LogComponent at \c level
356 *
357 * @param [in] level The LogLevel to enable.
358 */
359 void Enable(const LogLevel level);
360 /**
361 * Disable logging at \c level for this LogComponent.
362 *
363 * @param [in] level The LogLevel to disable.
364 */
365 void Disable(const LogLevel level);
366 /**
367 * Get the name of this LogComponent.
368 *
369 * @return The name of this LogComponent.
370 */
371 std::string Name() const;
372 /**
373 * Get the compilation unit defining this LogComponent.
374 * @returns The file name.
375 */
376 std::string File() const;
377 /**
378 * Get the string label for the given LogLevel.
379 *
380 * @param [in] level The LogLevel to get the label for.
381 * @return The string label for \c level.
382 */
383 static std::string GetLevelLabel(const LogLevel level);
384 /**
385 * Prevent the enabling of a specific LogLevel.
386 *
387 * @param [in] level The LogLevel to block.
388 */
389 void SetMask(const LogLevel level);
390
391 /**
392 * LogComponent name map.
393 *
394 * @internal
395 * This should really be considered an internal API.
396 * It is exposed here to allow print-introspected-doxygen.cc
397 * to generate a list of all LogComponents.
398 */
399 using ComponentList = std::unordered_map<std::string, LogComponent*>;
400
401 /**
402 * Get the list of LogComponents.
403 *
404 * @internal
405 * This should really be considered an internal API.
406 * It is exposed here to allow print-introspected-doxygen.cc
407 * to generate a list of all LogComponents.
408 *
409 * @returns The list of LogComponents.
410 */
412
413 private:
414 /**
415 * Parse the `NS_LOG` environment variable for options relating to this
416 * LogComponent.
417 */
418 void EnvVarCheck();
419
420 int32_t m_levels; //!< Enabled LogLevels.
421 int32_t m_mask; //!< Blocked LogLevels.
422 std::string m_name; //!< LogComponent name.
423 std::string m_file; //!< File defining this LogComponent.
424
425 // end of class LogComponent
426};
427
428/**
429 * Get the LogComponent registered with the given name.
430 *
431 * @param [in] name The name of the LogComponent.
432 * @return a reference to the requested LogComponent
433 */
434LogComponent& GetLogComponent(const std::string name);
435
436/**
437 * Insert `, ` when streaming function arguments.
438 */
440{
441 public:
442 /**
443 * Constructor.
444 *
445 * @param [in] os Underlying output stream.
446 */
447 ParameterLogger(std::ostream& os);
448
449 /**
450 * Write a function parameter on the output stream,
451 * separating parameters after the first by `,` strings.
452 *
453 * @param [in] param The function parameter.
454 * @return This ParameterLogger, so it's chainable.
455 */
456 template <typename T>
457 ParameterLogger& operator<<(const T& param);
458
459 /**
460 * Overload for vectors, to print each element.
461 *
462 * @param [in] vector The vector of parameters
463 * @return This ParameterLogger, so it's chainable.
464 */
465 template <typename T>
466 ParameterLogger& operator<<(const std::vector<T>& vector);
467
468 private:
469 /** Add `, ` before every parameter after the first. */
470 void CommaRest();
471
472 bool m_first{true}; //!< First argument flag, doesn't get `, `.
473 std::ostream& m_os; //!< Underlying output stream.
474
475 // end of class ParameterLogger
476};
477
478template <typename T>
480ParameterLogger::operator<<(const T& param)
481{
482 CommaRest();
483
484 if constexpr (std::is_convertible_v<T, std::string>)
485 {
486 m_os << "\"" << param << "\"";
487 }
488 else if constexpr (std::is_arithmetic_v<T>)
489 {
490 // Use + unary operator to cast uint8_t / int8_t to uint32_t / int32_t, respectively
491 m_os << +param;
492 }
493 else if constexpr (std::is_pointer_v<T>)
494 {
496 }
497 else
498 {
499 m_os << param;
500 }
501
502 return *this;
503}
504
505template <typename T>
507ParameterLogger::operator<<(const std::vector<T>& vector)
508{
509 for (const auto& i : vector)
510 {
511 *this << i;
512 }
513 return *this;
514}
515
516} // namespace ns3
517
518/**@}*/ // \ingroup logging
519
520#endif /* NS3_LOG_H */
A single log component configuration.
Definition log.h:320
static ComponentList * GetComponentList()
Get the list of LogComponents.
Definition log.cc:132
void Enable(const LogLevel level)
Enable this LogComponent at level.
Definition log.cc:248
bool IsEnabled(const LogLevel level) const
Check if this LogComponent is enabled for level.
Definition log.h:343
std::string File() const
Get the compilation unit defining this LogComponent.
Definition log.cc:266
int32_t m_levels
Enabled LogLevels.
Definition log.h:420
void Disable(const LogLevel level)
Disable logging at level for this LogComponent.
Definition log.cc:254
static std::string GetLevelLabel(const LogLevel level)
Get the string label for the given LogLevel.
Definition log.cc:273
void EnvVarCheck()
Parse the NS_LOG environment variable for options relating to this LogComponent.
Definition log.cc:187
std::string m_file
File defining this LogComponent.
Definition log.h:423
bool IsNoneEnabled() const
Check if all levels are disabled.
Definition log.cc:236
std::string Name() const
Get the name of this LogComponent.
Definition log.cc:260
std::unordered_map< std::string, LogComponent * > ComponentList
LogComponent name map.
Definition log.h:399
int32_t m_mask
Blocked LogLevels.
Definition log.h:421
LogComponent(const std::string &name, const std::string &file, const LogLevel mask=LOG_NONE)
Constructor.
Definition log.cc:148
void SetMask(const LogLevel level)
Prevent the enabling of a specific LogLevel.
Definition log.cc:242
std::string m_name
LogComponent name.
Definition log.h:422
void CommaRest()
Add , before every parameter after the first.
Definition log.cc:511
bool m_first
First argument flag, doesn't get , .
Definition log.h:472
ParameterLogger & operator<<(const T &param)
Write a function parameter on the output stream, separating parameters after the first by ,...
Definition log.h:480
ParameterLogger(std::ostream &os)
Constructor.
Definition log.cc:505
std::ostream & m_os
Underlying output stream.
Definition log.h:473
STL class.
Definition of empty logging macros and the NS_LOG_NOOP_INTERNAL macro.
NS_LOG and related logging macro definitions.
Every class exported by the ns3 library is enclosed in the ns3 namespace.
void LogComponentEnable(const std::string &name, LogLevel level)
Enable the logging output associated with that log component.
Definition log.cc:284
void LogSetTimePrinter(TimePrinter printer)
Set the TimePrinter function to be used to prepend log messages with the simulation time.
Definition log.cc:476
void(* TimePrinter)(std::ostream &os)
Function signature for features requiring a time formatter, such as logging or ShowProgress.
void(* NodePrinter)(std::ostream &os)
Function signature for prepending the node id to a log message.
NodePrinter LogGetNodePrinter()
Get the LogNodePrinter function currently in use.
Definition log.cc:500
void LogComponentDisable(const std::string &name, LogLevel level)
Disable the logging output associated with that log component.
Definition log.cc:312
LogLevel
Logging severity classes and levels.
Definition log.h:86
@ LOG_LEVEL_ALL
Print everything.
Definition log.h:108
@ LOG_PREFIX_FUNC
Prefix all trace prints with function.
Definition log.h:110
@ LOG_LEVEL_LOGIC
LOG_LOGIC and above.
Definition log.h:102
@ LOG_NONE
No logging.
Definition log.h:87
@ LOG_PREFIX_TIME
Prefix all trace prints with simulation time.
Definition log.h:111
@ LOG_FUNCTION
Function tracing for non-trivial function calls.
Definition log.h:98
@ LOG_ERROR
Serious error messages only.
Definition log.h:89
@ LOG_WARN
Warning messages.
Definition log.h:92
@ LOG_INFO
Something happened to change state.
Definition log.h:95
@ LOG_PREFIX_ALL
All prefixes.
Definition log.h:114
@ LOG_LEVEL_FUNCTION
LOG_FUNCTION and above.
Definition log.h:99
@ LOG_LEVEL_ERROR
LOG_ERROR and above.
Definition log.h:90
@ LOG_ALL
Print everything.
Definition log.h:107
@ LOG_LEVEL_WARN
LOG_WARN and above.
Definition log.h:93
@ LOG_LEVEL_DEBUG
LOG_DEBUG and above.
Definition log.h:105
@ LOG_PREFIX_LEVEL
Prefix all trace prints with log level (severity).
Definition log.h:113
@ LOG_LOGIC
Debugging logs for key branches and decisions in a function.
Definition log.h:101
@ LOG_PREFIX_NODE
Prefix all trace prints with simulation node.
Definition log.h:112
@ LOG_LEVEL_INFO
LOG_INFO and above.
Definition log.h:96
@ LOG_DEBUG
Full voluminous logging to support debugging.
Definition log.h:104
TimePrinter LogGetTimePrinter()
Get the LogTimePrinter function currently in use.
Definition log.cc:488
void LogComponentDisableAll(LogLevel level)
Disable all logging for all components.
Definition log.cc:324
LogComponent & GetLogComponent(const std::string name)
Get the LogComponent registered with the given name.
Definition log.cc:170
void LogComponentEnableAll(LogLevel level)
Enable the logging output for all registered log components.
Definition log.cc:302
void LogSetNodePrinter(NodePrinter printer)
Set the LogNodePrinter function to be used to prepend log messages with the node id.
Definition log.cc:494
void LogComponentPrintList()
Print the list of logging messages available.
Definition log.cc:334
Declaration of ns3::NodePrinter function pointer type and ns3::DefaultNodePrinter function.
Declaration of ns3::TimePrinter function pointer type and ns3::DefaultTimePrinter function.