Skip to content

Commit b805dbb

Browse files
committed
Merge #19809: log: Prefix log messages with function name and source code location if -logsourcelocations is set
b4511e2 log: Prefix log messages with function name if -logsourcelocations is set (practicalswift) Pull request description: Prefix log messages with function name if `-logfunctionnames` is set. Yes, exactly like `-logthreadnames` but for function names instead of thread names :) This is a small developer ergonomics improvement: I've found this to be a cheap/simple way to correlate log output and originating function. For me it beats the ordinary cycle of 1.) try to figure out a regexp matching the static part of the dynamic log message, 2.) `git grep -E 'Using .* MiB out of .* requested for signature cache'`, 3.) `mcedit filename.cpp` (`openemacs filename.cpp` works too!) and 4.) search for log message and scroll up to find the function name :) Without any logging parameters: ``` $ src/bitcoind -regtest 2020-08-25T03:29:04Z Using RdRand as an additional entropy source 2020-08-25T03:29:04Z Using 16 MiB out of 32/2 requested for signature cache, able to store 524288 elements 2020-08-25T03:29:04Z Using 16 MiB out of 32/2 requested for script execution cache, able to store 524288 elements 2020-08-25T03:29:04Z Loaded best chain: hashBestChain=0fff88f13cb7b2c71f2a335e3a4fc328bf5beb436012afca590b1a11466e22ff height=0 date=2011-02-02T23:16:42Z progress=1.000000 2020-08-25T03:29:04Z block tree size = 1 2020-08-25T03:29:04Z nBestHeight = 0 2020-08-25T03:29:04Z Imported mempool transactions from disk: 0 succeeded, 0 failed, 0 expired, 0 already there, 0 waiting for initial broadcast 2020-08-25T03:29:04Z 0 addresses found from DNS seeds ``` With `-logthreadnames` and `-logfunctionnames`: ``` $ src/bitcoind -regtest -logthreadnames -logfunctionnames 2020-08-25T03:29:04Z [init] [ReportHardwareRand] Using RdRand as an additional entropy source 2020-08-25T03:29:04Z [init] [InitSignatureCache] Using 16 MiB out of 32/2 requested for signature cache, able to store 524288 elements 2020-08-25T03:29:04Z [init] [InitScriptExecutionCache] Using 16 MiB out of 32/2 requested for script execution cache, able to store 524288 elements 2020-08-25T03:29:04Z [init] [LoadChainTip] Loaded best chain: hashBestChain=0fff88f13cb7b2c71f2a335e3a4fc328bf5beb436012afca590b1a11466e22ff height=0 date=2011-02-02T23:16:42Z progress=1.000000 2020-08-25T03:29:04Z [init] [AppInitMain] block tree size = 1 2020-08-25T03:29:04Z [init] [AppInitMain] nBestHeight = 0 2020-08-25T03:29:04Z [loadblk] [LoadMempool] Imported mempool transactions from disk: 0 succeeded, 0 failed, 0 expired, 0 already there, 0 waiting for initial broadcast 2020-08-25T03:29:04Z [dnsseed] [ThreadDNSAddressSeed] 0 addresses found from DNS seeds ``` ACKs for top commit: laanwj: Code review ACK b4511e2 MarcoFalke: review ACK b4511e2 🌃 Tree-SHA512: d100f5364630c323f31d275259864c597f7725e462d5f4bdedcc7033ea616d7fc0d16ef1b2af557e692f4deea73c6773ccfc681589e7bf6ba970b9ec169040c7
2 parents 860f916 + b4511e2 commit b805dbb

File tree

8 files changed

+40
-4
lines changed

8 files changed

+40
-4
lines changed

src/init.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -533,6 +533,7 @@ void SetupServerArgs(NodeContext& node)
533533
#else
534534
hidden_args.emplace_back("-logthreadnames");
535535
#endif
536+
argsman.AddArg("-logsourcelocations", strprintf("Prepend debug output with name of the originating source location (source file, line number and function name) (default: %u)", DEFAULT_LOGSOURCELOCATIONS), ArgsManager::ALLOW_ANY, OptionsCategory::DEBUG_TEST);
536537
argsman.AddArg("-logtimemicros", strprintf("Add microsecond precision to debug timestamps (default: %u)", DEFAULT_LOGTIMEMICROS), ArgsManager::ALLOW_ANY | ArgsManager::DEBUG_ONLY, OptionsCategory::DEBUG_TEST);
537538
argsman.AddArg("-mocktime=<n>", "Replace actual time with " + UNIX_EPOCH_TIME + " (default: 0)", ArgsManager::ALLOW_ANY | ArgsManager::DEBUG_ONLY, OptionsCategory::DEBUG_TEST);
538539
argsman.AddArg("-maxsigcachesize=<n>", strprintf("Limit sum of signature cache and script execution cache sizes to <n> MiB (default: %u)", DEFAULT_MAX_SIG_CACHE_SIZE), ArgsManager::ALLOW_ANY | ArgsManager::DEBUG_ONLY, OptionsCategory::DEBUG_TEST);
@@ -883,6 +884,7 @@ void InitLogging(const ArgsManager& args)
883884
#ifdef HAVE_THREAD_LOCAL
884885
LogInstance().m_log_threadnames = args.GetBoolArg("-logthreadnames", DEFAULT_LOGTHREADNAMES);
885886
#endif
887+
LogInstance().m_log_sourcelocations = args.GetBoolArg("-logsourcelocations", DEFAULT_LOGSOURCELOCATIONS);
886888

887889
fLogIPs = args.GetBoolArg("-logips", DEFAULT_LOGIPS);
888890

src/logging.cpp

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55

66
#include <logging.h>
77
#include <util/threadnames.h>
8+
#include <util/string.h>
89
#include <util/time.h>
910

1011
#include <mutex>
@@ -236,11 +237,15 @@ namespace BCLog {
236237
}
237238
}
238239

