2
$\begingroup$

The following NodeJS code, when run (v16.8.0), logs 512 to stdout.

const crypto = require("crypto");
const { privateKey } = crypto.generateKeyPairSync("rsa", {
    modulusLength: 4096,
});
const sign = crypto.createSign("RSA-SHA256").update("somestringtosign");
const signature = sign.sign(privateKey);
console.log(signature.length); // logs 512

If I change the modulus length to 2048, then 256 is logged to standard out.

I guess this makes sense, as the RSA spec says: signature, an octet string of length k, where k is the length in octets of the RSA modulus n. So a 256 bit hash (SHA256), when signed with an RSA key with a 4096 bits modulus, has a 4096 bits (512 bytes) output.

Can the signature length in RS256 indeed be longer than 256, depending on the size of the RSA key used? Is it "weird" to use a modulus that is longer than the hash function used? I see various identity providers that sign JWTs indeed all use 2048 bits modulus, but that might be coincidental.

(I noticed the IETF spec for RS256 says: A key of size 2048 bits or larger MUST be used with these algorithms. so apparently a modulus of 4096 would be allowed by the spec`)

UPDATE

Thanks to the comments and answers I now understand I asked the "wrong" question. I was (erroneously) expecting the length of the JWT's signature to equal the length of the hash digest produced by the hash algorithm (SHA256). I was therein confusing bits and bytes, because e.g SHA256 produces a digest of 256 bits (not bytes). The signature length I witnessed in my case was 256 bytes (not bits), which I now understand should equal the length of the public key's modulus (which indeed is the case as I was able to verify later).

$\endgroup$
3
  • 2
    $\begingroup$ Well, we have tons of questions about this. RSA signature needs padding to be secure that's RSA-PSS (search for RSA Probabilistic Signature Scheme). And also there is RSA-FDH (RSA-Full Domain Hash) signature and that is secure, too. In this case you need at least RSA-2048 and a hash function that can be output ~2047 bits like Shake128 of SHA3. $\endgroup$
    – kelalaka
    Nov 1, 2021 at 12:30
  • 1
    $\begingroup$ SHA-256 is a 256-BIT hash = 32 bytes not 256 bytes. Most cryptographic data is described in bits not bytes, although PKCS1 (nd JOSE) only supports multiples of a byte (formally octet) of 8 bits. To be secure RSA modulus must be much bigger than is needed for the hash -- SHA-256 gives 128-bit strength but RSA-3072 is needed to match it (and some people do 4096 because it looks nicer). See keylength.com and many many dozen existing questions. $\endgroup$ Nov 2, 2021 at 2:31
  • $\begingroup$ Thanks @dave_thompson_085! I edited and changed bytes to bit in the hash reference. $\endgroup$
    – Otto
    Nov 2, 2021 at 7:19

1 Answer 1

5
$\begingroup$

Can the signature length in RS256 indeed be longer than 256, depending on the size of the RSA key used?

Yes. In RSA (including RS256, which is RSASSA-PKCS1-v1_5 with SHA-256 as hash), the signature size depend on the size of the RSA key (actually, it's public modulus) used for signing. Specifically, the signature size (in bytes, before re-encoding as text) is the key size (in bit), divided by 8 and rounded up to the next integer. $\lceil 2048/8\rceil=256$ bytes. $\lceil 4096/8\rceil=512$ bytes.

Is it "weird" to use a modulus that is longer than the hash function used?

No. That's even required. From a formatting standpoint, the minimum signature size for RS256 (RSASSA-PKCS1-v1_5 with SHA-256) would be $2+8+1+19+32=62$ bytes, that is a 489-bit public modulus. That would be way too small to be secure, though. 2048-bit is considered the baseline for new applications. It's expected to provide 112-bit to 128-bit security against classical computers, comparable to a 224-bit or 256-bit hash's collision resistance. See this for recommendations on key size, and this for the status of factorization attacks.

I know no standard upper limit, and I see no reason for an implementation not to support at least 2048-byte (16384-bit) signatures.

$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.