C# 反弹城堡,RSA:将密钥转换为字符串格式

C# 反弹城堡,RSA:将密钥转换为字符串格式,c#,rsa,bouncycastle,C#,Rsa,Bouncycastle,我在我的C#项目中使用RSA(Bouncy Castle API)。我使用以下方法生成密钥对: RsaKeyPairGenerator r = new RsaKeyPairGenerator(); r.Init(new KeyGenerationParameters(new SecureRandom(), 1024)); AsymmetricCipherKeyPair keys = r.GenerateKeyPair(); AsymmetricKeyParameter private_key

我在我的C#项目中使用RSA(Bouncy Castle API)。我使用以下方法生成密钥对:

RsaKeyPairGenerator r = new RsaKeyPairGenerator();
r.Init(new KeyGenerationParameters(new SecureRandom(), 1024));
AsymmetricCipherKeyPair keys = r.GenerateKeyPair();

AsymmetricKeyParameter private_key = keys.Private;
AsymmetricKeyParameter public_key = keys.Public;
现在我想将它们保存在txt文件中,但问题是我无法将它们转换为字符串格式。我在另一篇文章中读到,密钥必须使用以下方式序列化:

PrivateKeyInfo k = PrivateKeyInfoFactory.CreatePrivateKeyInfo(private_key);
byte[] serializedKey = k.ToAsn1Object().GetDerEncoded();

这条路对吗?如果是,在此之后我应该做什么?只需将它们从字节[]转换为字符串?

好吧,我不知道RSA的具体方面,但一旦你得到了一个不透明的二进制字符串(即,它可能包含任何任意数据),文本转换的最佳选择就是你可以用它来反转


不要使用
Encoding.GetString(byte[])
Encoding.GetBytes(string)
进行此操作-二进制数据在特定编码中不是文本,不应被视为文本。如果您尝试此操作,几乎肯定会丢失数据。

您也可以使用PemWriter以PEM格式存储数据:

TextWriter textWriter = new StringWriter();
PemWriter pemWriter = new PemWriter(textWriter);
pemWriter.WriteObject(keys.Private);
pemWriter.Writer.Flush();

string privateKey = textWriter.ToString();
现在,privateKey包含如下内容:

-----BEGIN RSA PRIVATE KEY-----
MIICXQIBAAKBgQDFhB3xI1AzSMsKvt7rZ7gp2o/vd49zON89iL1ENvKkph7oFXa2
ew/hjzbAV33lHnFFlA/vA5SDCbggRyU1/SmjfuPJFEzFbgcPLuO1Sw6z+bWXiIFp
QNCOTIw11c0fbwk+kB2y4E1OkLv5f9atlNlekb4wBn8bMbFYtu6LGWjkFQIDAQAB
AoGANPoMteLM3hSGMSmkzOsS4Fb5CDe/SB5W8kA805ERX8wWuhUXtDYpukwZWVme
MNgLdagS5f7F1KfEtROgDW0Lv4/T/FWAbpgh8O2CPKYDY4ZXl8tmRH9dtYn/824l
veLxdgNjHwo5OMvuTSDMjC3tbg2UA3kmV4VAm5QotlRinUECQQDo4zvI5e81zWnS
kNrUARX80t432MOZyr0RvAaVJfBNQpJl0H0xp5LKP74hvPVO9WdJvJ0M4Z4QrmGO
bm2Hsfz5AkEA2R469YXxgPLDg/LvUQqfrl8Ji9+rip7eQP7iS/dt66NMS31/HymT
+HscEZ3qGlnQuyyyRR2rGQdhdjU42HNy/QJBAKbPTF1DxSmGbovyUauU84jaCW17
B++6dd6kDRr7x7mvO2lOAr50RwIy0h8cV6EsycTZIqy9VhigryP0GOQfKxECQA8T
uVZpab7hnNAh45qGGVabhOcwrhHfPGHZEU/jK7/sRBUN7vD0CzF7IxTaGXKhAAyv
auW/zKzdRVhXE858HeUCQQCGaaAg8GwM0qIS0nHRTLldu4hIGjKn7Sk0Z46Plfwr
oqPCtuP4ehX85EIhqCcoFnG6Ttr6AxSgNMZvErVxDBiD
-----END RSA PRIVATE KEY-----

如果将bouncycastle证书转换为.net证书。实现这一点的函数位于bouncycastle库中(我相信它位于名为DotNetUtilities的类中)。RSACryptServiceProvider具有以下功能:

ToXmlString(bool includePrivateKey). 

如果希望私钥包含分别序列化为base64的所有组件(指数、模数和d(专用指数)),则为证书提供x表示形式。这可能是您需要的:

尝试以下方法

        RsaKeyPairGenerator rsaKeyPairGenerator = new RsaKeyPairGenerator();
        rsaKeyPairGenerator.Init(new KeyGenerationParameters(new SecureRandom(), XXX));

        AsymmetricCipherKeyPair keys = rsaKeyPairGenerator.GenerateKeyPair();

        PrivateKeyInfo privateKeyInfo = PrivateKeyInfoFactory.CreatePrivateKeyInfo(keys.Private);
        // Write out an RSA private key with it's asscociated information as described in PKCS8.
        byte[] serializedPrivateBytes = privateKeyInfo.ToAsn1Object().GetDerEncoded();
        // Convert to Base64 ..
        string serializedPrivateString = Convert.ToBase64String(serializedPrivateBytes);

        SubjectPublicKeyInfo publicKeyInfo = SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(keys.Public);
        byte[] serializedPublicBytes = publicKeyInfo.ToAsn1Object().GetDerEncoded();
        string serializedPublicString = Convert.ToBase64String(serializedPublicBytes);

谢谢你的快速回答。我照你说的做了,结果我得到了这个Miicdwibadanbgkqhkig9w0baqefaascamewgjgaoaogbaj7s/B4XNHmNa9LwZ91z。。。我想应该是个大整数不?因为在RSA中我们使用数字(p,q…),所以方法名(GetDeRecoded)表明返回的数据包含DER编码格式的所有RSA密钥参数(p,q…)。@Rami:您的目标是获得可以“再水化”为PrivateKeyInfo的数据吗?如果是这样的话,你不需要知道整数等。。。您只需要确保可以序列化为字节数组(然后是字符串),反之亦然。@谢谢,所以我将所有参数都以一种格式返回。很酷,但我怎样才能除以它得到(p,q…)的值呢?有什么办法吗?再次感谢。@Rami:查看Bouncy Castle API文档的其余部分,了解GetDeRecoded和ToAsn1Object的反向操作。这个答案是正确的,但只需更改最后一行,而不是
string privateKey=pemWriter.ToString()
try
string privateKey=textWriter.ToString()