Skip to content

Commit

Permalink
Use correct representation of hash in circuits.
Browse files Browse the repository at this point in the history
Interface for computing sah256 is currently limited in circuits' code
to only be able to compute the sha256 of 2 32 bytes variables after they
are converted to nil::crypto3::hashes::sha2<256>::block_type.
  • Loading branch information
HristoStaykov committed Jan 29, 2024
1 parent 9fd86fb commit 33bcd6f
Show file tree
Hide file tree
Showing 4 changed files with 78 additions and 29 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -66,10 +66,11 @@ namespace circuit_byte_utils {
}

template<std::size_t N, typename T, std::size_t InputSize>
std::array<T, N> take(const std::array<T, InputSize>& val) {
std::array<T, N> take(const std::array<T, InputSize>& val, size_t offset = 0) {
static_assert(N <= InputSize);
assert_true(N + offset <= InputSize);
std::array<T, N> ret {};
std::copy(val.begin(), val.begin() + N, ret.begin());
std::copy(val.begin() + offset, val.begin() + offset + N, ret.begin());

return ret;
}
Expand Down Expand Up @@ -214,8 +215,40 @@ namespace circuit_byte_utils {
#ifdef __ZKLLVM__
return hash<hashes::sha2<256>>(child1, child2);
#else
exit(1);
assert_true(false && "Using sha256_t in executable. Use Bytes32 instead.");
#endif
}

#ifdef __ZKLLVM__
#include <nil/crypto3/algebra/curves/pallas.hpp>

using namespace nil::crypto3;
using namespace nil::crypto3::algebra::curves;
sha256_t bytes_to_hash_type(const std::array<unsigned char, 32>& bytes) {

sha256_t converted;
// MSB first
std::array<typename algebra::curves::pallas::base_field_type::value_type, 128> decomposed_block_1;
std::array<typename algebra::curves::pallas::base_field_type::value_type, 128> decomposed_block_2;

for(size_t i = 0; i < 16; i++) {
__builtin_assigner_bit_decomposition(decomposed_block_1.data() + (i * 8), 8, bytes[i], true);
__builtin_assigner_bit_decomposition(decomposed_block_2.data() + (i * 8), 8, bytes[i + 16], true);
}

typename algebra::curves::pallas::base_field_type::value_type first_block = __builtin_assigner_bit_composition(
decomposed_block_1.data(), 128, true);
typename algebra::curves::pallas::base_field_type::value_type second_block = __builtin_assigner_bit_composition(
decomposed_block_2.data(), 128, true);

converted = {first_block, second_block};

return converted;
}

#else
#define bytes_to_hash_type(X) (X)

#endif

} // namespace circuit_byte_utils
2 changes: 2 additions & 0 deletions vendor/zkllvm-metacraft-circuits/src/circuits/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
add_example(compute_shuffled_index SOURCES compute_shuffled_index.cpp INPUT main.inp)
add_example(weigh_justification_and_finalization SOURCES weigh_justification_and_finalization.cpp INPUT main.inp)
add_example(verify_attestation_data SOURCES verify_attestation_data.cpp INPUT main.inp)

add_dependencies(template compute_shuffled_index)
add_dependencies(template weigh_justification_and_finalization)
add_dependencies(template verify_attestation_data)
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ using namespace circuit_byte_utils;
using namespace ssz_utils;
using namespace nil::crypto3::algebra::curves;

using Proof = static_vector<Bytes32, 64>;
using Proof = static_vector<HashType, 41>;
using PubKey = Bytes48;

struct AttestationData {
Expand Down Expand Up @@ -62,13 +62,13 @@ struct Attestation {
// We should be able to prove that the majority of validators
// participating in this attestation are part of the validator set
// associated with the state of the last trusted block.
Bytes32 state_root;
HashType state_root;
MerkleProof<3> state_root_proof;

Bytes32 validators_root;
HashType validators_root;
MerkleProof<5> validators_root_proof;

static_vector<Validator, 1024> validators;
static_vector<Validator, 415> validators;
};

struct Transition {
Expand Down Expand Up @@ -117,9 +117,9 @@ static_vector<HashType> compute_zero_hashes(int length = 64) {
return xs;
}

static const auto zero_hashes = compute_zero_hashes();

Proof fill_zero_hashes(const Proof& xs, size_t length = 0) {
const auto zero_hashes = compute_zero_hashes();
#ifdef __ZKLLVM__
sha256_t empty_hash = {0};
#else
Expand All @@ -129,7 +129,7 @@ Proof fill_zero_hashes(const Proof& xs, size_t length = 0) {
int additions_count = length - xs.size();

for (int i = 0; i < ws.size(); i++) {
if (ws[i] == empty_hash) {
if (sha256_equals(ws[i], empty_hash)) {
ws[i] = zero_hashes[i];
}
}
Expand All @@ -139,30 +139,44 @@ Proof fill_zero_hashes(const Proof& xs, size_t length = 0) {
return ws;
}

Bytes32 hash_validator(Bytes64 pubkey,
Bytes32 withdrawal_credentials,
uint64_t effective_balance_,
uint64_t activation_eligibility_epoch_,
uint64_t activation_epoch_,
uint64_t exit_epoch_,
uint64_t withdrawable_epoch_) {
HashType hash_validator(Bytes64 pubkey,
Bytes32 withdrawal_credentials_,
uint64_t effective_balance_,
uint64_t activation_eligibility_epoch_,
uint64_t activation_epoch_,
uint64_t exit_epoch_,
uint64_t withdrawable_epoch_) {
// Convert parameters.
auto effective_balance = int_to_bytes<uint64_t, 32, true>(effective_balance_);
auto slashed = int_to_bytes<uint64_t, 32, true>(0);
auto activation_eligibility_epoch = int_to_bytes<uint64_t, 32, true>(activation_eligibility_epoch_);
auto activation_epoch = int_to_bytes<uint64_t, 32, true>(activation_epoch_);
auto exit_epoch = int_to_bytes<uint64_t, 32, true>(exit_epoch_);
auto withdrawable_epoch = int_to_bytes<uint64_t, 32, true>(withdrawable_epoch_);
auto effective_balance = bytes_to_hash_type((int_to_bytes<uint64_t, 32, true>(effective_balance_)));
auto slashed = bytes_to_hash_type((int_to_bytes<uint64_t, 32, true>(0)));
auto activation_eligibility_epoch = bytes_to_hash_type((int_to_bytes<uint64_t, 32, true>(activation_eligibility_epoch_)));
auto activation_epoch = bytes_to_hash_type((int_to_bytes<uint64_t, 32, true>(activation_epoch_)));
auto exit_epoch = bytes_to_hash_type((int_to_bytes<uint64_t, 32, true>(exit_epoch_)));
auto withdrawable_epoch = bytes_to_hash_type((int_to_bytes<uint64_t, 32, true>(withdrawable_epoch_)));
auto withdrawal_credentials = bytes_to_hash_type((withdrawal_credentials_));

#ifdef __ZKLLVM__
auto hash = [](const HashType& lhs, const HashType& rhs) {
return parent_hash(lhs, rhs);
};
auto pubkey_hash = hash(bytes_to_hash_type(take<32>(pubkey)), bytes_to_hash_type(take<32>(pubkey, 32)));
#else
auto hash = [](const HashType& lhs, const HashType& rhs) {
return sha256(lhs, rhs);
};
auto pubkey_hash = sha256(pubkey);
#endif

// Hash branches.
auto retval = sha256(
sha256(sha256(sha256(pubkey), withdrawal_credentials), sha256(effective_balance, slashed)),
sha256(sha256(activation_eligibility_epoch, activation_epoch),
sha256(exit_epoch, withdrawable_epoch)));
auto retval = hash(
hash(hash(pubkey_hash, withdrawal_credentials), hash(effective_balance, slashed)),
hash(hash(activation_eligibility_epoch, activation_epoch),
hash(exit_epoch, withdrawable_epoch)));

return retval;
}

VoteToken verify_attestation_data(const Bytes32& block_root, const Attestation& attestation, base_field_type sigma) {
VoteToken verify_attestation_data_imp(const HashType& block_root, const Attestation& attestation, base_field_type sigma) {
assert_true(sigma != 0);

ssz_verify_proof(
Expand Down Expand Up @@ -239,7 +253,7 @@ VoteToken verify_attestation_data(const Bytes32& block_root, const Attestation&
VoteToken combine_finality_votes(const static_vector<VoteToken, 8192>& tokens) {
VoteToken result;
result.transition = tokens[0].transition;
result.token = 0;
result.token = {};
for (auto it = tokens.begin(); it != tokens.end(); ++it) {
assert_true(result.transition == it->transition);
result.token += it->token;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -416,7 +416,7 @@ int main(int argc, char* argv[]) {

verify_attestation(attestation, json_attestation);

auto vote = verify_attestation_data(
auto vote = verify_attestation_data_imp(
hexToBytes<32>("d5c0418465ffab221522a6991c2d4c0041f1b8e91d01b1ea3f6b882369f689b7"), attestation, sigma);

tokens.push_back(std::move(vote));
Expand Down

0 comments on commit 33bcd6f

Please sign in to comment.