Beispiel #1
0
 def get_private_key_secret(self, public_key):
     if public_key in self.wallet_database.keys:  # private key is not crypted
         k = KEY()
         k.set_privkey(self.wallet_database.keys[public_key].private_key)
         return k.get_secret()
     crypted_secret = self.wallet_database.get_crypted_keys()[public_key]
     for key in self.plain_masterkeys:
         self.crypter.set_key(key, doublesha256(public_key))
         secret = self.crypter.decrypt(crypted_secret)
         k = KEY()
         is_compressed = len(public_key) == 33
         k.set_secret(secret, is_compressed)
         if k.get_pubkey() == public_key:
             return secret
     raise KeyDecryptException(
         "Can't decrypt private key, wallet not unlocked or incorrect masterkey"
     )
Beispiel #2
0
 def create(self, passphrase):
     self.wallet_database.begin_updates()
     crypter = Crypter()
     #first create masterkey
     master_key =  new_masterkey(passphrase)
     plain_masterkey = decrypt_masterkey(master_key, passphrase)
     self.wallet_database.add_master_key(master_key)
     #create transaction pool
     for i in range(100):
         k = KEY()
         k.generate(True)
         public_key = k.get_pubkey()
         crypter.set_key(plain_masterkey, doublesha256(public_key))
         crypted_secret = crypter.encrypt(k.get_secret())
         self.wallet_database.add_crypted_key(public_key, crypted_secret)
         pool_key = WalletPoolKey(i, 60000, time.time(), public_key)
         self.wallet_database.add_poolkey(pool_key)
         
         
     self.wallet_database.commit_updates()
     self.load()
Beispiel #3
0
def sign_transaction_input(tx,
                           input_index,
                           txout_script,
                           intput_script_type,
                           secret,
                           compressed_pubkey=True):
    # Set all txin to empty
    txin_scripts_save = [txin.script for txin in tx.in_list]
    for txin in tx.in_list:
        txin.script = Script([])
    # Set the current input script to the outpoint's script value
    tx.in_list[input_index].script = txout_script
    # Serialize and append hash type
    enctx = TxSerializer().serialize(tx) + b"\x01\x00\x00\x00"
    # Get hash and Sign
    txhash = doublesha256(enctx)
    key = KEY()
    key.set_secret(secret, compressed_pubkey)
    signature = key.sign(txhash) + "\x01"  # append hash_type SIGHASH_ALL
    # Restore Txin scripts
    for txin, script_save in zip(tx.in_list, txin_scripts_save):
        txin.script = script_save
    # Set the signed script
    if intput_script_type == TX_PUBKEYHASH:
        tx.in_list[input_index].script = make_script_pubkeyhash_sig(
            key.get_pubkey(), signature)
    if intput_script_type == TX_PUBKEY:
        tx.in_list[input_index].script = make_script_pubkey_sig(signature)
