簡體   English   中英

RSA 公鑰未導入 C# - ASN1 數據損壞異常

[英]RSA Public key not importing into C# - ASN1 corrupted data exception

我正在使用 Crypto library在 Python 中創建一組 RSA 密鑰,然后導出公鑰,並將其發送到 .NET Core 6 應用程序。 但是 .NET 無法讀取公鑰。

Python 加密庫代碼 - 此代碼在 Ubuntu Linux 開發 PC 上運行:

key = RSA.generate(2048)
public_key = base64.b64encode(key.publickey().exportKey()).decode('utf8')

C# 代碼 - 這是在 Windows 10 開發 PC 上運行的:

byte[] publicKeyBytes = Convert.FromBase64String(base64PublicKey);
RSA rsa = RSA.Create();
rsa.ImportRSAPublicKey(publicKeyBytes, out int bytesRead);

我收到的錯誤是:

AsnContentException:提供的數據標記為“通用”class 值“13”,但它應該是“通用”class 值“16”。

看看這篇 SO 文章這個 GitHub 問題,看起來我需要不同的導入方法。 所以我也嘗試將最后一行更改為:

rsa.ImportSubjectPublicKeyInfo(publicKeyBytes, out int bytesRead);

但我得到了完全相同的錯誤。 只有堆棧跟蹤有點不同,因為它使用了不同的提供程序。

如果有幫助,下面是 Crypto 庫的export_key()方法的完整幫助文本的鏈接。 但這是我認為最相關的部分,是什么讓我認為ImportSubjectPublicKeyInfo()會起作用:

對於公鑰,此(pkcs)參數將被忽略。 對於 DER 和 PEM,始終使用 ASN.1 DER SubjectPublicKeyInfo 結構。

編輯:這可能與編碼有關,或者可能與庫之間的小端與大端問題有關......

這是 exportKey() function 的完整描述的鏈接。

編輯:重要的部分原來是format參數默認為 PEM 格式。

在 Python 端, key.publickey().exportKey()返回 X.509/SPKI 格式的 PEM 編碼密鑰。 不需要額外的 Base64 編碼:

from Crypto.PublicKey import RSA

key = RSA.generate(2048)
public_key = key.publickey().exportKey().decode('utf8')
print(public_key)

給出例如:

-----BEGIN PUBLIC KEY-----
MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA5mPsHC34l7uz/Qlxma0s
fibiql2hcqbNVG/jyW6qAD9w+L9/ZBmaSo+wLMKI+xXVp5aHqDlgS07PxcWWLXFf
FLwdIk12rEXisbEPIj+3O+Fayqvk9NuUh9sDiVGOX7pMlnICFc+CdB3mK0sFRGkK
zOq3FJO19VxhzAI0dPQ6HDD4SLz/onuOoYMpcVfPa6bWDEe9MBCc1U+ypn9JNaq+
WrUjEw5RJbYCz451WPLa6wMKyIwA0EPck+h1yQc9+VCXwoK97awKE7wEPBwEG9HV
7UYMLJiVGvPkJypR+9+h/3M7CGVruhQwZG9Cz7QEqNm7oBQuyki5jyFAQueq8nKd
kwIDAQAB
-----END PUBLIC KEY-----

在 C# 端,可以使用RSA.ImportFromPem()直接導入 PEM 編碼的密鑰,自 .NET 5 起可用。
或者RSA.ImportSubjectPublicKeyInfo()可用於導入 X.509/SPKI 格式的公鑰,該格式自 .NET Core 3.0 起可用。 但是,這只能導入 DER 編碼的密鑰。 從 PEM 編碼的密鑰中,可以通過刪除 header、頁腳和換行符以及 Base64 解碼 rest 輕松導出 DER 編碼密鑰。
由於您正在使用 .NET 6 並且兩種實現都可用, RSA.ImportFromPem()是最方便的:

using System.Security.Cryptography;
...
string pemX509 = @"-----BEGIN PUBLIC KEY-----
                MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA5mPsHC34l7uz/Qlxma0s
                fibiql2hcqbNVG/jyW6qAD9w+L9/ZBmaSo+wLMKI+xXVp5aHqDlgS07PxcWWLXFf
                FLwdIk12rEXisbEPIj+3O+Fayqvk9NuUh9sDiVGOX7pMlnICFc+CdB3mK0sFRGkK
                zOq3FJO19VxhzAI0dPQ6HDD4SLz/onuOoYMpcVfPa6bWDEe9MBCc1U+ypn9JNaq+
                WrUjEw5RJbYCz451WPLa6wMKyIwA0EPck+h1yQc9+VCXwoK97awKE7wEPBwEG9HV
                7UYMLJiVGvPkJypR+9+h/3M7CGVruhQwZG9Cz7QEqNm7oBQuyki5jyFAQueq8nKd
                kwIDAQAB
                -----END PUBLIC KEY-----";
RSA rsa = RSA.Create();
rsa.ImportFromPem(pemX509);

為了完整起見: RSA.ImportRSAPublicKey()從 .NET Core 3.0 開始可用,用於導入 PKCS#1 格式的 DER 編碼公鑰,這不適用於導出的密鑰。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM