如何在Java中获取RSA密钥的大小

如何在Java中获取RSA密钥的大小,java,rsa,Java,Rsa,给定java.security.interfaces.RSAKey,如何获取其大小?您可以尝试以下方法: key.getModulus().bitLength(); RSA密钥的大小是其模中的位数,因此您需要 myRSAKey.GetModules().bitLength()(编辑:我在理解为RSA密钥生成的素整数的限制之前编写了此响应。我现在认为,任何好的密钥生成器都应该确保模数在2^(n-1)之间和2^n-1。因此,模的最小补码表示形式将始终精确地具有在创建密钥时为密钥长度指定的位数。因此

给定java.security.interfaces.RSAKey,如何获取其大小?

您可以尝试以下方法:

key.getModulus().bitLength();

RSA密钥的大小是其模中的位数,因此您需要
myRSAKey.GetModules().bitLength()
(编辑:我在理解为RSA密钥生成的素整数的限制之前编写了此响应。我现在认为,任何好的密钥生成器都应该确保模数在2^(n-1)之间和2^n-1。因此,模的最小补码表示形式将始终精确地具有在创建密钥时为密钥长度指定的位数。因此,例如,如果创建2048位密钥,则key.getmodule().bitLength()将始终返回2048。)

请原谅,但是当模的最高有效位为0时,
key.getmodule().bitLength()
是否返回错误的值?例如,对于2048位的键,如果模的最高有效位为0,则
key.getmodule().bitLength()
将返回2047(如果更多位为0,则返回的值会更小)。我认为在这种情况下,预期的结果实际上是2048年

本文件内容如下:

返回此BigInteger的最小补码表示形式中的位数,不包括符号位。对于正大整数,这相当于普通二进制表示中的位数。(计算(ceil(log2(this<0?:this+1)))

恐怕我们需要对钥匙的尺寸做出一些假设。例如,您必须假设只会看到1024、2048或4096位密钥,然后执行以下操作:

int keySize;
int bitLength = key.getModulus().bitLength();
if (bitLength <= 512) {
  throw new IllegalArgumentException(...)
}
else if (bitLength <= 1024) {
  keySize = 1024;
}
else if (bitLength <= 2048) {
  keySize = 2048;
}
else if (bitLength <= 4096) {
  keySize = 4096;
}
else {
  throw new IllegalArgumentException(...)
}
return keySize;
int-keySize;
int bitLength=key.getModules().bitLength();

如果(bitLength我同意公认答案中提到的Wheezil的担忧。8个前导0位的模将破坏该方法。这有0.4%的几率发生,这在我看来是不可接受的。因此我个人使用该方法:

Cipher rsa = Cipher.getInstance("RSA");
rsa.init(Cipher.ENCRYPT_MODE, yourKey);
int keyBitSize = rsa.getOutputSize(0) * Byte.SIZE;

…因为RSA输出大小始终与密钥的模数大小相同,即使输入长度为0。

不要重复发布:此代码在任何情况下都是错误的。
key.getmodule().bitLength()
是由“密钥大小”或“密钥长度”定义的值术语。用任意选择的值替换它是完全错误的。Oleg,你当然是对的。我添加编辑是为了解释我对生成密钥的主要因素限制的误解。如果仍然对糟糕的密钥生成器心存疑虑,可以使用取整:keySize=((bitLength+127)/128)*128.比猜测更好。高128位全为零的可能性是2^128中的1。不幸的是,在一些互操作情况下,需要选择2的幂。如果您尝试将Java生成的公钥导入.Net并使用它加密数据,则除非密钥长度与预期值匹配,否则它不会在Java中解密如果生成了2048位的密钥,则不能为.Net提供2040位(密钥大小写为8个前导零)或2052位的密钥(如果将BigInteger转换为十六进制字符串,则可以获得额外的前导0)。您必须给它精确的2048位。这并不总是导致错误,但会影响OAEP填充方案。如中所述,如果您的密钥有八个前导零,则此策略可能会失败。不幸的是,在某些互操作情况下,必须选择二的幂。如果您尝试将Java生成的公钥导入.Net并使用它加密数据,除非密钥长度与预期相符,否则它不会在Java中解密。如果生成2048位密钥,则无法为.Net提供2040位(密钥大小写为8个前导零)或2052位的密钥(如果将BigInteger转换为十六进制字符串,则可以获得额外的前导0)。您必须精确地给它2048位。它会影响OAEP填充方案。正如4分钟中所解释的,太晚了,该死!:P