当前位置: 首页 > 知识库问答 >
问题:

如何将JavaRSA公钥移植到c#加密函数?

梁存
2023-03-14

想要在java中使用生成的RSA公钥,在c#函数中加密数据并在Java解密函数中解密。

生成的Java公钥已被替换为c#中的模数标记:

static string publicKey = "<RSAKeyValue><Modulus>MFwwDQ...wEAAQ==</Modulus><Exponent>AQAB</Exponent></RSAKeyValue>";

C#加密功能:

  static string Encrypt(string text)
    {
        const int PROVIDER_RSA_FULL = 1;
        const string CONTAINER_NAME = "Tracker";

        CspParameters cspParams;
        cspParams = new CspParameters(PROVIDER_RSA_FULL);
        cspParams.KeyContainerName = CONTAINER_NAME;
       
        RSACryptoServiceProvider rsa1 = new RSACryptoServiceProvider(512,cspParams);
        rsa1.FromXmlString(publicKey);

        byte[] textBytes = Encoding.UTF8.GetBytes(text);
        byte[] encryptedOutput = rsa1.Encrypt(textBytes, RSAEncryptionPadding.Pkcs1);
        string outputB64 = Convert.ToBase64String(encryptedOutput);

        return outputB64;
    }

Java解密函数:

static String Decrypt(String encodedString,PrivateKey privKey) {
    try {
        Cipher cipher = Cipher.getInstance(cipherInstancename);
        cipher.init(Cipher.DECRYPT_MODE, privKey);
        byte[] decrypted = cipher.doFinal(Base64.getDecoder().decode(encodedString));
        return new String(decrypted, "UTF-8");
    } catch (Exception err) {
        return err.fillInStackTrace().toString();
    }
}

第一个问题:在c#XML字符串中替换模数标记中的Java公钥正确吗?指数标签呢?我用了AQAB值。

第二个问题:为什么在解密Java得到这个错误:

 javax.crypto.IllegalBlockSizeException: Data must not be longer than 64 bytes

经过一些研究,我发现这是一个普遍的错误,什么原因会导致这种错误?

共有1个答案

宗政颖逸
2023-03-14

第一个问题:在c#XML字符串中替换模数标记中的Java公钥正确吗?

不键与模数不同,但包含模数和指数。因此,在您的情况下,两者都必须根据Java中生成的密钥来确定。

公钥可以以不同的格式给出。例如,在本机Java中生成的公钥通常具有X.509/SPKI格式,并且可能是一个byte[],即DER编码。如果byte[]是Base64编码的(这对应于发布的MFwdq... wEAAQ==),并且添加了头-----BEGIN PUBLIC KEY-----和页脚-----END PUBLIC KEY-----(通常在Base64编码的正文中,每64个字符后面还有一个换行符),则密钥将采用PEM编码。

手动确定模数和指数的最简单方法是在ASN.1解析器中加载PEM密钥,例如这里,或者在合适的网站上直接将其转换为XML格式,例如这里。

指数标签呢?我用了AQAB值。

这个问题已经用之前说过的话得到了含蓄的回答。但有一点值得注意:对于指数,通常选择65537(十六进制编码0x010001和Base64编码AQAB)。但情况并非总是如此。因此,如果一个现有密钥的指数被盲目地替换为这个值,它很有可能会工作,但你不能依赖它,请参见这里和这里。

第二个问题:为什么在Java解密得到这个错误:javax.crypto.IllegalBlockSizeExctive:数据不能超过64字节?

在Michael Fehr的评论中已经回答了这一点,以及其他重要的问题(如安全性、性能和混合加密):密钥长度限制了明文的长度,使用512位密钥最多可以加密64字节。

此外,应该注意的是,不仅密钥的长度,而且使用的填充也限制了明文的长度,例如PKCS#1 v1.5填充需要11个字节,因此512位密钥的最大明文长度为64 - 11 = 53字节。在OAEP的情况下,使用的摘要决定了填充需要多少字节,参见例如这里。如果不使用填充(Tetxbook RSA),明文的最大长度对应于密钥长度。然而,在实践中,出于安全原因,必须始终使用填充。

从…开始。NET Core 3.0直接支持导入X.509/SPKI密钥(在DER编码中)和类似格式,请参见此处,尤其是RSA。导入对象公钥。在早些时候。NET核心版本和。NET Framework这些函数不可用,但可以使用BouncyCastle。

 类似资料:
  • 问题内容: 我有.Net系统中xml格式的私钥和公钥。我必须使用此密钥在Java中执行加密/解密。有什么办法吗? 公钥看起来像这样: 私钥: 我已经写了一些代码来加密数据,但是我不确定它是否正确。 如何从xml制作私钥以解密数据? 问题答案: 在您的示例中,这是进行Base64解码吗?看起来您可能正在依赖它,并且依赖那些内部类通常不是一个好主意(例如,其他JVM不会拥有它)。您可以使用具有Base

  • 我在C#程序(我在下面提到)中使用了RSA非对称密钥加密算法,我必须通过java程序加密数据。我希望我的java程序生成与C#程序相同的加密密钥。 公钥: C#加密程序: Java加密方案: 我尝试了上述java程序,但结果如下: O+gw 7+X hY x A 9 ltD V 5 zE RsF 4 Dy Xg MTc/gx 82 wR tT 1 x fR 3 su Y 0 XB JLa dp 7

  • null Edit2:为了一致性和正确性,将填充重命名为iVector。

  • 我找到了几个可以使用的解决方案。Net RSA Provider使用公钥对消息进行加密,并使用私钥对其解密。 但我想要的是用私钥加密,用公钥解密。 我希望在我的应用程序中存储公钥,并使用私钥加密许可证,例如在我的开发人员计算机上,将其发送到应用程序,并让信息使用公钥解密。 我怎样才能做到这一点?

  • 问题内容: SqlCommand.ExecuteScalar方法 执行查询,并返回查询返回的结果集中第一行的第一列。其他列或行将被忽略。 我猜这将涉及大量使用泛型。 假设我有一个SQLiteDatabase / Cursor对象。 问题答案: 这种逻辑对我有用:

  • 这里是一个JavaScript部分,它用AES加密解码字符串 我试图用python编写一个类似的解码函数,并导入AES。 谁能帮我做这个吗。我无法找出js到python的所有等效代码。 我查了这个页面Python AES解密例程(代码帮助)和 AES-加密与加密(node-js)/解密与Pycrypto(python) 不确定他们的代码是否与我这里的js相似 这在python中是什么意思 我从另一