42#include "status_words.h"
43#include "tlv_library.h"
54#if defined(HAVE_ADDRESS_BOOK)
57#define STRUCT_VERSION 0x01
62 TLV_reception_t received_tags;
63 uint8_t hmac_proof[CX_SHA256_SIZE];
64 uint8_t hmac_rest[CX_SHA256_SIZE];
65 uint8_t group_handle[GROUP_HANDLE_SIZE];
69#define EDIT_SCOPE_TAGS(X) \
70 X(0x01, TAG_STRUCTURE_TYPE, handle_struct_type, ENFORCE_UNIQUE_TAG) \
71 X(0x02, TAG_STRUCTURE_VERSION, handle_struct_version, ENFORCE_UNIQUE_TAG) \
72 X(0xf0, TAG_CONTACT_NAME, handle_contact_name, ENFORCE_UNIQUE_TAG) \
73 X(0xf1, TAG_SCOPE, handle_scope, ENFORCE_UNIQUE_TAG) \
74 X(0xf2, TAG_ACCOUNT_IDENTIFIER, handle_identifier, ENFORCE_UNIQUE_TAG) \
75 X(0xf5, TAG_PREVIOUS_SCOPE, handle_previous_scope, ENFORCE_UNIQUE_TAG) \
76 X(0xf6, TAG_GROUP_HANDLE, handle_group_handle, ENFORCE_UNIQUE_TAG) \
77 X(0x21, TAG_DERIVATION_PATH, handle_derivation_path, ENFORCE_UNIQUE_TAG) \
78 X(0x23, TAG_CHAIN_ID, handle_chain_id, ENFORCE_UNIQUE_TAG) \
79 X(0x29, TAG_HMAC_PROOF, handle_hmac_proof, ENFORCE_UNIQUE_TAG) \
80 X(0xf7, TAG_HMAC_REST, handle_hmac_rest, ENFORCE_UNIQUE_TAG) \
81 X(0x51, TAG_BLOCKCHAIN_FAMILY, handle_blockchain_family, ENFORCE_UNIQUE_TAG)
94static bool handle_struct_type(
const tlv_data_t *data, s_edit_scope_ctx *context)
97 if (!tlv_enforce_u8_value(data, TYPE_EDIT_SCOPE)) {
98 PRINTF(
"[Edit Scope] Invalid STRUCTURE_TYPE value\n");
111static bool handle_struct_version(
const tlv_data_t *data, s_edit_scope_ctx *context)
114 if (!tlv_enforce_u8_value(data, STRUCT_VERSION)) {
115 PRINTF(
"[Edit Scope] Invalid STRUCTURE_VERSION value\n");
128static bool handle_contact_name(
const tlv_data_t *data, s_edit_scope_ctx *context)
130 if (!address_book_handle_printable_string(data,
131 context->edit->identity.contact_name,
132 sizeof(context->edit->identity.contact_name))) {
133 PRINTF(
"[Edit Scope] CONTACT_NAME: failed to parse\n");
148static bool handle_scope(
const tlv_data_t *data, s_edit_scope_ctx *context)
150 if (!address_book_handle_printable_string(
151 data, context->edit->identity.scope,
sizeof(context->edit->identity.scope))) {
152 PRINTF(
"[Edit Scope] SCOPE: failed to parse\n");
165static bool handle_identifier(
const tlv_data_t *data, s_edit_scope_ctx *context)
168 if (!get_buffer_from_tlv_data(data, &buf, 1, IDENTIFIER_MAX_LENGTH)) {
169 PRINTF(
"[Edit Scope] IDENTIFIER: failed to extract\n");
172 memmove(context->edit->identity.identifier, buf.
ptr, buf.
size);
173 context->edit->identity.identifier_len = (uint8_t) buf.
size;
186static bool handle_previous_scope(
const tlv_data_t *data, s_edit_scope_ctx *context)
188 if (!address_book_handle_printable_string(
189 data, context->edit->old_scope,
sizeof(context->edit->old_scope))) {
190 PRINTF(
"[Edit Scope] PREVIOUS_SCOPE: failed to parse\n");
203static bool handle_group_handle(
const tlv_data_t *data, s_edit_scope_ctx *context)
206 if (!get_buffer_from_tlv_data(data, &buf, GROUP_HANDLE_SIZE, GROUP_HANDLE_SIZE)) {
207 PRINTF(
"[Edit Scope] GROUP_HANDLE: invalid length (expected %d bytes)\n",
211 memmove(context->group_handle, buf.
ptr, GROUP_HANDLE_SIZE);
222static bool handle_derivation_path(
const tlv_data_t *data, s_edit_scope_ctx *context)
224 return address_book_handle_derivation_path(data, &context->edit->identity.bip32_path);
234static bool handle_chain_id(
const tlv_data_t *data, s_edit_scope_ctx *context)
236 return address_book_handle_chain_id(data, &context->edit->identity.chain_id);
246static bool handle_blockchain_family(
const tlv_data_t *data, s_edit_scope_ctx *context)
248 return address_book_handle_blockchain_family(data, &context->edit->identity.blockchain_family);
258static bool handle_hmac_proof(
const tlv_data_t *data, s_edit_scope_ctx *context)
261 if (!get_buffer_from_tlv_data(data, &buf, CX_SHA256_SIZE, CX_SHA256_SIZE)) {
262 PRINTF(
"[Edit Scope] HMAC_PROOF: invalid length (expected %d bytes)\n", CX_SHA256_SIZE);
265 memmove(context->hmac_proof, buf.
ptr, CX_SHA256_SIZE);
276static bool handle_hmac_rest(
const tlv_data_t *data, s_edit_scope_ctx *context)
279 if (!get_buffer_from_tlv_data(data, &buf, CX_SHA256_SIZE, CX_SHA256_SIZE)) {
280 PRINTF(
"[Edit Scope] HMAC_REST: invalid length (expected %d bytes)\n", CX_SHA256_SIZE);
283 memmove(context->hmac_rest, buf.
ptr, CX_SHA256_SIZE);
287DEFINE_TLV_PARSER(EDIT_SCOPE_TAGS, NULL, edit_scope_tlv_parser)
295static bool verify_fields(
const s_edit_scope_ctx *context)
297 bool result = TLV_CHECK_RECEIVED_TAGS(context->received_tags,
299 TAG_STRUCTURE_VERSION,
302 TAG_ACCOUNT_IDENTIFIER,
306 TAG_BLOCKCHAIN_FAMILY,
310 PRINTF(
"[Edit Scope] Missing mandatory fields!\n");
314 result = TLV_CHECK_RECEIVED_TAGS(context->received_tags, TAG_CHAIN_ID);
316 PRINTF(
"[Edit Scope] Missing CHAIN_ID for Ethereum!\n");
329static void print_payload(
const s_edit_scope_ctx *context)
332 PRINTF(
"****************************************************************************\n");
333 PRINTF(
"[Edit Scope] - Retrieved Descriptor:\n");
334 PRINTF(
"[Edit Scope] - Contact name: %s\n", context->edit->identity.contact_name);
335 PRINTF(
"[Edit Scope] - Old scope: %s\n", context->edit->old_scope);
336 PRINTF(
"[Edit Scope] - New scope: %s\n", context->edit->identity.scope);
337 PRINTF(
"[Edit Scope] - Blockchain family: %s\n",
340 PRINTF(
"[Edit Scope] - Chain ID: %llu\n", context->edit->identity.chain_id);
352static bool build_and_send_response(
void)
354 uint8_t hmac_rest[CX_SHA256_SIZE] = {0};
356 if (!address_book_compute_hmac_rest(&g_ab_payload.edit_scope.identity.bip32_path,
357 g_ab_payload.edit_scope.identity.gid,
358 g_ab_payload.edit_scope.identity.scope,
359 g_ab_payload.edit_scope.identity.identifier,
360 g_ab_payload.edit_scope.identity.identifier_len,
361 g_ab_payload.edit_scope.identity.blockchain_family,
362 g_ab_payload.edit_scope.identity.chain_id,
364 PRINTF(
"[Edit Scope] Error: Failed to compute new HMAC_REST\n");
368 bool ok = address_book_send_hmac_proof(TYPE_EDIT_SCOPE, hmac_rest);
369 explicit_bzero(hmac_rest,
sizeof(hmac_rest));
378static void review_choice(
bool confirm)
381 bool ok = build_and_send_response();
382 const char *successMsg
383 = (g_ab_payload.edit_scope.identity.blockchain_family ==
FAMILY_BITCOIN)
385 :
"Address name changed";
387 on_edit_scope_applied(&g_ab_payload.edit_scope);
390 PRINTF(
"[Edit Scope] Error: Failed to build and send HMAC proof\n");
392 address_book_finalize_review(ok, successMsg,
"Error during update", finalize_ui_edit_scope);
395 address_book_handle_review_rejected(finalize_ui_edit_scope);
402static void ui_display(
void)
405 bool isBitcoin = (g_ab_payload.edit_scope.identity.blockchain_family ==
FAMILY_BITCOIN);
407 memset(&g_ab_ui.list, 0,
sizeof(g_ab_ui.list));
408 memset(g_ab_ui.pairs, 0,
sizeof(g_ab_ui.pairs));
409 g_ab_ui.pairs[nbPairs].item =
"Contact name";
410 g_ab_ui.pairs[nbPairs].value = g_ab_payload.edit_scope.identity.contact_name;
412 g_ab_ui.pairs[nbPairs].item = isBitcoin ?
"Old scope" :
"Old address name";
413 g_ab_ui.pairs[nbPairs].value = g_ab_payload.edit_scope.old_scope;
415 g_ab_ui.pairs[nbPairs].item = isBitcoin ?
"New scope" :
"New address name";
416 g_ab_ui.pairs[nbPairs].value = g_ab_payload.edit_scope.identity.scope;
418 g_ab_ui.list.pairs = g_ab_ui.pairs;
419 g_ab_ui.list.nbPairs = nbPairs;
420 address_book_display_review(&LARGE_ADDRESS_BOOK_ICON,
421 "Review change to contact details",
422#ifdef SCREEN_SIZE_WALLET
439bolos_err_t edit_scope(uint8_t *buffer_in,
size_t buffer_in_length)
441 const buffer_t payload = {.
ptr = buffer_in, .size = buffer_in_length};
442 s_edit_scope_ctx ctx = {0};
445 ctx.edit = &g_ab_payload.edit_scope;
446 memset(&g_ab_payload.edit_scope, 0,
sizeof(g_ab_payload.edit_scope));
449 if (!edit_scope_tlv_parser(&payload, &ctx, &ctx.received_tags)) {
450 PRINTF(
"[Edit Scope] TLV parsing failed\n");
451 return SWO_INCORRECT_DATA;
453 if (!verify_fields(&ctx)) {
454 return SWO_INCORRECT_DATA;
459 if (!address_book_verify_group_handle(&g_ab_payload.edit_scope.identity.bip32_path,
461 g_ab_payload.edit_scope.identity.gid)) {
462 PRINTF(
"[Edit Scope] Group handle verification failed\n");
463 return SWO_SECURITY_CONDITION_NOT_SATISFIED;
467 if (!address_book_verify_hmac_proof(&g_ab_payload.edit_scope.identity.bip32_path,
468 g_ab_payload.edit_scope.identity.gid,
469 g_ab_payload.edit_scope.identity.contact_name,
471 PRINTF(
"[Edit Scope] HMAC_PROOF verification failed\n");
472 return SWO_SECURITY_CONDITION_NOT_SATISFIED;
476 if (!address_book_verify_hmac_rest(&g_ab_payload.edit_scope.identity.bip32_path,
477 g_ab_payload.edit_scope.identity.gid,
478 g_ab_payload.edit_scope.old_scope,
479 g_ab_payload.edit_scope.identity.identifier,
480 g_ab_payload.edit_scope.identity.identifier_len,
481 g_ab_payload.edit_scope.identity.blockchain_family,
482 g_ab_payload.edit_scope.identity.chain_id,
484 PRINTF(
"[Edit Scope] HMAC_REST verification failed\n");
485 return SWO_SECURITY_CONDITION_NOT_SATISFIED;
490 return SWO_NO_RESPONSE;
Register / Edit Contact Name / Edit Scope / Edit Identifier.
API of the Advanced BOLOS Graphical Library, for typical application use-cases.
size_t size
Pointer to byte buffer.