@@ -16,13 +16,13 @@ use crate::tests::test_utils::{
1616
1717type NIProtocol = NISigmaProtocol < SchnorrProtocolCustom < G > , KeccakByteSchnorrCodec < G > > ;
1818
19- /// Macro to generate non-interactive sigma protocols test functions
20- macro_rules! generate_ni_function {
19+ /// Macro to generate non-interactive sigma protocols test functions with IV
20+ macro_rules! generate_ni_function_iv {
2121 ( $name: ident, $test_fn: ident, $( $param: tt) ,* ) => {
2222 #[ allow( non_snake_case) ]
2323 fn $name( seed: & [ u8 ] , iv: [ u8 ; 32 ] ) -> ( Vec <Scalar >, Vec <u8 >) {
2424 let mut rng = TestDRNG :: new( seed) ;
25- let ( instance, witness) = $test_fn( $( generate_ni_function !( @arg rng, $param) ) ,* ) ;
25+ let ( instance, witness) = $test_fn( $( generate_ni_function_iv !( @arg rng, $param) ) ,* ) ;
2626
2727 let protocol = SchnorrProtocolCustom :: from( instance) ;
2828 let nizk = NIProtocol :: from_iv( iv, protocol) ;
@@ -42,23 +42,73 @@ macro_rules! generate_ni_function {
4242 } ;
4343}
4444
45- generate_ni_function ! ( NI_discrete_logarithm , discrete_logarithm, srandom) ;
46- generate_ni_function ! ( NI_dleq , dleq, prandom, srandom) ;
47- generate_ni_function ! (
48- NI_pedersen_commitment ,
45+ /// Macro to generate non-interactive sigma protocols test functions with session ID
46+ macro_rules! generate_ni_function_session {
47+ ( $name: ident, $test_fn: ident, $( $param: tt) ,* ) => {
48+ #[ allow( non_snake_case) ]
49+ fn $name( seed: & [ u8 ] , session_id: & [ u8 ] ) -> ( Vec <Scalar >, Vec <u8 >, Vec <u8 >) {
50+ let mut rng = TestDRNG :: new( seed) ;
51+ let ( instance, witness) = $test_fn( $( generate_ni_function_session!( @arg rng, $param) ) ,* ) ;
52+
53+ let statement = instance. label( ) ;
54+ let protocol = SchnorrProtocolCustom :: from( instance) ;
55+ let nizk = NIProtocol :: new( session_id, protocol) ;
56+
57+ let proof_bytes = nizk. prove_batchable( & witness, & mut rng) . unwrap( ) ;
58+ let verified = nizk. verify_batchable( & proof_bytes) . is_ok( ) ;
59+ assert!( verified, "Fiat-Shamir Schnorr proof verification failed" ) ;
60+ ( witness, proof_bytes, statement)
61+ }
62+ } ;
63+
64+ ( @arg $rng: ident, $type: ident) => {
65+ G :: $type( & mut $rng)
66+ } ;
67+ ( @arg $rng: ident, [ $type: ident; $count: expr] ) => {
68+ ( 0 ..$count) . map( |_| G :: $type( & mut $rng) ) . collect:: <Vec <_>>( ) . try_into( ) . unwrap( )
69+ } ;
70+ }
71+
72+ generate_ni_function_iv ! ( NI_discrete_logarithm_iv , discrete_logarithm, srandom) ;
73+ generate_ni_function_iv ! ( NI_dleq_iv , dleq, prandom, srandom) ;
74+ generate_ni_function_iv ! (
75+ NI_pedersen_commitment_iv ,
4976 pedersen_commitment,
5077 prandom,
5178 srandom,
5279 srandom
5380) ;
54- generate_ni_function ! (
55- NI_pedersen_commitment_dleq ,
81+ generate_ni_function_iv ! (
82+ NI_pedersen_commitment_dleq_iv ,
5683 pedersen_commitment_dleq,
5784 [ prandom; 4 ] ,
5885 [ srandom; 2 ]
5986) ;
60- generate_ni_function ! (
61- NI_bbs_blind_commitment_computation ,
87+ generate_ni_function_iv ! (
88+ NI_bbs_blind_commitment_computation_iv ,
89+ bbs_blind_commitment_computation,
90+ [ prandom; 4 ] ,
91+ [ srandom; 3 ] ,
92+ srandom
93+ ) ;
94+
95+ generate_ni_function_session ! ( NI_discrete_logarithm_session , discrete_logarithm, srandom) ;
96+ generate_ni_function_session ! ( NI_dleq_session , dleq, prandom, srandom) ;
97+ generate_ni_function_session ! (
98+ NI_pedersen_commitment_session ,
99+ pedersen_commitment,
100+ prandom,
101+ srandom,
102+ srandom
103+ ) ;
104+ generate_ni_function_session ! (
105+ NI_pedersen_commitment_dleq_session ,
106+ pedersen_commitment_dleq,
107+ [ prandom; 4 ] ,
108+ [ srandom; 2 ]
109+ ) ;
110+ generate_ni_function_session ! (
111+ NI_bbs_blind_commitment_computation_session ,
62112 bbs_blind_commitment_computation,
63113 [ prandom; 4 ] ,
64114 [ srandom; 3 ] ,
@@ -71,14 +121,14 @@ generate_ni_function!(
71121fn test_spec_testvectors ( ) {
72122 let seed = b"hello world" ;
73123 let iv = * b"yellow submarineyellow submarine" ;
74- let vectors = extract_vectors ( "src/tests/spec/vectors/allVectors.json" ) . unwrap ( ) ;
124+ let vectors = extract_vectors_iv ( "src/tests/spec/vectors/allVectors.json" ) . unwrap ( ) ;
75125
76126 let functions: [ fn ( & [ u8 ] , [ u8 ; 32 ] ) -> ( Vec < Scalar > , Vec < u8 > ) ; 5 ] = [
77- NI_discrete_logarithm ,
78- NI_dleq ,
79- NI_pedersen_commitment ,
80- NI_pedersen_commitment_dleq ,
81- NI_bbs_blind_commitment_computation ,
127+ NI_discrete_logarithm_iv ,
128+ NI_dleq_iv ,
129+ NI_pedersen_commitment_iv ,
130+ NI_pedersen_commitment_dleq_iv ,
131+ NI_bbs_blind_commitment_computation_iv ,
82132 ] ;
83133
84134 for ( i, f) in functions. iter ( ) . enumerate ( ) {
@@ -95,7 +145,61 @@ fn test_spec_testvectors() {
95145 }
96146}
97147
98- fn extract_vectors ( path : & str ) -> json:: Result < Vec < ( Vec < u8 > , Vec < u8 > ) > > {
148+ #[ allow( clippy:: type_complexity) ]
149+ #[ allow( non_snake_case) ]
150+ #[ test]
151+ fn test_spec_testvectors_with_fixed_label ( ) {
152+ let seed = b"hello world" ;
153+ let session_id = b"yellow submarineyellow submarine" ;
154+ let vectors = extract_vectors_session ( "src/tests/spec/vectors/fixedLabelVectors.json" ) . unwrap ( ) ;
155+
156+ let functions: [ fn ( & [ u8 ] , & [ u8 ] ) -> ( Vec < Scalar > , Vec < u8 > , Vec < u8 > ) ; 5 ] = [
157+ NI_discrete_logarithm_session ,
158+ NI_dleq_session ,
159+ NI_pedersen_commitment_session ,
160+ NI_pedersen_commitment_dleq_session ,
161+ NI_bbs_blind_commitment_computation_session ,
162+ ] ;
163+
164+ for ( i, f) in functions. iter ( ) . enumerate ( ) {
165+ let ( _, proof_bytes, statement) = f ( seed, session_id) ;
166+ assert_eq ! (
167+ session_id. as_slice( ) ,
168+ vectors[ i] . 0 . as_slice( ) ,
169+ "context for test vector {i} does not match"
170+ ) ;
171+ assert_eq ! (
172+ proof_bytes, vectors[ i] . 1 ,
173+ "proof bytes for test vector {i} does not match"
174+ ) ;
175+ assert_eq ! (
176+ statement, vectors[ i] . 2 ,
177+ "statement for test vector {i} does not match"
178+ ) ;
179+ }
180+ }
181+
182+ fn extract_vectors_iv ( path : & str ) -> json:: Result < Vec < ( Vec < u8 > , Vec < u8 > ) > > {
183+ let content = fs:: read_to_string ( path) . expect ( "Unable to read JSON file" ) ;
184+ let root: JsonValue = json:: parse ( & content) . expect ( "JSON parsing error" ) ;
185+ root. entries ( )
186+ . map ( |( _, obj) | {
187+ let context_hex = obj[ "Context" ]
188+ . as_str ( )
189+ . expect ( "Context field not found or not a string" ) ;
190+ let proof_hex = obj[ "Proof" ]
191+ . as_str ( )
192+ . expect ( "Proof field not found or not a string" ) ;
193+ Ok ( (
194+ Vec :: from_hex ( context_hex) . unwrap ( ) ,
195+ Vec :: from_hex ( proof_hex) . unwrap ( ) ,
196+ ) )
197+ } )
198+ . collect ( )
199+ }
200+
201+ #[ allow( clippy:: type_complexity) ]
202+ fn extract_vectors_session ( path : & str ) -> json:: Result < Vec < ( Vec < u8 > , Vec < u8 > , Vec < u8 > ) > > {
99203 let content = fs:: read_to_string ( path) . expect ( "Unable to read JSON file" ) ;
100204 let root: JsonValue = json:: parse ( & content) . expect ( "JSON parsing error" ) ;
101205 root. entries ( )
@@ -106,9 +210,13 @@ fn extract_vectors(path: &str) -> json::Result<Vec<(Vec<u8>, Vec<u8>)>> {
106210 let proof_hex = obj[ "Proof" ]
107211 . as_str ( )
108212 . expect ( "Proof field not found or not a string" ) ;
213+ let statement_hex = obj[ "Statement" ]
214+ . as_str ( )
215+ . expect ( "Statement field not found or not a string" ) ;
109216 Ok ( (
110217 Vec :: from_hex ( context_hex) . unwrap ( ) ,
111218 Vec :: from_hex ( proof_hex) . unwrap ( ) ,
219+ Vec :: from_hex ( statement_hex) . unwrap ( ) ,
112220 ) )
113221 } )
114222 . collect ( )
0 commit comments