2009-02-17 44 views
9

我有一個ASP.NET Web服務,它接收一個字節數組,代表包含X.509證書的.pfx文件的內容。服務器端代碼使用的是System.Security.Cryptography.X509Certificate2構造函數加載從字節證書:爲什麼X509Certificate2有時無法從blob創建?

X509Certificate2 native_cert = new X509Certificate2(
       pkcs12_buf /*byte array*/, 
       password, 
       X509KeyStorageFlags.PersistKeySet | 
       X509KeyStorageFlags.Exportable 
      ); 

取決於誰是我的服務進程正在運行的,這個調用要麼成功,或失敗併產生「內部錯誤」異常。異常堆棧上的最後一個調用爲X509Utils._LoadCertFromBlob,這是mscore.dll中的非託管代碼。

使用服務帳戶憑證在交互式登錄中從控制檯應用程序運行時,此代碼成功。在使用服務帳戶憑證的應用程序池中運行w3wp.exe時失敗。將應用程序池標識更改爲管理員可以修復問題,因此它必定是一個特權問題,但我不知道此特權可能需要什麼權限。代碼不會觸及文件系統或Windows證書存儲區。

[更新:更多信息]
此錯誤出現在Windows事件日誌:

*Cryptographic Parameters:* 
**Provider Name:** Microsoft Software Key Storage Provider 
**Algorithm Name:** Not Available. 
**Key Name:** {E182E13B-166D-472A-A24A-CBEF0808E9ED} 
    **Key Type:** User key. 

*Cryptographic Operation:* 
**Operation:** Open Key. 
    **Return Code:** 0x2 

任何想法?

回答

8

我只是找到了解決這一個自己:

X509KeyStorageFlags flags = X509KeyStorageFlags.PersistKeySet | X509KeyStorageFlags.MachineKeySet; 

X509Certificate2 cert = new X509Certificate2(pkcs12_buf, password, flags); 

訣竅這裏將使用本地密鑰存儲區MachineKeySet標誌而不是用戶配置文件密鑰存儲區,如果您未指定其他位置,則該默認值爲默認值。由於ASP.NET進程標識不會加載用戶配置文件存儲,因此在以編程方式導入證書時無法訪問存儲,但可以訪問機器存儲。

我認爲PersistKeySet只是保持私鑰加載,但我不確定它到底做了什麼 - 如果您因爲某些原因需要訪問私鑰,這是必需的。

2

嘗試授予ASP.NET帳戶權限到以下文件夾:C:\Documents And Settings\All Users\Microsoft\Crypto\RSA\MachineKeys\(可根據您的環境會發生變化)

+0

我認爲你在正確的軌道上,但似乎並沒有試圖訪問文件系統。成功的帳戶在用戶的個人配置文件(而不是AllUsers)下訪問Microsoft \ Crypto \ RSA。根據procmon的說法,失敗的人甚至不會嘗試訪問文件系統。 – jlew 2009-02-17 23:30:23

+0

此權限更改適用於Win2k8上的我。爲我節省了大量的時間調試。謝謝! – CodingWithSpike 2011-06-25 02:54:30

相關問題