diff --git a/CMakeLists.txt b/CMakeLists.txt index ae6ce0555fcc..dcdf6942dcae 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -85,12 +85,7 @@ endif() find_package(LibEvent REQUIRED) -find_package(GMP) -if(GMP_FOUND) -else() - message(WARNING "GMP not found, falling back to OpenSSL for bignum!") - set(BIGNUM_CONFIGURE_FLAGS "--with-zerocoin-bignum=openssl") -endif() +find_package(GMP REQUIRED) find_package(ZMQ) find_package(Miniupnp) @@ -363,11 +358,6 @@ set(ZEROCOIN_SOURCES ./src/libzerocoin/ParamGeneration.cpp ./src/libzerocoin/Params.cpp ) -if(GMP_FOUND) - list(APPEND ZEROCOIN_SOURCES ./src/libzerocoin/bignum_gmp.cpp) -else() - list(APPEND ZEROCOIN_SOURCES ./src/libzerocoin/bignum_openssl.cpp) -endif() add_library(ZEROCOIN_A STATIC ${ZEROCOIN_SOURCES}) target_include_directories(ZEROCOIN_A PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/src ${OPENSSL_INCLUDE_DIR} @@ -529,14 +519,11 @@ target_link_libraries(pivx-tx secp256k1 SAPLING_A rustzcash - ${Boost_LIBRARIES} ${OPENSSL_CRYPTO_LIBRARY} ${LIBEVENT_LIB} ${sodium_LIBRARY_RELEASE} -ldl pthread + ${Boost_LIBRARIES} ${OPENSSL_CRYPTO_LIBRARY} ${LIBEVENT_LIB} ${sodium_LIBRARY_RELEASE} ${GMP_LIBRARY} -ldl pthread ) if($ENV{target} MATCHES "Windows") target_link_libraries(pivx-tx ${WINDOWS_LDADD}) endif() -if(GMP_FOUND) - target_link_libraries(pivx-tx ${GMP_LIBRARY}) -endif() if(${CMAKE_SYSTEM_NAME} MATCHES "Darwin") target_link_libraries(pivx-tx "-framework Cocoa") endif() @@ -551,7 +538,8 @@ target_include_directories(pivxd PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/src ${CMAKE_CURRENT_SOURCE_DIR}/src/leveldb ${CMAKE_CURRENT_SOURCE_DIR}/src/leveldb/include ${CMAKE_CURRENT_SOURCE_DIR}/src/leveldb/helpers/memenv - ${LIBEVENT_INCLUDE_DIR}) + ${LIBEVENT_INCLUDE_DIR} + ${GMP_INCLUDE_DIR}) target_link_libraries(pivxd pthread SERVER_A @@ -566,16 +554,12 @@ target_link_libraries(pivxd crc32c secp256k1 rustzcash - ${BerkeleyDB_LIBRARIES} ${OPENSSL_CRYPTO_LIBRARY} ${Boost_LIBRARIES} ${LIBEVENT_LIB} pthread + ${BerkeleyDB_LIBRARIES} ${OPENSSL_CRYPTO_LIBRARY} ${Boost_LIBRARIES} ${LIBEVENT_LIB} ${GMP_LIBRARY} pthread ) if($ENV{target} MATCHES "Windows") set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -Wstack-protector -fstack-protector-all -fPIE -pipe -O2 -pthread -Wl,--dynamicbase -Wl,--nxcompat -Wl,--high-entropy-va -pie --static") target_link_libraries(pivxd ${WINDOWS_LDADD}) endif() -if(GMP_FOUND) - target_link_libraries(pivxd ${GMP_LIBRARY}) - target_include_directories(pivxd PUBLIC ${GMP_INCLUDE_DIR}) -endif() if(ZMQ_FOUND) target_link_libraries(pivxd ZMQ_A ${ZMQ_LIB}) target_include_directories(pivxd PUBLIC ${ZMQ_INCLUDE_DIR}) diff --git a/build-aux/m4/gmp.m4 b/build-aux/m4/gmp.m4 index 60fa06b44e72..2bc4200cd7a9 100644 --- a/build-aux/m4/gmp.m4 +++ b/build-aux/m4/gmp.m4 @@ -9,7 +9,6 @@ if test x"$has_gmp" != x"yes"; then AC_CHECK_LIB(gmp, __gmpz_init,[ has_gmp=yes; LIBS="$LIBS -lgmp"; - AC_DEFINE(HAVE_LIBGMP, 1, [Define this symbol if libgmp is installed]) ]) ]) fi diff --git a/configure.ac b/configure.ac index dc917b016087..5bc0eafe05c4 100644 --- a/configure.ac +++ b/configure.ac @@ -237,12 +237,6 @@ AC_ARG_ENABLE([zmq], [use_zmq=$enableval], [use_zmq=yes]) -AC_ARG_WITH([zerocoin-bignum], - [AS_HELP_STRING([--with-zerocoin-bignum=gmp|openssl|auto], - [Specify Bignum Implementation. Default is auto])], - [req_bignum=$withval], - [req_bignum=auto]) - AC_ARG_ENABLE(man, [AS_HELP_STRING([--disable-man], [do not install man pages (default is to install)])],, @@ -1159,6 +1153,12 @@ else fi fi +dnl gmp check +GMP_CHECK +if test x"$has_gmp" != x"yes"; then + AC_MSG_ERROR([libgmp not found]) +fi + dnl univalue check need_bundled_univalue=yes @@ -1265,32 +1265,6 @@ if test "x$use_ccache" = "xyes"; then AX_CHECK_PREPROC_FLAG([-Qunused-arguments],[CPPFLAGS="-Qunused-arguments $CPPFLAGS"]) fi -dnl bignum value -set_bignum=$req_bignum -case $req_bignum in -auto) - GMP_CHECK - if test x"$has_gmp" != x"yes"; then - AC_MSG_ERROR([gmp bignum automatically selected but libgmp is not available. Use depends, - install libgmp or select an other bignum implementation (ONLY gmp is fully SUPPORTED)]) - else - set_bignum=gmp - fi - ;; -gmp) - GMP_CHECK - if test x"$has_gmp" != x"yes"; then - AC_MSG_ERROR([gmp bignum explicitly requested but libgmp is not available]) - fi - ;; -openssl) - AC_MSG_WARN([openssl bignum explicitly requested. This is DEPRECATED.]) - ;; -*) - AC_MSG_ERROR([invalid bignum implementation selection]) - ;; -esac - dnl enable wallet AC_MSG_CHECKING([if wallet should be enabled]) if test x$enable_wallet != xno; then @@ -1381,22 +1355,6 @@ fi AM_CONDITIONAL([ENABLE_ZMQ], [test "x$use_zmq" = "xyes"]) -# select bignum implementation -case $set_bignum in -gmp) - AC_DEFINE(USE_NUM_GMP, 1, [Define this symbol to use the gmp implementation]) - ;; -openssl) - AC_DEFINE(USE_NUM_OPENSSL, 1, [Define this symbol to use openssl implementation]) - ;; -*) - AC_MSG_ERROR([invalid bignum implementation]) - ;; -esac - -AM_CONDITIONAL([USE_NUM_GMP], [test "x$set_bignum" = "xgmp"]) -AM_CONDITIONAL([USE_NUM_OPENSSL], [test "x$set_bignum" = "xopenssl"]) - AC_MSG_CHECKING([whether to build test_pivx]) if test x$use_tests = xyes; then AC_MSG_RESULT([yes]) @@ -1494,8 +1452,6 @@ AC_SUBST(SODIUM_LIBS) AC_SUBST(ZMQ_LIBS) AC_SUBST(LIBZCASH_LIBS) AC_SUBST(QR_LIBS) -AC_SUBST(USE_NUM_GMP) -AC_SUBST(USE_NUM_OPENSSL) AC_SUBST(HAVE_FDATASYNC) AC_SUBST(HAVE_FULLFSYNC) AC_SUBST(HAVE_O_CLOEXEC) @@ -1571,7 +1527,6 @@ if test x$bitcoin_enable_qt != xno; then echo " with qtcharts = $use_qtcharts" fi echo " with zmq = $use_zmq" -echo " with bignum = $set_bignum" echo " with test = $use_tests" echo " with bench = $use_bench" echo " with upnp = $use_upnp" diff --git a/src/Makefile.am b/src/Makefile.am index 8d248316fd7b..12af80058fdd 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -480,12 +480,6 @@ libzerocoin_libbitcoin_zerocoin_a_SOURCES = \ libzerocoin/ParamGeneration.cpp \ libzerocoin/Params.cpp \ zpiv/zpivmodule.cpp -if USE_NUM_GMP - libzerocoin_libbitcoin_zerocoin_a_SOURCES += libzerocoin/bignum_gmp.cpp -endif -if USE_NUM_OPENSSL - libzerocoin_libbitcoin_zerocoin_a_SOURCES += libzerocoin/bignum_openssl.cpp -endif # common: shared between pivxd, and pivx-qt and non-server tools libbitcoin_common_a_CPPFLAGS = $(AM_CPPFLAGS) $(BITCOIN_INCLUDES) diff --git a/src/libzerocoin/bignum.cpp b/src/libzerocoin/bignum.cpp index 6b19ea1bd416..f139e9bbc9ee 100644 --- a/src/libzerocoin/bignum.cpp +++ b/src/libzerocoin/bignum.cpp @@ -6,13 +6,347 @@ #include "bignum.h" -#if defined(USE_NUM_GMP) -#include "bignum_gmp.cpp" -#endif +/** C++ wrapper for BIGNUM (Gmp bignum) */ +CBigNum::CBigNum() +{ + mpz_init(bn); +} + +CBigNum::CBigNum(const CBigNum& b) +{ + mpz_init(bn); + mpz_set(bn, b.bn); +} + +CBigNum& CBigNum::operator=(const CBigNum& b) +{ + mpz_set(bn, b.bn); + return (*this); +} + +CBigNum::~CBigNum() +{ + mpz_clear(bn); +} + +//CBigNum(char n) is not portable. Use 'signed char' or 'unsigned char'. +CBigNum::CBigNum(signed char n) { mpz_init(bn); if (n >= 0) mpz_set_ui(bn, n); else mpz_set_si(bn, n); } +CBigNum::CBigNum(short n) { mpz_init(bn); if (n >= 0) mpz_set_ui(bn, n); else mpz_set_si(bn, n); } +CBigNum::CBigNum(int n) { mpz_init(bn); if (n >= 0) mpz_set_ui(bn, n); else mpz_set_si(bn, n); } +CBigNum::CBigNum(long n) { mpz_init(bn); if (n >= 0) mpz_set_ui(bn, n); else mpz_set_si(bn, n); } +CBigNum::CBigNum(long long n) { mpz_init(bn); mpz_set_si(bn, n); } +CBigNum::CBigNum(unsigned char n) { mpz_init(bn); mpz_set_ui(bn, n); } +CBigNum::CBigNum(unsigned short n) { mpz_init(bn); mpz_set_ui(bn, n); } +CBigNum::CBigNum(unsigned int n) { mpz_init(bn); mpz_set_ui(bn, n); } +CBigNum::CBigNum(unsigned long n) { mpz_init(bn); mpz_set_ui(bn, n); } + +CBigNum::CBigNum(uint256 n) { mpz_init(bn); setuint256(n); } + +CBigNum::CBigNum(const std::vector& vch) +{ + mpz_init(bn); + setvch(vch); +} + +/** PRNGs use OpenSSL for consistency with seed initialization **/ + +/** Generates a cryptographically secure random number between zero and range-1 (inclusive) +* i.e. 0 <= returned number < range +* @param range The upper bound on the number. +* @return +*/ +CBigNum CBigNum::randBignum(const CBigNum& range) +{ + if (range < 2) + return 0; + + size_t size = (mpz_sizeinbase (range.bn, 2) + CHAR_BIT-1) / CHAR_BIT; + std::vector buf(size); + + GetStrongRandBytes(buf.data(), size); + + CBigNum ret(buf); + if (ret < 0) + mpz_neg(ret.bn, ret.bn); + return (ret % range); +} + +/** Generates a cryptographically secure random k-bit number +* @param k The bit length of the number. +* @return +*/ +CBigNum CBigNum::randKBitBignum(const uint32_t k) +{ + std::vector buf((k+7)/8); + + GetStrongRandBytes(buf.data(), (k+7)/8); + + CBigNum ret(buf); + if (ret < 0) + mpz_neg(ret.bn, ret.bn); + return ret % (BN_ONE << k); +} + +/**Returns the size in bits of the underlying bignum. + * + * @return the size + */ +int CBigNum::bitSize() const +{ + return mpz_sizeinbase(bn, 2); +} + +void CBigNum::setulong(unsigned long n) +{ + mpz_set_ui(bn, n); +} + +unsigned long CBigNum::getulong() const +{ + return mpz_get_ui(bn); +} + +unsigned int CBigNum::getuint() const +{ + return mpz_get_ui(bn); +} + +int CBigNum::getint() const +{ + unsigned long n = getulong(); + if (mpz_cmp(bn, BN_ZERO.bn) >= 0) { + 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); + } +} + +void CBigNum::setuint256(uint256 n) +{ + mpz_import(bn, n.size(), -1, 1, 0, 0, (unsigned char*)&n); +} + +uint256 CBigNum::getuint256() const +{ + if(bitSize() > 256) { + throw std::range_error("cannot convert to uint256, bignum longer than 256 bits"); + } + uint256 n = UINT256_ZERO; + mpz_export((unsigned char*)&n, NULL, -1, 1, 0, 0, bn); + return n; +} + +void CBigNum::setvch(const std::vector& vch) +{ + std::vector vch2 = vch; + unsigned char sign = 0; + if (vch2.size() > 0) { + sign = vch2[vch2.size()-1] & 0x80; + vch2[vch2.size()-1] = vch2[vch2.size()-1] & 0x7f; + mpz_import(bn, vch2.size(), -1, 1, 0, 0, &vch2[0]); + if (sign) + mpz_neg(bn, bn); + } + else { + mpz_set_si(bn, 0); + } +} + +std::vector CBigNum::getvch() const +{ + if (mpz_cmp(bn, BN_ZERO.bn) == 0) { + return std::vector(0); + } + size_t size = (mpz_sizeinbase (bn, 2) + CHAR_BIT-1) / CHAR_BIT; + if (size <= 0) + return std::vector(); + std::vector v(size + 1); + mpz_export(&v[0], &size, -1, 1, 0, 0, bn); + if (v[v.size()-2] & 0x80) { + if (mpz_sgn(bn)<0) { + v[v.size()-1] = 0x80; + } else { + v[v.size()-1] = 0x00; + } + } else { + v.pop_back(); + if (mpz_sgn(bn)<0) { + v[v.size()-1] |= 0x80; + } + } + return v; +} + +void CBigNum::SetDec(const std::string& str) +{ + const char* psz = str.c_str(); + mpz_set_str(bn, psz, 10); +} + +bool CBigNum::SetHexBool(const std::string& str) +{ + const char* psz = str.c_str(); + int ret = 1 + mpz_set_str(bn, psz, 16); + return (bool) ret; +} + +std::string CBigNum::ToString(int nBase) const +{ + char* c_str = mpz_get_str(NULL, nBase, bn); + std::string str(c_str); + // Free c_str with the right free function: + void (*freefunc)(void *, size_t); + mp_get_memory_functions (NULL, NULL, &freefunc); + freefunc(c_str, strlen(c_str) + 1); -#if defined(USE_NUM_OPENSSL) -#include "bignum_openssl.cpp" -#endif + return str; +} + +/** + * exponentiation this^e + * @param e the exponent + * @return + */ +CBigNum CBigNum::pow(const CBigNum& e) const +{ + CBigNum ret; + long unsigned int ei = mpz_get_ui (e.bn); + mpz_pow_ui(ret.bn, bn, ei); + return ret; +} + +/** + * modular multiplication: (this * b) mod m + * @param b operand + * @param m modulus + */ +CBigNum CBigNum::mul_mod(const CBigNum& b, const CBigNum& m) const +{ + CBigNum ret; + mpz_mul (ret.bn, bn, b.bn); + mpz_mod (ret.bn, ret.bn, m.bn); + return ret; +} + +/** + * modular exponentiation: this^e mod n + * @param e exponent + * @param m modulus + */ +CBigNum CBigNum::pow_mod(const CBigNum& e, const CBigNum& m) const +{ + CBigNum ret; + if (e > BN_ZERO && mpz_odd_p(m.bn)) + mpz_powm_sec (ret.bn, bn, e.bn, m.bn); + else + mpz_powm (ret.bn, bn, e.bn, m.bn); + return ret; +} + +/** +* Calculates the inverse of this element mod m. +* i.e. i such this*i = 1 mod m +* @param m the modu +* @return the inverse +*/ +CBigNum CBigNum::inverse(const CBigNum& m) const +{ + CBigNum ret; + mpz_invert(ret.bn, bn, m.bn); + return ret; +} + +/** + * Generates a random (safe) prime of numBits bits + * @param numBits the number of bits + * @param safe true for a safe prime + * @return the prime + */ +CBigNum CBigNum::generatePrime(const unsigned int numBits, bool safe) +{ + CBigNum rand = randKBitBignum(numBits); + CBigNum prime; + mpz_nextprime(prime.bn, rand.bn); + return prime; +} + +/** + * Calculates the greatest common divisor (GCD) of two numbers. + * @param m the second element + * @return the GCD + */ +CBigNum CBigNum::gcd( const CBigNum& b) const +{ + CBigNum ret; + mpz_gcd(ret.bn, bn, b.bn); + return ret; +} + +/** +* Miller-Rabin primality test on this element +* @param checks: optional, the number of Miller-Rabin tests to run +* default causes error rate of 2^-80. +* @return true if prime +*/ +bool CBigNum::isPrime(const int checks) const +{ + int ret = mpz_probab_prime_p(bn, checks); + return ret; +} + +bool CBigNum::isOne() const +{ + return mpz_cmp(bn, BN_ONE.bn) == 0; +} + +bool CBigNum::operator!() const +{ + return mpz_cmp(bn, BN_ZERO.bn) == 0; +} + +CBigNum& CBigNum::operator+=(const CBigNum& b) +{ + mpz_add(bn, bn, b.bn); + return *this; +} + +CBigNum& CBigNum::operator-=(const CBigNum& b) +{ + mpz_sub(bn, bn, b.bn); + return *this; +} + +CBigNum& CBigNum::operator*=(const CBigNum& b) +{ + mpz_mul(bn, bn, b.bn); + return *this; +} + +CBigNum& CBigNum::operator<<=(unsigned int shift) +{ + mpz_mul_2exp(bn, bn, shift); + return *this; +} + +CBigNum& CBigNum::operator>>=(unsigned int shift) +{ + mpz_div_2exp(bn, bn, shift); + return *this; +} + +CBigNum& CBigNum::operator++() +{ + // prefix operator + mpz_add(bn, bn, BN_ONE.bn); + return *this; +} + +CBigNum& CBigNum::operator--() +{ + // prefix operator + mpz_sub(bn, bn, BN_ONE.bn); + return *this; +} std::string CBigNum::GetHex() const { diff --git a/src/libzerocoin/bignum.h b/src/libzerocoin/bignum.h index 53c9d21e5b8a..b320bae2f48a 100755 --- a/src/libzerocoin/bignum.h +++ b/src/libzerocoin/bignum.h @@ -11,12 +11,7 @@ #include "config/pivx-config.h" #endif -#if defined(USE_NUM_OPENSSL) -#include -#endif -#if defined(USE_NUM_GMP) #include -#endif #include #include @@ -37,12 +32,7 @@ class bignum_error : public std::runtime_error /** C++ wrapper for BIGNUM */ class CBigNum { -#if defined(USE_NUM_OPENSSL) - BIGNUM* bn; -#endif -#if defined(USE_NUM_GMP) mpz_t bn; -#endif public: CBigNum(); CBigNum(const CBigNum& b); @@ -169,12 +159,7 @@ class CBigNum * default causes error rate of 2^-80. * @return true if prime */ -#if defined(USE_NUM_OPENSSL) - bool isPrime(const int checks=BN_prime_checks) const; -#endif -#if defined(USE_NUM_GMP) bool isPrime(const int checks=15) const; -#endif bool isOne() const; bool operator!() const; @@ -205,91 +190,6 @@ class CBigNum friend inline bool operator>(const CBigNum& a, const CBigNum& b); }; -#if defined(USE_NUM_OPENSSL) -class CAutoBN_CTX -{ -protected: - BN_CTX* pctx; - BN_CTX* operator=(BN_CTX* pnew) { return pctx = pnew; } - -public: - CAutoBN_CTX() - { - pctx = BN_CTX_new(); - if (pctx == NULL) - throw bignum_error("CAutoBN_CTX : BN_CTX_new() returned NULL"); - } - - ~CAutoBN_CTX() - { - if (pctx != NULL) - BN_CTX_free(pctx); - } - - operator BN_CTX*() { return pctx; } - BN_CTX& operator*() { return *pctx; } - BN_CTX** operator&() { return &pctx; } - bool operator!() { return (pctx == NULL); } -}; - -inline const CBigNum operator+(const CBigNum& a, const CBigNum& b) { - CBigNum r; - if (!BN_add(r.bn, a.bn, b.bn)) - throw bignum_error("CBigNum::operator+ : BN_add failed"); - return r; -} -inline const CBigNum operator-(const CBigNum& a, const CBigNum& b) { - CBigNum r; - if (!BN_sub(r.bn, a.bn, b.bn)) - throw bignum_error("CBigNum::operator- : BN_sub failed"); - return r; -} -inline const CBigNum operator-(const CBigNum& a) { - CBigNum r(a); - BN_set_negative(r.bn, !BN_is_negative(r.bn)); - return r; -} -inline const CBigNum operator*(const CBigNum& a, const CBigNum& b) { - CAutoBN_CTX pctx; - CBigNum r; - if (!BN_mul(r.bn, a.bn, b.bn, pctx)) - throw bignum_error("CBigNum::operator* : BN_mul failed"); - return r; -} -inline const CBigNum operator/(const CBigNum& a, const CBigNum& b) { - CAutoBN_CTX pctx; - CBigNum r; - if (!BN_div(r.bn, NULL, a.bn, b.bn, pctx)) - throw bignum_error("CBigNum::operator/ : BN_div failed"); - return r; -} -inline const CBigNum operator%(const CBigNum& a, const CBigNum& b) { - CAutoBN_CTX pctx; - CBigNum r; - if (!BN_nnmod(r.bn, a.bn, b.bn, pctx)) - throw bignum_error("CBigNum::operator% : BN_div failed"); - return r; -} -inline const CBigNum operator<<(const CBigNum& a, unsigned int shift) { - CBigNum r; - if (!BN_lshift(r.bn, a.bn, shift)) - throw bignum_error("CBigNum:operator<< : BN_lshift failed"); - return r; -} -inline const CBigNum operator>>(const CBigNum& a, unsigned int shift) { - CBigNum r = a; - r >>= shift; - return r; -} -inline bool operator==(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.bn, b.bn) == 0); } -inline bool operator!=(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.bn, b.bn) != 0); } -inline bool operator<=(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.bn, b.bn) <= 0); } -inline bool operator>=(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.bn, b.bn) >= 0); } -inline bool operator<(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.bn, b.bn) < 0); } -inline bool operator>(const CBigNum& a, const CBigNum& b) { return (BN_cmp(a.bn, b.bn) > 0); } -#endif - -#if defined(USE_NUM_GMP) inline const CBigNum operator+(const CBigNum& a, const CBigNum& b) { CBigNum r; mpz_add(r.bn, a.bn, b.bn); @@ -336,7 +236,6 @@ inline bool operator<=(const CBigNum& a, const CBigNum& b) { return (mpz_cmp(a.b inline bool operator>=(const CBigNum& a, const CBigNum& b) { return (mpz_cmp(a.bn, b.bn) >= 0); } inline bool operator<(const CBigNum& a, const CBigNum& b) { return (mpz_cmp(a.bn, b.bn) < 0); } inline bool operator>(const CBigNum& a, const CBigNum& b) { return (mpz_cmp(a.bn, b.bn) > 0); } -#endif inline std::ostream& operator<<(std::ostream &strm, const CBigNum &b) { return strm << b.ToString(10); } @@ -348,4 +247,4 @@ const CBigNum BN_ONE = CBigNum(1); const CBigNum BN_TWO = CBigNum(2); const CBigNum BN_THREE = CBigNum(3); -#endif +#endif // BITCOIN_BIGNUM_H diff --git a/src/libzerocoin/bignum_gmp.cpp b/src/libzerocoin/bignum_gmp.cpp deleted file mode 100644 index dee024cfc2d1..000000000000 --- a/src/libzerocoin/bignum_gmp.cpp +++ /dev/null @@ -1,349 +0,0 @@ -// Copyright (c) 2009-2010 Satoshi Nakamoto -// Copyright (c) 2009-2012 The Bitcoin developers -// Copyright (c) 2017-2020 The PIVX developers -// Distributed under the MIT/X11 software license, see the accompanying -// file COPYING or http://www.opensource.org/licenses/mit-license.php. - -#include "bignum.h" - -/** C++ wrapper for BIGNUM (Gmp bignum) */ -CBigNum::CBigNum() -{ - mpz_init(bn); -} - -CBigNum::CBigNum(const CBigNum& b) -{ - mpz_init(bn); - mpz_set(bn, b.bn); -} - -CBigNum& CBigNum::operator=(const CBigNum& b) -{ - mpz_set(bn, b.bn); - return (*this); -} - -CBigNum::~CBigNum() -{ - mpz_clear(bn); -} - -//CBigNum(char n) is not portable. Use 'signed char' or 'unsigned char'. -CBigNum::CBigNum(signed char n) { mpz_init(bn); if (n >= 0) mpz_set_ui(bn, n); else mpz_set_si(bn, n); } -CBigNum::CBigNum(short n) { mpz_init(bn); if (n >= 0) mpz_set_ui(bn, n); else mpz_set_si(bn, n); } -CBigNum::CBigNum(int n) { mpz_init(bn); if (n >= 0) mpz_set_ui(bn, n); else mpz_set_si(bn, n); } -CBigNum::CBigNum(long n) { mpz_init(bn); if (n >= 0) mpz_set_ui(bn, n); else mpz_set_si(bn, n); } -CBigNum::CBigNum(long long n) { mpz_init(bn); mpz_set_si(bn, n); } -CBigNum::CBigNum(unsigned char n) { mpz_init(bn); mpz_set_ui(bn, n); } -CBigNum::CBigNum(unsigned short n) { mpz_init(bn); mpz_set_ui(bn, n); } -CBigNum::CBigNum(unsigned int n) { mpz_init(bn); mpz_set_ui(bn, n); } -CBigNum::CBigNum(unsigned long n) { mpz_init(bn); mpz_set_ui(bn, n); } - -CBigNum::CBigNum(uint256 n) { mpz_init(bn); setuint256(n); } - -CBigNum::CBigNum(const std::vector& vch) -{ - mpz_init(bn); - setvch(vch); -} - -/** PRNGs use OpenSSL for consistency with seed initialization **/ - -/** Generates a cryptographically secure random number between zero and range-1 (inclusive) -* i.e. 0 <= returned number < range -* @param range The upper bound on the number. -* @return -*/ -CBigNum CBigNum::randBignum(const CBigNum& range) -{ - if (range < 2) - return 0; - - size_t size = (mpz_sizeinbase (range.bn, 2) + CHAR_BIT-1) / CHAR_BIT; - std::vector buf(size); - - GetStrongRandBytes(buf.data(), size); - - CBigNum ret(buf); - if (ret < 0) - mpz_neg(ret.bn, ret.bn); - return (ret % range); -} - -/** Generates a cryptographically secure random k-bit number -* @param k The bit length of the number. -* @return -*/ -CBigNum CBigNum::randKBitBignum(const uint32_t k) -{ - std::vector buf((k+7)/8); - - GetStrongRandBytes(buf.data(), (k+7)/8); - - CBigNum ret(buf); - if (ret < 0) - mpz_neg(ret.bn, ret.bn); - return ret % (BN_ONE << k); -} - -/**Returns the size in bits of the underlying bignum. - * - * @return the size - */ -int CBigNum::bitSize() const -{ - return mpz_sizeinbase(bn, 2); -} - -void CBigNum::setulong(unsigned long n) -{ - mpz_set_ui(bn, n); -} - -unsigned long CBigNum::getulong() const -{ - return mpz_get_ui(bn); -} - -unsigned int CBigNum::getuint() const -{ - return mpz_get_ui(bn); -} - -int CBigNum::getint() const -{ - unsigned long n = getulong(); - if (mpz_cmp(bn, BN_ZERO.bn) >= 0) { - 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); - } -} - -void CBigNum::setuint256(uint256 n) -{ - mpz_import(bn, n.size(), -1, 1, 0, 0, (unsigned char*)&n); -} - -uint256 CBigNum::getuint256() const -{ - if(bitSize() > 256) { - throw std::range_error("cannot convert to uint256, bignum longer than 256 bits"); - } - uint256 n = UINT256_ZERO; - mpz_export((unsigned char*)&n, NULL, -1, 1, 0, 0, bn); - return n; -} - -void CBigNum::setvch(const std::vector& vch) -{ - std::vector vch2 = vch; - unsigned char sign = 0; - if (vch2.size() > 0) { - sign = vch2[vch2.size()-1] & 0x80; - vch2[vch2.size()-1] = vch2[vch2.size()-1] & 0x7f; - mpz_import(bn, vch2.size(), -1, 1, 0, 0, &vch2[0]); - if (sign) - mpz_neg(bn, bn); - } - else { - mpz_set_si(bn, 0); - } -} - -std::vector CBigNum::getvch() const -{ - if (mpz_cmp(bn, BN_ZERO.bn) == 0) { - return std::vector(0); - } - size_t size = (mpz_sizeinbase (bn, 2) + CHAR_BIT-1) / CHAR_BIT; - if (size <= 0) - return std::vector(); - std::vector v(size + 1); - mpz_export(&v[0], &size, -1, 1, 0, 0, bn); - if (v[v.size()-2] & 0x80) { - if (mpz_sgn(bn)<0) { - v[v.size()-1] = 0x80; - } else { - v[v.size()-1] = 0x00; - } - } else { - v.pop_back(); - if (mpz_sgn(bn)<0) { - v[v.size()-1] |= 0x80; - } - } - return v; -} - -void CBigNum::SetDec(const std::string& str) -{ - const char* psz = str.c_str(); - mpz_set_str(bn, psz, 10); -} - -bool CBigNum::SetHexBool(const std::string& str) -{ - const char* psz = str.c_str(); - int ret = 1 + mpz_set_str(bn, psz, 16); - return (bool) ret; -} - -std::string CBigNum::ToString(int nBase) const -{ - char* c_str = mpz_get_str(NULL, nBase, bn); - std::string str(c_str); - // Free c_str with the right free function: - void (*freefunc)(void *, size_t); - mp_get_memory_functions (NULL, NULL, &freefunc); - freefunc(c_str, strlen(c_str) + 1); - - return str; -} - -/** - * exponentiation this^e - * @param e the exponent - * @return - */ -CBigNum CBigNum::pow(const CBigNum& e) const -{ - CBigNum ret; - long unsigned int ei = mpz_get_ui (e.bn); - mpz_pow_ui(ret.bn, bn, ei); - return ret; -} - -/** - * modular multiplication: (this * b) mod m - * @param b operand - * @param m modulus - */ -CBigNum CBigNum::mul_mod(const CBigNum& b, const CBigNum& m) const -{ - CBigNum ret; - mpz_mul (ret.bn, bn, b.bn); - mpz_mod (ret.bn, ret.bn, m.bn); - return ret; -} - -/** - * modular exponentiation: this^e mod n - * @param e exponent - * @param m modulus - */ -CBigNum CBigNum::pow_mod(const CBigNum& e, const CBigNum& m) const -{ - CBigNum ret; - if (e > BN_ZERO && mpz_odd_p(m.bn)) - mpz_powm_sec (ret.bn, bn, e.bn, m.bn); - else - mpz_powm (ret.bn, bn, e.bn, m.bn); - return ret; -} - -/** -* Calculates the inverse of this element mod m. -* i.e. i such this*i = 1 mod m -* @param m the modu -* @return the inverse -*/ -CBigNum CBigNum::inverse(const CBigNum& m) const -{ - CBigNum ret; - mpz_invert(ret.bn, bn, m.bn); - return ret; -} - -/** - * Generates a random (safe) prime of numBits bits - * @param numBits the number of bits - * @param safe true for a safe prime - * @return the prime - */ -CBigNum CBigNum::generatePrime(const unsigned int numBits, bool safe) -{ - CBigNum rand = randKBitBignum(numBits); - CBigNum prime; - mpz_nextprime(prime.bn, rand.bn); - return prime; -} - -/** - * Calculates the greatest common divisor (GCD) of two numbers. - * @param m the second element - * @return the GCD - */ -CBigNum CBigNum::gcd( const CBigNum& b) const -{ - CBigNum ret; - mpz_gcd(ret.bn, bn, b.bn); - return ret; -} - -/** -* Miller-Rabin primality test on this element -* @param checks: optional, the number of Miller-Rabin tests to run -* default causes error rate of 2^-80. -* @return true if prime -*/ -bool CBigNum::isPrime(const int checks) const -{ - int ret = mpz_probab_prime_p(bn, checks); - return ret; -} - -bool CBigNum::isOne() const -{ - return mpz_cmp(bn, BN_ONE.bn) == 0; -} - -bool CBigNum::operator!() const -{ - return mpz_cmp(bn, BN_ZERO.bn) == 0; -} - -CBigNum& CBigNum::operator+=(const CBigNum& b) -{ - mpz_add(bn, bn, b.bn); - return *this; -} - -CBigNum& CBigNum::operator-=(const CBigNum& b) -{ - mpz_sub(bn, bn, b.bn); - return *this; -} - -CBigNum& CBigNum::operator*=(const CBigNum& b) -{ - mpz_mul(bn, bn, b.bn); - return *this; -} - -CBigNum& CBigNum::operator<<=(unsigned int shift) -{ - mpz_mul_2exp(bn, bn, shift); - return *this; -} - -CBigNum& CBigNum::operator>>=(unsigned int shift) -{ - mpz_div_2exp(bn, bn, shift); - return *this; -} - -CBigNum& CBigNum::operator++() -{ - // prefix operator - mpz_add(bn, bn, BN_ONE.bn); - return *this; -} - -CBigNum& CBigNum::operator--() -{ - // prefix operator - mpz_sub(bn, bn, BN_ONE.bn); - return *this; -} diff --git a/src/libzerocoin/bignum_openssl.cpp b/src/libzerocoin/bignum_openssl.cpp deleted file mode 100644 index 30e38b2dd173..000000000000 --- a/src/libzerocoin/bignum_openssl.cpp +++ /dev/null @@ -1,508 +0,0 @@ -// Copyright (c) 2009-2010 Satoshi Nakamoto -// Copyright (c) 2009-2012 The Bitcoin developers -// Copyright (c) 2017-2019 The PIVX developers -// Distributed under the MIT/X11 software license, see the accompanying -// file COPYING or http://www.opensource.org/licenses/mit-license.php. - -#include "bignum.h" - -CBigNum::CBigNum() -{ - bn = BN_new(); -} - -CBigNum::CBigNum(const CBigNum& b) -{ - bn = BN_new(); - if (!BN_copy(bn, b.bn)) - { - BN_clear_free(bn); - throw bignum_error("CBigNum::CBigNum(const CBigNum&) : BN_copy failed"); - } -} - -CBigNum& CBigNum::operator=(const CBigNum& b) -{ - if (!BN_copy(bn, b.bn)) - throw bignum_error("CBigNum::operator= : BN_copy failed"); - return (*this); -} - -CBigNum::~CBigNum() -{ - BN_clear_free(bn); -} - -//CBigNum(char n) is not portable. Use 'signed char' or 'unsigned char'. -CBigNum::CBigNum(signed char n) { bn = BN_new(); if (n >= 0) setulong(n); else setint64(n); } -CBigNum::CBigNum(short n) { bn = BN_new(); if (n >= 0) setulong(n); else setint64(n); } -CBigNum::CBigNum(int n) { bn = BN_new(); if (n >= 0) setulong(n); else setint64(n); } -CBigNum::CBigNum(long n) { bn = BN_new(); if (n >= 0) setulong(n); else setint64(n); } -CBigNum::CBigNum(long long n) { bn = BN_new(); setint64(n); } -CBigNum::CBigNum(unsigned char n) { bn = BN_new(); setulong(n); } -CBigNum::CBigNum(unsigned short n) { bn = BN_new(); setulong(n); } -CBigNum::CBigNum(unsigned int n) { bn = BN_new(); setulong(n); } -CBigNum::CBigNum(unsigned long n) { bn = BN_new(); setulong(n); } -CBigNum::CBigNum(unsigned long long n) { bn = BN_new(); setuint64(n); } -CBigNum::CBigNum(uint256 n) { bn = BN_new(); setuint256(n); } - -CBigNum::CBigNum(const std::vector& vch) -{ - bn = BN_new(); - setvch(vch); -} - -/** Generates a cryptographically secure random number between zero and range-1 (inclusive) -* i.e. 0 <= returned number < range -* @param range The upper bound on the number. -* @return -*/ -CBigNum CBigNum::randBignum(const CBigNum& range) -{ - CBigNum ret; - if(!BN_rand_range(ret.bn, range.bn)){ - throw bignum_error("CBigNum:rand element : BN_rand_range failed"); - } - return ret; -} - -/** Generates a cryptographically secure random k-bit number -* @param k The bit length of the number. -* @return -*/ -CBigNum CBigNum::randKBitBignum(const uint32_t k) -{ - CBigNum ret; - if(!BN_rand(ret.bn, k, -1, 0)){ - throw bignum_error("CBigNum:rand element : BN_rand failed"); - } - return ret; -} - -/**Returns the size in bits of the underlying bignum. - * - * @return the size - */ -int CBigNum::bitSize() const -{ - return BN_num_bits(bn); -} - -void CBigNum::setulong(unsigned long n) -{ - if (!BN_set_word(bn, n)) - throw bignum_error("CBigNum conversion from unsigned long : BN_set_word failed"); -} - -unsigned long CBigNum::getulong() const -{ - return BN_get_word(bn); -} - -unsigned int CBigNum::getuint() const -{ - return BN_get_word(bn); -} - -int CBigNum::getint() const -{ - 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); -} - -void CBigNum::setint64(int64_t sn) -{ - unsigned char pch[sizeof(sn) + 6]; - unsigned char* p = pch + 4; - bool fNegative; - uint64_t n; - - if (sn < (int64_t)0) - { - // Since the minimum signed integer cannot be represented as positive so long as its type is signed, - // and it's not well-defined what happens if you make it unsigned before negating it, - // we instead increment the negative integer by 1, convert it, then increment the (now positive) unsigned integer by 1 to compensate - n = -(sn + 1); - ++n; - fNegative = true; - } else { - n = sn; - fNegative = false; - } - - bool fLeadingZeroes = true; - for (int i = 0; i < 8; i++) - { - unsigned char c = (n >> 56) & 0xff; - n <<= 8; - if (fLeadingZeroes) - { - if (c == 0) - continue; - if (c & 0x80) - *p++ = (fNegative ? 0x80 : 0); - else if (fNegative) - c |= 0x80; - fLeadingZeroes = false; - } - *p++ = c; - } - unsigned int nSize = p - (pch + 4); - pch[0] = (nSize >> 24) & 0xff; - pch[1] = (nSize >> 16) & 0xff; - pch[2] = (nSize >> 8) & 0xff; - pch[3] = (nSize) & 0xff; - BN_mpi2bn(pch, p - pch, bn); -} - -void CBigNum::setuint64(uint64_t n) -{ - unsigned char pch[sizeof(n) + 6]; - unsigned char* p = pch + 4; - bool fLeadingZeroes = true; - for (int i = 0; i < 8; i++) - { - unsigned char c = (n >> 56) & 0xff; - n <<= 8; - if (fLeadingZeroes) - { - if (c == 0) - continue; - if (c & 0x80) - *p++ = 0; - fLeadingZeroes = false; - } - *p++ = c; - } - unsigned int nSize = p - (pch + 4); - pch[0] = (nSize >> 24) & 0xff; - pch[1] = (nSize >> 16) & 0xff; - pch[2] = (nSize >> 8) & 0xff; - pch[3] = (nSize) & 0xff; - BN_mpi2bn(pch, p - pch, bn); -} - -void CBigNum::setuint256(uint256 n) -{ - unsigned char pch[sizeof(n) + 6]; - unsigned char* p = pch + 4; - bool fLeadingZeroes = true; - unsigned char* pbegin = (unsigned char*)&n; - unsigned char* psrc = pbegin + sizeof(n); - while (psrc != pbegin) - { - unsigned char c = *(--psrc); - if (fLeadingZeroes) - { - if (c == 0) - continue; - if (c & 0x80) - *p++ = 0; - fLeadingZeroes = false; - } - *p++ = c; - } - unsigned int nSize = p - (pch + 4); - pch[0] = (nSize >> 24) & 0xff; - pch[1] = (nSize >> 16) & 0xff; - pch[2] = (nSize >> 8) & 0xff; - pch[3] = (nSize >> 0) & 0xff; - BN_mpi2bn(pch, p - pch, bn); -} - -uint256 CBigNum::getuint256() const -{ - if(bitSize() > 256) { - throw std::range_error("cannot convert to uint256, bignum longer than 256 bits"); - } - unsigned int nSize = BN_bn2mpi(bn, NULL); - if (nSize < 4) - return 0; - std::vector vch(nSize); - BN_bn2mpi(bn, &vch[0]); - if (vch.size() > 4) - vch[4] &= 0x7f; - uint256 n = 0; - for (unsigned int i = 0, j = vch.size()-1; i < sizeof(n) && j >= 4; i++, j--) - ((unsigned char*)&n)[i] = vch[j]; - return n; -} - -void CBigNum::setvch(const std::vector& vch) -{ - std::vector vch2(vch.size() + 4); - unsigned int nSize = vch.size(); - // BIGNUM's byte stream format expects 4 bytes of - // big endian size data info at the front - vch2[0] = (nSize >> 24) & 0xff; - vch2[1] = (nSize >> 16) & 0xff; - vch2[2] = (nSize >> 8) & 0xff; - 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(), bn); -} - -std::vector CBigNum::getvch() const -{ - unsigned int nSize = BN_bn2mpi(bn, NULL); - if (nSize <= 4) - return std::vector(); - std::vector vch(nSize); - BN_bn2mpi(bn, &vch[0]); - vch.erase(vch.begin(), vch.begin() + 4); - reverse(vch.begin(), vch.end()); - return vch; -} - -void CBigNum::SetDec(const std::string& str) -{ - BN_dec2bn(&bn, str.c_str()); -} - -bool CBigNum::SetHexBool(const std::string& str) -{ - // skip 0x - const char* psz = str.c_str(); - while (isspace(*psz)) - psz++; - bool fNegative = false; - if (*psz == '-') - { - fNegative = true; - psz++; - } - if (psz[0] == '0' && tolower(psz[1]) == 'x') - psz += 2; - while (isspace(*psz)) - psz++; - - // hex string to bignum - static const signed char phexdigit[256] = { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,1,2,3,4,5,6,7,8,9,0,0,0,0,0,0, 0,0xa,0xb,0xc,0xd,0xe,0xf,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0xa,0xb,0xc,0xd,0xe,0xf,0,0,0,0,0,0,0,0,0 }; - *this = 0; - while (isxdigit(*psz)) - { - *this <<= 4; - int n = phexdigit[(unsigned char)*psz++]; - *this += n; - } - if (fNegative) - *this = 0 - *this; - - return true; -} - - -std::string CBigNum::ToString(int nBase) const -{ - CAutoBN_CTX pctx; - CBigNum bnBase = nBase; - CBigNum bn0 = 0; - CBigNum locBn = *this; - std::string str; - BN_set_negative(locBn.bn, false); - CBigNum dv; - CBigNum rem; - if (BN_cmp(locBn.bn, bn0.bn) == 0) - return "0"; - while (BN_cmp(locBn.bn, bn0.bn) > 0) - { - if (!BN_div(dv.bn, rem.bn, locBn.bn, bnBase.bn, pctx)) - throw bignum_error("CBigNum::ToString() : BN_div failed"); - locBn = dv; - unsigned int c = rem.getulong(); - str += "0123456789abcdef"[c]; - } - if (BN_is_negative(bn)) - str += "-"; - reverse(str.begin(), str.end()); - return str; -} - -/** - * exponentiation this^e - * @param e the exponent - * @return - */ -CBigNum CBigNum::pow(const CBigNum& e) const -{ - CAutoBN_CTX pctx; - CBigNum ret; - if (!BN_exp(ret.bn, bn, e.bn, pctx)) - throw bignum_error("CBigNum::pow : BN_exp failed"); - return ret; -} - -/** - * modular multiplication: (this * b) mod m - * @param b operand - * @param m modulus - */ -CBigNum CBigNum::mul_mod(const CBigNum& b, const CBigNum& m) const -{ - CAutoBN_CTX pctx; - CBigNum ret; - if (!BN_mod_mul(ret.bn, bn, b.bn, m.bn, pctx)) - throw bignum_error("CBigNum::mul_mod : BN_mod_mul failed"); - - return ret; -} - -/** - * modular exponentiation: this^e mod n - * @param e exponent - * @param m modulus - */ -CBigNum CBigNum::pow_mod(const CBigNum& e, const CBigNum& m) const -{ - CAutoBN_CTX pctx; - CBigNum ret; - if( e < 0){ - // g^-x = (g^-1)^x - CBigNum inv = this->inverse(m); - CBigNum posE = e * -1; - if (!BN_mod_exp(ret.bn, inv.bn, posE.bn, m.bn, pctx)) - throw bignum_error("CBigNum::pow_mod: BN_mod_exp failed on negative exponent"); - }else - if (!BN_mod_exp(ret.bn, bn, e.bn, m.bn, pctx)) - throw bignum_error("CBigNum::pow_mod : BN_mod_exp failed"); - - return ret; -} - -/** -* Calculates the inverse of this element mod m. -* i.e. i such this*i = 1 mod m -* @param m the modu -* @return the inverse -*/ -CBigNum CBigNum::inverse(const CBigNum& m) const -{ - CAutoBN_CTX pctx; - CBigNum ret; - if (!BN_mod_inverse(ret.bn, bn, m.bn, pctx)) - throw bignum_error("CBigNum::inverse*= :BN_mod_inverse"); - return ret; -} - -/** - * Generates a random (safe) prime of numBits bits - * @param numBits the number of bits - * @param safe true for a safe prime - * @return the prime - */ -CBigNum CBigNum::generatePrime(const unsigned int numBits, bool safe) -{ - CBigNum ret; - if(!BN_generate_prime_ex(ret.bn, numBits, (safe == true), NULL, NULL, NULL)) - throw bignum_error("CBigNum::generatePrime*= :BN_generate_prime_ex"); - return ret; -} - -/** - * Calculates the greatest common divisor (GCD) of two numbers. - * @param m the second element - * @return the GCD - */ -CBigNum CBigNum::gcd( const CBigNum& b) const -{ - CAutoBN_CTX pctx; - CBigNum ret; - if (!BN_gcd(ret.bn, bn, b.bn, pctx)) - throw bignum_error("CBigNum::gcd*= :BN_gcd"); - return ret; -} - -/** -* Miller-Rabin primality test on this element -* @param checks: optional, the number of Miller-Rabin tests to run -* default causes error rate of 2^-80. -* @return true if prime -*/ -bool CBigNum::isPrime(const int checks) const -{ - CAutoBN_CTX pctx; - int ret = BN_is_prime_ex(bn, checks, pctx, NULL); - if(ret < 0){ - throw bignum_error("CBigNum::isPrime :BN_is_prime"); - } - return ret; -} - -bool CBigNum::isOne() const -{ - return BN_is_one(bn); -} - -bool CBigNum::operator!() const -{ - return BN_is_zero(bn); -} - -CBigNum& CBigNum::operator+=(const CBigNum& b) -{ - if (!BN_add(bn, bn, b.bn)) - throw bignum_error("CBigNum::operator+= : BN_add failed"); - return *this; -} - -CBigNum& CBigNum::operator-=(const CBigNum& b) -{ - if (!BN_sub(bn, bn, b.bn)) - throw bignum_error("CBigNum::operator-= : BN_sub failed"); - return *this; -} - -CBigNum& CBigNum::operator*=(const CBigNum& b) -{ - CAutoBN_CTX pctx; - if (!BN_mul(bn, bn, b.bn, pctx)) - throw bignum_error("CBigNum::operator*= : BN_mul failed"); - return *this; -} - -CBigNum& CBigNum::operator<<=(unsigned int shift) -{ - if (!BN_lshift(bn, bn, shift)) - throw bignum_error("CBigNum:operator<<= : BN_lshift failed"); - return *this; -} - -CBigNum& CBigNum::operator>>=(unsigned int shift) -{ - // Note: BN_rshift segfaults on 64-bit if 2^shift is greater than the number - // if built on ubuntu 9.04 or 9.10, probably depends on version of OpenSSL - CBigNum a = 1; - a <<= shift; - if (BN_cmp(a.bn, bn) > 0) - { - bn = 0; - return *this; - } - - if (!BN_rshift(bn, bn, shift)) - throw bignum_error("CBigNum:operator>>= : BN_rshift failed"); - return *this; -} - - -CBigNum& CBigNum::operator++() -{ - // prefix operator - if (!BN_add(bn, bn, BN_value_one())) - throw bignum_error("CBigNum::operator++ : BN_add failed"); - return *this; -} - -CBigNum& CBigNum::operator--() -{ - // prefix operator - CBigNum r; - if (!BN_sub(r.bn, bn, BN_value_one())) - throw bignum_error("CBigNum::operator-- : BN_sub failed"); - bn = r.bn; - return *this; -} diff --git a/src/qt/CMakeLists.txt b/src/qt/CMakeLists.txt index 1a7d9cbee9f1..be80498154a3 100644 --- a/src/qt/CMakeLists.txt +++ b/src/qt/CMakeLists.txt @@ -198,23 +198,19 @@ QT5_ADD_RESOURCES(QRC_LOCALE_RESOURCE pivx_locale.qrc) add_executable(pivx-qt pivx.cpp ${QM} ${QRC_RESOURCE} ${QRC_LOCALE_RESOURCE}) add_dependencies(pivx-qt translations_target libunivalue libsecp256k1 libzcashrust leveldb crc32c) -target_include_directories(pivx-qt PUBLIC ${ENDIAN_INCLUDES}) +target_include_directories(pivx-qt PUBLIC ${ENDIAN_INCLUDES} ${GMP_INCLUDE_DIR}) target_link_libraries(pivx-qt qt_stuff univalue SERVER_A WALLET_A COMMON_A ZEROCOIN_A UTIL_A SAPLING_A BITCOIN_CRYPTO_A CLI_A leveldb crc32c secp256k1 rustzcash ${BerkeleyDB_LIBRARIES} ${OPENSSL_CRYPTO_LIBRARY} ${Boost_LIBRARIES} ${LIBEVENT_LIB} - ${sodium_LIBRARY_RELEASE} + ${sodium_LIBRARY_RELEASE} ${GMP_LIBRARY} -ldl pthread ) if (${CMAKE_SYSTEM_NAME} MATCHES "Darwin") target_link_libraries(pivx-qt "-framework Cocoa") endif() -if(GMP_FOUND) - target_link_libraries(pivx-qt ${GMP_LIBRARY}) - target_include_directories(pivx-qt PUBLIC ${GMP_INCLUDE_DIR}) -endif() if(ZMQ_FOUND) target_link_libraries(pivx-qt ZMQ_A ${ZMQ_LIB}) target_include_directories(pivx-qt PUBLIC ${ZMQ_INCLUDE_DIR}) diff --git a/src/test/CMakeLists.txt b/src/test/CMakeLists.txt index 10d6cdaddc0d..2ab562ce70ca 100644 --- a/src/test/CMakeLists.txt +++ b/src/test/CMakeLists.txt @@ -148,7 +148,8 @@ target_include_directories(test_pivx PRIVATE ${CMAKE_CURRENT_SOURCE_DIR} ${CMAKE_SOURCE_DIR}/src/leveldb ${CMAKE_SOURCE_DIR}/src/leveldb/include ${CMAKE_SOURCE_DIR}/src/leveldb/helpers/memenv - ${LIBEVENT_INCLUDE_DIR}) + ${LIBEVENT_INCLUDE_DIR} + ${GMP_INCLUDE_DIR}) target_link_libraries(test_pivx PRIVATE SERVER_A CLI_A @@ -163,12 +164,8 @@ target_link_libraries(test_pivx PRIVATE crc32c secp256k1 rustzcash - ${BerkeleyDB_LIBRARIES} ${OPENSSL_CRYPTO_LIBRARY} ${Boost_LIBRARIES} ${Boost_UNIT_TEST_FRAMEWORK_LIBRARY} ${LIBEVENT_LIB} pthread + ${BerkeleyDB_LIBRARIES} ${OPENSSL_CRYPTO_LIBRARY} ${Boost_LIBRARIES} ${Boost_UNIT_TEST_FRAMEWORK_LIBRARY} ${LIBEVENT_LIB} ${GMP_LIBRARY} pthread ) -if(GMP_FOUND) - target_link_libraries(test_pivx PRIVATE ${GMP_LIBRARY}) - target_include_directories(test_pivx PRIVATE ${GMP_INCLUDE_DIR}) -endif() if(ZMQ_FOUND) target_link_libraries(test_pivx PRIVATE ZMQ_A ${ZMQ_LIB}) target_include_directories(test_pivx PRIVATE ${ZMQ_INCLUDE_DIR})