1
0
Fork 0
forked from lthn/blockchain

checkpoints: get_checkpoint_before_height() added with unit tests (+ unit tests for is_in_checkpoint_zone())

This commit is contained in:
sowle 2021-11-26 16:06:44 +03:00
parent 88e361bb38
commit 71ef04d9e6
No known key found for this signature in database
GPG key ID: C07A24B2D89D49FC
3 changed files with 72 additions and 2 deletions

View file

@ -36,11 +36,11 @@ namespace currency
if(height > blockchain_last_block_height)
return false;
auto it = m_points.lower_bound(height);
auto it = m_points.lower_bound(height); // if found, it->first >= height
if(it == m_points.end())
return false;
if(it->first <= blockchain_last_block_height)
return true;
return true; // this is the case only if height <= it->first <= blockchain_last_block_height
else
return false;
}
@ -68,4 +68,27 @@ namespace currency
return false;
}
}
//---------------------------------------------------------------------------
uint64_t checkpoints::get_checkpoint_before_height(uint64_t height) const
{
// returns height of the leftmost CP with height that is LESS than the given height
// ex:
// If there are two CP at 11 and 15:
// get_checkpoint_before_height(10) = 0
// get_checkpoint_before_height(11) = 0
// get_checkpoint_before_height(12) = 11
// get_checkpoint_before_height(13) = 11
// get_checkpoint_before_height(14) = 11
// get_checkpoint_before_height(15) = 11
// get_checkpoint_before_height(16) = 15
uint64_t top_cp = get_top_checkpoint_height();
if (height > top_cp)
return top_cp;
auto it = m_points.lower_bound(height); // if found, it->first >= height
if (it == m_points.end() || --it == m_points.end())
return 0;
return it->first;
}
}

View file

@ -20,6 +20,8 @@ namespace currency
bool is_height_passed_zone(uint64_t height, uint64_t blockchain_last_block_height) const;
bool check_block(uint64_t height, const crypto::hash& h) const;
uint64_t get_top_checkpoint_height() const;
uint64_t get_checkpoint_before_height(uint64_t height) const;
private:
std::map<uint64_t, crypto::hash> m_points;
};

View file

@ -39,3 +39,48 @@ TEST(checkpoints_test, test_checkpoints_for_alternative)
r = cp.is_height_passed_zone(11, 12);
ASSERT_FALSE(r);
}
TEST(checkpoints_test, get_checkpoint_before_height)
{
currency::checkpoints cp;
cp.add_checkpoint(11, "0000000000000000000000000000000000000000000000000000000000000000");
cp.add_checkpoint(15, "0000000000000000000000000000000000000000000000000000000000000000");
cp.add_checkpoint(21, "0000000000000000000000000000000000000000000000000000000000000000");
for(uint64_t h = 0; h < 11; ++h)
ASSERT_TRUE(cp.get_checkpoint_before_height(h) == 0);
ASSERT_TRUE(cp.get_checkpoint_before_height(11) == 0);
ASSERT_TRUE(cp.get_checkpoint_before_height(12) == 11);
ASSERT_TRUE(cp.get_checkpoint_before_height(13) == 11);
ASSERT_TRUE(cp.get_checkpoint_before_height(14) == 11);
ASSERT_TRUE(cp.get_checkpoint_before_height(15) == 11);
ASSERT_TRUE(cp.get_checkpoint_before_height(16) == 15);
ASSERT_TRUE(cp.get_checkpoint_before_height(17) == 15);
ASSERT_TRUE(cp.get_checkpoint_before_height(18) == 15);
ASSERT_TRUE(cp.get_checkpoint_before_height(19) == 15);
ASSERT_TRUE(cp.get_checkpoint_before_height(20) == 15);
ASSERT_TRUE(cp.get_checkpoint_before_height(21) == 15);
ASSERT_TRUE(cp.get_checkpoint_before_height(22) == 21);
for(uint64_t h = 22; h < 100; ++h)
ASSERT_TRUE(cp.get_checkpoint_before_height(h) == 21);
}
TEST(checkpoints_test, is_in_checkpoint_zone)
{
currency::checkpoints cp;
cp.add_checkpoint(11, "0000000000000000000000000000000000000000000000000000000000000000");
cp.add_checkpoint(15, "0000000000000000000000000000000000000000000000000000000000000000");
cp.add_checkpoint(21, "0000000000000000000000000000000000000000000000000000000000000000");
for (uint64_t h = 0; h < 22; ++h)
ASSERT_TRUE(cp.is_in_checkpoint_zone(h));
for (uint64_t h = 22; h < 100; ++h)
ASSERT_FALSE(cp.is_in_checkpoint_zone(h));
}