From 13d98e2cad86a30d08801511ad92dc4426b7b463 Mon Sep 17 00:00:00 2001 From: Nathan Hourt Date: Tue, 25 Apr 2017 15:50:56 -0500 Subject: [PATCH 1/7] Add OpenSSL 1.1.0 support These changes should add support for openssl 1.1.0 while maintaining compatibility with 1.0.2 --- src/crypto/base58.cpp | 142 ++++++++++++++++++++++-------------------- src/crypto/dh.cpp | 47 +++++++++++++- 2 files changed, 119 insertions(+), 70 deletions(-) diff --git a/src/crypto/base58.cpp b/src/crypto/base58.cpp index 4551678..6cc7e58 100644 --- a/src/crypto/base58.cpp +++ b/src/crypto/base58.cpp @@ -66,74 +66,71 @@ public: /** C++ wrapper for BIGNUM (OpenSSL bignum) */ -class CBigNum : public BIGNUM +class CBigNum { + BIGNUM* bn; public: CBigNum() - { - BN_init(this); - } + : bn(BN_new()) {} CBigNum(const CBigNum& b) + : CBigNum() { - BN_init(this); - if (!BN_copy(this, &b)) + if (!BN_copy(bn, b.bn)) { - BN_clear_free(this); + BN_clear_free(bn); throw bignum_error("CBigNum::CBigNum(const CBigNum&) : BN_copy failed"); } } CBigNum& operator=(const CBigNum& b) { - if (!BN_copy(this, &b)) + if (!BN_copy(bn, b.bn)) throw bignum_error("CBigNum::operator= : BN_copy failed"); return (*this); } ~CBigNum() { - BN_clear_free(this); + BN_clear_free(bn); } //CBigNum(char n) is not portable. Use 'signed char' or 'unsigned char'. - CBigNum(signed char n) { BN_init(this); if (n >= 0) setulong(n); else setint64(n); } - CBigNum(short n) { BN_init(this); if (n >= 0) setulong(n); else setint64(n); } - CBigNum(int n) { BN_init(this); if (n >= 0) setulong(n); else setint64(n); } - //CBigNum(long n) { BN_init(this); if (n >= 0) setulong(n); else setint64(n); } - CBigNum(int64_t n) { BN_init(this); setint64(n); } - CBigNum(unsigned char n) { BN_init(this); setulong(n); } - CBigNum(unsigned short n) { BN_init(this); setulong(n); } - CBigNum(unsigned int n) { BN_init(this); setulong(n); } - //CBigNum(unsigned long n) { BN_init(this); setulong(n); } - CBigNum(uint64_t n) { BN_init(this); setuint64(n); } + CBigNum(signed char n) :CBigNum() { if (n >= 0) setulong(n); else setint64(n); } + CBigNum(short n) :CBigNum() { if (n >= 0) setulong(n); else setint64(n); } + CBigNum(int n) :CBigNum() { if (n >= 0) setulong(n); else setint64(n); } + CBigNum(int64_t n) :CBigNum() { setint64(n); } + CBigNum(unsigned char n) :CBigNum() { setulong(n); } + CBigNum(unsigned short n) :CBigNum() { setulong(n); } + CBigNum(unsigned int n) :CBigNum() { setulong(n); } + CBigNum(uint64_t n) :CBigNum() { setuint64(n); } explicit CBigNum(const std::vector& vch) + : CBigNum() { - BN_init(this); setvch(vch); } void setulong(unsigned long n) { - if (!BN_set_word(this, n)) + if (!BN_set_word(bn, n)) throw bignum_error("CBigNum conversion from unsigned long : BN_set_word failed"); } unsigned long getulong() const { - return BN_get_word(this); + return BN_get_word(bn); } unsigned int getuint() const { - return BN_get_word(this); + return BN_get_word(bn); } int getint() const { - unsigned long n = BN_get_word(this); - if (!BN_is_negative(this)) + unsigned long n = BN_get_word(bn); + if (!BN_is_negative(bn)) return (n > (unsigned long)std::numeric_limits::max() ? std::numeric_limits::max() : n); else return (n > (unsigned long)std::numeric_limits::max() ? std::numeric_limits::min() : -(int)n); @@ -171,7 +168,7 @@ public: pch[1] = (nSize >> 16) & 0xff; pch[2] = (nSize >> 8) & 0xff; pch[3] = (nSize) & 0xff; - BN_mpi2bn(pch, p - pch, this); + BN_mpi2bn(pch, p - pch, bn); } void setuint64(uint64_t n) @@ -198,7 +195,7 @@ public: pch[1] = (nSize >> 16) & 0xff; pch[2] = (nSize >> 8) & 0xff; pch[3] = (nSize) & 0xff; - BN_mpi2bn(pch, p - pch, this); + BN_mpi2bn(pch, p - pch, bn); } @@ -214,16 +211,16 @@ public: vch2[3] = (nSize >> 0) & 0xff; // swap data to big endian reverse_copy(vch.begin(), vch.end(), vch2.begin() + 4); - BN_mpi2bn(&vch2[0], vch2.size(), this); + BN_mpi2bn(&vch2[0], vch2.size(), bn); } std::vector getvch() const { - unsigned int nSize = BN_bn2mpi(this, NULL); + unsigned int nSize = BN_bn2mpi(bn, NULL); if (nSize <= 4) return std::vector(); std::vector vch(nSize); - BN_bn2mpi(this, &vch[0]); + BN_bn2mpi(bn, &vch[0]); vch.erase(vch.begin(), vch.begin() + 4); reverse(vch.begin(), vch.end()); return vch; @@ -237,16 +234,16 @@ public: if (nSize >= 1) vch[4] = (nCompact >> 16) & 0xff; if (nSize >= 2) vch[5] = (nCompact >> 8) & 0xff; if (nSize >= 3) vch[6] = (nCompact >> 0) & 0xff; - BN_mpi2bn(&vch[0], vch.size(), this); + BN_mpi2bn(&vch[0], vch.size(), bn); return *this; } unsigned int GetCompact() const { - unsigned int nSize = BN_bn2mpi(this, NULL); + unsigned int nSize = BN_bn2mpi(bn, NULL); std::vector vch(nSize); nSize -= 4; - BN_bn2mpi(this, &vch[0]); + BN_bn2mpi(bn, &vch[0]); unsigned int nCompact = nSize << 24; if (nSize >= 1) nCompact |= (vch[4] << 16); if (nSize >= 2) nCompact |= (vch[5] << 8); @@ -281,7 +278,7 @@ public: *this += n; } if (fNegative) - *this = 0 - *this; + BN_set_negative(bn, 1); } std::string ToString(int nBase=10) const @@ -291,20 +288,20 @@ public: CBigNum bn0 = 0; std::string str; CBigNum bn = *this; - BN_set_negative(&bn, false); + BN_set_negative(bn.bn, false); CBigNum dv; CBigNum rem; - if (BN_cmp(&bn, &bn0) == 0) + if (BN_cmp(bn.bn, bn0.bn) == 0) return "0"; - while (BN_cmp(&bn, &bn0) > 0) + while (BN_cmp(bn.bn, bn0.bn) > 0) { - if (!BN_div(&dv, &rem, &bn, &bnBase, pctx)) + if (!BN_div(dv.bn, rem.bn, bn.bn, bnBase.bn, pctx)) throw bignum_error("CBigNum::ToString() : BN_div failed"); bn = dv; unsigned int c = rem.getulong(); str += "0123456789abcdef"[c]; } - if (BN_is_negative(this)) + if (BN_is_negative(this->bn)) str += "-"; reverse(str.begin(), str.end()); return str; @@ -319,45 +316,50 @@ public: bool operator!() const { - return BN_is_zero(this); + return BN_is_zero(bn); } CBigNum& operator+=(const CBigNum& b) { - if (!BN_add(this, this, &b)) + if (!BN_add(bn, bn, b.bn)) throw bignum_error("CBigNum::operator+= : BN_add failed"); return *this; } CBigNum& operator-=(const CBigNum& b) { - *this = *this - b; + if (!BN_sub(bn, bn, b.bn)) + throw bignum_error("CBigNum::operator-= : BN_sub failed"); return *this; } CBigNum& operator*=(const CBigNum& b) { CAutoBN_CTX pctx; - if (!BN_mul(this, this, &b, pctx)) + if (!BN_mul(bn, bn, b.bn, pctx)) throw bignum_error("CBigNum::operator*= : BN_mul failed"); return *this; } CBigNum& operator/=(const CBigNum& b) { - *this = *this / b; + CAutoBN_CTX pctx; + if (!BN_div(bn, NULL, bn, b.bn, pctx)) + throw bignum_error("CBigNum::operator/= : BN_div failed"); return *this; } CBigNum& operator%=(const CBigNum& b) { - *this = *this % b; + CAutoBN_CTX pctx; + if (!BN_div(NULL, bn, bn, b.bn, pctx)) + throw bignum_error("CBigNum::operator%= : BN_div failed"); return *this; } CBigNum& operator<<=(unsigned int shift) { - if (!BN_lshift(this, this, shift)) + if (!BN_lshift(bn, bn, shift)) throw bignum_error("CBigNum:operator<<= : BN_lshift failed"); return *this; } @@ -368,13 +370,13 @@ public: // if built on ubuntu 9.04 or 9.10, probably depends on version of openssl CBigNum a = 1; a <<= shift; - if (BN_cmp(&a, this) > 0) + if (BN_cmp(a.bn, bn) > 0) { *this = 0; return *this; } - if (!BN_rshift(this, this, shift)) + if (!BN_rshift(bn, bn, shift)) throw bignum_error("CBigNum:operator>>= : BN_rshift failed"); return *this; } @@ -383,7 +385,7 @@ public: CBigNum& operator++() { // prefix operator - if (!BN_add(this, this, BN_value_one())) + if (!BN_add(bn, bn, BN_value_one())) throw bignum_error("CBigNum::operator++ : BN_add failed"); return *this; } @@ -400,7 +402,7 @@ public: { // prefix operator CBigNum r; - if (!BN_sub(&r, this, BN_value_one())) + if (!BN_sub(r.bn, bn, BN_value_one())) throw bignum_error("CBigNum::operator-- : BN_sub failed"); *this = r; return *this; @@ -414,10 +416,12 @@ public: return ret; } - - friend inline const CBigNum operator-(const CBigNum& a, const CBigNum& b); - friend inline const CBigNum operator/(const CBigNum& a, const CBigNum& b); - friend inline const CBigNum operator%(const CBigNum& a, const CBigNum& b); + const BIGNUM* to_bignum() const { + return bn; + } + BIGNUM* to_bignum() { + return bn; + } }; @@ -425,7 +429,7 @@ public: inline const CBigNum operator+(const CBigNum& a, const CBigNum& b) { CBigNum r; - if (!BN_add(&r, &a, &b)) + if (!BN_add(r.to_bignum(), a.to_bignum(), b.to_bignum())) throw bignum_error("CBigNum::operator+ : BN_add failed"); return r; } @@ -433,7 +437,7 @@ inline const CBigNum operator+(const CBigNum& a, const CBigNum& b) inline const CBigNum operator-(const CBigNum& a, const CBigNum& b) { CBigNum r; - if (!BN_sub(&r, &a, &b)) + if (!BN_sub(r.to_bignum(), a.to_bignum(), b.to_bignum())) throw bignum_error("CBigNum::operator- : BN_sub failed"); return r; } @@ -441,7 +445,7 @@ inline const CBigNum operator-(const CBigNum& a, const CBigNum& b) inline const CBigNum operator-(const CBigNum& a) { CBigNum r(a); - BN_set_negative(&r, !BN_is_negative(&r)); + BN_set_negative(r.to_bignum(), !BN_is_negative(r.to_bignum())); return r; } @@ -449,7 +453,7 @@ inline const CBigNum operator*(const CBigNum& a, const CBigNum& b) { CAutoBN_CTX pctx; CBigNum r; - if (!BN_mul(&r, &a, &b, pctx)) + if (!BN_mul(r.to_bignum(), a.to_bignum(), b.to_bignum(), pctx)) throw bignum_error("CBigNum::operator* : BN_mul failed"); return r; } @@ -458,7 +462,7 @@ inline const CBigNum operator/(const CBigNum& a, const CBigNum& b) { CAutoBN_CTX pctx; CBigNum r; - if (!BN_div(&r, NULL, &a, &b, pctx)) + if (!BN_div(r.to_bignum(), NULL, a.to_bignum(), b.to_bignum(), pctx)) throw bignum_error("CBigNum::operator/ : BN_div failed"); return r; } @@ -467,7 +471,7 @@ inline const CBigNum operator%(const CBigNum& a, const CBigNum& b) { CAutoBN_CTX pctx; CBigNum r; - if (!BN_mod(&r, &a, &b, pctx)) + if (!BN_mod(r.to_bignum(), a.to_bignum(), b.to_bignum(), pctx)) throw bignum_error("CBigNum::operator% : BN_div failed"); return r; } @@ -475,7 +479,7 @@ inline const CBigNum operator%(const CBigNum& a, const CBigNum& b) inline const CBigNum operator<<(const CBigNum& a, unsigned int shift) { CBigNum r; - if (!BN_lshift(&r, &a, shift)) + if (!BN_lshift(r.to_bignum(), a.to_bignum(), shift)) throw bignum_error("CBigNum:operator<< : BN_lshift failed"); return r; } @@ -487,12 +491,12 @@ inline const CBigNum operator>>(const CBigNum& a, unsigned int shift) return r; } -inline bool operator==(const CBigNum& a, const CBigNum& b) { return (BN_cmp(&a, &b) == 0); } -inline bool operator!=(const CBigNum& a, const CBigNum& b) { return (BN_cmp(&a, &b) != 0); } -inline bool operator<=(const CBigNum& a, const CBigNum& b) { return (BN_cmp(&a, &b) <= 0); } -inline bool operator>=(const CBigNum& a, const CBigNum& b) { return (BN_cmp(&a, &b) >= 0); } -inline bool operator<(const CBigNum& a, const CBigNum& b) { return (BN_cmp(&a, &b) < 0); } -inline bool operator>(const CBigNum& a, const CBigNum& b) { return (BN_cmp(&a, &b) > 0); } +inline bool operator==(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.to_bignum(), b.to_bignum()) == 0); } +inline bool operator!=(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.to_bignum(), b.to_bignum()) != 0); } +inline bool operator<=(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.to_bignum(), b.to_bignum()) <= 0); } +inline bool operator>=(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.to_bignum(), b.to_bignum()) >= 0); } +inline bool operator<(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.to_bignum(), b.to_bignum()) < 0); } +inline bool operator>(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.to_bignum(), b.to_bignum()) > 0); } static const char* pszBase58 = "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz"; @@ -522,7 +526,7 @@ inline std::string EncodeBase58(const unsigned char* pbegin, const unsigned char CBigNum rem; while (bn > bn0) { - if (!BN_div(&dv, &rem, &bn, &bn58, pctx)) + if (!BN_div(dv.to_bignum(), rem.to_bignum(), bn.to_bignum(), bn58.to_bignum(), pctx)) throw bignum_error("EncodeBase58 : BN_div failed"); bn = dv; unsigned int c = rem.getulong(); @@ -572,7 +576,7 @@ inline bool DecodeBase58(const char* psz, std::vector& vchRet) break; } bnChar.setulong(p1 - pszBase58); - if (!BN_mul(&bn, &bn, &bn58, pctx)) + if (!BN_mul(bn.to_bignum(), bn.to_bignum(), bn58.to_bignum(), pctx)) throw bignum_error("DecodeBase58 : BN_mul failed"); bn += bnChar; } diff --git a/src/crypto/dh.cpp b/src/crypto/dh.cpp index cbd7dcc..e7f6c59 100644 --- a/src/crypto/dh.cpp +++ b/src/crypto/dh.cpp @@ -1,6 +1,9 @@ #include #include +#if OPENSSL_VERSION_NUMBER >= 0x10100000L +#endif + namespace fc { SSL_TYPE(ssl_dh, DH, DH_free) @@ -12,10 +15,19 @@ namespace fc { bool diffie_hellman::generate_params( int s, uint8_t g ) { - ssl_dh dh = DH_generate_parameters( s, g, NULL, NULL ); + ssl_dh dh; + DH_generate_parameters_ex(dh.obj, s, g, NULL); +#if OPENSSL_VERSION_NUMBER >= 0x10100000L + ssl_bignum bn_p; + DH_get0_pqg(dh.obj, (const BIGNUM**)&bn_p.obj, NULL, NULL); + p.resize( BN_num_bytes( bn_p ) ); + if( p.size() ) + BN_bn2bin( bn_p, (unsigned char*)&p.front() ); +#else p.resize( BN_num_bytes( dh->p ) ); if( p.size() ) BN_bn2bin( dh->p, (unsigned char*)&p.front() ); +#endif this->g = g; return fc::validate( dh, valid ); } @@ -25,8 +37,14 @@ namespace fc { if( !p.size() ) return valid = false; ssl_dh dh = DH_new(); +#if OPENSSL_VERSION_NUMBER >= 0x10100000L + const auto bn_p = BN_bin2bn( (unsigned char*)&p.front(), p.size(), NULL ); + const auto bn_g = BN_bin2bn( (unsigned char*)&g, 1, NULL ); + DH_set0_pqg(dh.obj, bn_p, NULL, bn_g); +#else dh->p = BN_bin2bn( (unsigned char*)&p.front(), p.size(), NULL ); dh->g = BN_bin2bn( (unsigned char*)&g, 1, NULL ); +#endif return fc::validate( dh, valid ); } @@ -35,8 +53,14 @@ namespace fc { if( !p.size() ) return valid = false; ssl_dh dh = DH_new(); +#if OPENSSL_VERSION_NUMBER >= 0x10100000L + const auto bn_p = BN_bin2bn( (unsigned char*)&p.front(), p.size(), NULL ); + const auto bn_g = BN_bin2bn( (unsigned char*)&g, 1, NULL ); + DH_set0_pqg(dh.obj, bn_p, NULL, bn_g); +#else dh->p = BN_bin2bn( (unsigned char*)&p.front(), p.size(), NULL ); dh->g = BN_bin2bn( (unsigned char*)&g, 1, NULL ); +#endif if( !fc::validate( dh, valid ) ) { @@ -44,21 +68,42 @@ namespace fc { } DH_generate_key(dh); +#if OPENSSL_VERSION_NUMBER >= 0x10100000L + ssl_bignum bn_pub_key; + ssl_bignum bn_priv_key; + DH_get0_key(dh.obj, (const BIGNUM**)&bn_pub_key.obj, (const BIGNUM**)&bn_priv_key.obj); + pub_key.resize( BN_num_bytes( bn_pub_key ) ); + priv_key.resize( BN_num_bytes( bn_priv_key ) ); + if( pub_key.size() ) + BN_bn2bin( bn_pub_key.obj, (unsigned char*)&pub_key.front() ); + if( priv_key.size() ) + BN_bn2bin( bn_priv_key.obj, (unsigned char*)&priv_key.front() ); +#else pub_key.resize( BN_num_bytes( dh->pub_key ) ); priv_key.resize( BN_num_bytes( dh->priv_key ) ); if( pub_key.size() ) BN_bn2bin( dh->pub_key, (unsigned char*)&pub_key.front() ); if( priv_key.size() ) BN_bn2bin( dh->priv_key, (unsigned char*)&priv_key.front() ); +#endif return true; } bool diffie_hellman::compute_shared_key( const char* buf, uint32_t s ) { ssl_dh dh = DH_new(); +#if OPENSSL_VERSION_NUMBER >= 0x10100000L + auto bn_p = BN_bin2bn( (unsigned char*)&p.front(), p.size(), NULL ); + auto bn_pub_key = BN_bin2bn( (unsigned char*)&pub_key.front(), pub_key.size(), NULL ); + auto bn_priv_key = BN_bin2bn( (unsigned char*)&priv_key.front(), priv_key.size(), NULL ); + auto bn_g = BN_bin2bn( (unsigned char*)&g, 1, NULL ); + DH_set0_pqg(dh.obj, bn_p, NULL, bn_g); + DH_set0_key(dh.obj, bn_pub_key, bn_priv_key); +#else dh->p = BN_bin2bn( (unsigned char*)&p.front(), p.size(), NULL ); dh->pub_key = BN_bin2bn( (unsigned char*)&pub_key.front(), pub_key.size(), NULL ); dh->priv_key = BN_bin2bn( (unsigned char*)&priv_key.front(), priv_key.size(), NULL ); dh->g = BN_bin2bn( (unsigned char*)&g, 1, NULL ); +#endif int check; DH_check(dh,&check); From ef27d4b3a17b7db4875326d9d8a6f1ffa7e21483 Mon Sep 17 00:00:00 2001 From: Fabian Schuh Date: Fri, 5 Jan 2018 16:10:37 +0100 Subject: [PATCH 2/7] Initial work for openssl-1.1 support --- src/log/file_appender.cpp | 1 + tests/blinding_test.cpp | 2 ++ vendor/websocketpp | 2 +- 3 files changed, 4 insertions(+), 1 deletion(-) diff --git a/src/log/file_appender.cpp b/src/log/file_appender.cpp index 844a705..49ae357 100644 --- a/src/log/file_appender.cpp +++ b/src/log/file_appender.cpp @@ -9,6 +9,7 @@ #include #include #include +#include namespace fc { diff --git a/tests/blinding_test.cpp b/tests/blinding_test.cpp index 318f161..bfc84b7 100644 --- a/tests/blinding_test.cpp +++ b/tests/blinding_test.cpp @@ -42,6 +42,7 @@ static fc::string BLIND_T_X = "80deff382af8a8e4a5f297588e44d5bf858f30a524f74b13e static fc::string BLINDED_HASH = "7196e80cdafdfdfb7496323ad24bf47dda8447febd7426e444facc04940c7309"; static fc::string BLIND_SIG = "40d6a477d849cc860df8ad159481f2ffc5b4dc3131b86a799d7d10460824dd53"; static fc::string UNBLINDED = "700092a72a05e33509f9b068aa1d7c5336d8b5692b4157da199d7ec1e10fd7c0"; +/* BOOST_AUTO_TEST_CASE(test_extended_keys_1) { @@ -302,3 +303,4 @@ BOOST_AUTO_TEST_CASE(openssl_blinding) // printf("\nunblinded: "); print(sig->s); // printf("\n"); } +*/ diff --git a/vendor/websocketpp b/vendor/websocketpp index e6c4e3c..19cad99 160000 --- a/vendor/websocketpp +++ b/vendor/websocketpp @@ -1 +1 @@ -Subproject commit e6c4e3c54bf9cf1892c85a6ed6289486bba36fa1 +Subproject commit 19cad9925f83d15d7487c16f0491f4741ec9f674 From 6b81aab6ef9ad18dfeb9743164f5fe8c4fd2ed5a Mon Sep 17 00:00:00 2001 From: Fabian Schuh Date: Wed, 14 Feb 2018 09:59:36 +0100 Subject: [PATCH 3/7] [websocketpp] update submodule and provide patched version via separate repository --- vendor/diff-match-patch-cpp-stl | 1 - vendor/websocketpp | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) delete mode 160000 vendor/diff-match-patch-cpp-stl diff --git a/vendor/diff-match-patch-cpp-stl b/vendor/diff-match-patch-cpp-stl deleted file mode 160000 index 7f95b37..0000000 --- a/vendor/diff-match-patch-cpp-stl +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 7f95b37e554453262e2bcda830724fc362614103 diff --git a/vendor/websocketpp b/vendor/websocketpp index 19cad99..e6c4e3c 160000 --- a/vendor/websocketpp +++ b/vendor/websocketpp @@ -1 +1 @@ -Subproject commit 19cad9925f83d15d7487c16f0491f4741ec9f674 +Subproject commit e6c4e3c54bf9cf1892c85a6ed6289486bba36fa1 From c0db16bf3b325061247d45d04dbf55342591287c Mon Sep 17 00:00:00 2001 From: Fabian Schuh Date: Fri, 13 Apr 2018 11:21:36 +0200 Subject: [PATCH 4/7] Fix erros in unittest --- src/crypto/dh.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/crypto/dh.cpp b/src/crypto/dh.cpp index e7f6c59..981ba47 100644 --- a/src/crypto/dh.cpp +++ b/src/crypto/dh.cpp @@ -15,7 +15,7 @@ namespace fc { bool diffie_hellman::generate_params( int s, uint8_t g ) { - ssl_dh dh; + ssl_dh dh(DH_new()); DH_generate_parameters_ex(dh.obj, s, g, NULL); #if OPENSSL_VERSION_NUMBER >= 0x10100000L ssl_bignum bn_p; From 5706d58cdc72be4ea5834dd14266605e7e09f85a Mon Sep 17 00:00:00 2001 From: Peter Conrad Date: Sat, 21 Apr 2018 20:39:40 +0200 Subject: [PATCH 5/7] Fixed DH memory handling with openssl-1.1 --- src/crypto/dh.cpp | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/src/crypto/dh.cpp b/src/crypto/dh.cpp index 981ba47..e6f4f03 100644 --- a/src/crypto/dh.cpp +++ b/src/crypto/dh.cpp @@ -18,8 +18,8 @@ namespace fc { ssl_dh dh(DH_new()); DH_generate_parameters_ex(dh.obj, s, g, NULL); #if OPENSSL_VERSION_NUMBER >= 0x10100000L - ssl_bignum bn_p; - DH_get0_pqg(dh.obj, (const BIGNUM**)&bn_p.obj, NULL, NULL); + const BIGNUM* bn_p; // must not be free'd! + DH_get0_pqg(dh.obj, &bn_p, NULL, NULL); p.resize( BN_num_bytes( bn_p ) ); if( p.size() ) BN_bn2bin( bn_p, (unsigned char*)&p.front() ); @@ -69,15 +69,15 @@ namespace fc { DH_generate_key(dh); #if OPENSSL_VERSION_NUMBER >= 0x10100000L - ssl_bignum bn_pub_key; - ssl_bignum bn_priv_key; - DH_get0_key(dh.obj, (const BIGNUM**)&bn_pub_key.obj, (const BIGNUM**)&bn_priv_key.obj); + const BIGNUM* bn_pub_key; // must not be free'd! + const BIGNUM* bn_priv_key; // must not be free'd! + DH_get0_key(dh.obj, &bn_pub_key, &bn_priv_key); pub_key.resize( BN_num_bytes( bn_pub_key ) ); priv_key.resize( BN_num_bytes( bn_priv_key ) ); if( pub_key.size() ) - BN_bn2bin( bn_pub_key.obj, (unsigned char*)&pub_key.front() ); + BN_bn2bin( bn_pub_key, (unsigned char*)&pub_key.front() ); if( priv_key.size() ) - BN_bn2bin( bn_priv_key.obj, (unsigned char*)&priv_key.front() ); + BN_bn2bin( bn_priv_key, (unsigned char*)&priv_key.front() ); #else pub_key.resize( BN_num_bytes( dh->pub_key ) ); priv_key.resize( BN_num_bytes( dh->priv_key ) ); From fccabf1eb6a2cd4458182929368448e783008013 Mon Sep 17 00:00:00 2001 From: Peter Conrad Date: Sat, 21 Apr 2018 21:42:45 +0200 Subject: [PATCH 6/7] Fixed blinding test + implementation --- src/crypto/elliptic_common.cpp | 5 ++- src/crypto/elliptic_secp256k1.cpp | 2 +- tests/blinding_test.cpp | 61 +++++++++++-------------------- 3 files changed, 25 insertions(+), 43 deletions(-) diff --git a/src/crypto/elliptic_common.cpp b/src/crypto/elliptic_common.cpp index 7027179..6cfd60d 100644 --- a/src/crypto/elliptic_common.cpp +++ b/src/crypto/elliptic_common.cpp @@ -231,11 +231,12 @@ namespace fc { namespace ecc { static fc::string _to_base58( const extended_key_data& key ) { - char *buffer = (char*)alloca(key.size() + 4); + size_t buf_len = key.size() + 4; + char *buffer = (char*)alloca(buf_len); memcpy( buffer, key.begin(), key.size() ); fc::sha256 double_hash = fc::sha256::hash( fc::sha256::hash( key.begin(), key.size() )); memcpy( buffer + key.size(), double_hash.data(), 4 ); - return fc::to_base58( buffer, sizeof(buffer) ); + return fc::to_base58( buffer, buf_len ); } static void _parse_extended_data( unsigned char* buffer, fc::string base58 ) diff --git a/src/crypto/elliptic_secp256k1.cpp b/src/crypto/elliptic_secp256k1.cpp index ecb2c0c..4c7dcfe 100644 --- a/src/crypto/elliptic_secp256k1.cpp +++ b/src/crypto/elliptic_secp256k1.cpp @@ -193,7 +193,7 @@ namespace fc { namespace ecc { unsigned char *buffer = (unsigned char*)alloca(len + 1); *buffer = 0; memcpy( buffer + 1, in, len ); - BN_bin2bn( buffer, sizeof(buffer), out ); + BN_bin2bn( buffer, len + 1, out ); } else { diff --git a/tests/blinding_test.cpp b/tests/blinding_test.cpp index bfc84b7..7f30c74 100644 --- a/tests/blinding_test.cpp +++ b/tests/blinding_test.cpp @@ -42,7 +42,6 @@ static fc::string BLIND_T_X = "80deff382af8a8e4a5f297588e44d5bf858f30a524f74b13e static fc::string BLINDED_HASH = "7196e80cdafdfdfb7496323ad24bf47dda8447febd7426e444facc04940c7309"; static fc::string BLIND_SIG = "40d6a477d849cc860df8ad159481f2ffc5b4dc3131b86a799d7d10460824dd53"; static fc::string UNBLINDED = "700092a72a05e33509f9b068aa1d7c5336d8b5692b4157da199d7ec1e10fd7c0"; -/* BOOST_AUTO_TEST_CASE(test_extended_keys_1) { @@ -120,7 +119,7 @@ BOOST_AUTO_TEST_CASE(test_extended_keys_2) //} BOOST_AUTO_TEST_CASE(test_blinding_1) -{ +{ try { char buffer[7] = "test_"; fc::ecc::extended_private_key alice = fc::ecc::extended_private_key::generate_master( "master" ); fc::ecc::extended_private_key bob = fc::ecc::extended_private_key::generate_master( "puppet" ); @@ -136,8 +135,6 @@ BOOST_AUTO_TEST_CASE(test_blinding_1) try { fc::ecc::compact_signature sig = alice.unblind_signature( bob_pub, blind_sig, hash, i ); fc::ecc::public_key validate( sig, hash ); -// printf("Validated: "); print((unsigned char*) validate.serialize().begin(), 33); -// printf("\nT: "); print((unsigned char*) t.serialize().begin(), 33); printf("\n"); BOOST_CHECK( validate.serialize() == t.serialize() ); } catch (const fc::exception& e) { printf( "Test %d: %s\n", i, e.to_string().c_str() ); @@ -145,10 +142,10 @@ BOOST_AUTO_TEST_CASE(test_blinding_1) alice = alice.derive_child( i ); bob = bob.derive_child( i | 0x80000000 ); } -} +} FC_LOG_AND_RETHROW() } BOOST_AUTO_TEST_CASE(test_blinding_2) -{ +{ try { char message[7] = "test_0"; fc::ecc::extended_private_key alice = fc::ecc::extended_private_key::generate_master( "master" ); fc::ecc::extended_private_key bob = fc::ecc::extended_private_key::generate_master( "puppet" ); @@ -174,7 +171,7 @@ BOOST_AUTO_TEST_CASE(test_blinding_2) BOOST_CHECK( !memcmp( sig.begin() + 1, buffer, sizeof(buffer) ) ); fc::from_hex( UNBLINDED, buffer, sizeof(buffer) ); BOOST_CHECK( !memcmp( sig.begin() + 33, buffer, sizeof(buffer) ) ); -} +} FC_LOG_AND_RETHROW() } static void to_bignum(const char* data32, fc::ssl_bignum& out) { unsigned char dummy[33]; dummy[0] = 0; @@ -182,32 +179,6 @@ static void to_bignum(const char* data32, fc::ssl_bignum& out) { BN_bin2bn((unsigned char*) data32, 32, out); } -//static void print(const fc::sha256 hash) { -// print((unsigned char*) hash.data(), hash.data_size()); -//} -// -//static void print(const BIGNUM* bn) { -// unsigned char buffer[64]; -// int len = BN_num_bytes(bn); -// if (len > sizeof(buffer)) { -// printf("BN too long - %d bytes?!", len); -// return; -// } -// BN_bn2bin(bn, buffer); -// print(buffer, len); -//} -// -//static void print(const fc::ec_group& curve, const fc::ec_point& p, fc::bn_ctx& ctx) { -// fc::ssl_bignum x; -// fc::ssl_bignum y; -// EC_POINT_get_affine_coordinates_GFp(curve, p, x, y, ctx); -// printf("("); -// print(x); -// printf(", "); -// print(y); -// printf(")"); -//} - namespace fc { SSL_TYPE(ec_key, EC_KEY, EC_KEY_free) } @@ -275,15 +246,26 @@ BOOST_AUTO_TEST_CASE(openssl_blinding) BN_mod_mul(blind_sig, p, blinded, n, ctx); BN_mod_add(blind_sig, blind_sig, q, n, ctx); - fc::ecdsa_sig sig(ECDSA_SIG_new()); - BN_copy(sig->r, Kx); - BN_mod_mul(sig->s, c, blind_sig, n, ctx); - BN_mod_add(sig->s, sig->s, d, n, ctx); + fc::ssl_bignum sig_r; + fc::ssl_bignum sig_s; + BN_copy(sig_r, Kx); + BN_mod_mul(sig_s, c, blind_sig, n, ctx); + BN_mod_add(sig_s, sig_s, d, n, ctx); - if (BN_cmp(sig->s, n_half) > 0) { - BN_sub(sig->s, n, sig->s); + if (BN_cmp(sig_s, n_half) > 0) { + BN_sub(sig_s, n, sig_s); } + fc::ecdsa_sig sig(ECDSA_SIG_new()); +#if OPENSSL_VERSION_NUMBER >= 0x10100000L + ECDSA_SIG_set0(sig, sig_r, sig_s); +#else + sig->r = sig_r; + sig->s = sig_s; +#endif + sig_r.obj = nullptr; + sig_s.obj = nullptr; + fc::ec_key verify(EC_KEY_new()); EC_KEY_set_public_key(verify, T); BOOST_CHECK( ECDSA_do_verify( (unsigned char*) hash_.data(), hash_.data_size(), sig, verify ) ); @@ -303,4 +285,3 @@ BOOST_AUTO_TEST_CASE(openssl_blinding) // printf("\nunblinded: "); print(sig->s); // printf("\n"); } -*/ From a3272e4f9e6bb46021c5c760f07ec22d650f1cb6 Mon Sep 17 00:00:00 2001 From: Peter Conrad Date: Sat, 21 Apr 2018 10:57:56 +0200 Subject: [PATCH 7/7] Ripped out unused blinding stuff --- include/fc/crypto/elliptic.hpp | 27 +-- src/crypto/elliptic_common.cpp | 8 - src/crypto/elliptic_secp256k1.cpp | 254 -------------------------- tests/CMakeLists.txt | 3 - tests/blinding_test.cpp | 287 ------------------------------ 5 files changed, 1 insertion(+), 578 deletions(-) delete mode 100644 tests/blinding_test.cpp diff --git a/include/fc/crypto/elliptic.hpp b/include/fc/crypto/elliptic.hpp index 954fc89..3bc16b7 100644 --- a/include/fc/crypto/elliptic.hpp +++ b/include/fc/crypto/elliptic.hpp @@ -25,8 +25,6 @@ namespace fc { typedef fc::array compact_signature; typedef std::vector range_proof_type; typedef fc::array extended_key_data; - typedef fc::sha256 blinded_hash; - typedef fc::sha256 blind_signature; /** * @class public_key @@ -38,7 +36,6 @@ namespace fc { public_key(); public_key(const public_key& k); ~public_key(); -// bool verify( const fc::sha256& digest, const signature& sig ); public_key_data serialize()const; public_key_point_data serialize_ecc_point()const; @@ -52,8 +49,6 @@ namespace fc { public_key child( const fc::sha256& offset )const; bool valid()const; - /** Computes new pubkey = generator * offset + old pubkey ?! */ -// public_key mult( const fc::sha256& offset )const; /** Computes new pubkey = regenerate(offset).pubkey + old pubkey * = offset * G + 1 * old pubkey ?! */ public_key add( const fc::sha256& offset )const; @@ -122,9 +117,7 @@ namespace fc { */ fc::sha512 get_shared_secret( const public_key& pub )const; -// signature sign( const fc::sha256& digest )const; compact_signature sign_compact( const fc::sha256& digest, bool require_canonical = true )const; -// bool verify( const fc::sha256& digest, const signature& sig ); public_key get_public_key()const; @@ -164,8 +157,6 @@ namespace fc { fc::string to_base58() const { return str(); } static extended_public_key from_base58( const fc::string& base58 ); - public_key generate_p( int i ) const; - public_key generate_q( int i ) const; private: sha256 c; int child_num, parent_fp; @@ -192,25 +183,9 @@ namespace fc { static extended_private_key generate_master( const fc::string& seed ); static extended_private_key generate_master( const char* seed, uint32_t seed_len ); - // Oleg Andreev's blind signature scheme, - // see http://blog.oleganza.com/post/77474860538/blind-signatures - public_key blind_public_key( const extended_public_key& bob, int i ) const; - blinded_hash blind_hash( const fc::sha256& hash, int i ) const; - blind_signature blind_sign( const blinded_hash& hash, int i ) const; - // WARNING! This may produce non-canonical signatures! - compact_signature unblind_signature( const extended_public_key& bob, - const blind_signature& sig, - const fc::sha256& hash, int i ) const; - - private: + private: extended_private_key private_derive_rest( const fc::sha512& hash, int num ) const; - private_key generate_a( int i ) const; - private_key generate_b( int i ) const; - private_key generate_c( int i ) const; - private_key generate_d( int i ) const; - private_key_secret compute_p( int i ) const; - private_key_secret compute_q( int i, const private_key_secret& p ) const; sha256 c; int child_num, parent_fp; uint8_t depth; diff --git a/src/crypto/elliptic_common.cpp b/src/crypto/elliptic_common.cpp index 6cfd60d..b736e24 100644 --- a/src/crypto/elliptic_common.cpp +++ b/src/crypto/elliptic_common.cpp @@ -302,9 +302,6 @@ namespace fc { namespace ecc { return extended_public_key( get_public_key(), c, child_num, parent_fp, depth ); } - public_key extended_public_key::generate_p(int i) const { return derive_normal_child(2*i + 0); } - public_key extended_public_key::generate_q(int i) const { return derive_normal_child(2*i + 1); } - extended_private_key extended_private_key::derive_child(int i) const { return i < 0 ? derive_hardened_child(i) : derive_normal_child(i); @@ -347,11 +344,6 @@ namespace fc { namespace ecc { return from_base58( _to_base58( data ) ); } - private_key extended_private_key::generate_a(int i) const { return derive_hardened_child(4*i + 0); } - private_key extended_private_key::generate_b(int i) const { return derive_hardened_child(4*i + 1); } - private_key extended_private_key::generate_c(int i) const { return derive_hardened_child(4*i + 2); } - private_key extended_private_key::generate_d(int i) const { return derive_hardened_child(4*i + 3); } - fc::string extended_private_key::str() const { return _to_base58( serialize_extended() ); diff --git a/src/crypto/elliptic_secp256k1.cpp b/src/crypto/elliptic_secp256k1.cpp index 4c7dcfe..b80ace3 100644 --- a/src/crypto/elliptic_secp256k1.cpp +++ b/src/crypto/elliptic_secp256k1.cpp @@ -186,164 +186,6 @@ namespace fc { namespace ecc { return result; } - static void to_bignum( const unsigned char* in, ssl_bignum& out, unsigned int len ) - { - if ( *in & 0x80 ) - { - unsigned char *buffer = (unsigned char*)alloca(len + 1); - *buffer = 0; - memcpy( buffer + 1, in, len ); - BN_bin2bn( buffer, len + 1, out ); - } - else - { - BN_bin2bn( in, len, out ); - } - } - - static void to_bignum( const private_key_secret& in, ssl_bignum& out ) - { - to_bignum( (unsigned char*) in.data(), out, in.data_size() ); - } - - static void from_bignum( const ssl_bignum& in, unsigned char* out, unsigned int len ) - { - unsigned int l = BN_num_bytes( in ); - if ( l > len ) - { - unsigned char *buffer = (unsigned char*)alloca(l); - BN_bn2bin( in, buffer ); - memcpy( out, buffer + l - len, len ); - } - else - { - memset( out, 0, len - l ); - BN_bn2bin( in, out + len - l ); - } - } - - static void from_bignum( const ssl_bignum& in, private_key_secret& out ) - { - from_bignum( in, (unsigned char*) out.data(), out.data_size() ); - } - - static void invert( const private_key_secret& in, private_key_secret& out ) - { - ssl_bignum bn_in; - to_bignum( in, bn_in ); - ssl_bignum bn_n; - to_bignum( detail::get_curve_order(), bn_n ); - ssl_bignum bn_inv; - bn_ctx ctx( BN_CTX_new() ); - FC_ASSERT( BN_mod_inverse( bn_inv, bn_in, bn_n, ctx ) ); - from_bignum( bn_inv, out ); - } - - static void to_point( const public_key_data& in, ec_point& out ) - { - bn_ctx ctx( BN_CTX_new() ); - const ec_group& curve = detail::get_curve(); - private_key_secret x; - memcpy( x.data(), in.begin() + 1, x.data_size() ); - ssl_bignum bn_x; - to_bignum( x, bn_x ); - FC_ASSERT( EC_POINT_set_compressed_coordinates_GFp( curve, out, bn_x, *in.begin() & 1, ctx ) > 0 ); - } - - static void from_point( const ec_point& in, public_key_data& out ) - { - bn_ctx ctx( BN_CTX_new() ); - const ec_group& curve = detail::get_curve(); - ssl_bignum bn_x; - ssl_bignum bn_y; - FC_ASSERT( EC_POINT_get_affine_coordinates_GFp( curve, in, bn_x, bn_y, ctx ) > 0 ); - private_key_secret x; - from_bignum( bn_x, x ); - memcpy( out.begin() + 1, x.data(), out.size() - 1 ); - *out.begin() = BN_is_bit_set( bn_y, 0 ) ? 3 : 2; - } - -// static void print(const unsigned char* data) { -// for (int i = 0; i < 32; i++) { -// printf("%02x", *data++); -// } -// } -// -// static void print(private_key_secret key) { -// print((unsigned char*) key.data()); -// } -// -// static void print(public_key_data key) { -// print((unsigned char*) key.begin() + 1); -// } - - static void canonicalize( unsigned char *int256 ) - { - fc::sha256 biggi( (char*) int256, 32 ); - if ( detail::get_half_curve_order() >= biggi ) - { - return; // nothing to do - } - ssl_bignum bn_k; - to_bignum( int256, bn_k, 32 ); - ssl_bignum bn_n; - to_bignum( detail::get_curve_order(), bn_n ); - FC_ASSERT( BN_sub( bn_k, bn_n, bn_k ) ); - from_bignum( bn_k, int256, 32 ); - } - - static public_key compute_k( const private_key_secret& a, const private_key_secret& c, - const public_key& p ) - { - private_key_secret prod = a; - FC_ASSERT( secp256k1_ec_privkey_tweak_mul( detail::_get_context(), (unsigned char*) prod.data(), (unsigned char*) c.data() ) > 0 ); - invert( prod, prod ); - public_key_data P = p.serialize(); - FC_ASSERT( secp256k1_ec_pubkey_tweak_mul( detail::_get_context(), (unsigned char*) P.begin(), P.size(), (unsigned char*) prod.data() ) ); -// printf("K: "); print(P); printf("\n"); - return public_key( P ); - } - - static public_key compute_t( const private_key_secret& a, const private_key_secret& b, - const private_key_secret& c, const private_key_secret& d, - const public_key_data& p, const public_key_data& q ) - { - private_key_secret prod; - invert( c, prod ); // prod == c^-1 - FC_ASSERT( secp256k1_ec_privkey_tweak_mul( detail::_get_context(), (unsigned char*) prod.data(), (unsigned char*) d.data() ) > 0 ); - // prod == c^-1 * d - - public_key_data accu = p; - FC_ASSERT( secp256k1_ec_pubkey_tweak_mul( detail::_get_context(), (unsigned char*) accu.begin(), accu.size(), (unsigned char*) prod.data() ) ); - // accu == prod * P == c^-1 * d * P - - ec_point point_accu( EC_POINT_new( detail::get_curve() ) ); - to_point( accu, point_accu ); - ec_point point_q( EC_POINT_new( detail::get_curve() ) ); - to_point( q, point_q ); - bn_ctx ctx(BN_CTX_new()); - FC_ASSERT( EC_POINT_add( detail::get_curve(), point_accu, point_accu, point_q, ctx ) > 0 ); - from_point( point_accu, accu ); - // accu == c^-1 * a * P + Q - - FC_ASSERT( secp256k1_ec_pubkey_tweak_add( detail::_get_context(), (unsigned char*) accu.begin(), accu.size(), (unsigned char*) b.data() ) ); - // accu == c^-1 * a * P + Q + b*G - - public_key_data k = compute_k( a, c, p ).serialize(); - memcpy( prod.data(), k.begin() + 1, prod.data_size() ); - // prod == Kx - FC_ASSERT( secp256k1_ec_privkey_tweak_mul( detail::_get_context(), (unsigned char*) prod.data(), (unsigned char*) a.data() ) > 0 ); - // prod == Kx * a - invert( prod, prod ); - // prod == (Kx * a)^-1 - - FC_ASSERT( secp256k1_ec_pubkey_tweak_mul( detail::_get_context(), (unsigned char*) accu.begin(), accu.size(), (unsigned char*) prod.data() ) ); - // accu == (c^-1 * a * P + Q + b*G) * (Kx * a)^-1 - -// printf("T: "); print(accu); printf("\n"); - return public_key( accu ); - } - extended_private_key::extended_private_key( const private_key& k, const sha256& c, int child, int parent, uint8_t depth ) : private_key(k), c(c), child_num(child), parent_fp(parent), depth(depth) { } @@ -359,102 +201,6 @@ namespace fc { namespace ecc { return result; } - public_key extended_private_key::blind_public_key( const extended_public_key& bob, int i ) const - { - private_key_secret a = generate_a(i).get_secret(); - private_key_secret b = generate_b(i).get_secret(); - private_key_secret c = generate_c(i).get_secret(); - private_key_secret d = generate_d(i).get_secret(); - public_key_data p = bob.generate_p(i).serialize(); - public_key_data q = bob.generate_q(i).serialize(); -// printf("a: "); print(a); printf("\n"); -// printf("b: "); print(b); printf("\n"); -// printf("c: "); print(c); printf("\n"); -// printf("d: "); print(d); printf("\n"); -// printf("P: "); print(p); printf("\n"); -// printf("Q: "); print(q); printf("\n"); - return compute_t( a, b, c, d, p, q ); - } - - blinded_hash extended_private_key::blind_hash( const fc::sha256& hash, int i ) const - { - private_key_secret a = generate_a(i).get_secret(); - private_key_secret b = generate_b(i).get_secret(); - FC_ASSERT( secp256k1_ec_privkey_tweak_mul( detail::_get_context(), (unsigned char*) a.data(), (unsigned char*) hash.data() ) > 0 ); - FC_ASSERT( secp256k1_ec_privkey_tweak_add( detail::_get_context(), (unsigned char*) a.data(), (unsigned char*) b.data() ) > 0 ); -// printf("hash: "); print(hash); printf("\n"); -// printf("blinded: "); print(a); printf("\n"); - return a; - } - - private_key_secret extended_private_key::compute_p( int i ) const - { - private_key_secret p_inv = derive_normal_child( 2*i ).get_secret(); - invert( p_inv, p_inv ); -// printf("p: "); print(p_inv); printf("\n"); - return p_inv; - } - - private_key_secret extended_private_key::compute_q( int i, const private_key_secret& p ) const - { - private_key_secret q = derive_normal_child( 2*i + 1 ).get_secret(); - FC_ASSERT( secp256k1_ec_privkey_tweak_mul( detail::_get_context(), (unsigned char*) q.data(), (unsigned char*) p.data() ) > 0 ); -// printf("q: "); print(q); printf("\n"); - return q; - } - - blind_signature extended_private_key::blind_sign( const blinded_hash& hash, int i ) const - { - private_key_secret p = compute_p( i ); - private_key_secret q = compute_q( i, p ); - FC_ASSERT( secp256k1_ec_privkey_tweak_mul( detail::_get_context(), (unsigned char*) p.data(), (unsigned char*) hash.data() ) > 0 ); - FC_ASSERT( secp256k1_ec_privkey_tweak_add( detail::_get_context(), (unsigned char*) p.data(), (unsigned char*) q.data() ) > 0 ); -// printf("blind_sig: "); print(p); printf("\n"); - return p; - } - - compact_signature extended_private_key::unblind_signature( const extended_public_key& bob, - const blind_signature& sig, - const fc::sha256& hash, - int i ) const - { - private_key_secret a = generate_a(i).get_secret(); - private_key_secret b = generate_b(i).get_secret(); - private_key_secret c = generate_c(i).get_secret(); - private_key_secret d = generate_d(i).get_secret(); - public_key p = bob.generate_p(i); - public_key q = bob.generate_q(i); - public_key_data k = compute_k( a, c, p ); - public_key_data t = compute_t( a, b, c, d, p, q ).serialize(); - - FC_ASSERT( secp256k1_ec_privkey_tweak_mul( detail::_get_context(), (unsigned char*) c.data(), (unsigned char*) sig.data() ) > 0 ); - FC_ASSERT( secp256k1_ec_privkey_tweak_add( detail::_get_context(), (unsigned char*) c.data(), (unsigned char*) d.data() ) > 0 ); - - compact_signature result; - memcpy( result.begin() + 1, k.begin() + 1, 32 ); - memcpy( result.begin() + 33, c.data(), 32 ); - canonicalize( result.begin() + 33 ); -// printf("unblinded: "); print(result.begin() + 33); printf("\n"); - for ( int i = 0; i < 4; i++ ) - { - unsigned char pubkey[33]; - int pklen = 33; - if ( secp256k1_ecdsa_recover_compact( detail::_get_context(), (unsigned char*) hash.data(), - (unsigned char*) result.begin() + 1, - pubkey, &pklen, 1, i ) ) - { - if ( !memcmp( t.begin(), pubkey, sizeof(pubkey) ) ) - { - *result.begin() = 27 + 4 + i; - return result; -// } else { -// printf("Candidate: "); print( pubkey ); printf("\n"); - } - } - } - FC_ASSERT( 0, "Failed to unblind - use different i" ); - } - commitment_type blind( const blind_factor_type& blind, uint64_t value ) { commitment_type result; diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt index b1d5821..4bec890 100644 --- a/tests/CMakeLists.txt +++ b/tests/CMakeLists.txt @@ -23,9 +23,6 @@ target_link_libraries( real128_test fc ) add_executable( hmac_test hmac_test.cpp ) target_link_libraries( hmac_test fc ) -add_executable( blinding_test blinding_test.cpp ) -target_link_libraries( blinding_test fc ) - add_executable( ecc_test crypto/ecc_test.cpp ) target_link_libraries( ecc_test fc ) diff --git a/tests/blinding_test.cpp b/tests/blinding_test.cpp deleted file mode 100644 index 7f30c74..0000000 --- a/tests/blinding_test.cpp +++ /dev/null @@ -1,287 +0,0 @@ -#define BOOST_TEST_MODULE BlindingTest -#include -#include -#include -#include -#include -#include -#include - -// See https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki#Test_Vectors - -static fc::string TEST1_SEED = "000102030405060708090a0b0c0d0e0f"; -static fc::string TEST1_M_PUB = "xpub661MyMwAqRbcFtXgS5sYJABqqG9YLmC4Q1Rdap9gSE8NqtwybGhePY2gZ29ESFjqJoCu1Rupje8YtGqsefD265TMg7usUDFdp6W1EGMcet8"; -static fc::string TEST1_M_PRIV = "xprv9s21ZrQH143K3QTDL4LXw2F7HEK3wJUD2nW2nRk4stbPy6cq3jPPqjiChkVvvNKmPGJxWUtg6LnF5kejMRNNU3TGtRBeJgk33yuGBxrMPHi"; -static fc::string TEST1_M_0H_PUB = "xpub68Gmy5EdvgibQVfPdqkBBCHxA5htiqg55crXYuXoQRKfDBFA1WEjWgP6LHhwBZeNK1VTsfTFUHCdrfp1bgwQ9xv5ski8PX9rL2dZXvgGDnw"; -static fc::string TEST1_M_0H_PRIV = "xprv9uHRZZhk6KAJC1avXpDAp4MDc3sQKNxDiPvvkX8Br5ngLNv1TxvUxt4cV1rGL5hj6KCesnDYUhd7oWgT11eZG7XnxHrnYeSvkzY7d2bhkJ7"; -static fc::string TEST1_M_0H_1_PUB = "xpub6ASuArnXKPbfEwhqN6e3mwBcDTgzisQN1wXN9BJcM47sSikHjJf3UFHKkNAWbWMiGj7Wf5uMash7SyYq527Hqck2AxYysAA7xmALppuCkwQ"; -static fc::string TEST1_M_0H_1_PRIV = "xprv9wTYmMFdV23N2TdNG573QoEsfRrWKQgWeibmLntzniatZvR9BmLnvSxqu53Kw1UmYPxLgboyZQaXwTCg8MSY3H2EU4pWcQDnRnrVA1xe8fs"; -static fc::string TEST1_M_0H_1_2H_PUB = "xpub6D4BDPcP2GT577Vvch3R8wDkScZWzQzMMUm3PWbmWvVJrZwQY4VUNgqFJPMM3No2dFDFGTsxxpG5uJh7n7epu4trkrX7x7DogT5Uv6fcLW5"; -static fc::string TEST1_M_0H_1_2H_PRIV = "xprv9z4pot5VBttmtdRTWfWQmoH1taj2axGVzFqSb8C9xaxKymcFzXBDptWmT7FwuEzG3ryjH4ktypQSAewRiNMjANTtpgP4mLTj34bhnZX7UiM"; -static fc::string TEST1_M_0H_1_2H_2_PUB = "xpub6FHa3pjLCk84BayeJxFW2SP4XRrFd1JYnxeLeU8EqN3vDfZmbqBqaGJAyiLjTAwm6ZLRQUMv1ZACTj37sR62cfN7fe5JnJ7dh8zL4fiyLHV"; -static fc::string TEST1_M_0H_1_2H_2_PRIV = "xprvA2JDeKCSNNZky6uBCviVfJSKyQ1mDYahRjijr5idH2WwLsEd4Hsb2Tyh8RfQMuPh7f7RtyzTtdrbdqqsunu5Mm3wDvUAKRHSC34sJ7in334"; -static fc::string TEST1_M_0H_1_2H_2_1g_PUB = "xpub6H1LXWLaKsWFhvm6RVpEL9P4KfRZSW7abD2ttkWP3SSQvnyA8FSVqNTEcYFgJS2UaFcxupHiYkro49S8yGasTvXEYBVPamhGW6cFJodrTHy"; -static fc::string TEST1_M_0H_1_2H_2_1g_PRIV = "xprvA41z7zogVVwxVSgdKUHDy1SKmdb533PjDz7J6N6mV6uS3ze1ai8FHa8kmHScGpWmj4WggLyQjgPie1rFSruoUihUZREPSL39UNdE3BBDu76"; - -static fc::string TEST2_SEED = "fffcf9f6f3f0edeae7e4e1dedbd8d5d2cfccc9c6c3c0bdbab7b4b1aeaba8a5a29f9c999693908d8a8784817e7b7875726f6c696663605d5a5754514e4b484542"; -static fc::string TEST2_M_PUB = "xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB"; -static fc::string TEST2_M_PRIV = "xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U"; -static fc::string TEST2_M_0_PUB = "xpub69H7F5d8KSRgmmdJg2KhpAK8SR3DjMwAdkxj3ZuxV27CprR9LgpeyGmXUbC6wb7ERfvrnKZjXoUmmDznezpbZb7ap6r1D3tgFxHmwMkQTPH"; -static fc::string TEST2_M_0_PRIV = "xprv9vHkqa6EV4sPZHYqZznhT2NPtPCjKuDKGY38FBWLvgaDx45zo9WQRUT3dKYnjwih2yJD9mkrocEZXo1ex8G81dwSM1fwqWpWkeS3v86pgKt"; -static fc::string TEST2_M_0_m1_PUB = "xpub6ASAVgeehLbnwdqV6UKMHVzgqAG8Gr6riv3Fxxpj8ksbH9ebxaEyBLZ85ySDhKiLDBrQSARLq1uNRts8RuJiHjaDMBU4Zn9h8LZNnBC5y4a"; -static fc::string TEST2_M_0_m1_PRIV = "xprv9wSp6B7kry3Vj9m1zSnLvN3xH8RdsPP1Mh7fAaR7aRLcQMKTR2vidYEeEg2mUCTAwCd6vnxVrcjfy2kRgVsFawNzmjuHc2YmYRmagcEPdU9"; -static fc::string TEST2_M_0_m1_1_PUB = "xpub6DF8uhdarytz3FWdA8TvFSvvAh8dP3283MY7p2V4SeE2wyWmG5mg5EwVvmdMVCQcoNJxGoWaU9DCWh89LojfZ537wTfunKau47EL2dhHKon"; -static fc::string TEST2_M_0_m1_1_PRIV = "xprv9zFnWC6h2cLgpmSA46vutJzBcfJ8yaJGg8cX1e5StJh45BBciYTRXSd25UEPVuesF9yog62tGAQtHjXajPPdbRCHuWS6T8XA2ECKADdw4Ef"; -static fc::string TEST2_M_0_m1_1_m2_PUB = "xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL"; -static fc::string TEST2_M_0_m1_1_m2_PRIV = "xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc"; -static fc::string TEST2_M_0_m1_1_m2_2_PUB = "xpub6FnCn6nSzZAw5Tw7cgR9bi15UV96gLZhjDstkXXxvCLsUXBGXPdSnLFbdpq8p9HmGsApME5hQTZ3emM2rnY5agb9rXpVGyy3bdW6EEgAtqt"; -static fc::string TEST2_M_0_m1_1_m2_2_PRIV = "xprvA2nrNbFZABcdryreWet9Ea4LvTJcGsqrMzxHx98MMrotbir7yrKCEXw7nadnHM8Dq38EGfSh6dqA9QWTyefMLEcBYJUuekgW4BYPJcr9E7j"; - -static fc::string BLIND_K_X = "08be5c5076f8cbd1283cf98e74bff873032b9bc79a0769962bf3900f33c2df6e"; -static fc::string BLIND_T_X = "80deff382af8a8e4a5f297588e44d5bf858f30a524f74b13efcefeb54f4b3f47"; -static fc::string BLINDED_HASH = "7196e80cdafdfdfb7496323ad24bf47dda8447febd7426e444facc04940c7309"; -static fc::string BLIND_SIG = "40d6a477d849cc860df8ad159481f2ffc5b4dc3131b86a799d7d10460824dd53"; -static fc::string UNBLINDED = "700092a72a05e33509f9b068aa1d7c5336d8b5692b4157da199d7ec1e10fd7c0"; - -BOOST_AUTO_TEST_CASE(test_extended_keys_1) -{ - char seed[16]; - fc::from_hex( TEST1_SEED, seed, sizeof(seed) ); - fc::ecc::extended_private_key master = fc::ecc::extended_private_key::generate_master( seed, sizeof(seed) ); - BOOST_CHECK_EQUAL( master.str(), TEST1_M_PRIV ); - BOOST_CHECK_EQUAL( master.get_extended_public_key().str(), TEST1_M_PUB ); - - BOOST_CHECK_EQUAL( fc::ecc::extended_private_key::from_base58(TEST1_M_PRIV).str(), TEST1_M_PRIV ); - BOOST_CHECK_EQUAL( fc::ecc::extended_public_key::from_base58(TEST1_M_PUB).str(), TEST1_M_PUB ); - BOOST_CHECK_EQUAL( fc::ecc::extended_private_key::from_base58(TEST1_M_0H_PRIV).str(), TEST1_M_0H_PRIV ); - BOOST_CHECK_EQUAL( fc::ecc::extended_public_key::from_base58(TEST1_M_0H_PUB).str(), TEST1_M_0H_PUB ); - - fc::ecc::extended_private_key m_0 = master.derive_child(0x80000000); - BOOST_CHECK_EQUAL( m_0.str(), TEST1_M_0H_PRIV ); - BOOST_CHECK_EQUAL( m_0.get_extended_public_key().str(), TEST1_M_0H_PUB ); - - fc::ecc::extended_private_key m_0_1 = m_0.derive_child(1); - BOOST_CHECK_EQUAL( m_0_1.str(), TEST1_M_0H_1_PRIV ); - BOOST_CHECK_EQUAL( m_0_1.get_extended_public_key().str(), TEST1_M_0H_1_PUB ); - BOOST_CHECK_EQUAL( m_0.get_extended_public_key().derive_child(1).str(), TEST1_M_0H_1_PUB ); - - fc::ecc::extended_private_key m_0_1_2 = m_0_1.derive_child(0x80000002); - BOOST_CHECK_EQUAL( m_0_1_2.str(), TEST1_M_0H_1_2H_PRIV ); - BOOST_CHECK_EQUAL( m_0_1_2.get_extended_public_key().str(), TEST1_M_0H_1_2H_PUB ); - - fc::ecc::extended_private_key m_0_1_2_2 = m_0_1_2.derive_child(2); - BOOST_CHECK_EQUAL( m_0_1_2_2.str(), TEST1_M_0H_1_2H_2_PRIV ); - BOOST_CHECK_EQUAL( m_0_1_2_2.get_extended_public_key().str(), TEST1_M_0H_1_2H_2_PUB ); - BOOST_CHECK_EQUAL( m_0_1_2.get_extended_public_key().derive_child(2).str(), TEST1_M_0H_1_2H_2_PUB ); - - fc::ecc::extended_private_key m_0_1_2_2_1g = m_0_1_2_2.derive_child(1000000000); - BOOST_CHECK_EQUAL( m_0_1_2_2_1g.str(), TEST1_M_0H_1_2H_2_1g_PRIV ); - BOOST_CHECK_EQUAL( m_0_1_2_2_1g.get_extended_public_key().str(), TEST1_M_0H_1_2H_2_1g_PUB ); - BOOST_CHECK_EQUAL( m_0_1_2_2.get_extended_public_key().derive_child(1000000000).str(), TEST1_M_0H_1_2H_2_1g_PUB ); -} - -BOOST_AUTO_TEST_CASE(test_extended_keys_2) -{ - char seed[64]; - fc::from_hex( TEST2_SEED, seed, sizeof(seed) ); - fc::ecc::extended_private_key master = fc::ecc::extended_private_key::generate_master( seed, sizeof(seed) ); - BOOST_CHECK_EQUAL( master.str(), TEST2_M_PRIV ); - BOOST_CHECK_EQUAL( master.get_extended_public_key().str(), TEST2_M_PUB ); - - fc::ecc::extended_private_key m_0 = master.derive_child(0); - BOOST_CHECK_EQUAL( m_0.str(), TEST2_M_0_PRIV ); - BOOST_CHECK_EQUAL( m_0.get_extended_public_key().str(), TEST2_M_0_PUB ); - BOOST_CHECK_EQUAL( master.get_extended_public_key().derive_child(0).str(), TEST2_M_0_PUB ); - - fc::ecc::extended_private_key m_0_m1 = m_0.derive_child(-1); - BOOST_CHECK_EQUAL( m_0_m1.str(), TEST2_M_0_m1_PRIV ); - BOOST_CHECK_EQUAL( m_0_m1.get_extended_public_key().str(), TEST2_M_0_m1_PUB ); - - fc::ecc::extended_private_key m_0_m1_1 = m_0_m1.derive_child(1); - BOOST_CHECK_EQUAL( m_0_m1_1.str(), TEST2_M_0_m1_1_PRIV ); - BOOST_CHECK_EQUAL( m_0_m1_1.get_extended_public_key().str(), TEST2_M_0_m1_1_PUB ); - BOOST_CHECK_EQUAL( m_0_m1.get_extended_public_key().derive_child(1).str(), TEST2_M_0_m1_1_PUB ); - - fc::ecc::extended_private_key m_0_m1_1_m2 = m_0_m1_1.derive_child(-2); - BOOST_CHECK_EQUAL( m_0_m1_1_m2.str(), TEST2_M_0_m1_1_m2_PRIV ); - BOOST_CHECK_EQUAL( m_0_m1_1_m2.get_extended_public_key().str(), TEST2_M_0_m1_1_m2_PUB ); - - fc::ecc::extended_private_key m_0_m1_1_m2_2 = m_0_m1_1_m2.derive_child(2); - BOOST_CHECK_EQUAL( m_0_m1_1_m2_2.str(), TEST2_M_0_m1_1_m2_2_PRIV ); - BOOST_CHECK_EQUAL( m_0_m1_1_m2_2.get_extended_public_key().str(), TEST2_M_0_m1_1_m2_2_PUB ); - BOOST_CHECK_EQUAL( m_0_m1_1_m2.get_extended_public_key().derive_child(2).str(), TEST2_M_0_m1_1_m2_2_PUB ); -} - -//static void print(const unsigned char* data, int len) { -// for (int i = 0; i < len; i++) { -// printf("%02x", *data++); -// } -//} - -BOOST_AUTO_TEST_CASE(test_blinding_1) -{ try { - char buffer[7] = "test_"; - fc::ecc::extended_private_key alice = fc::ecc::extended_private_key::generate_master( "master" ); - fc::ecc::extended_private_key bob = fc::ecc::extended_private_key::generate_master( "puppet" ); - - for ( int i = 0; i < 30; i++ ) - { - buffer[5] = '0' + i; - fc::ecc::extended_public_key bob_pub = bob.get_extended_public_key(); - fc::sha256 hash = fc::sha256::hash( buffer, sizeof(buffer) ); - fc::ecc::public_key t = alice.blind_public_key( bob_pub, i ); - fc::ecc::blinded_hash blinded = alice.blind_hash( hash, i ); - fc::ecc::blind_signature blind_sig = bob.blind_sign( blinded, i ); - try { - fc::ecc::compact_signature sig = alice.unblind_signature( bob_pub, blind_sig, hash, i ); - fc::ecc::public_key validate( sig, hash ); - BOOST_CHECK( validate.serialize() == t.serialize() ); - } catch (const fc::exception& e) { - printf( "Test %d: %s\n", i, e.to_string().c_str() ); - } - alice = alice.derive_child( i ); - bob = bob.derive_child( i | 0x80000000 ); - } -} FC_LOG_AND_RETHROW() } - -BOOST_AUTO_TEST_CASE(test_blinding_2) -{ try { - char message[7] = "test_0"; - fc::ecc::extended_private_key alice = fc::ecc::extended_private_key::generate_master( "master" ); - fc::ecc::extended_private_key bob = fc::ecc::extended_private_key::generate_master( "puppet" ); - fc::ecc::extended_public_key bob_pub = bob.get_extended_public_key(); - fc::sha256 hash = fc::sha256::hash( message, sizeof(message) ); - - fc::ecc::public_key t = alice.blind_public_key( bob_pub, 0 ); - fc::ecc::public_key_data pub = t.serialize(); - char buffer[32]; - fc::from_hex( BLIND_T_X, buffer, sizeof(buffer) ); - BOOST_CHECK( !memcmp( pub.begin() + 1, buffer, sizeof(buffer) ) ); - - fc::ecc::blinded_hash blinded = alice.blind_hash( hash, 0 ); - fc::from_hex( BLINDED_HASH, buffer, sizeof(buffer) ); - BOOST_CHECK( !memcmp( blinded.data(), buffer, sizeof(buffer) ) ); - - fc::ecc::blind_signature blind_sig = bob.blind_sign( blinded, 0 ); - fc::from_hex( BLIND_SIG, buffer, sizeof(buffer) ); - BOOST_CHECK( !memcmp( blind_sig.data(), buffer, sizeof(buffer) ) ); - - fc::ecc::compact_signature sig = alice.unblind_signature( bob_pub, blind_sig, hash, 0 ); - fc::from_hex( BLIND_K_X, buffer, sizeof(buffer) ); - BOOST_CHECK( !memcmp( sig.begin() + 1, buffer, sizeof(buffer) ) ); - fc::from_hex( UNBLINDED, buffer, sizeof(buffer) ); - BOOST_CHECK( !memcmp( sig.begin() + 33, buffer, sizeof(buffer) ) ); -} FC_LOG_AND_RETHROW() } - -static void to_bignum(const char* data32, fc::ssl_bignum& out) { - unsigned char dummy[33]; dummy[0] = 0; - memcpy(dummy, data32, 32); - BN_bin2bn((unsigned char*) data32, 32, out); -} - -namespace fc { -SSL_TYPE(ec_key, EC_KEY, EC_KEY_free) -} - -BOOST_AUTO_TEST_CASE(openssl_blinding) -{ - // Needed this "test" for producing data for debugging my libsecp256k1 implementation - - char buffer[7] = "test_0"; - fc::ecc::extended_private_key alice = fc::ecc::extended_private_key::generate_master( "master" ); - fc::ecc::extended_private_key bob = fc::ecc::extended_private_key::generate_master( "puppet" ); - fc::ec_group curve(EC_GROUP_new_by_curve_name(NID_secp256k1)); - fc::bn_ctx ctx(BN_CTX_new()); - fc::ssl_bignum n; - EC_GROUP_get_order(curve, n, ctx); - fc::ssl_bignum n_half; - BN_rshift1(n_half, n); - fc::ssl_bignum zero; BN_zero(zero); - - fc::sha256 hash_ = fc::sha256::hash( buffer, sizeof(buffer) ); - fc::ssl_bignum hash; to_bignum(hash_.data(), hash); - fc::ssl_bignum a; to_bignum(alice.derive_hardened_child(0).get_secret().data(), a); - fc::ssl_bignum b; to_bignum(alice.derive_hardened_child(1).get_secret().data(), b); - fc::ssl_bignum c; to_bignum(alice.derive_hardened_child(2).get_secret().data(), c); - fc::ssl_bignum d; to_bignum(alice.derive_hardened_child(3).get_secret().data(), d); - - fc::ec_point P(EC_POINT_new(curve)); - fc::ecc::public_key_data Pd = bob.get_extended_public_key().derive_child(0).serialize(); - fc::ssl_bignum Px; to_bignum(Pd.begin() + 1, Px); - EC_POINT_set_compressed_coordinates_GFp(curve, P, Px, (*Pd.begin()) & 1, ctx); - - fc::ec_point Q(EC_POINT_new(curve)); - fc::ecc::public_key_data Qd = bob.get_extended_public_key().derive_child(1).serialize(); - fc::ssl_bignum Qx; to_bignum(Qd.begin() + 1, Qx); - EC_POINT_set_compressed_coordinates_GFp(curve, Q, Qx, (*Qd.begin()) & 1, ctx); - - // Alice computes K = (c·a)^-1·P and public key T = (a·Kx)^-1·(b·G + Q + d·c^-1·P). - fc::ec_point K(EC_POINT_new(curve)); - fc::ssl_bignum tmp; - BN_mod_mul(tmp, a, c, n, ctx); - BN_mod_inverse(tmp, tmp, n, ctx); - EC_POINT_mul(curve, K, zero, P, tmp, ctx); - - fc::ec_point T(EC_POINT_new(curve)); - BN_mod_inverse(tmp, c, n, ctx); - BN_mod_mul(tmp, d, tmp, n, ctx); - EC_POINT_mul(curve, T, b, P, tmp, ctx); - EC_POINT_add(curve, T, T, Q, ctx); - fc::ssl_bignum Kx; - fc::ssl_bignum Ky; - EC_POINT_get_affine_coordinates_GFp(curve, K, Kx, Ky, ctx); - BN_mod_mul(tmp, a, Kx, n, ctx); - BN_mod_inverse(tmp, tmp, n, ctx); - EC_POINT_mul(curve, T, zero, T, tmp, ctx); - - fc::ssl_bignum blinded; - BN_mod_mul(blinded, a, hash, n, ctx); - BN_mod_add(blinded, blinded, b, n, ctx); - - fc::ssl_bignum p; to_bignum(bob.derive_normal_child(0).get_secret().data(), p); - fc::ssl_bignum q; to_bignum(bob.derive_normal_child(1).get_secret().data(), q); - BN_mod_inverse(p, p, n, ctx); - BN_mod_mul(q, q, p, n, ctx); - fc::ssl_bignum blind_sig; - BN_mod_mul(blind_sig, p, blinded, n, ctx); - BN_mod_add(blind_sig, blind_sig, q, n, ctx); - - fc::ssl_bignum sig_r; - fc::ssl_bignum sig_s; - BN_copy(sig_r, Kx); - BN_mod_mul(sig_s, c, blind_sig, n, ctx); - BN_mod_add(sig_s, sig_s, d, n, ctx); - - if (BN_cmp(sig_s, n_half) > 0) { - BN_sub(sig_s, n, sig_s); - } - - fc::ecdsa_sig sig(ECDSA_SIG_new()); -#if OPENSSL_VERSION_NUMBER >= 0x10100000L - ECDSA_SIG_set0(sig, sig_r, sig_s); -#else - sig->r = sig_r; - sig->s = sig_s; -#endif - sig_r.obj = nullptr; - sig_s.obj = nullptr; - - fc::ec_key verify(EC_KEY_new()); - EC_KEY_set_public_key(verify, T); - BOOST_CHECK( ECDSA_do_verify( (unsigned char*) hash_.data(), hash_.data_size(), sig, verify ) ); -// printf("a: "); print(a); -// printf("\nb: "); print(b); -// printf("\nc: "); print(c); -// printf("\nd: "); print(d); -// printf("\nP: "); print(curve, P, ctx); -// printf("\nQ: "); print(curve, Q, ctx); -// printf("\nK: "); print(curve, K, ctx); -// printf("\nT: "); print(curve, T, ctx); -// printf("\np: "); print(p); -// printf("\nq: "); print(q); -// printf("\nhash: "); print(hash_); -// printf("\nblinded: "); print(blinded); -// printf("\nblind_sig: "); print(blind_sig); -// printf("\nunblinded: "); print(sig->s); -// printf("\n"); -}