RustCrypto / hashes

Collection of cryptographic hash functions written in pure Rust
1.75k stars 238 forks source link

Broken documentation: What on earth is "GenericArray" #563

Closed VorpalBlade closed 2 weeks ago

VorpalBlade commented 4 months ago

https://docs.rs/sha2/latest/sha2/trait.Digest.html indicates I need to finalise into something called an "GenericArray". Unfortunately I have no idea what that is, as unlike most types this is not actually a link to the type. Usually rustdoc is pretty good about this, so I assume you did something unusual.

Hm, maybe it is some sort of trait. Lets try:

let mut hasher = Sha256::new();
// ...
let mut actual: [u8; 32] = [0; 32];
let hash = hasher.finalize_into(&mut actual);

Nope!

error[E0308]: mismatched types
   --> crates/paketkoll/src/arch.rs:191:45
    |
191 |             let hash = hasher.finalize_into(&mut actual);
    |                               ------------- ^^^^^^^^^^^ expected `&mut GenericArray<u8, UInt<..., ...>>`, found `&mut [u8; 32]`
    |                               |
    |                               arguments to this method are incorrect
    |
    = note: expected mutable reference `&mut GenericArray<u8, UInt<UInt<UInt<UInt<UInt<UInt<UTerm, B1>, B0>, B0>, B0>, B0>, B0>>`
               found mutable reference `&mut [u8; 32]`
note: method defined here

Also that is a really strange type. And it seems to confuse rust-analyzer in vscode such that I don't actually get any help for it.

All your examples in the sha2 crate only shows using finalize, not finalize_into. I want a stack allocated array in the end, and I need to compare it to an [u8; 32] that I get from elsewhere. It doesn't seem convertible. E.g. this doesn't work either:

let mut hasher = Sha256::new();
// ...
let mut actual = Default::default();
let hash = hasher.finalize_into(&mut actual);

if actual.into() != expected { // where expected is [u8; 32]
    // ...
}

(Nor does it help adding actual.into::<[u8; 32]>).

VorpalBlade commented 4 months ago

Apparently I can do actual[..] != expected[..], but that will have runtime bounds checks, so not an acceptable solution.

tarcieri commented 4 months ago

Usually rustdoc is pretty good about this, so I assume you did something unusual.

It actually seems like a bug in rustdoc. For whatever reason it's not linking to the relevant type, which is:

https://docs.rs/generic-array/0.14.7/generic_array/struct.GenericArray.html

Note that in the next release we'll be migrating to hybrid-array, although strangely the rustdoc issues seem to persist, e.g.:

https://docs.rs/digest/0.11.0-pre.8/digest/type.Output.html

I'm not sure why rustdoc is having an issue with this, but perhaps we should file an upstream bug, and in the meantime add manual links to the relevant types.

Note that hybrid-array will address your concerns about PartialEq impls.

tarcieri commented 4 months ago

This seems like a recent rustdoc regression. I've filed an upstream issue: https://github.com/rust-lang/rust/issues/120983

VorpalBlade commented 4 months ago

It also seems your types (e.g. Sha256 or Md5) confuses Rust Analyzer enough that I don't get any completion suggestions on them. Could it be related (e.g. your code is too confusing for the tools for some reason).

tarcieri commented 4 months ago

That's probably related to https://github.com/RustCrypto/traits/issues/1069

jssblck commented 4 months ago

It would be incredibly helpful if we could get a finalize_into_boxed_slice or something. GenreicArray has been a pain the whole time I've worked with this crate :(

VorpalBlade commented 4 months ago

It would be incredibly helpful if we could get a finalize_into_boxed_slice or something. GenreicArray has been a pain the whole time I've worked with this crate :(

That wouldn't solve my problem. I don't want to do extra allocations. I want to finalize into a statically sized array on the stack. That would be the ideal solutions for me.

tarcieri commented 4 months ago

Digest::finalize_into can be used for that

newpavlov commented 2 weeks ago

Closing in favor of https://github.com/rust-lang/docs.rs/issues/2528