Skip to content

Commit

Permalink
Merge pull request #288 from selfcustody/bugfixes
Browse files Browse the repository at this point in the history
Bugfixes
  • Loading branch information
odudex authored Nov 20, 2023
2 parents 26e2adb + dd4a228 commit a304206
Show file tree
Hide file tree
Showing 18 changed files with 1,633 additions and 1,421 deletions.
9 changes: 9 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,12 @@
# Version 23.09.1 - November 18, 2023
This release contain bugfixes:

Encrypted Mnemonic QR codes would fail to decrypt if PBKDF2 iterations settings was changed to non multiple of 10,000.

QR code transcription helpers that highlight regions could crash on edges of some QR code sizes.

Address navigation "previous" menu option wouldn't show correct number.

# Version 23.09.0 - September 12, 2023
After a long year, new features are finally coming out of beta and making their way into a stable release. Also @jreesun appointed @odudex as the new lead maintainer of the project.

Expand Down
2 changes: 2 additions & 0 deletions docs/getting-started/settings.en.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,8 @@ When you enter a encryption key it is not directly used to encrypt your data. As

If you increase this value it will make the encryption harder, at the cost of taking longer to encrypt and decrypt your mnemonics

Values must be multiple of 10,000. This was done to save data space on QR codes, also, intermediary values wouldn't significantly affect safety or computation time.

<div style="clear: both"></div>

#### Encryption Mode
Expand Down
1 change: 1 addition & 0 deletions i18n/translations/de-DE.json
Original file line number Diff line number Diff line change
Expand Up @@ -225,6 +225,7 @@
"Use camera's entropy to create a new mnemonic": "Verwende die Entropie der Kamera, um eine neue Mnemonic zu erstellen",
"Used: ": "Belegt: ",
"Value %s out of range: [%s, %s]": "Wert %S außerhalb des Bereichs: [ %s, %s]",
"Value must be multiple of %s": "Der Wert muss ein Vielfaches von %s sein",
"Via Camera": "Via Kamera",
"Via D20": "Via D20",
"Via D6": "Via D6",
Expand Down
1 change: 1 addition & 0 deletions i18n/translations/es-MX.json
Original file line number Diff line number Diff line change
Expand Up @@ -225,6 +225,7 @@
"Use camera's entropy to create a new mnemonic": "Use la entropía de la cámara para crear una nueva mnemónica",
"Used: ": "Usado: ",
"Value %s out of range: [%s, %s]": "Valor %s fuera del rango: [ %s, %s]",
"Value must be multiple of %s": "El valor debe ser múltiple de %s",
"Via Camera": "Vía cámara",
"Via D20": "Via D20",
"Via D6": "Via D6",
Expand Down
7 changes: 4 additions & 3 deletions i18n/translations/fr-FR.json
Original file line number Diff line number Diff line change
Expand Up @@ -126,7 +126,7 @@
"Location": "Emplacement",
"Log Level": "Niveau de journalisation",
"Logging": "Enregistrement",
"Maximum length exceeded (%s)": "Longueur maximale dépassée (% s)",
"Maximum length exceeded (%s)": "Longueur maximale dépassée (%s)",
"Message": "Message",
"Missing signature file": "Fichier de signature manquant",
"Mnemonic": "Mnémonique",
Expand Down Expand Up @@ -177,7 +177,7 @@
"SD card not detected": "Carte SD non détectée",
"SD card not detected.": "Carte SD non détectée.",
"SHA256 of rolls:\n\n%s": "SHA256 de rouleaux:\n\n%s",
"SHA256 of snapshot:\n\n%s": "Sha256 de Snapshot:\n\n% s",
"SHA256 of snapshot:\n\n%s": "Sha256 de Snapshot:\n\n%s",
"SHA256:\n%s": "SHA256:\n%s",
"Save to SD card?": "Enregistrer sur la carte SD ?",
"Saved to SD card:\n%s": "Enregistré sur la carte SD :\n%s",
Expand Down Expand Up @@ -224,7 +224,8 @@
"Use a black background surface.": "Utilisez une surface de fond noire.",
"Use camera's entropy to create a new mnemonic": "Utilisez l'entropie de la caméra pour créer un nouveau mnémonique",
"Used: ": "Utilisé: ",
"Value %s out of range: [%s, %s]": "Valeur% s hors de portée: [% s,% s]",
"Value %s out of range: [%s, %s]": "Valeur %s hors de portée: [%s, %s]",
"Value must be multiple of %s": "La valeur doit être multiple de %s",
"Via Camera": "Par caméra",
"Via D20": "Via D20",
"Via D6": "Via D6",
Expand Down
1 change: 1 addition & 0 deletions i18n/translations/nl-NL.json
Original file line number Diff line number Diff line change
Expand Up @@ -225,6 +225,7 @@
"Use camera's entropy to create a new mnemonic": "Gebruik de camera als entropie voor het aanmaken van een nieuwe geheugensteun",
"Used: ": "Gebruikt: ",
"Value %s out of range: [%s, %s]": "Waarde %s is buiten bereik: [%s, %s]",
"Value must be multiple of %s": "Waarde moet meerdere van %s zijn",
"Via Camera": "Via camera",
"Via D20": "Via D20",
"Via D6": "Via D6",
Expand Down
1 change: 1 addition & 0 deletions i18n/translations/pt-BR.json
Original file line number Diff line number Diff line change
Expand Up @@ -225,6 +225,7 @@
"Use camera's entropy to create a new mnemonic": "Use a entropia da câmera para criar um novo mnemônico",
"Used: ": "Usado: ",
"Value %s out of range: [%s, %s]": "Valor %s fora do alcance: [ %s, %s]",
"Value must be multiple of %s": "O valor deve ser múltiplo de %s",
"Via Camera": "Pela Câmera",
"Via D20": "Via D20",
"Via D6": "Via D6",
Expand Down
1 change: 1 addition & 0 deletions i18n/translations/vi-VN.json
Original file line number Diff line number Diff line change
Expand Up @@ -225,6 +225,7 @@
"Use camera's entropy to create a new mnemonic": "Sử dụng entropy của máy ảnh để tạo ra một bản ghi âm mới",
"Used: ": "Đã sử dụng: ",
"Value %s out of range: [%s, %s]": "Giá trị %s ngoài phạm vi: [ %s, %s]",
"Value must be multiple of %s": "Giá trị phải là bội của %s",
"Via Camera": "Qua máy ảnh",
"Via D20": "Qua D20",
"Via D6": "Qua D6",
Expand Down
2 changes: 1 addition & 1 deletion pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@

