generated from noir-lang/noir-library-starter
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
34dbea0
commit 514a121
Showing
6 changed files
with
158 additions
and
37 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,7 +1,8 @@ | ||
--- | ||
title: "Tests fail on latest Nargo nightly release" | ||
assignees: TomAFrench, kashbrti, jtriley-eth | ||
--- | ||
|
||
The tests on this Noir project have started failing when using the latest nightly release of the Noir compiler. This likely means that there have been breaking changes for which this project needs to be updated to take into account. | ||
|
||
Check the [{{env.WORKFLOW_NAME}}]({{env.WORKFLOW_URL}}) workflow for details. | ||
Check the [{{env.WORKFLOW_NAME}}]({{env.WORKFLOW_URL}}) workflow for details. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -17,12 +17,12 @@ jobs: | |
- name: Install Nargo | ||
uses: noir-lang/[email protected] | ||
with: | ||
toolchain: 0.34.0 | ||
toolchain: 1.0.0-beta.0 | ||
|
||
- name: Install bb | ||
run: | | ||
npm install -g bbup | ||
bbup -nv 0.34.0 | ||
bbup -nv 1.0.0-beta.0 | ||
- name: Build Noir benchmark programs | ||
run: nargo export | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -16,7 +16,7 @@ jobs: | |
strategy: | ||
fail-fast: false | ||
matrix: | ||
toolchain: [nightly, 0.34.0] | ||
toolchain: [nightly, 1.0.0-beta.0] | ||
steps: | ||
- name: Checkout sources | ||
uses: actions/checkout@v4 | ||
|
@@ -38,7 +38,7 @@ jobs: | |
- name: Install Nargo | ||
uses: noir-lang/[email protected] | ||
with: | ||
toolchain: 0.34.0 | ||
toolchain: 1.0.0-beta.0 | ||
|
||
- name: Run formatter | ||
run: nargo fmt --check | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,7 +1,7 @@ | ||
[package] | ||
name = "noir_library" | ||
name = "schnorr" | ||
type = "lib" | ||
authors = [""] | ||
compiler_version = ">=0.34.0" | ||
compiler_version = ">=1.0.0" | ||
|
||
[dependencies] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,15 +1,151 @@ | ||
/// This doesn't really do anything by ensures that there is a test for CI to run. | ||
#[test] | ||
fn smoke_test() { | ||
assert(true); | ||
use std::embedded_curve_ops::{EmbeddedCurvePoint, EmbeddedCurveScalar, multi_scalar_mul}; | ||
use std::hash::{blake2s, pedersen_hash}; | ||
|
||
pub fn verify_signature<let N: u32>( | ||
public_key: EmbeddedCurvePoint, | ||
signature: [u8; 64], | ||
message: [u8; N], | ||
) -> bool { | ||
//scalar lo/hi from bytes | ||
let sig_s = scalar_from_bytes(signature, 0); | ||
let sig_e = scalar_from_bytes(signature, 32); | ||
// pub_key is on Grumpkin curve | ||
let mut is_ok = (public_key.y * public_key.y == public_key.x * public_key.x * public_key.x - 17) | ||
& (!public_key.is_infinite); | ||
|
||
if ((sig_s.lo != 0) | (sig_s.hi != 0)) & ((sig_e.lo != 0) | (sig_e.hi != 0)) { | ||
let (r_is_infinite, result) = | ||
calculate_signature_challenge(public_key, sig_s, sig_e, message); | ||
|
||
is_ok &= !r_is_infinite; | ||
for i in 0..32 { | ||
is_ok &= result[i] == signature[32 + i]; | ||
} | ||
} else { | ||
is_ok = false; | ||
} | ||
is_ok | ||
} | ||
|
||
pub fn assert_valid_signature<let N: u32>( | ||
public_key: EmbeddedCurvePoint, | ||
signature: [u8; 64], | ||
message: [u8; N], | ||
) { | ||
//scalar lo/hi from bytes | ||
let sig_s = scalar_from_bytes(signature, 0); | ||
let sig_e = scalar_from_bytes(signature, 32); | ||
|
||
// assert pub_key is on Grumpkin curve | ||
assert(public_key.y * public_key.y == public_key.x * public_key.x * public_key.x - 17); | ||
assert(public_key.is_infinite == false); | ||
// assert signature is not null | ||
assert((sig_s.lo != 0) | (sig_s.hi != 0)); | ||
assert((sig_e.lo != 0) | (sig_e.hi != 0)); | ||
|
||
let (r_is_infinite, result) = calculate_signature_challenge(public_key, sig_s, sig_e, message); | ||
|
||
assert(!r_is_infinite); | ||
for i in 0..32 { | ||
assert(result[i] == signature[32 + i]); | ||
} | ||
} | ||
|
||
fn calculate_signature_challenge<let N: u32>( | ||
public_key: EmbeddedCurvePoint, | ||
sig_s: EmbeddedCurveScalar, | ||
sig_e: EmbeddedCurveScalar, | ||
message: [u8; N], | ||
) -> (bool, [u8; 32]) { | ||
let g1 = EmbeddedCurvePoint { | ||
x: 1, | ||
y: 17631683881184975370165255887551781615748388533673675138860, | ||
is_infinite: false, | ||
}; | ||
let r = multi_scalar_mul([g1, public_key], [sig_s, sig_e]); | ||
// compare the _hashes_ rather than field elements modulo r | ||
let pedersen_hash = pedersen_hash([r.x, public_key.x, public_key.y]); | ||
let pde: [u8; 32] = pedersen_hash.to_be_bytes(); | ||
|
||
let mut hash_input = [0; N + 32]; | ||
for i in 0..32 { | ||
hash_input[i] = pde[i]; | ||
} | ||
for i in 0..N { | ||
hash_input[32 + i] = message[i]; | ||
} | ||
|
||
let result = blake2s(hash_input); | ||
(r.is_infinite, result) | ||
} | ||
|
||
// This is an example benchmark. | ||
// Changes to the number of constraints generated by this function will show in PRs. | ||
#[export] | ||
fn bench_test(mut x: Field) -> Field { | ||
for _ in 0..100 { | ||
x *= x; | ||
//Bytes to scalar: take the first (after the specified offset) 16 bytes of the input as the lo value, and the next 16 bytes as the hi value | ||
fn scalar_from_bytes(bytes: [u8; 64], offset: u32) -> EmbeddedCurveScalar { | ||
let mut v: Field = 1; | ||
let mut lo: Field = 0; | ||
let mut hi: Field = 0; | ||
for i in 0..16 { | ||
lo = lo + (bytes[offset + 31 - i] as Field) * v; | ||
hi = hi + (bytes[offset + 15 - i] as Field) * v; | ||
v = v * 256; | ||
} | ||
x | ||
let sig_s = EmbeddedCurveScalar::new(lo, hi); | ||
sig_s | ||
} | ||
|
||
mod test { | ||
use std::embedded_curve_ops::EmbeddedCurvePoint; | ||
|
||
use super::verify_signature; | ||
|
||
#[test] | ||
fn test_zero_signature() { | ||
let public_key: EmbeddedCurvePoint = EmbeddedCurvePoint { | ||
x: 1, | ||
y: 17631683881184975370165255887551781615748388533673675138860, | ||
is_infinite: false, | ||
}; | ||
let signature: [u8; 64] = [0; 64]; | ||
let message: [u8; _] = [2; 64]; // every message | ||
let verified = verify_signature(public_key, signature, message); | ||
assert(!verified); | ||
} | ||
|
||
#[test] | ||
fn smoke_test() { | ||
let message: [u8; 10] = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]; | ||
let message_field: Field = 0x010203040506070809; | ||
let pub_key_x: Field = 0x04b260954662e97f00cab9adb773a259097f7a274b83b113532bce27fa3fb96a; | ||
let pub_key_y: Field = 0x2fd51571db6c08666b0edfbfbc57d432068bccd0110a39b166ab243da0037197; | ||
let signature: [u8; 64] = [ | ||
1, 13, 119, 112, 212, 39, 233, 41, 84, 235, 255, 93, 245, 172, 186, 83, 157, 253, 76, | ||
77, 33, 128, 178, 15, 214, 67, 105, 107, 177, 234, 77, 48, 27, 237, 155, 84, 39, 84, | ||
247, 27, 22, 8, 176, 230, 24, 115, 145, 220, 254, 122, 135, 179, 171, 4, 214, 202, 64, | ||
199, 19, 84, 239, 138, 124, 12, | ||
]; | ||
|
||
// Regression for issue #2421 | ||
// We want to make sure that we can accurately verify a signature whose message is a slice vs. an array | ||
let message_field_bytes: [u8; 10] = message_field.to_be_bytes(); | ||
|
||
// Is there ever a situation where someone would want | ||
// to ensure that a signature was invalid? | ||
// Check that passing a slice as the message is valid | ||
let valid_signature = std::schnorr::verify_signature_slice( | ||
pub_key_x, | ||
pub_key_y, | ||
signature, | ||
message_field_bytes, | ||
); | ||
assert(valid_signature); | ||
// Check that passing an array as the message is valid | ||
let valid_signature = | ||
std::schnorr::verify_signature(pub_key_x, pub_key_y, signature, message); | ||
assert(valid_signature); | ||
let pub_key = EmbeddedCurvePoint { x: pub_key_x, y: pub_key_y, is_infinite: false }; | ||
let valid_signature = std::schnorr::verify_signature_noir(pub_key, signature, message); | ||
assert(valid_signature); | ||
std::schnorr::assert_valid_signature(pub_key, signature, message); | ||
} | ||
|
||
} |