@@ -294,6 +294,48 @@ BOOST_FIXTURE_TEST_CASE(rbf_helper_functions, TestChain100Setup)
294
294
BOOST_CHECK_EQUAL (pool.CheckConflictTopology ({entry_two_parent_child}).value (), strprintf (" %s has 2 ancestors, max 1 allowed" , entry_two_parent_child->GetSharedTx ()->GetHash ().ToString ()));
295
295
}
296
296
297
+ BOOST_FIXTURE_TEST_CASE (improves_feerate, TestChain100Setup)
298
+ {
299
+ CTxMemPool& pool = *Assert (m_node.mempool );
300
+ LOCK2 (::cs_main, pool.cs );
301
+ TestMemPoolEntryHelper entry;
302
+
303
+ const CAmount low_fee{CENT/100 };
304
+ const CAmount normal_fee{CENT/10 };
305
+
306
+ // low feerate parent with normal feerate child
307
+ const auto tx1 = make_tx (/* inputs=*/ {m_coinbase_txns[0 ]}, /* output_values=*/ {10 * COIN});
308
+ pool.addUnchecked (entry.Fee (low_fee).FromTx (tx1));
309
+ const auto tx2 = make_tx (/* inputs=*/ {tx1}, /* output_values=*/ {995 * CENT});
310
+ pool.addUnchecked (entry.Fee (normal_fee).FromTx (tx2));
311
+
312
+ const auto entry1 = pool.GetIter (tx1->GetHash ()).value ();
313
+ const auto tx1_fee = entry1->GetModifiedFee ();
314
+ const auto tx1_size = entry1->GetTxSize ();
315
+ const auto entry2 = pool.GetIter (tx2->GetHash ()).value ();
316
+ const auto tx2_fee = entry2->GetModifiedFee ();
317
+ const auto tx2_size = entry2->GetTxSize ();
318
+
319
+ // Now test ImprovesFeerateDiagram with various levels of "package rbf" feerates
320
+
321
+ // It doesn't improve itself
322
+ const auto res1 = ImprovesFeerateDiagram (pool, {entry1}, {entry1, entry2}, tx1_fee + tx2_fee, tx1_size + tx2_size);
323
+ BOOST_CHECK (res1.has_value ());
324
+ BOOST_CHECK (res1.value ().first == DiagramCheckError::FAILURE);
325
+ BOOST_CHECK (res1.value ().second == " insufficient feerate: does not improve feerate diagram" );
326
+
327
+ // With one more satoshi it does
328
+ BOOST_CHECK (ImprovesFeerateDiagram (pool, {entry1}, {entry1, entry2}, tx1_fee + tx2_fee + 1 , tx1_size + tx2_size) == std::nullopt);
329
+
330
+ // Adding a grandchild makes the cluster size 3, which is uncalculable
331
+ const auto tx3 = make_tx (/* inputs=*/ {tx2}, /* output_values=*/ {995 * CENT});
332
+ pool.addUnchecked (entry.Fee (normal_fee).FromTx (tx3));
333
+ const auto res3 = ImprovesFeerateDiagram (pool, {entry1}, {entry1, entry2}, tx1_fee + tx2_fee + 1 , tx1_size + tx2_size);
334
+ BOOST_CHECK (res3.has_value ());
335
+ BOOST_CHECK (res3.value ().first == DiagramCheckError::UNCALCULABLE);
336
+ BOOST_CHECK (res3.value ().second == strprintf (" %s has 2 descendants, max 1 allowed" , tx1->GetHash ().GetHex ()));
337
+ }
338
+
297
339
BOOST_AUTO_TEST_CASE (feerate_diagram_utilities)
298
340
{
299
341
// Sanity check the correctness of the feerate diagram comparison.
0 commit comments