# Are RSA-SHA256 signatures prone to length extension attacks?

I need to sign a message using a private key and verify the message with a public key, while making sure the message hasn’t been tampered.

I know that SHA-256 itself is prone to length-extension attacks.

I also know that things like HMAC have been specifically designed to circumvent such attacks.

But what if I sign a message with RSA and SHA-256? Are they safe?

Do I need to sign the RSA/SHA3 to be protected? Or maybe truncated versions of SHA2 (namely SHA-384 and SHA-512/256) which are allegedly not susceptible to length-extension attacks?

Would HMAC be a better approach to this problem?

I’m considering using RSA which is probably the most famous among asymmetric cryptography. Feel free to point me to something else if there’s a better option. I need something supported by OpenSSL and the Node.js crypto module (which, as far as I know, is also based on OpenSSL).

PS. I’m a bit new to the crypto community, so I hope my words make sense.

Here is my concern about RSA-SHA256.

Let’s say the message is $$M$$ and its hash is $$SHA256(M)$$.

An attacker can use them to compute $$M||X$$ and $$SHA256(M||X)$$, even without knowing the private key. In this case, the recipient of $$M||X$$ and its signature $$SHA256(M||X)$$ shall believe that the message is valid because the message and its signature do match.

At least that’s what happens if RSA_sign simply uses the raw hash. If RSA passes the hash through a HMAC-like technique or any algorithm that prevents the attacker from forging a signature, I guess we’re safe.

• A possible dupe of: How can Hashed Value be same in length extension attack? Mar 21 at 12:28
• Does this answer your question? Is HMAC needed for a SHA-3 based MAC? Mar 21 at 14:08
• @AleksanderCH thanks for the link. It partially answers the question. It shows that a SHA3-based MAC would be safe without a HMAC, which was one of my assumptions. But it doesn’t tell if RSA-SHA256 sign/verify is safe, which is my main question. Mar 21 at 14:26
• Does this answer your question? How can Hashed Value be same in length extension attack? Mar 21 at 20:34
• @kelalaka that’s an interesting read about how length-extension attacks work, but it doesn’t tell if RSA-SHA256 is susceptible to them. Mar 22 at 9:52

But what if I sign a message with RSA and SHA-256? Are they safe?

Length extension attacks are not a concern.

Here is what a length extension attack allows you do to: if you are given the hash $$\text{SHA256}(M)$$, but you don't know the original message $$M$$ (but you do know its length), then you can compute the value of the hash $$\text{SHA256}(M || X)$$ (where $$||$$ is bitstring concatenation, and for some values of the string $$X$$); the value of this hash will be different than the original hash.

So, why isn't this a concern:

• When you have a signature of a known message $$M$$, you obviously know $$M$$; you can (should you want) compute $$\text{SHA256}(M || X)$$ for any string $$X$$ you want; you don't need a "length extension attack"

• RSA signs the value $$\text{SHA256}(M)$$; the value $$\text{SHA256}(M || X)$$ will be different, and so if you replace $$M$$ with $$M || X$$, the signature will not verify

• My concern is, the attacker knows M and SHA256(M), so he may compute M||X and SHA256(M||X) (even without knowing the private key). In this case, the recipient of M||X and its signature SHA256(M||X) will not know that the message was tampered because the altered message and its signature will match. Well, at least that’s what happens if RSA_sign simply uses the raw hash. If RSA passes the hash through a HMAC-like technique, I guess we’re safe. Mar 21 at 12:59
• @vdavid: "so he may compute M||X and SHA256(M||X) (even without knowing the private key)." - how is that different from (say) SHA3? With SHA3, if he knows $M$ and selects $X$, he can compute SHA3(M||X). If you're thinking that SHA256(M||X) will be the same value as SHA256(M), well no, that's not how it works. Mar 21 at 13:14
• @vdavid: Your "the recipient of M||X and its signature SHA256(M||X)…" is in error. SHA256(M||X) is not the signature of M||X. It's an intermediary step in computing a signature of M||X, as a function of SHA256(M||X), private key, optional randomness. Among the three inputs of this function, only the private key is secret. Thus it is not an issue that SHA256(M||X) is easy to compute; it's a functional requirement.
– fgrieu
Mar 21 at 13:56
• @vdavid: you are correct that SHA3, unlike SHA-256, has no length-extension property. However you are incorrect in what that prevents. It prevents computing SHA3(M||X) from SHA3(M) unless one has complete knowledge of M (in the case of SHA-256, one further needs to restrict to some X with precisely the right start, dependent on the length of M). With knowledge of Mand X one can compute SHA3(M||X), for any M and X. Note: the Right Thing will be to accept poncho's answer by clicking on the tick.
– fgrieu
Mar 21 at 14:25
• @fgrieu You’re right. And because M is not secret in my case, I believe this property doesn’t give SHA3 a significant advantage over SHA-256 (at least, not from a length-extension point of view). Mar 21 at 14:30