Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
29 commits
Select commit Hold shift + click to select a range
d29f49f
feat!: start using fixed size arrays for black box functions
TomAFrench Apr 8, 2024
1c6e807
chore: add regression test for `serde_big_array` not deserializing pr…
TomAFrench Apr 10, 2024
fe49ff8
chore: add missing import of `serde_big_array`
TomAFrench Apr 10, 2024
b7c7623
Merge branch 'master' into tf/fixed-length-black-box-arrays
TomAFrench Apr 10, 2024
28adbb0
chore: fix stuff
TomAFrench Apr 10, 2024
40f5e0b
Merge branch 'master' into tf/fixed-length-black-box-arrays
TomAFrench Apr 10, 2024
8323a7c
chore: fix
TomAFrench Apr 10, 2024
5e6b636
chore: cast stuff
TomAFrench Apr 10, 2024
c6042b7
chore: wip
TomAFrench Apr 10, 2024
9e12097
chore: stuff
TomAFrench Apr 10, 2024
2143604
chore: wip
TomAFrench Apr 10, 2024
50fbe91
chore: fix
TomAFrench Apr 10, 2024
e25c0c9
chore: update serialization of schnorr circuit
TomAFrench Apr 14, 2024
1a60184
Merge branch 'master' into tf/fixed-length-black-box-arrays
TomAFrench Apr 14, 2024
009f336
chore: replace vectors with arrays
TomAFrench Apr 14, 2024
b5b5114
chore: align k1 and r1 functions
TomAFrench Apr 15, 2024
e59e40b
chore: fix signature array length
TomAFrench Apr 15, 2024
151c2af
remove unused alias
guipublic Apr 15, 2024
62ecc2e
trying to fix the build
guipublic Apr 15, 2024
82d6feb
revert the test
guipublic Apr 15, 2024
42b2afd
chore: remove use of auto in ecdsa_secp256r1
TomAFrench Apr 15, 2024
7ce8129
chore: wrong auto
TomAFrench Apr 15, 2024
1eb0608
move ecdsa_convert_signature impl to header
vezenovm Apr 15, 2024
a202405
Merge branch 'master' into tf/fixed-length-black-box-arrays
vezenovm Apr 15, 2024
d891577
Merge branch 'master' into tf/fixed-length-black-box-arrays
TomAFrench Apr 15, 2024
783feeb
Merge branch 'master' into tf/fixed-length-black-box-arrays
TomAFrench Apr 16, 2024
268893a
Merge branch 'master' into tf/fixed-length-black-box-arrays
TomAFrench Apr 16, 2024
61ad6ad
chore: formatting
TomAFrench Apr 16, 2024
2e30fa2
chore: more formatting
TomAFrench Apr 16, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions avm-transpiler/Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Original file line number Diff line number Diff line change
Expand Up @@ -196,7 +196,7 @@ TEST_F(AcirFormatTests, TestSchnorrVerifyPass)
});
}

std::vector<uint32_t> signature(64);
std::array<uint32_t, 64> signature;
for (uint32_t i = 0, value = 12; i < 64; i++, value++) {
signature[i] = value;
range_constraints.push_back(RangeConstraint{
Expand Down Expand Up @@ -289,7 +289,7 @@ TEST_F(AcirFormatTests, TestSchnorrVerifySmallRange)
});
}

