@ -14,21 +14,7 @@
# include <secp256k1.h>
# include "ecwrapper.h"
//! anonymous namespace
namespace {
class CSecp256k1Init {
public :
CSecp256k1Init ( ) {
secp256k1_start ( SECP256K1_START_SIGN ) ;
}
~ CSecp256k1Init ( ) {
secp256k1_stop ( ) ;
}
} ;
static CSecp256k1Init instance_of_csecp256k1 ;
} // anon namespace
static secp256k1_context_t * secp256k1_context = NULL ;
bool CKey : : Check ( const unsigned char * vch ) {
return eccrypto : : Check ( vch ) ;
@ -44,7 +30,7 @@ void CKey::MakeNewKey(bool fCompressedIn) {
}
bool CKey : : SetPrivKey ( const CPrivKey & privkey , bool fCompressedIn ) {
if ( ! secp256k1_ec_privkey_import ( ( unsigned char * ) begin ( ) , & privkey [ 0 ] , privkey . size ( ) ) )
if ( ! secp256k1_ec_privkey_import ( secp256k1_context , ( unsigned char * ) begin ( ) , & privkey [ 0 ] , privkey . size ( ) ) )
return false ;
fCompressed = fCompressedIn ;
fValid = true ;
@ -57,7 +43,7 @@ CPrivKey CKey::GetPrivKey() const {
int privkeylen , ret ;
privkey . resize ( 279 ) ;
privkeylen = 279 ;
ret = secp256k1_ec_privkey_export ( begin( ) , ( unsigned char * ) & privkey [ 0 ] , & privkeylen , fCompressed ) ;
ret = secp256k1_ec_privkey_export ( secp256k1_context, begin( ) , ( unsigned char * ) & privkey [ 0 ] , & privkeylen , fCompressed ) ;
assert ( ret ) ;
privkey . resize ( privkeylen ) ;
return privkey ;
@ -67,7 +53,7 @@ CPubKey CKey::GetPubKey() const {
assert ( fValid ) ;
CPubKey result ;
int clen = 65 ;
int ret = secp256k1_ec_pubkey_create ( ( unsigned char * ) result . begin ( ) , & clen , begin ( ) , fCompressed ) ;
int ret = secp256k1_ec_pubkey_create ( secp256k1_context , ( unsigned char * ) result . begin ( ) , & clen , begin ( ) , fCompressed ) ;
assert ( ( int ) result . size ( ) = = clen ) ;
assert ( ret ) ;
assert ( result . IsValid ( ) ) ;
@ -81,7 +67,7 @@ bool CKey::Sign(const uint256 &hash, std::vector<unsigned char>& vchSig, uint32_
int nSigLen = 72 ;
unsigned char extra_entropy [ 32 ] = { 0 } ;
WriteLE32 ( extra_entropy , test_case ) ;
int ret = secp256k1_ecdsa_sign ( hash. begin ( ) , ( unsigned char * ) & vchSig [ 0 ] , & nSigLen , begin ( ) , secp256k1_nonce_function_rfc6979 , test_case ? extra_entropy : NULL ) ;
int ret = secp256k1_ecdsa_sign ( secp256k1_context, hash. begin ( ) , ( unsigned char * ) & vchSig [ 0 ] , & nSigLen , begin ( ) , secp256k1_nonce_function_rfc6979 , test_case ? extra_entropy : NULL ) ;
assert ( ret ) ;
vchSig . resize ( nSigLen ) ;
return true ;
@ -106,7 +92,7 @@ bool CKey::SignCompact(const uint256 &hash, std::vector<unsigned char>& vchSig)
return false ;
vchSig . resize ( 65 ) ;
int rec = - 1 ;
int ret = secp256k1_ecdsa_sign_compact ( hash. begin ( ) , & vchSig [ 1 ] , begin ( ) , secp256k1_nonce_function_rfc6979 , NULL , & rec ) ;
int ret = secp256k1_ecdsa_sign_compact ( secp256k1_context, hash. begin ( ) , & vchSig [ 1 ] , begin ( ) , secp256k1_nonce_function_rfc6979 , NULL , & rec ) ;
assert ( ret ) ;
assert ( rec ! = - 1 ) ;
vchSig [ 0 ] = 27 + rec + ( fCompressed ? 4 : 0 ) ;
@ -114,7 +100,7 @@ bool CKey::SignCompact(const uint256 &hash, std::vector<unsigned char>& vchSig)
}
bool CKey : : Load ( CPrivKey & privkey , CPubKey & vchPubKey , bool fSkipCheck = false ) {
if ( ! secp256k1_ec_privkey_import ( ( unsigned char * ) begin ( ) , & privkey [ 0 ] , privkey . size ( ) ) )
if ( ! secp256k1_ec_privkey_import ( secp256k1_context , ( unsigned char * ) begin ( ) , & privkey [ 0 ] , privkey . size ( ) ) )
return false ;
fCompressed = vchPubKey . IsCompressed ( ) ;
fValid = true ;
@ -140,7 +126,7 @@ bool CKey::Derive(CKey& keyChild, unsigned char ccChild[32], unsigned int nChild
}
memcpy ( ccChild , out + 32 , 32 ) ;
memcpy ( ( unsigned char * ) keyChild . begin ( ) , begin ( ) , 32 ) ;
bool ret = secp256k1_ec_privkey_tweak_add ( ( unsigned char * ) keyChild . begin ( ) , out ) ;
bool ret = secp256k1_ec_privkey_tweak_add ( secp256k1_context , ( unsigned char * ) keyChild . begin ( ) , out ) ;
UnlockObject ( out ) ;
keyChild . fCompressed = true ;
keyChild . fValid = ret ;
@ -206,3 +192,32 @@ bool ECC_InitSanityCheck() {
CPubKey pubkey = key . GetPubKey ( ) ;
return key . VerifyPubKey ( pubkey ) ;
}
void ECC_Start ( ) {
assert ( secp256k1_context = = NULL ) ;
secp256k1_context_t * ctx = secp256k1_context_create ( SECP256K1_CONTEXT_SIGN ) ;
assert ( ctx ! = NULL ) ;
{
// Pass in a random blinding seed to the secp256k1 context.
unsigned char seed [ 32 ] ;
LockObject ( seed ) ;
GetRandBytes ( seed , 32 ) ;
bool ret = secp256k1_context_randomize ( ctx , seed ) ;
assert ( ret ) ;
UnlockObject ( seed ) ;
}
secp256k1_context = ctx ;
}
void ECC_Stop ( ) {
secp256k1_context_t * ctx = secp256k1_context ;
secp256k1_context = NULL ;
if ( ctx ) {
secp256k1_context_destroy ( ctx ) ;
}
}