Skip to content

Sign V2#3284

Open
Antonio95 wants to merge 9 commits into
stagingfrom
feat/sign_v2
Open

Sign V2#3284
Antonio95 wants to merge 9 commits into
stagingfrom
feat/sign_v2

Conversation

@Antonio95

Copy link
Copy Markdown
Contributor

This PR

  • Introduces a Signature::sign_v2 function which adds a prefix to the message being signed.
  • Introduces Signature::sign_bits_v2 and Signature::sign_bytes_v2, which operate similarly to their original (non-v2) counterparts but 1) add the length of the message to the message itself and 2) sign using Signature::sign_v2 (i.e. with a prefix) under the hood.
  • Introduces Signature::sign_bits_raw_v2 and Signature::sign_bytes_raw_v2, analogous to the above but not including message length (i.e. incorporating 2) but not 1)).
  • Introduces a small restriction in the inputs allowed to Signature::sign.
  • Adds relevant tests that the above work as expected and some rejection tests.

Note that all Signature::sign*/verify* functions have also PrivateKey::sign*/verify* wrappers. Request::sign/verify are unaffected.

The last clean build is the next-to-last commit at the time of writing: c534e88.

This PR is in draft mode until we decide:

  • Whether to deprecate the original Signature::sign.
  • If so, what to do about the many uses of it present in snarkVM, snarkOS, the SDK and any other relevant repos.

Some options to handle the resulting complications include:

  • Not marking sign as deprecated, and simply documenting/making developers aware sign_v2 is the preferred option from now on.
  • Marking it as deprecated and doing one of the following:
    • Changing all uses across the relevant repos to sign_v2. Note signatures are used in some delicate (e.g. consensus-related) paths.
    • Annotating every current use in the relevant repos with #[allow(deprecated)] (deciding on a case-by-case basis whether to switch to sign_v2 instead)
    • Hiding the deprecation annotation behind the non-presence of a new feature (e.g. sign_v1) and updating our Cargo.tomls to import the crate with that flag. This makes it less likely external developers would use the deprecated function by mistake (they would have to activate the feature flag in the dependency). As a slightly negative aspect of this approach, this means future developers of our own repos would have to be aware that sign_v2 is the preferred option from now onwards (since the presence of the feature flag in the import means the deprecation notice would not be displayed).

The last commit at the time of writing, 96e9269, adds the deprecation notice to Signature::sign and, for most of its current uses, it switches to sign_v2 or annotates them with #[allow(deprecated)]. Note this is only for illustrative purposes.

let message: Vec<_> = (0..num_fields).map(|_| Uniform::rand(rng)).collect();
let signature = console::Signature::sign(&private_key, &message, rng).unwrap();
assert!(signature.verify(&address, &message));
let signature = console::Signature::sign_v2(&private_key, &message, rng).unwrap();

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this arithmetization equivalent / backwards compatible?

Comment on lines +102 to +109
// TODO (Antonio) re-introduce
// Ok(fields) => self.verify_v2(address, &fields),
Ok(fields) => {
for f in fields.iter() {
println!(" f: {f}");
}
self.verify_v2(address, &fields)
}

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Leftover debug code?

}

#[test]
fn test_sign_and_verify_bits_v2_padding() -> Result<()> {

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No test would catch a change to SIGNATURE_V2_PREFIX or the length encoding so maybe worth checking against hardcoded values?

Comment on lines +241 to +246
let candidate_string = serde_json::to_string(&expected_signature).unwrap();
assert_eq!(expected_string, serde_json::Value::from_str(&candidate_string).unwrap().as_str().unwrap());

// Deserialize
assert_eq!(expected_signature_v2, serde_json::from_str(&candidate_string).unwrap());
assert_eq!(expected_signature, Signature::<CurrentNetwork>::from_str(expected_string).unwrap());

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
let candidate_string = serde_json::to_string(&expected_signature).unwrap();
assert_eq!(expected_string, serde_json::Value::from_str(&candidate_string).unwrap().as_str().unwrap());
// Deserialize
assert_eq!(expected_signature_v2, serde_json::from_str(&candidate_string).unwrap());
assert_eq!(expected_signature, Signature::<CurrentNetwork>::from_str(expected_string).unwrap());
let candidate_string = serde_json::to_string(&expected_signature_v2).unwrap();
assert_eq!(expected_string, serde_json::Value::from_str(&candidate_string).unwrap().as_str().unwrap());
// Deserialize
assert_eq!(expected_signature_v2, serde_json::from_str(&candidate_string).unwrap());
assert_eq!(expected_signature_v2, Signature::<CurrentNetwork>::from_str(expected_string).unwrap());

Comment on lines 164 to +165
}

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
}
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants