Skip to content

Commit 574d3ab

Browse files
committed
Merge maxscriptsize-28+knots
2 parents 6c5ca3e + 5ca209e commit 574d3ab

File tree

4 files changed

+26
-3
lines changed

4 files changed

+26
-3
lines changed

src/init.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -690,6 +690,7 @@ void SetupServerArgs(ArgsManager& argsman)
690690
strprintf("Maximum size of data in data carrier transactions we relay and mine, in bytes (default: %u)",
691691
MAX_OP_RETURN_RELAY),
692692
ArgsManager::ALLOW_ANY, OptionsCategory::NODE_RELAY);
693+
argsman.AddArg("-maxscriptsize", strprintf("Maximum size of scripts we relay and mine, in bytes (default: %s)", DEFAULT_SCRIPT_SIZE_POLICY_LIMIT), ArgsManager::ALLOW_ANY, OptionsCategory::NODE_RELAY);
693694
argsman.AddArg("-mempoolfullrbf", strprintf("Accept transaction replace-by-fee without requiring replaceability signaling (default: %u)", (DEFAULT_MEMPOOL_RBF_POLICY == RBFPolicy::Always)), ArgsManager::ALLOW_ANY, OptionsCategory::NODE_RELAY);
694695
argsman.AddArg("-mempoolreplacement", strprintf("Set to 0 to disable RBF entirely, \"fee,optin\" to honour RBF opt-out signal, or \"fee,-optin\" to always RBF aka full RBF (default: %s)", "fee,-optin"), ArgsManager::ALLOW_ANY, OptionsCategory::NODE_RELAY);
695696
argsman.AddArg("-mempooltruc", strprintf("Behaviour for transactions requesting TRUC limits: \"reject\" the transactions entirely, \"accept\" them just like any other, or \"enforce\" to impose their requested restrictions (default: %s)", "enforce"), ArgsManager::ALLOW_ANY, OptionsCategory::NODE_RELAY);
@@ -1101,6 +1102,8 @@ bool AppInitParameterInteraction(const ArgsManager& args)
11011102
g_weight_per_data_byte = ((*parsed * WITNESS_SCALE_FACTOR) + 99) / 100;
11021103
}
11031104

1105+
g_script_size_policy_limit = args.GetIntArg("-maxscriptsize", g_script_size_policy_limit);
1106+
11041107
nBytesPerSigOp = args.GetIntArg("-bytespersigop", nBytesPerSigOp);
11051108
nBytesPerSigOpStrict = args.GetIntArg("-bytespersigopstrict", nBytesPerSigOpStrict);
11061109

src/policy/policy.cpp

Lines changed: 20 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
#include <consensus/validation.h>
1414
#include <kernel/mempool_options.h>
1515
#include <policy/feerate.h>
16+
#include <policy/settings.h>
1617
#include <primitives/transaction.h>
1718
#include <script/interpreter.h>
1819
#include <script/script.h>
@@ -25,6 +26,8 @@
2526
#include <utility>
2627
#include <vector>
2728

