Skip to content

Implement MultipartSigner/Verifier #982

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 6 commits into from
Jun 5, 2025

Conversation

daxpedda
Copy link
Contributor

@daxpedda daxpedda commented Jun 1, 2025

Implementation of MultipartSigner and MultipartVerifier added in RustCrypto/traits#1880.

The implementation in ML-DSA and SLH-DSA is not ideal. Basically all the relevant functions are public and only take &[u8]. So instead of changing public functions, I just moved the implementation of those functions into private functions that take &[&[u8]]. Let me know if you want me to solve this in any other way.

@tarcieri
Copy link
Member

tarcieri commented Jun 1, 2025

It would be good to add it to ecdsa for completeness, so the trait works over all signature algorithms.

(Maybe we can add a macro to write impls for types which impl DigestSigner, or possibly a blanket impl, but start with ecdsa first)

@daxpedda daxpedda force-pushed the multi-part-sign-verify branch from 5c3f521 to ea896d2 Compare June 1, 2025 19:21
@daxpedda
Copy link
Contributor Author

daxpedda commented Jun 1, 2025

Done.

Just leaving a list of potentially other applicable implementations:

  • bign256 (not covered by ecdsa)
  • sm2 (not covered by ecdsa)
  • DSA
  • LMS

@tarcieri
Copy link
Member

tarcieri commented Jun 1, 2025

There's also rsa (both RSASSA-PKCS#1v1.5 and PSS)

@daxpedda
Copy link
Contributor Author

daxpedda commented Jun 1, 2025

Just a thought I had: we could expose the new private functions in ML-DSA and SLH-DSA as sign_multi_part_internal(). But yeah, it would introduce a bunch of almost duplicate functions.

@daxpedda
Copy link
Contributor Author

daxpedda commented Jun 1, 2025

There's also rsa (both RSASSA-PKCS#1v1.5 and PSS)

Let me know if you want me to add if there as well.
Will add an up-to-date list in RustCrypto/traits#1880.

@daxpedda daxpedda changed the title Implement MultiPartSigner/Verifier for ML-DSA and SLH-DSA Implement MultipartSigner/Verifier for ML-DSA and SLH-DSA Jun 1, 2025
@daxpedda daxpedda changed the title Implement MultipartSigner/Verifier for ML-DSA and SLH-DSA Implement MultipartSigner/Verifier Jun 2, 2025
tarcieri pushed a commit to RustCrypto/traits that referenced this pull request Jun 2, 2025
This PR adds new traits for multipart messages: `MultipartSigner`,
`RandomizedMultipartSigner`, `RandomizedMultipartSignerMut` and
`MultipartVerifier`.

The idea here is to allow non-contiguous bytes to be passed, which is
necessary when the message has to be constructed from multiple sources
without wanting to allocate memory for a contiguous message. E.g. for
`no_std` environments or when the message is rather big but pre-hashing
is not applicable, e.g. PureEdDSA, ML-DSA or SLH-DSA.

I know this is a rather big breaking change, so let me know what you
think!

These new traits can be implemented by a bunch of crates:
- [x] `ecdsa`: RustCrypto/signatures#982
- [x] `ml-dsa`: RustCrypto/signatures#982
- [x]  `slh-dsa`: RustCrypto/signatures#982
- [x] `bign256`: RustCrypto/elliptic-curves#1221
- [x] `sm2`: RustCrypto/elliptic-curves#1221
- [x] `k256`: RustCrypto/elliptic-curves#1221
- [x] `dsa`: RustCrypto/signatures#982
- [x] `lms`: RustCrypto/signatures#982
- [x] `rsa`: RustCrypto/RSA#525
- [ ] `ed25519-dalek`

Resolves RustCrypto/signatures#959.
@daxpedda daxpedda marked this pull request as ready for review June 2, 2025 22:09
Comment on lines +171 to +174
fn message_representative(tr: &[u8], Mp: &[&[&[u8]]]) -> B64 {
let mut h = H::default().absorb(tr);

for m in Mp {
for m in Mp.iter().copied().flatten() {
Copy link
Member

Choose a reason for hiding this comment

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

Hmm, is the &[&[&[u8]]] really necessary here?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

We have to prefix the message with a couple of things: a tag (0), a context length and the context (&[u8]) itself. Unfortunately you can't concat stuff to an existing &[&[u8]], so this is what I went for.

We could add a prefix: &[&[u8]] parameter instead. Another alternative would be to change it to a impl Iterator<Item = &[u8]>, then we can Iterator::chain() stuff to each other.

Let me know if you prefer any of these alternatives.

@tarcieri tarcieri merged commit 85c1abb into RustCrypto:master Jun 5, 2025
75 checks passed
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.

2 participants