Skip to content

Commit 7bf078f

Browse files
committed
Merge bitcoin/bitcoin#28237: refactor: Enforce C-str fmt strings in WalletLogPrintf()
fa60fa3 bitcoin-tidy: Apply bitcoin-unterminated-logprintf to spkm as well (MarcoFalke) faa1143 refactor: Enable all clang-tidy plugin bitcoin tests (MarcoFalke) fa6dc57 refactor: Enforce C-str fmt strings in WalletLogPrintf() (MarcoFalke) fa244f3 doc: Fix bitcoin-unterminated-logprintf tidy comments (MarcoFalke) Pull request description: All fmt functions only accept a raw C-string as argument. There should never be a need to pass a format string that is not a compile-time string literal, so disallow it in `WalletLogPrintf()` to avoid accidentally introducing it. Apart from consistency, this also fixes the clang-tidy plugin bug bitcoin/bitcoin#26296 (comment). ACKs for top commit: theuni: ACK fa60fa3 Tree-SHA512: fa6f4984c50f9b34e850bdfee7236706af586e512d866cc869cf0cdfaf9aa707029c210ca72d91f85e75fcbd8efe0d77084701de8c3d2004abfd7e46b6fa9072
2 parents 5eb6690 + fa60fa3 commit 7bf078f

File tree

8 files changed

+37
-19
lines changed

8 files changed

+37
-19
lines changed

contrib/devtools/bitcoin-tidy/example_logprintf.cpp

Lines changed: 22 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,10 @@
22
// Distributed under the MIT software license, see the accompanying
33
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
44

5-
// Warn about any use of LogPrintf that does not end with a newline.
65
#include <string>
76

