crypto.Crypto: new encrypt_aes_ctr() method

This commit is contained in:
The MMGen Project 2026-05-21 12:09:33 +00:00
commit 3d8e98f31e
Signed by: mmgen
GPG key ID: 3F8B1861E32B7DA2
5 changed files with 27 additions and 35 deletions

View file

@ -14,7 +14,7 @@ altcoin.util: various altcoin-related utilities
from ..util import die
def decrypt_keystore(data, passwd, *, mac_algo=None, mac_params={}):
def decrypt_keystore(cfg, data, passwd, *, mac_algo=None, mac_params={}):
"""
Decrypt the encrypted data in a cross-chain keystore
Returns the decrypted data as a bytestring
@ -70,12 +70,8 @@ def decrypt_keystore(data, passwd, *, mac_algo=None, mac_params={}):
die(1, 'incorrect password')
# Decrypt data:
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
from cryptography.hazmat.backends import default_backend
cipher_len = int(cipher.split('-')[1]) // 8
c = Cipher(
algorithms.AES(hashed_pw[:cipher_len]),
modes.CTR(bytes.fromhex(cdata['cipherparams']['iv'])),
backend = default_backend())
encryptor = c.encryptor()
return encryptor.update(bytes.fromhex(cdata['ciphertext'])) + encryptor.finalize()
from ..crypto import Crypto
return Crypto(cfg).encrypt_aes_ctr(
hashed_pw[:int(cipher.split('-')[1]) // 8],
bytes.fromhex(cdata['cipherparams']['iv']),
bytes.fromhex(cdata['ciphertext']))

View file

@ -68,6 +68,16 @@ class Crypto:
self.cfg = cfg
self.util = cfg._util
@staticmethod
def get_aes_ctr(key, iv):
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
from cryptography.hazmat.backends import default_backend
return Cipher(algorithms.AES(key), modes.CTR(iv), backend=default_backend()).encryptor()
def encrypt_aes_ctr(self, key, iv, data):
encryptor = self.get_aes_ctr(key, iv)
return encryptor.update(data) + encryptor.finalize()
def get_hash_params(self, hash_preset):
if hash_preset in self.hash_presets:
return self.hash_presets[hash_preset] # N, r, p
@ -126,20 +136,14 @@ class Crypto:
verify = True,
silent = False):
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
from cryptography.hazmat.backends import default_backend
if not silent:
self.util.vmsg(f'Encrypting {desc}')
c = Cipher(algorithms.AES(key), modes.CTR(iv), backend=default_backend())
encryptor = c.encryptor()
enc_data = encryptor.update(data) + encryptor.finalize()
enc_data = self.encrypt_aes_ctr(key, iv, data)
if verify:
self.util.vmsg_r(f'Performing a test decryption of the {desc}...')
c = Cipher(algorithms.AES(key), modes.CTR(iv), backend=default_backend())
encryptor = c.encryptor()
dec_data = encryptor.update(enc_data) + encryptor.finalize()
if dec_data != data:
if self.encrypt_aes_ctr(key, iv, enc_data) != data:
die(2, f'ERROR.\nDecrypted {desc} doesn’t match original {desc}')
if not silent:
self.util.vmsg('done')
@ -154,12 +158,9 @@ class Crypto:
iv = aesctr_dfl_iv,
desc = 'data'):
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
from cryptography.hazmat.backends import default_backend
self.util.vmsg_r(f'Decrypting {desc} with key...')
c = Cipher(algorithms.AES(key), modes.CTR(iv), backend=default_backend())
encryptor = c.encryptor()
return encryptor.update(enc_data) + encryptor.finalize()
return self.encrypt_aes_ctr(key, iv, enc_data)
def scrypt_hash_passphrase(
self,

View file

@ -27,6 +27,7 @@ def decrypt_geth_keystore(cfg, wallet_fn, passwd, *, check_addr=True):
from ...altcoin.util import decrypt_keystore
key = decrypt_keystore(
cfg,
wallet_data,
passwd,
mac_algo = get_keccak())

View file

@ -94,15 +94,12 @@ class tool_cmd(tool_cmd_base):
"""
from threading import Thread
from queue import Queue
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
from cryptography.hazmat.backends import default_backend
from ..util2 import parse_bytespec
from ..crypto import Crypto
def encrypt_worker():
ctr_init_val = os.urandom(Crypto.aesctr_iv_len)
c = Cipher(algorithms.AES(key), modes.CTR(ctr_init_val), backend=default_backend())
encryptor = c.encryptor()
encryptor = Crypto(self.cfg).get_aes_ctr(key, os.urandom(Crypto.aesctr_iv_len))
while True:
q2.put(encryptor.update(q1.get()))
q1.task_done()
@ -161,7 +158,7 @@ class tool_cmd(tool_cmd_base):
with open(wallet_file) as fh:
data = json.loads(fh.read())
from ..altcoin.util import decrypt_keystore
ret = decrypt_keystore(data[0]['keystore'], passwd)
ret = decrypt_keystore(self.cfg, data[0]['keystore'], passwd)
return ret.hex() if output_hex else ret
def decrypt_geth_keystore(self, wallet_file: str, *, check_addr=True):

View file

@ -75,11 +75,8 @@ class unit_tests:
return False
def cryptography(self, name, ut):
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
from cryptography.hazmat.backends import default_backend
c = Cipher(algorithms.AES(b'deadbeef'*4), modes.CTR(b'deadbeef'*2), backend=default_backend())
encryptor = c.encryptor()
encryptor.update(b'foo') + encryptor.finalize()
from mmgen.crypto import Crypto
Crypto(cfg).encrypt_aes_ctr(b'deadbeef' * 4, b'deadbeef' * 2, b'foo')
return True
def ecdsa(self, name, ut):