[英]D-Parameter of RSA change depending on how you access the private key of a certificate
我希望有人能向我解釋我在哪里犯了錯誤。 我一直認為,當我用私鑰導出證書並再次導入時,私鑰是穩定的,不會改變。 尤其是跨計算機。
現在我被證明是錯的,我不明白。
給定一個證書 Z。其中包含一個私鑰 pk。 我將此證書導入計算機 C1 和計算機 C2。
我在兩者上都獲得了私鑰的參數。
Result on C1:
Exponent : {1, 0, 1}
Modulus : {148, 19, 118, 153...}
P : {246, 42, 172, 195...}
Q : {153, 253, 180, 23...}
DP : {161, 179, 194, 172...}
DQ : {63, 22, 42, 14...}
InverseQ : {170, 228, 238, 93...}
D : {60, 36, 199, 168...}
Result on C2:
Exponent : {1, 0, 1}
Modulus : {148, 19, 118, 153...}
P : {246, 42, 172, 195...}
Q : {153, 253, 180, 23...}
DP : {161, 179, 194, 172...}
DQ : {63, 22, 42, 14...}
InverseQ : {170, 228, 238, 93...}
D : {0, 233, 203, 106...}
使用的代碼:
using (var store = new X509Store(storeNameEnum, storeLocationEnum))
{
X509Certificate2Collection certificates = null;
store.Open(OpenFlags.ReadOnly);
var certificates = store.Certificates;
var cert = certificates.Cast<X509Certificate2>().Single(c => c.SubjectName.Name.ToLower().Contains(subject.ToLower()));
var rsa = cert.GetRSAPrivateKey();
var params = rsa.ExportParameters(true);
}
RSA 參數的 D 部分不同。 為什么?
在計算機 C2 上,當我調用以下行時,我得到與 C1 上相同的 D:
var params (cert.PrivateKey as RSACryptoServiceProvider).ExportParameters(true).D;
但我不能使用它,因為我正在編寫一個也用於 Net5 項目的.NetStandard 庫。
接下來,我嘗試直接從 C2 上的文件中讀取 PFX 並檢查 PK。 以下幾行給了我在 C1 上的 PK。
string pfxPassword = "pw";
Pkcs12Store pkcs12 = new Pkcs12Store(new FileStream(@"C:\tmp\cert.p12", FileMode.Open, FileAccess.Read), pfxPassword.ToArray());
var cert = pkcs12.GetCertificate("certName");
var keyEntry = pkcs12.GetKey("certName");
RSAParameters rsaParams = Org.BouncyCastle.Security.DotNetUtilities.ToRSAParameters((RsaPrivateCrtKeyParameters)keyEntry.Key);
Console.WriteLine($"=> {String.Join(" ", rsaParams.D)}");
但是,當我隨后將其轉換為證書以將其導入商店時,PK 再次更改,因為它最初在 C2 上。
X509Certificate2 certificate = new System.Security.Cryptography.X509Certificates.X509Certificate2(Org.BouncyCastle.Security.DotNetUtilities.ToX509Certificate(cert.Certificate));
RSACryptoServiceProvider csp = new RSACryptoServiceProvider(new CspParameters(1, "Microsoft Strong Cryptographic Provider", new Guid().ToString(), new System.Security.AccessControl.CryptoKeySecurity(), null));
csp.ImportParameters(rsaParams);
certificate.PrivateKey = csp;
Console.WriteLine($"=> {String.Join(" ", certificate.GetRSAPrivateKey().ExportParameters(true).D)}");
顯然,有些計算機設置為始終給出與 C1 相同的結果,而其他計算機始終給出與 C2 相同的結果。 但是為什么它們會提供不同的結果呢? 是什么影響了這種行為?
我很感激任何提示。
基本上, D
值無關緊要,您會看到其結果。
“你剛才說D
值不重要嗎?RSA不是基於m == modpow(modpow(m, e, n), d, n)
嗎?
是的,是的。 但是中國剩余定理為modpow(m, d, n)
提供了更有效的實現,所以沒有人真正關心D
。
正在發生的另一件事是,當導入 RSA 私鑰時,您有幾個選擇:1) 驗證 n == (p * q) 和 d/dp/dq/qInv 在 n/e 的情況下是否有意義/p/q,如果他們不這樣做就失敗,2)相信導入密鑰,處理不一致的后果(“垃圾輸入,垃圾輸出”),3)做(1)但修復任何不正確的數據。
好的,所以我們有了為什么值可能會改變的前提(策略(3)),但為什么它們實際上會改變?
因為D
至少有兩個不同的常見答案。 (“D 不是唯一的嗎?”不。“你不是說 D 無關緊要嗎?”好的,所以它在計算 CRT 參數時很重要,然后就不再重要了。)
最初的 RSA 論文將 D 定義為 e 的模乘逆元,以 N 的歐拉總積分 function 為模。歐拉總積分 function的常用符號是希臘字母 phi。 許多聰明的人后來,該語句被更改為 D 是 e 模乘 N 的Carmichael function的模乘逆。 Carmichael function 的常用符號是希臘字母 Z945F3FC449518A4732
區別在於正方形與矩形的區別。 所有 D-phi 值都適用於 RSA,因為e * D-phi === 1 (mod lambda(N))
。 由於所有 D-lambda 值也適用於 RSA,但不遵守e * D-lambda === 1 (mod phi(N))
,公式被重寫。
好的,有背景,那么發生了什么?
所以,我的猜測是 C1 和 C2 在不同的操作系統(或同一操作系統的不同版本)上運行。
https://github.com/dotnet/runtime/commit/700a07cae19fe64649c2fb4c6c10e6b9aa85dc29展示了我們如何在 .NET 的測試套件中處理它。 對於應用程序代碼,我的建議是只信任系統。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.