Beispiel #4
0
def sign_transaction_input(tx, input_index, txout_script, intput_script_type, secret, compressed_pubkey=True):
    # Set all txin to empty
    txin_scripts_save = [txin.script for txin in tx.in_list]
    for txin in tx.in_list:
        txin.script = Script([])
    # Set the current input script to the outpoint's script value
    tx.in_list[input_index].script = txout_script
    # Serialize and append hash type
    enctx = TxSerializer().serialize(tx) + b"\x01\x00\x00\x00"
    # Get hash and Sign
    txhash = doublesha256(enctx)
    key = KEY()
    key.set_secret(secret, compressed_pubkey)
    signature = key.sign(txhash) + "\x01" # append hash_type SIGHASH_ALL
    # Restore Txin scripts
    for txin, script_save in zip(tx.in_list, txin_scripts_save):
        txin.script = script_save
    # Set the signed script
    if intput_script_type == TX_PUBKEYHASH:
        tx.in_list[input_index].script = make_script_pubkeyhash_sig(key.get_pubkey(), signature)
    if intput_script_type == TX_PUBKEY:
        tx.in_list[input_index].script = make_script_pubkey_sig(signature)
    def test_shamir_share_private_key(self):
        ssl_add_system_seeds()
        k = KEY()
        k.generate()
        pkey_bignum = k.get_privkey_bignum()
        pubkey = k.get_pubkey()
        numshares = 600
        threshold = 100
        sharenum_bytes = 2
        print "private_key_bignum:", pkey_bignum
        print "public_key:", hexstr(pubkey)
        print "address:", BitcoinAddress.from_publickey(pubkey, MAIN)
        
        field = ZpField()
        V = field.value_type
        ZpPkey = V(pkey_bignum)

        sharer = SecretSharer(field, ZpRandom(field))
        shares = sharer.share(ZpPkey, threshold, [V(i+1) for i in range(numshares)])
        # print shares
        print "Shamir Shares: (%d/%d):" % (threshold, numshares)
        shares_hex = [hexstr(base256encode(int(pt), sharenum_bytes) + base256encode(int(value), 32)) for pt, value in shares]
        
        for share in shares_hex:
            print share
        # Try to reconstruct the private key using the hex encoded shares.
        recombiner = SecretRecombiner(field)
        for i in range(10):
            random4_hex = random.sample(shares_hex, threshold)
            random4_decoded = [decodehexstr(h) for h in random4_hex]
            random4 = [(V(base256decode(data[:sharenum_bytes])), V(base256decode(data[sharenum_bytes:]))) for data in random4_decoded]
            recombined_pkey_bignum = recombiner.recombine(random4, V(0))
            assert recombined_pkey_bignum == ZpPkey
            k2 = KEY()
            k2.set_privkey_bignum(int(recombined_pkey_bignum))
            assert k2.get_pubkey() == pubkey
            print i
        # With threshold-1 shares this fails
        for i in range(10):
            random4_hex = random.sample(shares_hex, threshold-1)
            random4_decoded = [decodehexstr(h) for h in random4_hex]
            random4 = [(V(base256decode(data[:sharenum_bytes])), V(base256decode(data[sharenum_bytes:]))) for data in random4_decoded]
            recombined_pkey_bignum = recombiner.recombine(random4, V(0))
            assert recombined_pkey_bignum != ZpPkey
Beispiel #6
0
 def get_private_key_secret(self, public_key):
     if public_key in self.wallet_database.keys: # private key is not crypted
         k = KEY()
         k.set_privkey(self.wallet_database.keys[public_key].private_key)
         return k.get_secret()
     crypted_secret = self.wallet_database.get_crypted_keys()[public_key]
     for key in self.plain_masterkeys:
         self.crypter.set_key(key, doublesha256(public_key))
         secret = self.crypter.decrypt(crypted_secret)
         k = KEY()
         is_compressed = len(public_key) == 33
         k.set_secret(secret, is_compressed)
         if k.get_pubkey() == public_key:
             return secret
     raise KeyDecryptException("Can't decrypt private key, wallet not unlocked or incorrect masterkey")
Beispiel #7
0
    def create(self, passphrase):
        self.wallet_database.begin_updates()
        crypter = Crypter()
        #first create masterkey
        master_key = new_masterkey(passphrase)
        plain_masterkey = decrypt_masterkey(master_key, passphrase)
        self.wallet_database.add_master_key(master_key)
        #create transaction pool
        for i in range(100):
            k = KEY()
            k.generate(True)
            public_key = k.get_pubkey()
            crypter.set_key(plain_masterkey, doublesha256(public_key))
            crypted_secret = crypter.encrypt(k.get_secret())
            self.wallet_database.add_crypted_key(public_key, crypted_secret)
            pool_key = WalletPoolKey(i, 60000, time.time(), public_key)
            self.wallet_database.add_poolkey(pool_key)

        self.wallet_database.commit_updates()
        self.load()
