
EdDSA, Ed25519, Ed25519-IETF, Ed25519ph, Ed25519ctx, HashEdDSA, PureEdDSA, WTF? - baby
https://www.cryptologie.net/article/497/eddsa-ed25519-ed25519-ietf-ed25519ph-ed25519ctx-hasheddsa-pureeddsa-wtf/
======
wahern
Prehashing doesn't just solve the storage issue. Imagine you want to sign a
1MB or even 1GB file with a typical hardware token. Without prehashing you'd
have to send that entire 1MB or 1GB to the token, which has a throughput on
the order of KB/s or maybe MB/s, and process all that data with a CPU clocked
at MHz, not GHz. Breaking up the file into chunks doesn't help, and might even
make things slower, not to mention the added complexity introduced to your
file signature format.

The obvious solution is to _hash_ the data and sign the hash, just as is done
for every other signature scheme. The downside is that now your signature
scheme is only as strong as the hash. But if it turns out that SHA-512 isn't
collision resistant, you have much bigger problems.

PureEdDSA has its elegance, and, sure, use it if you can. But supporting off-
chip private keys (e.g. hardware tokens) is sometimes far more important to
security. If you're creating an API, keep that in mind.

~~~
dchest
Please stop saying "you have much bigger problems", this cliché is dangerous
and unproductive.

~~~
beart
I don't see why that's dangerous. it's just a rephrasing of "this assumes x
holds true" and if it doesn't none of this matters.

~~~
krick
I don't know what's the parent's problem, but "this assumes x holds true" is
actually much more clear and straight-forward, which really helps to stay on
track with the discussion. At the very least it allows the opponent to ask if
there's something available w/o this assumption, which "you have bigger
problems" barely does.

------
kwantam
A slightly unfortunate trend in protocol design has been to prepend rather
than append "info" fields to hash inputs. In other words, we tend to see

    
    
        H(info || msg)
    

instead of

    
    
        H(msg || info)
    

There are some good reasons to prefer append to prepend. One practical reason
is that---related to what's discussed in the article---if we have to compute
two values

    
    
        H(msg || info_1)
        H(msg || info_2)
    

we can do this with just one pass over msg (though admittedly in a non-
blackbox way, namely, by saving an intermediate state of the hash
computation). In contrast, for a well-designed hash function there should not
be any way to save work when computing

    
    
        H(info_1 || msg)
        H(info_2 || msg)
    

and this lack of work savings is one of the reasons we tend to get prehash
modes.

In addition, prepending to msg comes with a range of subtle security issues.
As an example, for Merkle-Damgaard hashes like SHA-2 a proper prefix design
needs to pad the prefix to a multiple of H's block length. This is to ensure
that msg starts on a block boundary, which means that the hash digests as much
of msg as possible in a single invocation of the compression function.
Otherwise, if msg is short and it gets broken across a block boundary, this
can make meet-in-the-middle--style attacks easier.

In contrast, appending the info string guarantees that msg starts at a block
boundary, which is a small nicety. Moreover, one can easily guarantee in a
black-box way (and independent of the value/encoding/&c of the info string)
that msg _ends_ at a block boundary (just by padding msg). This can be useful
as a defense against some kinds of power analysis in the case that msg is a
secret [1].

To be sure: appending also requires care---and care is always required when a
Merkle-Damgaard hash! (Sponges like SHA-3 are more resistant to misuse.) At
the very least, whatever is appended to msg should be prefix-free, and you
will likely want to stop length extension attacks and related issues (see [2]
for further discussion of this).

But in general my take is that the set of footguns for append is a subset of
the prepend ones, and I hope that more folks go towards appending in the
future.

[1] [https://eprint.iacr.org/2017/985](https://eprint.iacr.org/2017/985)

[2]
[https://cs.nyu.edu/~dodis/ps/merkle.pdf](https://cs.nyu.edu/~dodis/ps/merkle.pdf)

~~~
pbsd
> Otherwise, if msg is short and it gets broken across a block boundary, this
> can make meet-in-the-middle--style attacks easier.

Can you elaborate? Take SHA-512/256 with some awkward prefix size, let's say
127 bytes. Which attacks, presumably not side-channel based, become possible?

In any case, I am not convinced in the least by this suffix pitch. Handwaving
that "prefix-freeness" needs to be checked, when that's something that is
constantly gotten wrong and results in real breaks is a bit naïve. On the
other hand, I have real trouble thinking of a real break caused by prefixing.
The Ed25519 paper you link to does not point to prefixing as the culprit
either; that just happened to be where the key was, and the lack of randomness
makes power analysis possible. Without randomness, suffixing would suffer a
similar fate.

~~~
kwantam
SHA-512/256 is already quite misuse-resistant, so it's entirely plausible that
there's nothing to worry about in this specific case.

But if we limit ourselves to standard Merkle Damgaard hashes (i.e., _not_
ChopMD), then the specific concern is that putting a small amount (say, a few
bytes) of msg at the end of one block lets us, in effect, look for collisions
between two M-D hash functions where one has an attacker-chosen IV. Here, the
key property is that the IV space is large enough to be useful but small
enough to be feasibly searchable.

For SHA-2, this does not currently appear to be a problem, but the
conservative move is to rule this out by construction. HMAC does this, for
example (and as I'm certain you know, HMAC-SHA-1 remains plausibly secure in
spite of all of the attacks on SHA-1).

Regarding prefix-freeness: I completely agree with you that this is easy to
get wrong, and I didn't intend to hand-wave about this in the least. Note,
however, that the requirement for prefix-freeness obtains for both prepend and
append! So this isn't actually an argument against appending.

Regarding the power analysis: apologies, I should have been clearer on this
point. One interpretation of the Ed25519 paper I linked is that the issue has
to do with putting the secret in the same block as attacker-controlled bytes,
because this gives the attacker a lot more power to extract information about
the secret via power analysis. Even without randomness, this attack would be
_much_ harder to pull off (perhaps even impossible) if the secret were padded
to a full block length.

My point was just: don't put secrets and attacker-controlled data in the same
block. And suffixing always lets us do this by applying a padding routine that
is independent of the info string to msg.

------
dathinab
Don't confuse EdDSA with ECDSA, I was stumped for a moment until I realized my
mistake ;=)

------
jchook
To be sure, none of these are quantum-ready.

~~~
spopejoy
Yes but ED-448 is Spinal-Tap Grade

