Skip to content

Commit 8b26c92

Browse files
committed
sign transaction with chain hash at the end
1 parent e72b26b commit 8b26c92

10 files changed

Lines changed: 69 additions & 35 deletions

File tree

app/src/common/actions.h

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,9 @@
2424
#include "tx.h"
2525
#include "zxerror.h"
2626

27+
#include "common_txdef.h"
28+
#include "borsh.h"
29+
2730
extern uint16_t action_addrResponseLen;
2831

2932
__Z_INLINE zxerr_t app_fill_address() {
@@ -41,8 +44,8 @@ __Z_INLINE zxerr_t app_fill_address() {
4144
}
4245

4346
__Z_INLINE void app_sign() {
44-
const uint8_t *message = tx_get_buffer();
45-
const uint16_t messageLength = tx_get_buffer_length();
47+
const uint8_t *message = get_txn_raw();
48+
const uint16_t messageLength = get_txn_len() + CX_SHA256_SIZE;
4649

4750
const zxerr_t err = crypto_sign(G_io_apdu_buffer, IO_APDU_BUFFER_SIZE - 3, message, messageLength);
4851

app/src/common/tx.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -112,3 +112,8 @@ zxerr_t tx_getItem(int8_t displayIdx, char *outKey, uint16_t outKeyLen, char *ou
112112

113113
return zxerr_ok;
114114
}
115+
116+
const uint8_t *get_txn_raw() { return tx_obj.unsigned_transaction_raw.buffer.ptr; }
117+
118+
uint16_t get_txn_len() { return tx_obj.unsigned_transaction_raw.buffer.len; }
119+

app/src/common/tx.h

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,3 +50,11 @@ zxerr_t tx_getNumItems(uint8_t *num_items);
5050
/// Gets an specific item from the transaction (including paging)
5151
zxerr_t tx_getItem(int8_t displayIdx, char *outKey, uint16_t outKeyLen, char *outValue, uint16_t outValueLen,
5252
uint8_t pageIdx, uint8_t *pageCount);
53+
54+
/// Get the transaction raw bytes
55+
/// \return
56+
const uint8_t *get_txn_raw();
57+
58+
/// Get the transaction length
59+
/// \return
60+
uint16_t get_txn_len();

app/src/parser_impl.c

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,10 +19,21 @@
1919
#include "schema_reader.h"
2020
#include "unsigned_transaction_reader.h"
2121
#include "zxerror.h"
22+
#include "borsh.h"
2223

2324
parser_error_t _read(parser_context_t *c, parser_tx_t *v) {
2425
CHECK_ERROR(merkle_proofs_read(c, v));
26+
CHECK_ERROR(schema_extra_data_read(c, v));
2527
CHECK_ERROR(unsigned_transaction_read(c, v));
28+
CHECK_ERROR(schema_chain_hash_read(c, v));
29+
30+
// TODO: check that we have consumxed all data
31+
if (c->offset != c->buffer.len) {
32+
print_string("Failed to parse unsigned transaction\n");
33+
return parser_unexpected_error;
34+
} else {
35+
print_string("Successfully parsed unsigned transaction\n");
36+
}
2637

2738
return parser_ok;
2839
}

app/src/schema_reader.c

Lines changed: 16 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -858,8 +858,7 @@ parser_error_t compute_chain_hash(parser_tx_t *txObj) {
858858
return parser_ok;
859859
}
860860

861-
// | borsh(leaves_data) | borsh(indices_leaves) | borsh(lemmas) | borsh(tree_size) | borsh(root_hash) | borsh(root_indexes) |
862-
// borsh(chain_data) | borsh(extra_metadata_hash) | borsh(chain_hash)
861+
// | borsh(leaves_data) | borsh(indices_leaves) | borsh(lemmas) | borsh(tree_size) | borsh(root_hash) | borsh(chain_hash)
863862
parser_error_t merkle_proofs_read(parser_context_t *ctx, parser_tx_t *txObj) {
864863
CHECK_INPUT(ctx);
865864
CHECK_INPUT(txObj);
@@ -913,10 +912,20 @@ parser_error_t merkle_proofs_read(parser_context_t *ctx, parser_tx_t *txObj) {
913912

914913
// read root_hash
915914
txObj->merkle_proofs.root_hash.ptr = ctx->buffer.ptr + ctx->offset;
916-
txObj->merkle_proofs.root_hash.len = 32;
915+
txObj->merkle_proofs.root_hash.len = CX_SHA256_SIZE;
917916
CTX_CHECK_AND_ADVANCE(ctx, txObj->merkle_proofs.root_hash.len);
918917
print_buffer(&txObj->merkle_proofs.root_hash, "root_hash");
919918

919+
CHECK_ERROR(verify_merkle_proofs(&txObj->merkle_proofs));
920+
921+
return parser_ok;
922+
}
923+
924+
// borsh(root_indexes) | borsh(chain_data) | borsh(extra_metadata_hash)
925+
parser_error_t schema_extra_data_read(parser_context_t *ctx, parser_tx_t *txObj) {
926+
CHECK_INPUT(ctx);
927+
CHECK_INPUT(txObj);
928+
920929
// read root_type_indices
921930
CHECK_ERROR(read_root_type_indices(ctx, &txObj->schema.root_type_indices));
922931

@@ -929,13 +938,15 @@ parser_error_t merkle_proofs_read(parser_context_t *ctx, parser_tx_t *txObj) {
929938
CTX_CHECK_AND_ADVANCE(ctx, CX_SHA256_SIZE);
930939
print_buffer(&txObj->schema.extra_metadata_hash, "extra_metadata_hash");
931940

941+
return parser_ok;
942+
}
943+
944+
parser_error_t schema_chain_hash_read(parser_context_t *ctx, parser_tx_t *txObj) {
932945
// read chain hash
933946
txObj->schema.chain_hash.ptr = ctx->buffer.ptr + ctx->offset;
934947
txObj->schema.chain_hash.len = CX_SHA256_SIZE;
935948
CTX_CHECK_AND_ADVANCE(ctx, CX_SHA256_SIZE);
936949

937-
CHECK_ERROR(verify_merkle_proofs(&txObj->merkle_proofs));
938-
939950
// compute chain hash
940951
CHECK_ERROR(compute_chain_hash(txObj));
941952

app/src/schema_reader.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,8 @@ parser_error_t read_registry(parser_context_t *ctx, registry_t *registry);
3636

3737
parser_error_t metadata_read(parser_context_t *ctx, parser_tx_t *txObj);
3838
parser_error_t merkle_proofs_read(parser_context_t *ctx, parser_tx_t *txObj);
39+
parser_error_t schema_extra_data_read(parser_context_t *ctx, parser_tx_t *txObj);
40+
parser_error_t schema_chain_hash_read(parser_context_t *ctx, parser_tx_t *txObj);
3941

4042
#ifdef __cplusplus
4143
}

app/src/unsigned_transaction_reader.c

Lines changed: 12 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -93,9 +93,8 @@ parser_error_t unsigned_transaction_read(parser_context_t *ctx, parser_tx_t *txO
9393
CHECK_INPUT(ctx);
9494
CHECK_INPUT(txObj);
9595

96-
// read unsigned transaction raw
97-
txObj->unsigned_transaction_raw.buffer = ctx->buffer;
98-
txObj->unsigned_transaction_raw.offset = ctx->offset;
96+
const uint8_t *ptr_mem_txn = ctx->buffer.ptr + ctx->offset;
97+
uint16_t offset_mem_txn = ctx->offset;
9998

10099
// read runtime
101100
CHECK_ERROR(read_runtime(ctx, &txObj->unsigned_transaction.runtime_call));
@@ -106,18 +105,20 @@ parser_error_t unsigned_transaction_read(parser_context_t *ctx, parser_tx_t *txO
106105
// read tx details
107106
CHECK_ERROR(read_tx_details(ctx, &txObj->unsigned_transaction.tx_details));
108107

109-
// TODO: check that we have consumxed all data
110-
if (ctx->offset != ctx->buffer.len) {
111-
print_string("Failed to parse unsigned transaction\n");
112-
return parser_unexpected_error;
113-
} else {
114-
print_string("Successfully parsed unsigned transaction\n");
115-
}
116-
117108
uint64_t root_index;
118109
CHECK_ERROR(get_schema_unsigned_transaction_index(txObj, &root_index));
119110
print_u64("root_index:", root_index);
120111

112+
txObj->unsigned_transaction_raw.buffer.ptr = ptr_mem_txn;
113+
txObj->unsigned_transaction_raw.buffer.len = ctx->offset - offset_mem_txn;
114+
txObj->unsigned_transaction_raw.offset = 0;
115+
116+
117+
print_string("txObj->unsigned_transaction_raw.offset: ");
118+
print_u16("txObj->unsigned_transaction_raw.len: ", txObj->unsigned_transaction_raw.buffer.len);
119+
120+
print_buffer(&txObj->unsigned_transaction_raw.buffer, "txObj->unsigned_transaction_raw.buffer: ");
121+
121122
CHECK_ERROR(schema_display(txObj, root_index));
122123

123124
return parser_ok;

js

Submodule js updated 1 file

tests/parser_impl.cpp

Lines changed: 3 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -323,22 +323,15 @@ TEST(SCALE, ReadMultiProofUnsignedTransaction) {
323323
"40abff97bcb464bcca26c00000000000000f55d28d6582a2e492b325f097e1ebcc0a19eca8f506fb5a7c3473067d48f06f80400000000000000"
324324
"000000006b0000000000000003000000000000000b00000000000000e1100000000000000900000054657374436861696e06010000000900000"
325325
"0746f6b656e5f696473010000002000000017171717171717171717171717171717171717171717171717171717171717060900000054657374"
326-
"546f6b656e77f986b27d5c6e676fdb865f44833b5fe97f5cccafaf5b4733c21ba027f8b725a43850ba5603f89c05080e14ff868fec09f35fbfa"
327-
"a3c28ad76258fbac95d7432");
326+
"546f6b656e77f986b27d5c6e676fdb865f44833b5fe97f5cccafaf5b4733c21ba027f8b725");
328327

329328
auto bufferLen_tx =
330329
parseHexString(buffer + bufferLen, sizeof(buffer),
331-
"09000001102700000000000000000000000000000001d0070000000000000000000000000000d00700000000000000000000"
332-
"0000000001320000000000000001000000000b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b01010000"
333-
"00000b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b000000000000000000000000000000000000e876"
334-
"481700000000000000000000000100ca9a3b0000000000ca9a3b00000000e110000000000000");
330+
"09000001102700000000000000000000000000000001d0070000000000000000000000000000d007000000000000000000000000000001320000000000000001000000000b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0101000000000b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b000000000000000000000000000000000000e876481700000000000000000000000100ca9a3b0000000000ca9a3b00000000e110000000000000a43850ba5603f89c05080e14ff868fec09f35fbfaa3c28ad76258fbac95d7432");
335331

336332
ctx.buffer.ptr = buffer;
337333
ctx.buffer.len = bufferLen + bufferLen_tx;
338334

339-
err = merkle_proofs_read(&ctx, &tx_obj);
340-
EXPECT_EQ(err, parser_ok) << parser_getErrorDescription(err);
341-
342-
err = unsigned_transaction_read(&ctx, &tx_obj);
335+
err = parser_parse(&ctx, ctx.buffer.ptr, ctx.buffer.len, &tx_obj);
343336
EXPECT_EQ(err, parser_ok) << parser_getErrorDescription(err);
344337
}

0 commit comments

Comments
 (0)