diff options
author | Jack Lloyd <[email protected]> | 2020-10-20 19:17:28 -0400 |
---|---|---|
committer | Jack Lloyd <[email protected]> | 2020-10-20 19:17:28 -0400 |
commit | 54ccb865195aeecd40d6081dca0dab157b9f8fa5 (patch) | |
tree | 1b2a52a81097bdbe92136a56f831d9b9f31103a6 /src/lib/pubkey/ec_group | |
parent | f33f00e5d0add6b17c3a51407720710a58bacd0b (diff) |
Fix ECC multiexponentiation when two points are related
If the points are related by x = -{1,2,3}y then an infinity was
silently produced, causing validation failures.
Fixes #2424
Diffstat (limited to 'src/lib/pubkey/ec_group')
-rw-r--r-- | src/lib/pubkey/ec_group/point_gfp.cpp | 6 | ||||
-rw-r--r-- | src/lib/pubkey/ec_group/point_mul.cpp | 20 | ||||
-rw-r--r-- | src/lib/pubkey/ec_group/point_mul.h | 1 |
3 files changed, 25 insertions, 2 deletions
diff --git a/src/lib/pubkey/ec_group/point_gfp.cpp b/src/lib/pubkey/ec_group/point_gfp.cpp index c78763829..6c2302bd6 100644 --- a/src/lib/pubkey/ec_group/point_gfp.cpp +++ b/src/lib/pubkey/ec_group/point_gfp.cpp @@ -427,6 +427,12 @@ void PointGFp::force_all_affine(std::vector<PointGFp>& points, return; } + for(size_t i = 0; i != points.size(); ++i) + { + if(points[i].is_zero()) + throw Invalid_State("Cannot convert zero ECC point to affine"); + } + /* For >= 2 points use Montgomery's trick diff --git a/src/lib/pubkey/ec_group/point_mul.cpp b/src/lib/pubkey/ec_group/point_mul.cpp index d4a0b6ee6..2dff959d7 100644 --- a/src/lib/pubkey/ec_group/point_mul.cpp +++ b/src/lib/pubkey/ec_group/point_mul.cpp @@ -9,6 +9,7 @@ #include <botan/reducer.h> #include <botan/internal/rounding.h> #include <botan/internal/ct_utils.h> +#include <iostream> namespace Botan { @@ -375,7 +376,19 @@ PointGFp_Multi_Point_Precompute::PointGFp_Multi_Point_Precompute(const PointGFp& m_M.push_back(y3.plus(x2, ws)); m_M.push_back(y3.plus(x3, ws)); - PointGFp::force_all_affine(m_M, ws[0].get_word_vector()); + bool no_infinity = true; + for(auto& pt : m_M) + { + if(pt.is_zero()) + no_infinity = false; + } + + if(no_infinity) + { + PointGFp::force_all_affine(m_M, ws[0].get_word_vector()); + } + + m_no_infinity = no_infinity; } PointGFp PointGFp_Multi_Point_Precompute::multi_exp(const BigInt& z1, @@ -402,7 +415,10 @@ PointGFp PointGFp_Multi_Point_Precompute::multi_exp(const BigInt& z1, // This function is not intended to be const time if(z12) { - H.add_affine(m_M[z12-1], ws); + if(m_no_infinity) + H.add_affine(m_M[z12-1], ws); + else + H.add(m_M[z12-1], ws); } } diff --git a/src/lib/pubkey/ec_group/point_mul.h b/src/lib/pubkey/ec_group/point_mul.h index d503f4bee..095620428 100644 --- a/src/lib/pubkey/ec_group/point_mul.h +++ b/src/lib/pubkey/ec_group/point_mul.h @@ -77,6 +77,7 @@ class PointGFp_Multi_Point_Precompute final const BigInt& k2) const; private: std::vector<PointGFp> m_M; + bool m_no_infinity; }; } |