239-
void BCLog::Logger::LogPrintStr(const std::string& str)
240+
void BCLog::Logger::LogPrintStr(const std::string& str, const std::string& logging_function, const std::string& source_file, const int source_line)
240241
{
241242
StdLockGuard scoped_lock(m_cs);
242243
std::string str_prefixed = LogEscapeMessage(str);
243244

245+
if (m_log_sourcelocations && m_started_new_line) {
246+
str_prefixed.insert(0, "[" + RemovePrefix(source_file, "./") + ":" + ToString(source_line) + "] [" + logging_function + "] ");
247+
}
248+
244249
if (m_log_threadnames && m_started_new_line) {
245250
str_prefixed.insert(0, "[" + util::ThreadGetInternalName() + "] ");
246251
}

src/logging.h

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ static const bool DEFAULT_LOGTIMEMICROS = false;
2222
static const bool DEFAULT_LOGIPS = false;
2323
static const bool DEFAULT_LOGTIMESTAMPS = true;
2424
static const bool DEFAULT_LOGTHREADNAMES = false;
25+
static const bool DEFAULT_LOGSOURCELOCATIONS = false;
2526
extern const char * const DEFAULT_DEBUGLOGFILE;
2627

2728
extern bool fLogIPs;
@@ -90,12 +91,13 @@ namespace BCLog {
9091
bool m_log_timestamps = DEFAULT_LOGTIMESTAMPS;
9192
bool m_log_time_micros = DEFAULT_LOGTIMEMICROS;
9293
bool m_log_threadnames = DEFAULT_LOGTHREADNAMES;
94+
bool m_log_sourcelocations = DEFAULT_LOGSOURCELOCATIONS;
9395

9496
fs::path m_file_path;
9597
std::atomic<bool> m_reopen_file{false};
9698

9799
/** Send a string to the log output */
98-
void LogPrintStr(const std::string& str);
100+
void LogPrintStr(const std::string& str, const std::string& logging_function, const std::string& source_file, const int source_line);
99101

100102
/** Returns whether logs will be written to any output */
101103
bool Enabled() const
@@ -163,7 +165,7 @@ bool GetLogCategory(BCLog::LogFlags& flag, const std::string& str);
163165
// peer can fill up a user's disk with debug.log entries.
164166

165167
template <typename... Args>
166-
static inline void LogPrintf(const char* fmt, const Args&... args)
168+
static inline void LogPrintf_(const std::string& logging_function, const std::string& source_file, const int source_line, const char* fmt, const Args&... args)
167169
{
168170
if (LogInstance().Enabled()) {
169171
std::string log_msg;
@@ -173,10 +175,12 @@ static inline void LogPrintf(const char* fmt, const Args&... args)
173175
/* Original format string will have newline so don't add one here */
174176
log_msg = "Error \"" + std::string(fmterr.what()) + "\" while formatting log message: " + fmt;
175177
}
176-
LogInstance().LogPrintStr(log_msg);
178+
LogInstance().LogPrintStr(log_msg, logging_function, source_file, source_line);
177179
}
178180
}
179181

182+
#define LogPrintf(...) LogPrintf_(__func__, __FILE__, __LINE__, __VA_ARGS__)
183+
180184
// Use a macro instead of a function for conditional logging to prevent
181185
// evaluating arguments when logging for the category is not enabled.
182186
#define LogPrint(category, ...) \

src/test/fuzz/string.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -67,6 +67,7 @@ FUZZ_TARGET(string)
6767
}
6868
OutputType output_type;
6969
(void)ParseOutputType(random_string_1, output_type);
70+
(void)RemovePrefix(random_string_1, random_string_2);
7071
(void)ResolveErrMsg(random_string_1, random_string_2);
7172
try {
7273
(void)RPCConvertNamedValues(random_string_1, random_string_vector);

src/test/util/setup_common.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,7 @@ BasicTestingSetup::BasicTestingSetup(const std::string& chainName, const std::ve
7777
{
7878
"dummy",
7979
"-printtoconsole=0",
80+
"-logsourcelocations",
8081
"-logtimemicros",
8182
"-logthreadnames",
8283
"-debug",

src/test/util_tests.cpp

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2201,4 +2201,17 @@ BOOST_AUTO_TEST_CASE(message_hash)
22012201
BOOST_CHECK_NE(message_hash1, signature_hash);
22022202
}
22032203

2204+
BOOST_AUTO_TEST_CASE(remove_prefix)
2205+
{
2206+
BOOST_CHECK_EQUAL(RemovePrefix("./util/system.h", "./"), "util/system.h");
2207+
BOOST_CHECK_EQUAL(RemovePrefix("foo", "foo"), "");
2208+
BOOST_CHECK_EQUAL(RemovePrefix("foo", "fo"), "o");
2209+
BOOST_CHECK_EQUAL(RemovePrefix("foo", "f"), "oo");
2210+
BOOST_CHECK_EQUAL(RemovePrefix("foo", ""), "foo");
2211+
BOOST_CHECK_EQUAL(RemovePrefix("fo", "foo"), "fo");
2212+
BOOST_CHECK_EQUAL(RemovePrefix("f", "foo"), "f");
2213+
BOOST_CHECK_EQUAL(RemovePrefix("", "foo"), "");
2214+
BOOST_CHECK_EQUAL(RemovePrefix("", ""), "");
2215+
}
2216+
22042217
BOOST_AUTO_TEST_SUITE_END()

src/util/string.h

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,14 @@
2525
return str.substr(front, end - front + 1);
2626
}
2727

28+
[[nodiscard]] inline std::string RemovePrefix(const std::string& str, const std::string& prefix)
29+
{
30+
if (str.substr(0, prefix.size()) == prefix) {
31+
return str.substr(prefix.size());
32+
}
33+
return str;
34+
}
35+
2836
/**
2937
* Join a list of items
3038
*

test/functional/test_framework/test_node.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -115,6 +115,8 @@ def __init__(self, i, datadir, *, chain, rpchost, timewait, timeout_factor, bitc
115115

116116
if self.version_is_at_least(190000):
117117
self.args.append("-logthreadnames")
118+
if self.version_is_at_least(219900):
119+
self.args.append("-logsourcelocations")
118120

119121
self.cli = TestNodeCLI(bitcoin_cli, self.datadir)
120122
self.use_cli = use_cli

0 commit comments

Comments
 (0)