#include "../imports/stdlib.fc"; #include "utils.fc"; const int MERKLE_LEAF_PREFIX = 0; const int MERKLE_NODE_PREFIX = 1; int leaf_hash(slice message) { int hash = keccak256_slice(begin_cell() .store_uint(MERKLE_LEAF_PREFIX, 8) .store_slice(message) .end_cell().begin_parse()); return hash >> 96; } int node_hash(int a, int b) { int min_value = min(a, b); int max_value = max(a, b); int hash = keccak256_slice(begin_cell() .store_uint(MERKLE_NODE_PREFIX, 8) .store_uint(min_value, 160) .store_uint(max_value, 160) .end_cell().begin_parse()); return hash >> 96; } slice read_and_verify_proof(int root_digest, slice message, slice cs) impure { int current_hash = leaf_hash(message); int proof_size = cs~load_uint(8); repeat(proof_size) { builder sibling_digest = begin_cell(); (cell digest_cell, cs) = read_and_store_large_data(cs, 160); slice digest_slice = digest_cell.begin_parse(); sibling_digest = sibling_digest.store_slice(digest_slice); slice sibling_digest_slice = sibling_digest.end_cell().begin_parse(); int sibling_digest_int = sibling_digest_slice~load_uint(160); current_hash = node_hash(current_hash, sibling_digest_int); } throw_unless(ERROR_DIGEST_MISMATCH, root_digest == current_hash); return cs; }