Beispiel #8
0
def checksig(vm, sig_param, pubkey_param):
    transaction, inputindex, unspent_script = vm.checksig_data
    #Hash type is the last byte of the signature
    hash_type, sig = ord(sig_param[-1]), sig_param[:-1]
    
    # last 5 bits of hash_type : 1=SIGHASH_ALL,2=SIGHASH_NONE, 3=SIGHASH_SINGLE 
    # SIGHASH_ANYONECANPAY = 0x80
    
    # For performance reasons no full copy is made of the transaction
    # although it would be simpler to read.
    # e.g. tx_tmp = copy.deepcopy(transaction)
    # The input scripts are saved and then restored.
    tx_tmp = Tx(transaction.version, 
                [TxIn(txin.previous_output, txin.script, txin.sequence) for txin in transaction.in_list], 
                [TxOut(txout.value, txout.script) for txout in transaction.out_list], 
                transaction.locktime) 
    #Save input scripts to restore them later
    #inlist = transaction.in_list
    #outlist = transaction.out_list
    #inscripts = [txin.script for txin in transaction.in_list]
    #TODO: blank out ouputs depending of hash_type (SIGHASH_NONE, SIGHASH_SINGLE)
    if (hash_type & SIGHASH_MASK == SIGHASH_NONE):
        tx_tmp.out_list = []
    if (hash_type & SIGHASH_MASK == SIGHASH_SINGLE):
        if (inputindex > len(tx_tmp.out_list)):
            raise Exception("OP_CHECKSIG: no corresponding output for input %d using SIGHASH_SINGLE " % (inputindex))
        #n-1 empty TxOuts + original Txout
        tx_tmp.out_list = [TxOut(-1, Script([])) for _ in range(inputindex)] + \
                          [tx_tmp.out_list[inputindex]]
    if (hash_type & SIGHASH_MASK == SIGHASH_SINGLE or 
        hash_type & SIGHASH_MASK == SIGHASH_NONE):
        # let others update at will
        for i in range(len(tx_tmp.in_list)):
            if i != inputindex:
                tx_tmp.in_list[i].sequence = 0
    #blank out other inputs in case of SIGHASH_ANYONECANPAY
    if (hash_type & SIGHASH_ANYONECANPAY):
        tx_tmp.in_list = [tx_tmp.in_list[inputindex]]
        inputindex = 0
    #blank out input scripts
    for txin in tx_tmp.in_list:
        txin.script = Script([])
    #except the current one that is replaced by the signed part (e.g. from the last OP_CODESEPARATOR)
    # of current_script with signature push_data removed
    # note: only 'optimal' push_data instructions with the same signature are removed
    current_script = Script(filter(lambda instr: instr!=push_data_instruction(sig_param),
                            vm.current_script.signed_part().instructions))
    tx_tmp.in_list[inputindex].script = current_script
    #serialize and append hash type
    enctx = TxSerializer().serialize(tx_tmp) + chr(hash_type) + b"\x00\x00\x00"
    
    #print "enctx:", hexstr(enctx)
    #print "sig:", hexstr(sig)
    #print "pubkey:", hexstr(pubkey_param)
    
    #Get hash 
    hash = doublesha256(enctx)
    #Verify
    key = KEY()
    key.set_pubkey(pubkey_param)
    #ECDSA_verify: 1 = OK, 0=NOK, -1=ERROR
    result = key.verify(hash, sig) == 1
    if not result:
        pass
    #Restore transaction scripts
    #for txin, script in zip(inlist,inscripts):    
    #    txin.script = script
    #transaction.in_list = inlist 
    return (result)
Beispiel #9
0
def checksig(vm, sig_param, pubkey_param):
    transaction, inputindex, unspent_script = vm.checksig_data
    #Hash type is the last byte of the signature
    hash_type, sig = ord(sig_param[-1]), sig_param[:-1]

    # last 5 bits of hash_type : 1=SIGHASH_ALL,2=SIGHASH_NONE, 3=SIGHASH_SINGLE
    # SIGHASH_ANYONECANPAY = 0x80

    # For performance reasons no full copy is made of the transaction
    # although it would be simpler to read.
    # e.g. tx_tmp = copy.deepcopy(transaction)
    # The input scripts are saved and then restored.
    tx_tmp = Tx(transaction.version, [
        TxIn(txin.previous_output, txin.script, txin.sequence)
        for txin in transaction.in_list
    ], [TxOut(txout.value, txout.script) for txout in transaction.out_list],
                transaction.locktime)
    #Save input scripts to restore them later
    #inlist = transaction.in_list
    #outlist = transaction.out_list
    #inscripts = [txin.script for txin in transaction.in_list]
    #TODO: blank out ouputs depending of hash_type (SIGHASH_NONE, SIGHASH_SINGLE)
    if (hash_type & SIGHASH_MASK == SIGHASH_NONE):
        tx_tmp.out_list = []
    if (hash_type & SIGHASH_MASK == SIGHASH_SINGLE):
        if (inputindex > len(tx_tmp.out_list)):
            raise Exception(
                "OP_CHECKSIG: no corresponding output for input %d using SIGHASH_SINGLE "
                % (inputindex))
        #n-1 empty TxOuts + original Txout
        tx_tmp.out_list = [TxOut(-1, Script([])) for _ in range(inputindex)] + \
                          [tx_tmp.out_list[inputindex]]
    if (hash_type & SIGHASH_MASK == SIGHASH_SINGLE
            or hash_type & SIGHASH_MASK == SIGHASH_NONE):
        # let others update at will
        for i in range(len(tx_tmp.in_list)):
            if i != inputindex:
                tx_tmp.in_list[i].sequence = 0
    #blank out other inputs in case of SIGHASH_ANYONECANPAY
    if (hash_type & SIGHASH_ANYONECANPAY):
        tx_tmp.in_list = [tx_tmp.in_list[inputindex]]
        inputindex = 0
    #blank out input scripts
    for txin in tx_tmp.in_list:
        txin.script = Script([])
    #except the current one that is replaced by the signed part (e.g. from the last OP_CODESEPARATOR)
    # of current_script with signature push_data removed
    # note: only 'optimal' push_data instructions with the same signature are removed
    current_script = Script(
        filter(lambda instr: instr != push_data_instruction(sig_param),
               vm.current_script.signed_part().instructions))
    tx_tmp.in_list[inputindex].script = current_script
    #serialize and append hash type
    enctx = TxSerializer().serialize(tx_tmp) + chr(hash_type) + b"\x00\x00\x00"

    #print "enctx:", hexstr(enctx)
    #print "sig:", hexstr(sig)
    #print "pubkey:", hexstr(pubkey_param)

    #Get hash
    hash = doublesha256(enctx)
    #Verify
    key = KEY()
    key.set_pubkey(pubkey_param)
    #ECDSA_verify: 1 = OK, 0=NOK, -1=ERROR
    result = key.verify(hash, sig) == 1
    if not result:
        pass
    #Restore transaction scripts
    #for txin, script in zip(inlist,inscripts):
    #    txin.script = script
    #transaction.in_list = inlist
    return (result)
