forked from lthn/blockchain
experimental crypto: scalar_t::is_reduced(), tests, new primitives for performance test
This commit is contained in:
parent
9a594cc719
commit
aac094ce4b
1 changed files with 111 additions and 5 deletions
|
|
@ -16,6 +16,8 @@ extern "C" {
|
|||
#include "crypto/crypto-ops.h"
|
||||
} // extern "C"
|
||||
|
||||
namespace mp = boost::multiprecision;
|
||||
|
||||
// out = z ^ s (mod l)
|
||||
void sc_exp(unsigned char* out, const unsigned char* z, const unsigned char* s)
|
||||
{
|
||||
|
|
@ -302,6 +304,11 @@ struct alignas(32) scalar_t
|
|||
return sc_isnonzero(&m_s[0]) == 0;
|
||||
}
|
||||
|
||||
bool is_reduced() const
|
||||
{
|
||||
return sc_check(&m_s[0]) == 0;
|
||||
}
|
||||
|
||||
scalar_t operator+(const scalar_t& v) const
|
||||
{
|
||||
scalar_t result;
|
||||
|
|
@ -331,20 +338,20 @@ struct alignas(32) scalar_t
|
|||
scalar_t operator*(const scalar_t& v) const
|
||||
{
|
||||
scalar_t result;
|
||||
sc_mul(&result.m_s[0], &m_s[0], &v.m_s[0]);
|
||||
sc_mul(result.m_s, m_s, v.m_s);
|
||||
return result;
|
||||
}
|
||||
|
||||
scalar_t& operator*=(const scalar_t& v)
|
||||
{
|
||||
sc_mul(&m_s[0], &m_s[0], &v.m_s[0]);
|
||||
sc_mul(m_s, m_s, v.m_s);
|
||||
return *this;
|
||||
}
|
||||
|
||||
scalar_t reciprocal() const
|
||||
{
|
||||
scalar_t result;
|
||||
sc_invert(&result.m_s[0], &m_s[0]);
|
||||
sc_invert(result.m_s, m_s);
|
||||
return result;
|
||||
}
|
||||
|
||||
|
|
@ -997,8 +1004,8 @@ TEST(crypto, primitives)
|
|||
result += cb(t, rounds);
|
||||
t_total.stop();
|
||||
double run_time_mcs_x_100 = double(uint64_t(t.get_time_mcs() / (rounds / 100)));
|
||||
LOG_PRINT_L0(std::left << std::setw(50) << title << std::setw(7) << rounds << " rnds -> "
|
||||
<< std::right << std::setw(7) << std::fixed << std::setprecision(2) << run_time_mcs_x_100 / 100.0 << " mcs avg. (gross: "
|
||||
LOG_PRINT_L0(std::left << std::setw(40) << title << std::setw(7) << rounds << " rnds -> "
|
||||
<< std::right << std::setw(7) << std::fixed << std::setprecision(2) << run_time_mcs_x_100 / 100.0 << " mcs avg. (gross: "
|
||||
<< std::fixed << std::setprecision(2) << double(t_total.get_time_mcs()) / 1000.0 << " ms), result hash: " << result);
|
||||
};
|
||||
|
||||
|
|
@ -1006,6 +1013,91 @@ TEST(crypto, primitives)
|
|||
|
||||
LOG_PRINT_L0(ENDL << "native crypto primitives:");
|
||||
|
||||
run("sc_reduce", 30000, [](timer_t& t, size_t rounds) {
|
||||
std::vector<size_t> rnd_indecies;
|
||||
helper::make_rnd_indicies(rnd_indecies, rounds);
|
||||
|
||||
struct bytes64
|
||||
{
|
||||
unsigned char b[64];
|
||||
};
|
||||
|
||||
std::vector<bytes64> scalars_64(rounds);
|
||||
for (size_t i = 0; i < scalars_64.size(); ++i)
|
||||
crypto::generate_random_bytes(sizeof(bytes64), scalars_64[i].b);
|
||||
|
||||
t.start();
|
||||
for (size_t i = 0; i < rounds; ++i)
|
||||
{
|
||||
sc_reduce(scalars_64[rnd_indecies[i]].b);
|
||||
}
|
||||
t.stop();
|
||||
|
||||
return HASH_64_VEC(scalars_64);
|
||||
});
|
||||
|
||||
run("sc_reduce32", 30000, [](timer_t& t, size_t rounds) {
|
||||
std::vector<size_t> rnd_indecies;
|
||||
helper::make_rnd_indicies(rnd_indecies, rounds);
|
||||
|
||||
std::vector<crypto::ec_scalar> scalars(rounds);
|
||||
for (size_t i = 0; i < scalars.size(); ++i)
|
||||
crypto::generate_random_bytes(sizeof(crypto::ec_scalar), scalars[i].data);
|
||||
|
||||
t.start();
|
||||
for (size_t i = 0; i < rounds; ++i)
|
||||
{
|
||||
sc_reduce32((unsigned char*)&scalars[rnd_indecies[i]].data);
|
||||
}
|
||||
t.stop();
|
||||
|
||||
return HASH_64_VEC(scalars);
|
||||
});
|
||||
|
||||
run("ge_p3_tobytes", 10000, [](timer_t& t, size_t rounds) {
|
||||
std::vector<size_t> rnd_indecies;
|
||||
helper::make_rnd_indicies(rnd_indecies, rounds);
|
||||
|
||||
std::vector<ge_p3> points_p3(rounds);
|
||||
ge_scalarmult_base(&points_p3[0], c_scalar_1.data());
|
||||
for (size_t i = 1; i < points_p3.size(); ++i)
|
||||
ge_bytes_hash_to_ec(&points_p3[i], (const unsigned char*)&points_p3[i - 1].X); // P_{i+1} = Hp(P_i.X)
|
||||
|
||||
std::vector<crypto::ec_point> points(rounds);
|
||||
t.start();
|
||||
for (size_t i = 0; i < rounds; ++i)
|
||||
{
|
||||
ge_p3_tobytes((unsigned char*)points[i].data, &points_p3[rnd_indecies[i]]);
|
||||
}
|
||||
t.stop();
|
||||
|
||||
return HASH_64_VEC(points);
|
||||
});
|
||||
|
||||
run("ge_frombytes_vartime(p3)", 10000, [](timer_t& t, size_t rounds) {
|
||||
std::vector<size_t> rnd_indecies;
|
||||
helper::make_rnd_indicies(rnd_indecies, rounds);
|
||||
|
||||
point_t P = c_point_G;
|
||||
|
||||
std::vector<crypto::ec_point> points_p3_bytes(rounds);
|
||||
for (size_t i = 0; i < points_p3_bytes.size(); ++i)
|
||||
{
|
||||
P = hash_helper_t::hp(P);
|
||||
ge_p3_tobytes((unsigned char*)&points_p3_bytes[i], &P.m_p3);
|
||||
}
|
||||
|
||||
std::vector<ge_p3> points(rounds);
|
||||
t.start();
|
||||
for (size_t i = 0; i < rounds; ++i)
|
||||
{
|
||||
ge_frombytes_vartime(&points[i], (unsigned char*)&points_p3_bytes[rnd_indecies[i]]);
|
||||
}
|
||||
t.stop();
|
||||
|
||||
return HASH_64_VEC(points);
|
||||
});
|
||||
|
||||
run("ge_p3_to_cached(p3)", 10000, [](timer_t& t, size_t rounds) {
|
||||
std::vector<size_t> rnd_indecies;
|
||||
helper::make_rnd_indicies(rnd_indecies, rounds);
|
||||
|
|
@ -1643,6 +1735,7 @@ TEST(crypto, scalar_basics)
|
|||
{
|
||||
z.make_random();
|
||||
ASSERT_FALSE(z.is_zero());
|
||||
ASSERT_TRUE(z.is_reduced());
|
||||
ASSERT_TRUE(z > z - 1);
|
||||
ASSERT_TRUE(z < z + 1);
|
||||
}
|
||||
|
|
@ -1673,6 +1766,19 @@ TEST(crypto, scalar_basics)
|
|||
|
||||
ASSERT_EQ(scalar_t(3) / c_scalar_Lm1, scalar_t(3) * c_scalar_Lm1); // because (L - 1) ^ 2 = 1
|
||||
|
||||
// check is_reduced
|
||||
ASSERT_TRUE(c_scalar_Lm1.is_reduced());
|
||||
ASSERT_FALSE(c_scalar_L.is_reduced());
|
||||
scalar_t p = c_scalar_L;
|
||||
ASSERT_FALSE(p.is_reduced());
|
||||
p = p + 1;
|
||||
ASSERT_TRUE(p.is_reduced());
|
||||
p = 0;
|
||||
p = p + c_scalar_P;
|
||||
ASSERT_TRUE(p.is_reduced());
|
||||
mp::uint256_t mp_p_mod_l = c_scalar_P.as_boost_mp_type<mp::uint256_t>() % c_scalar_L.as_boost_mp_type<mp::uint256_t>();
|
||||
ASSERT_EQ(p, scalar_t(mp_p_mod_l));
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue