mirror of
https://github.com/trezor/trezor-firmware.git
synced 2024-12-16 11:28:14 +00:00
xmr: step_09_sign - manual MgSig serialization
This commit is contained in:
parent
90fd0bb67a
commit
a462ea35ce
@ -10,7 +10,8 @@ from .state import State
|
|||||||
|
|
||||||
from apps.monero.layout import confirms
|
from apps.monero.layout import confirms
|
||||||
from apps.monero.signing import RctType
|
from apps.monero.signing import RctType
|
||||||
from apps.monero.xmr import crypto, serialize
|
from apps.monero.xmr import crypto
|
||||||
|
from apps.monero.xmr.serialize import int_serialize
|
||||||
|
|
||||||
if False:
|
if False:
|
||||||
from trezor.messages.MoneroTransactionSourceEntry import (
|
from trezor.messages.MoneroTransactionSourceEntry import (
|
||||||
@ -66,7 +67,7 @@ async def sign_input(
|
|||||||
raise ValueError("HMAC is not correct")
|
raise ValueError("HMAC is not correct")
|
||||||
|
|
||||||
gc.collect()
|
gc.collect()
|
||||||
state.mem_trace(1)
|
state.mem_trace(1, True)
|
||||||
|
|
||||||
if state.rct_type == RctType.Simple:
|
if state.rct_type == RctType.Simple:
|
||||||
# both pseudo_out and its mask were offloaded so we need to
|
# both pseudo_out and its mask were offloaded so we need to
|
||||||
@ -78,8 +79,7 @@ async def sign_input(
|
|||||||
if not crypto.ct_equals(pseudo_out_hmac_comp, pseudo_out_hmac):
|
if not crypto.ct_equals(pseudo_out_hmac_comp, pseudo_out_hmac):
|
||||||
raise ValueError("HMAC is not correct")
|
raise ValueError("HMAC is not correct")
|
||||||
|
|
||||||
gc.collect()
|
state.mem_trace(2, True)
|
||||||
state.mem_trace(2)
|
|
||||||
|
|
||||||
from apps.monero.xmr.crypto import chacha_poly
|
from apps.monero.xmr.crypto import chacha_poly
|
||||||
|
|
||||||
@ -102,8 +102,7 @@ async def sign_input(
|
|||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
gc.collect()
|
state.mem_trace(3, True)
|
||||||
state.mem_trace(3)
|
|
||||||
|
|
||||||
# Basic setup, sanity check
|
# Basic setup, sanity check
|
||||||
index = src_entr.real_output
|
index = src_entr.real_output
|
||||||
@ -126,13 +125,15 @@ async def sign_input(
|
|||||||
"Real source entry's mask does not equal spend key's",
|
"Real source entry's mask does not equal spend key's",
|
||||||
)
|
)
|
||||||
|
|
||||||
gc.collect()
|
state.mem_trace(4, True)
|
||||||
state.mem_trace(4)
|
mg_buff = bytearray(_mg_size(len(src_entr.outputs)))
|
||||||
|
|
||||||
from apps.monero.xmr import mlsag
|
from apps.monero.xmr import mlsag
|
||||||
|
|
||||||
if state.rct_type == RctType.Simple:
|
if state.rct_type == RctType.Simple:
|
||||||
ring_pubkeys = [x.key for x in src_entr.outputs]
|
ring_pubkeys = [x.key for x in src_entr.outputs]
|
||||||
|
src_entr = None
|
||||||
|
|
||||||
mg = mlsag.generate_mlsag_simple(
|
mg = mlsag.generate_mlsag_simple(
|
||||||
state.full_message,
|
state.full_message,
|
||||||
ring_pubkeys,
|
ring_pubkeys,
|
||||||
@ -143,10 +144,14 @@ async def sign_input(
|
|||||||
index,
|
index,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
del (ring_pubkeys, input_secret_key, pseudo_out_alpha, pseudo_out_c)
|
||||||
|
|
||||||
else:
|
else:
|
||||||
# Full RingCt, only one input
|
# Full RingCt, only one input
|
||||||
txn_fee_key = crypto.scalarmult_h(state.fee)
|
txn_fee_key = crypto.scalarmult_h(state.fee)
|
||||||
ring_pubkeys = [[x.key] for x in src_entr.outputs]
|
ring_pubkeys = [[x.key] for x in src_entr.outputs]
|
||||||
|
src_entr = None
|
||||||
|
|
||||||
mg = mlsag.generate_mlsag_full(
|
mg = mlsag.generate_mlsag_full(
|
||||||
state.full_message,
|
state.full_message,
|
||||||
ring_pubkeys,
|
ring_pubkeys,
|
||||||
@ -158,35 +163,70 @@ async def sign_input(
|
|||||||
txn_fee_key,
|
txn_fee_key,
|
||||||
)
|
)
|
||||||
|
|
||||||
gc.collect()
|
del (ring_pubkeys, input_secret_key, txn_fee_key)
|
||||||
state.mem_trace(5)
|
|
||||||
|
del (mlsag, src_entr)
|
||||||
|
state.mem_trace(5, True)
|
||||||
|
|
||||||
# Encode
|
# Encode
|
||||||
mgs = _recode_msg([mg])
|
mg_buffer = _mg_serialize(mg, mg_buff)
|
||||||
|
state.mem_trace(6, True)
|
||||||
gc.collect()
|
|
||||||
state.mem_trace(6)
|
|
||||||
|
|
||||||
from trezor.messages.MoneroTransactionSignInputAck import (
|
from trezor.messages.MoneroTransactionSignInputAck import (
|
||||||
MoneroTransactionSignInputAck,
|
MoneroTransactionSignInputAck,
|
||||||
)
|
)
|
||||||
|
|
||||||
return MoneroTransactionSignInputAck(
|
return MoneroTransactionSignInputAck(signature=mg_buffer)
|
||||||
signature=serialize.dump_msg_gc(mgs[0], preallocate=488)
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def _recode_msg(mgs):
|
def _mg_size(num_outs):
|
||||||
"""
|
"""
|
||||||
Recodes MGs signatures from raw forms to bytearrays so it works with serialization
|
Computes size of the MgSig
|
||||||
|
:param num_outs:
|
||||||
|
:return:
|
||||||
"""
|
"""
|
||||||
for idx in range(len(mgs)):
|
size = 32 # cc
|
||||||
mgs[idx].cc = crypto.encodeint(mgs[idx].cc)
|
mg_cols = num_outs
|
||||||
if hasattr(mgs[idx], "II") and mgs[idx].II:
|
mg_rows = 2
|
||||||
for i in range(len(mgs[idx].II)):
|
cols_b_size = int_serialize.uvarint_size(mg_cols)
|
||||||
mgs[idx].II[i] = crypto.encodepoint(mgs[idx].II[i])
|
rows_b_size = 1
|
||||||
|
size += cols_b_size + mg_cols * (rows_b_size + mg_rows * 32)
|
||||||
|
return size
|
||||||
|
|
||||||
for i in range(len(mgs[idx].ss)):
|
|
||||||
for j in range(len(mgs[idx].ss[i])):
|
def _mg_serialize(mg, buff):
|
||||||
mgs[idx].ss[i][j] = crypto.encodeint(mgs[idx].ss[i][j])
|
"""
|
||||||
return mgs
|
Serializes MgSig structure: (("ss", KeyM), ("cc", ECKey))
|
||||||
|
:param mg:
|
||||||
|
:return:
|
||||||
|
"""
|
||||||
|
size = len(buff)
|
||||||
|
mg_cols = len(mg.ss)
|
||||||
|
mg_rows = len(mg.ss[0])
|
||||||
|
cols_b_size = int_serialize.uvarint_size(mg_cols)
|
||||||
|
rows_b_size = int_serialize.uvarint_size(mg_rows)
|
||||||
|
offset = 0
|
||||||
|
|
||||||
|
int_serialize.dump_uvarint_b_into(mg_cols, buff, offset)
|
||||||
|
offset += cols_b_size
|
||||||
|
|
||||||
|
for i in range(mg_cols):
|
||||||
|
utils.ensure(len(mg.ss[i]) == mg_rows, "Irregular matrix shape")
|
||||||
|
|
||||||
|
int_serialize.dump_uvarint_b_into(mg_rows, buff, offset)
|
||||||
|
offset += rows_b_size
|
||||||
|
|
||||||
|
for j in range(mg_rows):
|
||||||
|
crypto.encodeint_into(buff, mg.ss[i][j], offset)
|
||||||
|
offset += 32
|
||||||
|
|
||||||
|
mg.ss[i] = None
|
||||||
|
gc.collect()
|
||||||
|
|
||||||
|
mg.ss = None
|
||||||
|
|
||||||
|
crypto.encodeint_into(buff, mg.cc, offset)
|
||||||
|
offset += 32
|
||||||
|
|
||||||
|
utils.ensure(offset == size, "Invalid mg size computation")
|
||||||
|
return buff
|
||||||
|
Loading…
Reference in New Issue
Block a user