Beispiel #10
0
 def test_generate(self):
     key = KEY()
     key.generate()
     sig = key.sign("cool")
     self.assertEquals(key.verify("cool", sig), 1)
Beispiel #11
0
 def test_ssl_sign_verify(self):
     key = KEY()
     key.set_secret(decodehexstr("30d1d8d1d243ab41a80a3cc1481a626a137f771a636b2daca06c1f86cdfecffb"))
     sig = key.sign("cool")
     # verify on another key
     key2 = KEY()
     key2.set_pubkey(decodehexstr("030a43196c8bf389c0ce5987a3f4dac57f4ca0d9733c232659717d9404074b4504"))
     self.assertEquals(key2.verify("cool", sig), 1)
     self.assertEquals(key2.verify("coolx", sig), 0)
     self.assertEquals(key2.verify("cool", decodehexstr("3045022100ea3cbfca49123ecdcc419cf3277597307dca70b548ca1d4312f39186b043e86802201057af5c3889b65a59333d4f23bea915e76c2c26606dd35c57e00adf416ca31600")), 0)
Beispiel #12
0
 def test_ssl_get_pubkey(self):
     key = KEY()
     key.set_secret(decodehexstr("30d1d8d1d243ab41a80a3cc1481a626a137f771a636b2daca06c1f86cdfecffb"), True)
     self.assertEquals(hexstr(key.get_pubkey()), "030a43196c8bf389c0ce5987a3f4dac57f4ca0d9733c232659717d9404074b4504")
Beispiel #13
0
 def test_ssl_set_secret(self):
     key = KEY()
     key.set_secret(decodehexstr("30d1d8d1d243ab41a80a3cc1481a626a137f771a636b2daca06c1f86cdfecffb"), True)
     self.assertEquals(hexstr(key.get_privkey()), "3081d3020101042030d1d8d1d243ab41a80a3cc1481a626a137f771a636b2daca06c1f86cdfecffba08185308182020101302c06072a8648ce3d0101022100fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f300604010004010704210279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798022100fffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364141020101a124032200030a43196c8bf389c0ce5987a3f4dac57f4ca0d9733c232659717d9404074b4504")
Beispiel #14
0
 def test_set_pubkey(self):
     sig = decodehexstr("3046022100b2a3e589f5ccd266b0b3ca34ec28a8730c34f16e7de2889f91fcb63824cb0da9022100b04e7b58680c55bb3cd5394c0feb5cfad98ba3695802e4fab61308f18d474031")
     key2 = KEY()
     key2.set_pubkey(decodehexstr("030a43196c8bf389c0ce5987a3f4dac57f4ca0d9733c232659717d9404074b4504"))
     self.assertEquals(key2.verify("cool", sig), 1)