7+
// Test for bitcoin-unterminated-logprintf
8+
89
enum LogFlags {
910
NONE
1011
};
@@ -21,8 +22,6 @@ static inline void LogPrintf_(const std::string& logging_function, const std::st
2122
#define LogPrintLevel_(category, level, ...) LogPrintf_(__func__, __FILE__, __LINE__, category, level, __VA_ARGS__)
2223
#define LogPrintf(...) LogPrintLevel_(LogFlags::NONE, Level::None, __VA_ARGS__)
2324

24-
// Use a macro instead of a function for conditional logging to prevent
25-
// evaluating arguments when logging for the category is not enabled.
2625
#define LogPrint(category, ...) \
2726
do { \
2827
LogPrintf(__VA_ARGS__); \
@@ -38,9 +37,23 @@ class CWallet
3837

3938
public:
4039
template <typename... Params>
41-
void WalletLogPrintf(std::string fmt, Params... parameters) const
40+
void WalletLogPrintf(const char* fmt, Params... parameters) const
41+
{
42+
LogPrintf(("%s " + std::string{fmt}).c_str(), GetDisplayName(), parameters...);
43+
};
44+
};
45+
46+
struct ScriptPubKeyMan
47+
{
48+
std::string GetDisplayName() const
49+
{
50+
return "default wallet";
51+
}
52+
53+
template <typename... Params>
54+
void WalletLogPrintf(const char* fmt, Params... parameters) const
4255
{
43-
LogPrintf(("%s " + fmt).c_str(), GetDisplayName(), parameters...);
56+
LogPrintf(("%s " + std::string{fmt}).c_str(), GetDisplayName(), parameters...);
4457
};
4558
};
4659

@@ -52,6 +65,8 @@ void good_func2()
5265
{
5366
CWallet wallet;
5467
wallet.WalletLogPrintf("hi\n");
68+
ScriptPubKeyMan spkm;
69+
spkm.WalletLogPrintf("hi\n");
5570

5671
const CWallet& walletref = wallet;
5772
walletref.WalletLogPrintf("hi\n");
@@ -81,6 +96,8 @@ void bad_func5()
8196
{
8297
CWallet wallet;
8398
wallet.WalletLogPrintf("hi");
99+
ScriptPubKeyMan spkm;
100+
spkm.WalletLogPrintf("hi");
84101

85102
const CWallet& walletref = wallet;
86103
walletref.WalletLogPrintf("hi");

contrib/devtools/bitcoin-tidy/logprintf.cpp

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -36,14 +36,12 @@ void LogPrintfCheck::registerMatchers(clang::ast_matchers::MatchFinder* finder)
3636
this);
3737

3838
/*
39-
CWallet wallet;
4039
auto walletptr = &wallet;
4140
wallet.WalletLogPrintf("foo");
4241
wallet->WalletLogPrintf("foo");
4342
*/
4443
finder->addMatcher(
4544
cxxMemberCallExpr(
46-
thisPointerType(qualType(hasDeclaration(cxxRecordDecl(hasName("CWallet"))))),
4745
callee(cxxMethodDecl(hasName("WalletLogPrintf"))),
4846
hasArgument(0, stringLiteral(unterminated()).bind("logstring"))),
4947
this);

contrib/devtools/bitcoin-tidy/logprintf.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99

1010
namespace bitcoin {
1111

12+
// Warn about any use of LogPrintf that does not end with a newline.
1213
class LogPrintfCheck final : public clang::tidy::ClangTidyCheck
1314
{
1415
public:

src/.clang-tidy

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
Checks: '
22
-*,
3-
bitcoin-unterminated-logprintf,
3+
bitcoin-*,
44
bugprone-argument-comment,
55
bugprone-use-after-move,
66
misc-unused-using-decls,

src/wallet/scriptpubkeyman.h

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -250,9 +250,10 @@ class ScriptPubKeyMan
250250
virtual std::unordered_set<CScript, SaltedSipHasher> GetScriptPubKeys() const { return {}; };
251251

252252
/** Prepends the wallet name in logging output to ease debugging in multi-wallet use cases */
253-
template<typename... Params>
254-
void WalletLogPrintf(std::string fmt, Params... parameters) const {
255-
LogPrintf(("%s " + fmt).c_str(), m_storage.GetDisplayName(), parameters...);
253+
template <typename... Params>
254+
void WalletLogPrintf(const char* fmt, Params... parameters) const
255+
{
256+
LogPrintf(("%s " + std::string{fmt}).c_str(), m_storage.GetDisplayName(), parameters...);
256257
};
257258

258259
/** Watch-only address added */

src/wallet/wallet.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2320,7 +2320,7 @@ OutputType CWallet::TransactionChangeType(const std::optional<OutputType>& chang
23202320
void CWallet::CommitTransaction(CTransactionRef tx, mapValue_t mapValue, std::vector<std::pair<std::string, std::string>> orderForm)
23212321
{
23222322
LOCK(cs_wallet);
2323-
WalletLogPrintf("CommitTransaction:\n%s", tx->ToString());
2323+
WalletLogPrintf("CommitTransaction:\n%s", tx->ToString()); // NOLINT(bitcoin-unterminated-logprintf)
23242324

23252325
// Add tx to wallet, because if it has change it's also ours,
23262326
// otherwise just for transaction history.

src/wallet/wallet.h

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -891,9 +891,10 @@ class CWallet final : public WalletStorage, public interfaces::Chain::Notificati
891891
};
892892

893893
/** Prepends the wallet name in logging output to ease debugging in multi-wallet use cases */
894-
template<typename... Params>
895-
void WalletLogPrintf(std::string fmt, Params... parameters) const {
896-
LogPrintf(("%s " + fmt).c_str(), GetDisplayName(), parameters...);
894+
template <typename... Params>
895+
void WalletLogPrintf(const char* fmt, Params... parameters) const
896+
{
897+
LogPrintf(("%s " + std::string{fmt}).c_str(), GetDisplayName(), parameters...);
897898
};
898899

899900
/** Upgrade the wallet */

test/lint/run-lint-format-strings.py

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -20,10 +20,10 @@
2020
("src/clientversion.cpp", "strprintf(_(COPYRIGHT_HOLDERS).translated, COPYRIGHT_HOLDERS_SUBSTITUTION)"),
2121
("src/test/translation_tests.cpp", "strprintf(format, arg)"),
2222
("src/validationinterface.cpp", "LogPrint(BCLog::VALIDATION, fmt \"\\n\", __VA_ARGS__)"),
23-
("src/wallet/wallet.h", "WalletLogPrintf(std::string fmt, Params... parameters)"),
24-
("src/wallet/wallet.h", "LogPrintf((\"%s \" + fmt).c_str(), GetDisplayName(), parameters...)"),
25-
("src/wallet/scriptpubkeyman.h", "WalletLogPrintf(std::string fmt, Params... parameters)"),
26-
("src/wallet/scriptpubkeyman.h", "LogPrintf((\"%s \" + fmt).c_str(), m_storage.GetDisplayName(), parameters...)"),
23+
("src/wallet/wallet.h", "WalletLogPrintf(const char* fmt, Params... parameters)"),
24+
("src/wallet/wallet.h", "LogPrintf((\"%s \" + std::string{fmt}).c_str(), GetDisplayName(), parameters...)"),
25+
("src/wallet/scriptpubkeyman.h", "WalletLogPrintf(const char* fmt, Params... parameters)"),
26+
("src/wallet/scriptpubkeyman.h", "LogPrintf((\"%s \" + std::string{fmt}).c_str(), m_storage.GetDisplayName(), parameters...)"),
2727
]
2828

2929

0 commit comments

Comments
 (0)