Skip to content

Commit ac622ca

Browse files
committed
New encrypted wallet file header:
- the file is encrypted with a master key - the master key is encrypted with one or several passwords - passwords can be added to or removed from the list - a hmac of the file is written at the beginning of the file - passwords can be checked/updated without having to read/write the whole file - the GUI assumes a single password - partial writes: encrypted blobs are appended at the end of the file each blob is prefixed by its length can recover from incomplete write: hmac is updated after appending
1 parent cb7e550 commit ac622ca

File tree

7 files changed

+325
-114
lines changed

7 files changed

+325
-114
lines changed

electrum/crypto.py

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -134,9 +134,10 @@ def strip_PKCS7_padding(data: bytes) -> bytes:
134134
return data[0:-padlen]
135135

136136

137-
def aes_encrypt_with_iv(key: bytes, iv: bytes, data: bytes) -> bytes:
137+
def aes_encrypt_with_iv(key: bytes, iv: bytes, data: bytes, append_pkcs7=True) -> bytes:
138138
assert_bytes(key, iv, data)
139-
data = append_PKCS7_padding(data)
139+
if append_pkcs7:
140+
data = append_PKCS7_padding(data)
140141
if HAS_CRYPTODOME:
141142
e = CD_AES.new(key, CD_AES.MODE_CBC, iv).encrypt(data)
142143
elif HAS_CRYPTOGRAPHY:
@@ -152,7 +153,7 @@ def aes_encrypt_with_iv(key: bytes, iv: bytes, data: bytes) -> bytes:
152153
return e
153154

154155

155-
def aes_decrypt_with_iv(key: bytes, iv: bytes, data: bytes) -> bytes:
156+
def aes_decrypt_with_iv(key: bytes, iv: bytes, data: bytes, strip_pkcs7=True) -> bytes:
156157
assert_bytes(key, iv, data)
157158
if HAS_CRYPTODOME:
158159
cipher = CD_AES.new(key, CD_AES.MODE_CBC, iv)
@@ -168,9 +169,11 @@ def aes_decrypt_with_iv(key: bytes, iv: bytes, data: bytes) -> bytes:
168169
else:
169170
raise Exception("no AES backend found")
170171
try:
171-
return strip_PKCS7_padding(data)
172+
if strip_pkcs7:
173+
data = strip_PKCS7_padding(data)
172174
except InvalidPadding:
173175
raise InvalidPassword()
176+
return data
174177

175178

176179
def EncodeAES_bytes(secret: bytes, msg: bytes) -> bytes:

electrum/gui/qt/main_window.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1955,14 +1955,14 @@ def update_buttons_on_seed(self):
19551955
self.password_button.setVisible(self.wallet.may_have_password())
19561956

19571957
def change_password_dialog(self):
1958-
from electrum.storage import StorageEncryptionVersion
1959-
if StorageEncryptionVersion.XPUB_PASSWORD in self.wallet.get_available_storage_encryption_versions():
1958+
from electrum.storage import PasswordType
1959+
if PasswordType.XPUB in self.wallet.get_available_storage_encryption_versions():
19601960
from .password_dialog import ChangePasswordDialogForHW
19611961
d = ChangePasswordDialogForHW(self, self.wallet)
19621962
ok, old_password, new_password, encrypt_with_xpub = d.run()
19631963
if not ok:
19641964
return
1965-
has_xpub_encryption = self.wallet.storage.get_encryption_version() == StorageEncryptionVersion.XPUB_PASSWORD
1965+
has_xpub_encryption = self.wallet.storage.is_encrypted_with_hw_device()
19661966
def on_password(hw_dev_pw):
19671967
self._update_wallet_password(
19681968
old_password = hw_dev_pw if has_xpub_encryption else old_password,

0 commit comments

Comments
 (0)