29+
unsigned int g_script_size_policy_limit{DEFAULT_SCRIPT_SIZE_POLICY_LIMIT};
30+
2831
CAmount GetDustThreshold(const CTxOut& txout, const CFeeRate& dustRelayFeeIn)
2932
{
3033
// "Dust" is defined in terms of dustRelayFee,
@@ -143,7 +146,7 @@ bool IsStandardTx(const CTransaction& tx, const kernel::MemPoolOptions& opts, st
143146
// some minor future-proofing. That's also enough to spend a
144147
// 20-of-20 CHECKMULTISIG scriptPubKey, though such a scriptPubKey
145148
// is not considered standard.
146-
if (txin.scriptSig.size() > MAX_STANDARD_SCRIPTSIG_SIZE) {
149+
if (txin.scriptSig.size() > std::min(MAX_STANDARD_SCRIPTSIG_SIZE, g_script_size_policy_limit)) {
147150
MaybeReject("scriptsig-size");
148151
}
149152
if (!txin.scriptSig.IsPushOnly()) {
@@ -154,6 +157,10 @@ bool IsStandardTx(const CTransaction& tx, const kernel::MemPoolOptions& opts, st
154157
unsigned int nDataOut = 0;
155158
TxoutType whichType;
156159
for (const CTxOut& txout : tx.vout) {
160+
if (txout.scriptPubKey.size() > g_script_size_policy_limit) {
161+
MaybeReject("scriptpubkey-size");
162+
}
163+
157164
if (!::IsStandard(txout.scriptPubKey, opts.max_datacarrier_bytes, whichType)) {
158165
if (whichType == TxoutType::WITNESS_UNKNOWN) {
159166
MaybeReject("scriptpubkey-unknown-witnessversion");
@@ -215,6 +222,10 @@ bool AreInputsStandard(const CTransaction& tx, const CCoinsViewCache& mapInputs,
215222
for (unsigned int i = 0; i < tx.vin.size(); i++) {
216223
const CTxOut& prev = mapInputs.AccessCoin(tx.vin[i].prevout).out;
217224

225+
if (prev.scriptPubKey.size() > g_script_size_policy_limit) {
226+
MaybeReject("script-size");
227+
}
228+
218229
std::vector<std::vector<unsigned char> > vSolutions;
219230
TxoutType whichType = Solver(prev.scriptPubKey, vSolutions);
220231
if (whichType == TxoutType::NONSTANDARD) {
@@ -247,6 +258,9 @@ bool AreInputsStandard(const CTransaction& tx, const CCoinsViewCache& mapInputs,
247258
return false;
248259
}
249260
CScript subscript(stack.back().begin(), stack.back().end());
261+
if (subscript.size() > g_script_size_policy_limit) {
262+
MaybeReject("scriptcheck-size");
263+
}
250264
if (subscript.GetSigOpCount(true) > MAX_P2SH_SIGOPS) {
251265
MaybeReject("scriptcheck-sigops");
252266
}
@@ -310,7 +324,7 @@ bool IsWitnessStandard(const CTransaction& tx, const CCoinsViewCache& mapInputs,
310324

311325
// Check P2WSH standard limits
312326
if (witnessversion == 0 && witnessprogram.size() == WITNESS_V0_SCRIPTHASH_SIZE) {
313-
if (tx.vin[i].scriptWitness.stack.back().size() > MAX_STANDARD_P2WSH_SCRIPT_SIZE)
327+
if (tx.vin[i].scriptWitness.stack.back().size() > std::min(MAX_STANDARD_P2WSH_SCRIPT_SIZE, g_script_size_policy_limit))
314328
MaybeReject("script-size");
315329
size_t sizeWitnessStack = tx.vin[i].scriptWitness.stack.size() - 1;
316330
if (sizeWitnessStack > MAX_STANDARD_P2WSH_STACK_ITEMS)
@@ -336,12 +350,15 @@ bool IsWitnessStandard(const CTransaction& tx, const CCoinsViewCache& mapInputs,
336350
if (stack.size() >= 2) {
337351
// Script path spend (2 or more stack elements after removing optional annex)
338352
const auto& control_block = SpanPopBack(stack);
339-
SpanPopBack(stack); // Ignore script
353+
const auto& tapscript = SpanPopBack(stack);
340354
if (control_block.empty()) {
341355
// Empty control block is invalid
342356
out_reason = reason_prefix + "taproot-control-missing";
343357
return false;
344358
}
359+
if (tapscript.size() > g_script_size_policy_limit) {
360+
MaybeReject("script-size");
361+
}
345362
if ((control_block[0] & TAPROOT_LEAF_MASK) == TAPROOT_LEAF_TAPSCRIPT) {
346363
// Leaf version 0xc0 (aka Tapscript, see BIP 342)
347364
if (!ignore_rejects.count(reason_prefix + "taproot-stackitem-size")) {

src/policy/policy.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,8 @@ static constexpr unsigned int MAX_P2SH_SIGOPS{15};
4444
static constexpr unsigned int MAX_STANDARD_TX_SIGOPS_COST{MAX_BLOCK_SIGOPS_COST/5};
4545
/** Default for -incrementalrelayfee, which sets the minimum feerate increase for mempool limiting or replacement **/
4646
static constexpr unsigned int DEFAULT_INCREMENTAL_RELAY_FEE{1000};
47+
/** Default for -maxscriptsize */
48+
static constexpr unsigned int DEFAULT_SCRIPT_SIZE_POLICY_LIMIT{std::numeric_limits<unsigned int>::max()};
4749
/** Default for -bytespersigop */
4850
static constexpr unsigned int DEFAULT_BYTES_PER_SIGOP{20};
4951
/** Default for -bytespersigopstrict */

src/policy/settings.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
#ifndef BITCOIN_POLICY_SETTINGS_H
77
#define BITCOIN_POLICY_SETTINGS_H
88

9+
extern unsigned int g_script_size_policy_limit;
910
extern unsigned int nBytesPerSigOp;
1011
extern unsigned int nBytesPerSigOpStrict;
1112
extern unsigned int g_weight_per_data_byte;

0 commit comments

Comments
 (0)