[tool.poetry]
name = "krux"
version = "23.09.0"
version = "23.09.1"
description = "Open-source signing device firmware for Bitcoin"
authors = ["Jeff S <jeffreesun@protonmail.com>"]

Expand Down
21 changes: 18 additions & 3 deletions src/krux/encryption.py
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,8 @@
"AES-CBC": PBKDF2_HMAC_CBC,
}

QR_CODE_ITER_MULTIPLE = 10000


class AESCipher:
"""Helper for AES encrypt/decrypt"""
Expand Down Expand Up @@ -214,12 +216,22 @@ def create(self, key, mnemonic_id, mnemonic, i_vector=None):
"""Joins necessary data and creates encrypted mnemonic QR codes"""
name_lenght = len(mnemonic_id.encode())
version = VERSION_NUMBER[Settings().encryption.version]
key_iterations = Settings().encryption.pbkdf2_iterations
ten_k_iterations = Settings().encryption.pbkdf2_iterations

# Divide iterations by a Multiple(10,000) to save space
ten_k_iterations //= QR_CODE_ITER_MULTIPLE

# Add public data bytes
qr_code_data = name_lenght.to_bytes(1, "big")
qr_code_data += mnemonic_id.encode()
qr_code_data += version.to_bytes(1, "big")
qr_code_data += (key_iterations // 10000).to_bytes(3, "big")
encryptor = AESCipher(key, mnemonic_id, Settings().encryption.pbkdf2_iterations)
qr_code_data += ten_k_iterations.to_bytes(3, "big")

# Restore the iterations value assuring is a multiple of 10,000
ten_k_iterations *= QR_CODE_ITER_MULTIPLE

# Encrypted data
encryptor = AESCipher(key, mnemonic_id, ten_k_iterations)
mode = VERSION_MODE[Settings().encryption.version]
words = mnemonic.split(" ")
checksum_bits = 8 if len(words) == 24 else 4
Expand All @@ -231,7 +243,10 @@ def create(self, key, mnemonic_id, mnemonic, i_vector=None):
bytes_to_encrypt += hashlib.sha256(bytes_to_encrypt).digest()[:16]
base64_encrypted = encryptor.encrypt(bytes_to_encrypt, mode, i_vector)
bytes_encrypted = base_decode(base64_encrypted, 64)

# Add encrypted data bytes
qr_code_data += bytes_encrypted

return qr_code_data

def public_data(self, data):
Expand Down
2 changes: 1 addition & 1 deletion src/krux/metadata.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,5 +19,5 @@
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
# THE SOFTWARE.
VERSION = "23.09.0"
VERSION = "23.09.1"
SIGNER_PUBKEY = "03339e883157e45891e61ca9df4cd3bb895ef32d475b8e793559ea10a36766689b"
3 changes: 2 additions & 1 deletion src/krux/pages/addresses.py
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,8 @@ def list_address_type(self, addr_type=0):
if num_checked + 1 > LIST_ADDRESS_QTD:
items.append(
(
"%d..%d" % (num_checked - LIST_ADDRESS_QTD, num_checked),
"%d..%d"
% (num_checked - LIST_ADDRESS_QTD + 1, num_checked),
lambda: MENU_EXIT,
)
)
Expand Down
72 changes: 42 additions & 30 deletions src/krux/pages/qr_view.py
Original file line number Diff line number Diff line change
Expand Up @@ -111,24 +111,27 @@ def highlight_qr_region(self, code, region=(0, 0, 0, 0), zoom=False):
offset = (self.ctx.display.width() - qr_width) // 2
for y in range(reg_height): # vertical blocks loop
for x in range(reg_width): # horizontal blocks loop
xy_index = (reg_y + y + 1) * (size + 1)
xy_index += reg_x + x + 1
if code[xy_index] == "0":
self.ctx.display.fill_rectangle(
offset + (offset_x + x) * scale,
offset + (offset_y + y) * scale,
scale,
scale,
WHITE,
)
else:
self.ctx.display.fill_rectangle(
offset + (offset_x + x) * scale,
offset + (offset_y + y) * scale,
scale,
scale,
BLACK,
)
y_index = reg_y + y + 1
x_index = reg_x + x + 1
xy_index = y_index * (size + 1)
xy_index += x_index
if y_index < size and x_index < size:
if code[xy_index] == "0":
self.ctx.display.fill_rectangle(
offset + (offset_x + x) * scale,
offset + (offset_y + y) * scale,
scale,
scale,
WHITE,
)
else:
self.ctx.display.fill_rectangle(
offset + (offset_x + x) * scale,
offset + (offset_y + y) * scale,
scale,
scale,
BLACK,
)

def _region_legend(self, row, column):
region_char = chr(65 + row)
Expand Down Expand Up @@ -235,29 +238,38 @@ def draw_grided_qr(self, mode):
),
)
line_offset = grid_pad * row * self.region_size
colunm_offset = grid_pad * column * self.region_size
column_offset = grid_pad * column * self.region_size
draw_limit = grid_offset + self.qr_size * grid_pad
for i in range(self.region_size + 1):
x_position = grid_offset + colunm_offset
x_lenght = self.region_size * grid_pad + 1
display_transpose = x_position + x_lenght - self.ctx.display.width()
if display_transpose > 0:
x_lenght -= display_transpose
x_position = grid_offset + column_offset
x_length = self.region_size * grid_pad + 1
transposed = x_position + x_length - draw_limit
if transposed > 0:
x_length -= transposed
y_position = grid_offset + i * grid_pad + line_offset
if y_position > draw_limit:
break
self.ctx.display.fill_rectangle(
x_position,
grid_offset + i * grid_pad + line_offset,
x_lenght,
y_position,
x_length,
grid_size,
theme.highlight_color,
)
for i in range(self.region_size + 1):
x_position = grid_offset + i * grid_pad + colunm_offset
if x_position > self.ctx.display.width():
x_position = grid_offset + i * grid_pad + column_offset
if x_position > draw_limit:
break
y_position = grid_offset + line_offset
y_length = self.region_size * grid_pad + 1
transposed = y_position + y_length - draw_limit
if transposed > 0:
y_length -= transposed
self.ctx.display.fill_rectangle(
x_position,
grid_offset + line_offset,
y_position,
grid_size,
self.region_size * grid_pad + 1,
y_length,
theme.highlight_color,
)
self._region_legend(row, column)
Expand Down
14 changes: 12 additions & 2 deletions src/krux/pages/settings_page.py
Original file line number Diff line number Diff line change
Expand Up @@ -35,10 +35,11 @@
BitcoinSettings,
TouchSettings,
EncoderSettings,
t,
)
from ..input import BUTTON_ENTER, BUTTON_PAGE, BUTTON_PAGE_PREV, BUTTON_TOUCH
from ..krux_settings import t
from ..sd_card import SDHandler
from ..encryption import QR_CODE_ITER_MULTIPLE
from ..display import FLASH_MSG_TIME
from . import (
Page,
Expand Down Expand Up @@ -334,7 +335,16 @@ def number_setting(self, settings_namespace, setting):

new_value = setting.numtype(new_value)
if setting.value_range[0] <= new_value <= setting.value_range[1]:
setting.__set__(settings_namespace, new_value)
if (
setting.attr == "pbkdf2_iterations"
and (new_value % QR_CODE_ITER_MULTIPLE) != 0
):
self.ctx.display.flash_text(
t("Value must be multiple of %s") % QR_CODE_ITER_MULTIPLE,
theme.error_color,
)
else:
setting.__set__(settings_namespace, new_value)
else:
self.ctx.display.flash_text(
t("Value %s out of range: [%s, %s]")
Expand Down
Loading

0 comments on commit a304206

Please sign in to comment.