mirror of
https://github.com/trezor/trezor-firmware.git
synced 2024-11-22 15:38:11 +00:00
legacy/nem: Refactor nem_canonicalizeMosaics
GCC is able to reason about transfer->mosaics_count using Value Range Propagation. Using transfer->mosaics_count, instead of a mosaics_count argument, satisfies GCC that the variable-length skip array cannot be too large. Renamed variables to old_count and new_count to reduce ambiguity.
This commit is contained in:
parent
9ccde8d853
commit
1ca521eec9
@ -132,8 +132,7 @@ void fsm_msgNEMSignTx(NEMSignTx *msg) {
|
|||||||
hdnode_get_nem_address(node, common->network, address);
|
hdnode_get_nem_address(node, common->network, address);
|
||||||
|
|
||||||
if (msg->has_transfer) {
|
if (msg->has_transfer) {
|
||||||
msg->transfer.mosaics_count = nem_canonicalizeMosaics(
|
nem_canonicalizeMosaics(&msg->transfer);
|
||||||
msg->transfer.mosaics, msg->transfer.mosaics_count);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (msg->has_transfer && !nem_askTransfer(common, &msg->transfer, network)) {
|
if (msg->has_transfer && !nem_askTransfer(common, &msg->transfer, network)) {
|
||||||
|
@ -700,27 +700,31 @@ static inline size_t format_amount(const NEMMosaicDefinition *definition,
|
|||||||
-divisor, false, str_out, size);
|
-divisor, false, str_out, size);
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t nem_canonicalizeMosaics(NEMMosaic *mosaics, size_t mosaics_count) {
|
void nem_canonicalizeMosaics(NEMTransfer *transfer) {
|
||||||
if (mosaics_count <= 1) {
|
size_t old_count = transfer->mosaics_count;
|
||||||
return mosaics_count;
|
|
||||||
|
if (old_count <= 1) {
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t actual_count = 0;
|
NEMMosaic *const mosaics = transfer->mosaics;
|
||||||
|
|
||||||
bool skip[mosaics_count];
|
bool skip[old_count];
|
||||||
memzero(skip, sizeof(skip));
|
memzero(skip, sizeof(skip));
|
||||||
|
|
||||||
|
size_t new_count = 0;
|
||||||
|
|
||||||
// Merge duplicates
|
// Merge duplicates
|
||||||
for (size_t i = 0; i < mosaics_count; i++) {
|
for (size_t i = 0; i < old_count; i++) {
|
||||||
if (skip[i]) continue;
|
if (skip[i]) continue;
|
||||||
|
|
||||||
NEMMosaic *mosaic = &mosaics[actual_count];
|
NEMMosaic *mosaic = &mosaics[new_count];
|
||||||
|
|
||||||
if (actual_count++ != i) {
|
if (new_count++ != i) {
|
||||||
memcpy(mosaic, &mosaics[i], sizeof(NEMMosaic));
|
memcpy(mosaic, &mosaics[i], sizeof(NEMMosaic));
|
||||||
}
|
}
|
||||||
|
|
||||||
for (size_t j = i + 1; j < mosaics_count; j++) {
|
for (size_t j = i + 1; j < old_count; j++) {
|
||||||
if (skip[j]) continue;
|
if (skip[j]) continue;
|
||||||
|
|
||||||
const NEMMosaic *new_mosaic = &mosaics[j];
|
const NEMMosaic *new_mosaic = &mosaics[j];
|
||||||
@ -732,24 +736,23 @@ size_t nem_canonicalizeMosaics(NEMMosaic *mosaics, size_t mosaics_count) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
NEMMosaic temp;
|
transfer->mosaics_count = new_count;
|
||||||
|
|
||||||
// Sort mosaics
|
// Sort mosaics
|
||||||
for (size_t i = 0; i < actual_count - 1; i++) {
|
for (size_t i = 0; i < new_count - 1; i++) {
|
||||||
NEMMosaic *a = &mosaics[i];
|
NEMMosaic *a = &mosaics[i];
|
||||||
|
|
||||||
for (size_t j = i + 1; j < actual_count; j++) {
|
for (size_t j = i + 1; j < new_count; j++) {
|
||||||
NEMMosaic *b = &mosaics[j];
|
NEMMosaic *b = &mosaics[j];
|
||||||
|
|
||||||
if (nem_mosaicCompare(a, b) > 0) {
|
if (nem_mosaicCompare(a, b) > 0) {
|
||||||
|
NEMMosaic temp;
|
||||||
memcpy(&temp, a, sizeof(NEMMosaic));
|
memcpy(&temp, a, sizeof(NEMMosaic));
|
||||||
memcpy(a, b, sizeof(NEMMosaic));
|
memcpy(a, b, sizeof(NEMMosaic));
|
||||||
memcpy(b, &temp, sizeof(NEMMosaic));
|
memcpy(b, &temp, sizeof(NEMMosaic));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return actual_count;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void nem_mosaicFormatAmount(const NEMMosaicDefinition *definition,
|
void nem_mosaicFormatAmount(const NEMMosaicDefinition *definition,
|
||||||
|
@ -92,7 +92,7 @@ const NEMMosaicDefinition *nem_mosaicByName(const char *namespace,
|
|||||||
const char *mosaic,
|
const char *mosaic,
|
||||||
uint8_t network);
|
uint8_t network);
|
||||||
|
|
||||||
size_t nem_canonicalizeMosaics(NEMMosaic *mosaics, size_t mosaics_count);
|
void nem_canonicalizeMosaics(NEMTransfer *transfer);
|
||||||
void nem_mosaicFormatAmount(const NEMMosaicDefinition *definition,
|
void nem_mosaicFormatAmount(const NEMMosaicDefinition *definition,
|
||||||
uint64_t quantity, const bignum256 *multiplier,
|
uint64_t quantity, const bignum256 *multiplier,
|
||||||
char *str_out, size_t size);
|
char *str_out, size_t size);
|
||||||
|
Loading…
Reference in New Issue
Block a user