生成具有大 public 指数的 RSA 密钥
Generate RSA key with large public exponent
步骤 1. 我分别为 Alice 和 Bob 生成了 RSA 密钥对,并使用 Alice 的 public 密钥为 Alice 加密了一条消息。
第 2 步。 我将 Bob 的 public 密钥的 public 指数与 Alice 私钥的私有指数相乘得到一个新数字。
步骤 3. 我通过 keyRegen := rsa.PublicKey{N: keyPubAliceN, E: ENew}
生成了一个新的 RSA public 密钥,并用它来加密在步骤 1 中加密的消息。
步骤 4. 我使用 Bob 的私钥解密了步骤 3 中重新加密的消息。理论上现在 Bob 可以得到原始消息,这是预期的输出。
问题: 但是,我发现 rsa.PublicKey 中的 public 指数应该是 int
,而我的新 [=43] =] 第二步生成的指数是一个big.Int
。我将其转换为 int
并使用新生成的 public 密钥进行加密,但发生错误 panic: crypto/rsa: public exponent too small
。另外我想我不应该做这样的转换,因为新数字可能大于 int
范围。那么有什么方法可以生成具有大 public 指数的新 RSA 密钥?谢谢!
代码:
package main
import (
"crypto"
"crypto/rand"
"crypto/rsa"
"crypto/sha256"
"fmt"
"math/big"
)
func main() {
keyPriAlice, err := rsa.GenerateKey(rand.Reader, 1024)
if err != nil {
panic(err)
}
keyPubAlice := keyPriAlice.PublicKey
keyPriAliceD := keyPriAlice.D
keyPubAliceN := keyPubAlice.N
keyPriBob, err := rsa.GenerateKey(rand.Reader, 1024)
if err != nil {
panic(err)
}
keyPubBob := keyPriBob.PublicKey
keyPubBobE := big.NewInt(int64(keyPubBob.E))
message := "secret"
encryptedBytes, err := rsa.EncryptOAEP(
sha256.New(),
rand.Reader,
&keyPubAlice,
[]byte(message),
nil)
if err != nil {
panic(err)
}
z := new(big.Int)
y := z.Mul(keyPriAliceD, keyPubBobE)
ENew := int(y.Int64())
keyRegen := rsa.PublicKey{N: keyPubAliceN, E: ENew}
reEncryptedBytes, err := rsa.EncryptOAEP(
sha256.New(),
rand.Reader,
&keyRegen,
[]byte(encryptedBytes),
nil)
if err != nil {
panic(err)
}
// decrypt the re-encrypted plaintext using Bob's private key
decryptedBytes, err := keyPriBob.Decrypt(nil, reEncryptedBytes, &rsa.OAEPOptions{Hash: crypto.SHA256})
fmt.Println("decryptedBytes:", decryptedBytes)
}
您可能需要为此使用不同的库。在大多数现代 RSA 上下文中,出于安全原因,我们希望私有指数 d 较大,但出于性能原因,我们希望 e 较小。实际上,我见过的绝大多数安全实现都为 e 选择 65537,它既安全又快速(因为恰好包含两个)。
Go 库做出了这样的假设,基于这样一个事实,即几乎每个 real-world 不是漏洞利用的场景都需要一个小的 e,e 将适合一个 int,这可能是不慎重的,但最终是合理的。您可能会发现 OpenSSL 更适合此目的,因为它倾向于对传递给它的数据做出更少的假设。
步骤 1. 我分别为 Alice 和 Bob 生成了 RSA 密钥对,并使用 Alice 的 public 密钥为 Alice 加密了一条消息。
第 2 步。 我将 Bob 的 public 密钥的 public 指数与 Alice 私钥的私有指数相乘得到一个新数字。
步骤 3. 我通过 keyRegen := rsa.PublicKey{N: keyPubAliceN, E: ENew}
生成了一个新的 RSA public 密钥,并用它来加密在步骤 1 中加密的消息。
步骤 4. 我使用 Bob 的私钥解密了步骤 3 中重新加密的消息。理论上现在 Bob 可以得到原始消息,这是预期的输出。
问题: 但是,我发现 rsa.PublicKey 中的 public 指数应该是 int
,而我的新 [=43] =] 第二步生成的指数是一个big.Int
。我将其转换为 int
并使用新生成的 public 密钥进行加密,但发生错误 panic: crypto/rsa: public exponent too small
。另外我想我不应该做这样的转换,因为新数字可能大于 int
范围。那么有什么方法可以生成具有大 public 指数的新 RSA 密钥?谢谢!
代码:
package main
import (
"crypto"
"crypto/rand"
"crypto/rsa"
"crypto/sha256"
"fmt"
"math/big"
)
func main() {
keyPriAlice, err := rsa.GenerateKey(rand.Reader, 1024)
if err != nil {
panic(err)
}
keyPubAlice := keyPriAlice.PublicKey
keyPriAliceD := keyPriAlice.D
keyPubAliceN := keyPubAlice.N
keyPriBob, err := rsa.GenerateKey(rand.Reader, 1024)
if err != nil {
panic(err)
}
keyPubBob := keyPriBob.PublicKey
keyPubBobE := big.NewInt(int64(keyPubBob.E))
message := "secret"
encryptedBytes, err := rsa.EncryptOAEP(
sha256.New(),
rand.Reader,
&keyPubAlice,
[]byte(message),
nil)
if err != nil {
panic(err)
}
z := new(big.Int)
y := z.Mul(keyPriAliceD, keyPubBobE)
ENew := int(y.Int64())
keyRegen := rsa.PublicKey{N: keyPubAliceN, E: ENew}
reEncryptedBytes, err := rsa.EncryptOAEP(
sha256.New(),
rand.Reader,
&keyRegen,
[]byte(encryptedBytes),
nil)
if err != nil {
panic(err)
}
// decrypt the re-encrypted plaintext using Bob's private key
decryptedBytes, err := keyPriBob.Decrypt(nil, reEncryptedBytes, &rsa.OAEPOptions{Hash: crypto.SHA256})
fmt.Println("decryptedBytes:", decryptedBytes)
}
您可能需要为此使用不同的库。在大多数现代 RSA 上下文中,出于安全原因,我们希望私有指数 d 较大,但出于性能原因,我们希望 e 较小。实际上,我见过的绝大多数安全实现都为 e 选择 65537,它既安全又快速(因为恰好包含两个)。
Go 库做出了这样的假设,基于这样一个事实,即几乎每个 real-world 不是漏洞利用的场景都需要一个小的 e,e 将适合一个 int,这可能是不慎重的,但最终是合理的。您可能会发现 OpenSSL 更适合此目的,因为它倾向于对传递给它的数据做出更少的假设。