Skip to content

Commit 9775634

Browse files
authored
Merge pull request #1589 from evoskuil/master
Treat internal cb spend (immature) as locked in block.prevout().
2 parents d9ea76b + 8ccb445 commit 9775634

1 file changed

Lines changed: 10 additions & 6 deletions

File tree

src/chain/block.cpp

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -698,25 +698,24 @@ bool block::is_unspent_coinbase_collision() const NOEXCEPT
698698
return !txs_->front()->inputs_ptr()->front()->metadata.spent;
699699
}
700700

701-
// Search is not ordered, forward references are caught by block.check.
701+
// Search is unordered, forward refs (and duplicates) caught by block.check.
702702
bool block::populate(const chain::context& ctx) const NOEXCEPT
703703
{
704704
if (txs_->empty())
705705
return true;
706706

707-
const auto start = std::next(txs_->begin());
708707
const auto bip68 = ctx.is_enabled(chain::flags::bip68_rule);
709708
unordered_map_of_cref_point_to_output_cptr_cref points{ outputs() };
710709
uint32_t index{};
711710

712-
// Populate outputs hash table.
713-
for (auto tx = start; tx != txs_->end(); ++tx, index = 0)
711+
// Populate outputs hash table (coinbase included).
712+
for (auto tx = txs_->begin(); tx != txs_->end(); ++tx, index = 0)
714713
for (const auto& out: *(*tx)->outputs_ptr())
715714
points.emplace(cref_point{ (*tx)->get_hash(false), index++ }, out);
716715

717716
// Populate input prevouts from hash table and obtain locked state.
718717
auto locked = false;
719-
for (auto tx = start; tx != txs_->end(); ++tx)
718+
for (auto tx = std::next(txs_->begin()); tx != txs_->end(); ++tx)
720719
{
721720
for (const auto& in: *(*tx)->inputs_ptr())
722721
{
@@ -726,8 +725,13 @@ bool block::populate(const chain::context& ctx) const NOEXCEPT
726725

727726
if (point != points.end())
728727
{
728+
// Zero maturity coinbase spend is treated as locked.
729+
const auto lock = (bip68 && (*tx)->is_internal_lock(*in));
730+
const auto immature = !is_zero(coinbase_maturity) &&
731+
(in->point().hash() == txs_->front()->get_hash(false));
732+
729733
in->prevout = point->second;
730-
in->metadata.locked = bip68 && (*tx)->is_internal_lock(*in);
734+
in->metadata.locked = immature || lock;
731735
locked |= in->metadata.locked;
732736
}
733737
}

0 commit comments

Comments
 (0)