不支援將密碼編譯抽象概念的預設實作具現化
從 .NET 5.0 開始,密碼編譯抽象概念上的無參數 Create()
多載已淘汰,並會引發警告。
變更描述
在 .NET Framework 2.0 - 4.8 中,可以設定 HashAlgorithm.Create() 等抽象密碼編譯基本 Factory,以傳回不同的演算法。 例如,在 .NET Framework 4.8 的預設安裝 上,無參數靜態方法 HashAlgorithm.Create() 會傳回 SHA1 演算法的執行個體,如下列程式碼片段所示。
僅限 .NET Framework
// Return an instance of the default hash algorithm (SHA1).
HashAlgorithm alg = HashAlgorithm.Create();
// Prints 'System.Security.Cryptography.SHA1CryptoServiceProvider'.
Console.WriteLine(alg.GetType());
// Change the default algorithm to be SHA256, not SHA1.
CryptoConfig.AddAlgorithm(typeof(SHA256CryptoServiceProvider), typeof(HashAlgorithm).FullName);
alg = HashAlgorithm.Create();
// Prints 'System.Security.Cryptography.SHA256CryptoServiceProvider'.
Console.WriteLine(alg.GetType());
您也可以使用全機器組態來變更預設演算法,而不需要以程式設計方式呼叫 CryptoConfig
。
在 .NET Core 2.0 - 3.1 中,HashAlgorithm.Create() 等抽象密碼編譯基本 Factory 一律擲回 PlatformNotSupportedException。
// Throws PlatformNotSupportedException on .NET Core.
HashAlgorithm alg = HashAlgorithm.Create();
在 .NET 5 和更新版本中,HashAlgorithm.Create() 等抽象密碼編譯基本 Factory 已標示為已淘汰,並產生識別碼為 SYSLIB0007
的編譯時間警告。 在執行階段,這些方法會繼續擲回 PlatformNotSupportedException。
// Throws PlatformNotSupportedException.
// Also produces compile-time warning SYSLIB0007 on .NET 5+.
HashAlgorithm alg = HashAlgorithm.Create();
此變更僅限編譯時期。 舊版 .NET Core 沒有執行階段變更。
注意
只有
Create()
方法的無參數多載已淘汰。 參數化多載未淘汰,仍如預期運作。// Call Create(string), providing an explicit algorithm family name. // Works in .NET Framework, .NET Core, and .NET 5+. HashAlgorithm hashAlg = HashAlgorithm.Create("SHA256");
「特定」演算法系列的無參數多載 (非抽象概念) 未過時,會繼續如預期運作。
// Call a specific algorithm family's parameterless Create() ctor. // Works in .NET Framework, .NET Core, and .NET 5+. Aes aesAlg = Aes.Create();
變更原因
.NET Framework 中的密碼編譯組態系統,不再存在於 .NET Core 和 .NET 5+ 中,因為舊版系統不允許適度的加密彈性。 .NET 的回溯相容性需求也使得架構無法更新特定密碼編譯 API,以跟上密碼編譯的演進。 例如,在 SHA-1 雜湊演算法是先進技術的時期,.NET Framework 1.0 中引進了 HashAlgorithm.Create() 方法。 經過二十年,現在 SHA-1 已不敷使用,但我們無法將 HashAlgorithm.Create() 變更為傳回不同的演算法。 這麼做會在取用的應用程式中造成無法接受的中斷性變更。
最佳做法要求取用密碼編譯基本類型的程式庫 (例如 AES、SHA-* 和 RSA) 應完全控制其取用這些基本類型的方式。 需要未來校訂的應用程式,應利用較高層級的程式庫來包裝這些基本類型,並加入金鑰管理和密碼編譯功能。 這些程式庫通常是由裝載環境提供。 其中一個範例是 ASP.NET 的資料保護程式庫,可代表呼叫的應用程式處理這些疑慮。
導入的版本
5.0
建議的動作
建議的動作是,以特定演算法的 Factory 方法呼叫,取代已淘汰 API 的呼叫,例如 Aes.Create()。 這可讓您完全控制要具現化的演算法。
如果您需要與使用已淘汰 API 之 .NET Framework 應用程式所產生的現有承載保持相容,請使用下表中建議的取代項目。 表格提供從 .NET Framework 預設演算法到其 .NET 5+ 對等項目的對應。
.NET Framework .NET Core / .NET 5+ 相容的取代項目 備註 AsymmetricAlgorithm.Create() RSA.Create() HashAlgorithm.Create() SHA1.Create() SHA-1 演算法已被視為無效。 如果可行,請考慮使用更強大的演算法。 如需進一步指導,請洽詢安全顧問。 HMAC.Create() HMACSHA1() 對於大部分的新式應用程式,都不建議使用 HMACSHA1 演算法。 如果可行,請考慮使用更強大的演算法。 如需進一步指導,請洽詢安全顧問。 KeyedHashAlgorithm.Create() HMACSHA1() 對於大部分的新式應用程式,都不建議使用 HMACSHA1 演算法。 如果可行,請考慮使用更強大的演算法。 如需進一步指導,請洽詢安全顧問。 SymmetricAlgorithm.Create() Aes.Create() 如果您必須繼續呼叫已淘汰的無參數
Create()
多載,可以在程式碼中隱藏SYSLIB0007
警告。#pragma warning disable SYSLIB0007 // Disable the warning. HashAlgorithm alg = HashAlgorithm.Create(); // Still throws PNSE. #pragma warning restore SYSLIB0007 // Re-enable the warning.
您也可以在專案檔中隱藏警告。 這麼做會停用專案中所有來源檔案的警告。
<Project Sdk="Microsoft.NET.Sdk"> <PropertyGroup> <TargetFramework>net5.0</TargetFramework> <!-- NoWarn below suppresses SYSLIB0007 project-wide --> <NoWarn>$(NoWarn);SYSLIB0007</NoWarn> </PropertyGroup> </Project>
注意
隱藏
SYSLIB0007
只會停用此處所列密碼編譯 API 的淘汰警告, 而不會停用其他任何警告。 此外,即使您隱藏警告,這些已淘汰的 API 仍會在執行階段擲回 PlatformNotSupportedException。