std::vector<uint32_t> signature(64);
std::array<uint32_t, 64> signature;
for (uint32_t i = 0, value = 12; i < 64; i++, value++) {
signature[i] = value;
range_constraints.push_back(RangeConstraint{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ struct Blake2sInput {

struct Blake2sConstraint {
std::vector<Blake2sInput> inputs;
std::vector<uint32_t> result;
std::array<uint32_t, 32> result;

// For serialization, update with any new fields
MSGPACK_FIELDS(inputs, result);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ struct Blake3Input {

struct Blake3Constraint {
std::vector<Blake3Input> inputs;
std::vector<uint32_t> result;
std::array<uint32_t, 32> result;

// For serialization, update with any new fields
MSGPACK_FIELDS(inputs, result);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,44 +5,6 @@ namespace acir_format {

using namespace bb::plonk;

template <typename Builder>
crypto::ecdsa_signature ecdsa_convert_signature(Builder& builder, std::vector<uint32_t> signature)
{

crypto::ecdsa_signature signature_cr;

// Get the witness assignment for each witness index
// Write the witness assignment to the byte_array

for (unsigned int i = 0; i < 32; i++) {
auto witness_index = signature[i];

std::vector<uint8_t> fr_bytes(sizeof(fr));

fr value = builder.get_variable(witness_index);

fr::serialize_to_buffer(value, &fr_bytes[0]);

signature_cr.r[i] = fr_bytes.back();
}

for (unsigned int i = 32; i < 64; i++) {
auto witness_index = signature[i];

std::vector<uint8_t> fr_bytes(sizeof(fr));

fr value = builder.get_variable(witness_index);

fr::serialize_to_buffer(value, &fr_bytes[0]);

signature_cr.s[i - 32] = fr_bytes.back();
}

signature_cr.v = 27;

return signature_cr;
}

template <typename Builder>
secp256k1_ct::g1_ct ecdsa_convert_inputs(Builder* ctx, const secp256k1::g1::affine_element& input)
{
Expand All @@ -63,9 +25,9 @@ secp256k1_ct::g1_ct ecdsa_convert_inputs(Builder* ctx, const secp256k1::g1::affi
// vector of bytes here, assumes that the witness indices point to a field element which can be represented
// with just a byte.
// notice that this function truncates each field_element to a byte
template <typename Builder>
bb::stdlib::byte_array<Builder> ecdsa_vector_of_bytes_to_byte_array(Builder& builder,
std::vector<uint32_t> vector_of_bytes)
template <std::size_t SIZE, typename Builder>
bb::stdlib::byte_array<Builder> ecdsa_array_of_bytes_to_byte_array(Builder& builder,
std::array<uint32_t, SIZE> vector_of_bytes)
{
using byte_array_ct = bb::stdlib::byte_array<Builder>;
using field_ct = bb::stdlib::field_t<Builder>;
Expand Down Expand Up @@ -106,9 +68,9 @@ void create_ecdsa_k1_verify_constraints(Builder& builder,

auto new_sig = ecdsa_convert_signature(builder, input.signature);

byte_array_ct message = ecdsa_vector_of_bytes_to_byte_array(builder, input.hashed_message);
auto pub_key_x_byte_arr = ecdsa_vector_of_bytes_to_byte_array(builder, input.pub_x_indices);
auto pub_key_y_byte_arr = ecdsa_vector_of_bytes_to_byte_array(builder, input.pub_y_indices);
byte_array_ct message = ecdsa_array_of_bytes_to_byte_array(builder, input.hashed_message);
auto pub_key_x_byte_arr = ecdsa_array_of_bytes_to_byte_array(builder, input.pub_x_indices);
auto pub_key_y_byte_arr = ecdsa_array_of_bytes_to_byte_array(builder, input.pub_y_indices);

auto pub_key_x_fq = typename secp256k1_ct::fq_ct(pub_key_x_byte_arr);
auto pub_key_y_fq = typename secp256k1_ct::fq_ct(pub_key_y_byte_arr);
Expand Down Expand Up @@ -153,11 +115,10 @@ void create_ecdsa_k1_verify_constraints(Builder& builder,
template <typename Builder> void dummy_ecdsa_constraint(Builder& builder, EcdsaSecp256k1Constraint const& input)
{

std::vector<uint32_t> pub_x_indices_;
std::vector<uint32_t> pub_y_indices_;
std::vector<uint32_t> signature_;
std::vector<uint32_t> message_indices_;
signature_.resize(64);
std::array<uint32_t, 32> pub_x_indices_;
std::array<uint32_t, 32> pub_y_indices_;
std::array<uint32_t, 64> signature_;
std::array<uint32_t, 32> message_indices_;

// Create a valid signature with a valid public key
crypto::ecdsa_key_pair<secp256k1_ct::fr, secp256k1_ct::g1> account;
Expand All @@ -179,9 +140,9 @@ template <typename Builder> void dummy_ecdsa_constraint(Builder& builder, EcdsaS
uint32_t y_wit = builder.add_variable(pub_y_value.slice(248 - i * 8, 256 - i * 8));
uint32_t r_wit = builder.add_variable(signature.r[i]);
uint32_t s_wit = builder.add_variable(signature.s[i]);
message_indices_.emplace_back(m_wit);
pub_x_indices_.emplace_back(x_wit);
pub_y_indices_.emplace_back(y_wit);
message_indices_[i] = m_wit;
pub_x_indices_[i] = x_wit;
pub_y_indices_[i] = y_wit;
signature_[i] = r_wit;
signature_[i + 32] = s_wit;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,19 +8,19 @@ namespace acir_format {

struct EcdsaSecp256k1Constraint {
// This is the byte representation of the hashed message.
std::vector<uint32_t> hashed_message;
std::array<uint32_t, 32> hashed_message;

// This is the computed signature
//
std::vector<uint32_t> signature;
std::array<uint32_t, 64> signature;

// This is the supposed public key which signed the
// message, giving rise to the signature.
// Since Fr does not have enough bits to represent
// the prime field in secp256k1, a byte array is used.
// Can also use low and hi where lo=128 bits
std::vector<uint32_t> pub_x_indices;
std::vector<uint32_t> pub_y_indices;
std::array<uint32_t, 32> pub_x_indices;
std::array<uint32_t, 32> pub_y_indices;

// This is the result of verifying the signature
uint32_t result;
Expand All @@ -37,11 +37,51 @@ void create_ecdsa_k1_verify_constraints(Builder& builder,

template <typename Builder> void dummy_ecdsa_constraint(Builder& builder, EcdsaSecp256k1Constraint const& input);

template <typename Builder>
crypto::ecdsa_signature ecdsa_convert_signature(Builder& builder, std::vector<uint32_t> signature);
witness_ct ecdsa_index_to_witness(Builder& builder, uint32_t index);
template <std::size_t SIZE, typename Builder>
bb::stdlib::byte_array<Builder> ecdsa_array_of_bytes_to_byte_array(Builder& builder,
std::array<uint32_t, SIZE> vector_of_bytes);

// We have the implementation of this template in the header as this method is used
// by other ecdsa constraints over different curves (e.g. secp256r1).
// gcc needs to be able to see the implementation order to generate code for
// all Builder specializations (e.g. bb::Goblin::Builder vs. bb::UltraCircuitBuilder)
template <typename Builder>
bb::stdlib::byte_array<Builder> ecdsa_vector_of_bytes_to_byte_array(Builder& builder,
std::vector<uint32_t> vector_of_bytes);
crypto::ecdsa_signature ecdsa_convert_signature(Builder& builder, std::array<uint32_t, 64> signature)
{

crypto::ecdsa_signature signature_cr;

// Get the witness assignment for each witness index
// Write the witness assignment to the byte_array

for (unsigned int i = 0; i < 32; i++) {
auto witness_index = signature[i];

std::vector<uint8_t> fr_bytes(sizeof(fr));

fr value = builder.get_variable(witness_index);

fr::serialize_to_buffer(value, &fr_bytes[0]);

signature_cr.r[i] = fr_bytes.back();
}

for (unsigned int i = 32; i < 64; i++) {
auto witness_index = signature[i];

std::vector<uint8_t> fr_bytes(sizeof(fr));

fr value = builder.get_variable(witness_index);

fr::serialize_to_buffer(value, &fr_bytes[0]);

signature_cr.s[i - 32] = fr_bytes.back();
}

signature_cr.v = 27;

return signature_cr;
}

} // namespace acir_format
Original file line number Diff line number Diff line change
Expand Up @@ -37,35 +37,35 @@ size_t generate_ecdsa_constraint(EcdsaSecp256k1Constraint& ecdsa_constraint, Wit
uint256_t pub_x_value = account.public_key.x;
uint256_t pub_y_value = account.public_key.y;

std::vector<uint32_t> message_in;
std::vector<uint32_t> pub_x_indices_in;
std::vector<uint32_t> pub_y_indices_in;
std::vector<uint32_t> signature_in;
std::array<uint32_t, 32> message_in;
std::array<uint32_t, 32> pub_x_indices_in;
std::array<uint32_t, 32> pub_y_indices_in;
std::array<uint32_t, 64> signature_in;
size_t offset = 0;
for (size_t i = 0; i < hashed_message.size(); ++i) {
message_in.emplace_back(i + offset);
message_in[i] = static_cast<uint32_t>(i + offset);
const auto byte = static_cast<uint8_t>(hashed_message[i]);
witness_values.emplace_back(byte);
}
offset += message_in.size();

for (size_t i = 0; i < 32; ++i) {
pub_x_indices_in.emplace_back(i + offset);
pub_x_indices_in[i] = static_cast<uint32_t>(i + offset);
witness_values.emplace_back(pub_x_value.slice(248 - i * 8, 256 - i * 8));
}
offset += pub_x_indices_in.size();
for (size_t i = 0; i < 32; ++i) {
pub_y_indices_in.emplace_back(i + offset);
pub_y_indices_in[i] = static_cast<uint32_t>(i + offset);
witness_values.emplace_back(pub_y_value.slice(248 - i * 8, 256 - i * 8));
}
offset += pub_y_indices_in.size();
for (size_t i = 0; i < 32; ++i) {
signature_in.emplace_back(i + offset);
signature_in[i] = static_cast<uint32_t>(i + offset);
witness_values.emplace_back(signature.r[i]);
}
offset += signature.r.size();
for (size_t i = 0; i < 32; ++i) {
signature_in.emplace_back(i + offset);
signature_in[i + 32] = static_cast<uint32_t>(i + offset);
witness_values.emplace_back(signature.s[i]);
}
offset += signature.s.size();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,16 +33,17 @@ void create_ecdsa_r1_verify_constraints(Builder& builder,
using secp256r1_ct = bb::stdlib::secp256r1<Builder>;
using bool_ct = bb::stdlib::bool_t<Builder>;
using field_ct = bb::stdlib::field_t<Builder>;
using byte_array_ct = bb::stdlib::byte_array<Builder>;

if (has_valid_witness_assignments == false) {
dummy_ecdsa_constraint(builder, input);
}

auto new_sig = ecdsa_convert_signature(builder, input.signature);

auto message = ecdsa_vector_of_bytes_to_byte_array(builder, input.hashed_message);
auto pub_key_x_byte_arr = ecdsa_vector_of_bytes_to_byte_array(builder, input.pub_x_indices);
auto pub_key_y_byte_arr = ecdsa_vector_of_bytes_to_byte_array(builder, input.pub_y_indices);
byte_array_ct message = ecdsa_array_of_bytes_to_byte_array(builder, input.hashed_message);
auto pub_key_x_byte_arr = ecdsa_array_of_bytes_to_byte_array(builder, input.pub_x_indices);
auto pub_key_y_byte_arr = ecdsa_array_of_bytes_to_byte_array(builder, input.pub_y_indices);

auto pub_key_x_fq = typename secp256r1_ct::fq_ct(pub_key_x_byte_arr);
auto pub_key_y_fq = typename secp256r1_ct::fq_ct(pub_key_y_byte_arr);
Expand Down Expand Up @@ -87,11 +88,10 @@ void create_ecdsa_r1_verify_constraints(Builder& builder,
template <typename Builder> void dummy_ecdsa_constraint(Builder& builder, EcdsaSecp256r1Constraint const& input)
{

std::vector<uint32_t> pub_x_indices_;
std::vector<uint32_t> pub_y_indices_;
std::vector<uint32_t> signature_;
std::vector<uint32_t> message_indices_;
signature_.resize(64);
std::array<uint32_t, 32> pub_x_indices_;
std::array<uint32_t, 32> pub_y_indices_;
std::array<uint32_t, 64> signature_;
std::array<uint32_t, 32> message_indices_;

// Create a valid signature with a valid public key
std::string message_string = "Instructions unclear, ask again later.";
Expand Down Expand Up @@ -121,9 +121,9 @@ template <typename Builder> void dummy_ecdsa_constraint(Builder& builder, EcdsaS
uint32_t y_wit = builder.add_variable(pub_y_value.slice(248 - i * 8, 256 - i * 8));
uint32_t r_wit = builder.add_variable(signature.r[i]);
uint32_t s_wit = builder.add_variable(signature.s[i]);
message_indices_.emplace_back(m_wit);
pub_x_indices_.emplace_back(x_wit);
pub_y_indices_.emplace_back(y_wit);
message_indices_[i] = m_wit;
pub_x_indices_[i] = x_wit;
pub_y_indices_[i] = y_wit;
signature_[i] = r_wit;
signature_[i + 32] = s_wit;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,22 +6,22 @@ namespace acir_format {

struct EcdsaSecp256r1Constraint {
// This is the byte representation of the hashed message.
std::vector<uint32_t> hashed_message;
std::array<uint32_t, 32> hashed_message;

// This is the supposed public key which signed the
// message, giving rise to the signature.
// Since Fr does not have enough bits to represent
// the prime field in secp256r1, a byte array is used.
// Can also use low and hi where lo=128 bits
std::vector<uint32_t> pub_x_indices;
std::vector<uint32_t> pub_y_indices;
std::array<uint32_t, 32> pub_x_indices;
std::array<uint32_t, 32> pub_y_indices;

// This is the result of verifying the signature
uint32_t result;

// This is the computed signature
//
std::vector<uint32_t> signature;
std::array<uint32_t, 64> signature;

friend bool operator==(EcdsaSecp256r1Constraint const& lhs, EcdsaSecp256r1Constraint const& rhs) = default;
};
Expand Down
Loading