Importing a PFX file using X509Certificate from ASP/ASP.NET or COM+ fails

An ASP.NET or COM+ application attempts to import a certificate in a PFX file (PKCS12) programmatically using the X509Certificate or X509Certificate2 classes with code similar to the following:

X509Certificate cert = new X509Certificate(“a.pfx”, “password”);


The following exception occurs

System.Security.Cryptography.CryptographicException: The system cannot find the file specified
at System.Security.Cryptography.CryptographicException.ThrowCryptogaphicException(Int32 hr)
at System.Security.Cryptography.X509Certificates.X509Utils._LoadCertFromFile(String fileName, IntPtr password, UInt32 dwFlags, Boolean persistKeySet, SafeCertContextHandle& pCertCtx)
at System.Security.Cryptography.X509Certificates.X509Certificate.LoadCertificateFromFile(String fileName, Object password, X509KeyStorageFlags keyStorageFlags)
at System.Security.Cryptography.X509Certificates.X509Certificate2..ctor(String fileName, String password)


There two causes for this exception:

1. The specified PFX file doesn’t exist or the name was spelled incorrectly.
2. The X509Certificate and X509Certificate2 class constructors which accept a PFX file name and a password require the caller’s user account profile to be loaded.  However, ASP.NET and COM+ applications run in accounts which usually do not have the user profile loaded.

The X509Certificate2 class constructors attempt to import the certificate into the user profile of the user account that the application runs in.  Many times, ASP.NET and COM+ applications impersonate clients.  When they do, they do not load the user profiles for the impersonated user for performance reasons.  So, they cannot access the “User” certificate store for the impersonated user.

The same code will work when run from an interactive application or a Windows service that is running under a user account because the profile is loaded when the user is logged on or the service started.


To solve this problem, please perform the following steps:

1. An administrator on the machine where the ASP.NET/COM+ application runs should install the certificate in the machine certificate store, called the “Local Computer” store.  This should be done when the ASP.NET/COM+ application is installed.

2. The administrator should set the permissions on the private key associated with the certificate to give the ASP.NET process and the impersonated users access to the key.  This is needed because only the user account that installs the certificate or private key in the “Local Computer” store can later use the RSA private key associated with the certificate.  Use WinHttpCertCfg.exe available from the Windows Resource Kit Tools ( ( to configure the permissions.

The command you will use will depend on the user account under which the application code may be running.  For example, if the ASP.NET application always runs under a dedicated user account, you will use that account. You can determine the name of the account by calling WindowsIdentity.GetCurrent().Name to find what account you need to grant access.  Below are some examples:

a) To grant access to ASPNET account:

winhttpcertcfg -g -c LOCAL_MACHINE\MY -s MyCertificate -a ASPNET

b) To grant access to Network Service:

winhttpcertcfg -g -c LOCAL_MACHINE\MY -s MyCertificate -a “Network Service”

c) To grant access to Authenticated Users:

winhttpcertcfg -g -c LOCAL_MACHINE\MY -s MyCertificate -a “Authenticated Users”

where MyCertificate is the subject name.  For example, if the subject name of your certificate contains as an example CN=test name,OU=… you will actually pass the string “test name” for -s command line parameter above.

3. The ASP.NET/COM+ application code should use the installed certificate rather than attempt to install one from a PFX file.  Have the code locate the installed certificate using X509Store class.

a. Use StoreLocation.LocalMachine in the constructor of X509Store.
b. Once the store is opened, locate the desired certificate based on subject name programmatically using X509Certificate2Collection.Find method.

Example code will look similar to:

X509Store store = new X509Store(“My”, StoreLocation.LocalMachine);
store.Open(OpenFlags.ReadOnly | OpenFlags.OpenExistingOnly);

System.Security.Cryptography.X509Certificates.X509Certificate2 newCert =
store.Certificates.Find(X509FindType.FindBySubjectName, “XXXXXXXXXXXXX”, false)[0];

The subject name to use above in the second parameter of Find method will depend on the subject name of the installed certificate from p12 or PFX file in the Local Computer certificate store.

Microsoft .NET Framework 2.0
Microsoft .NET Framework 1.1


Microsoft Knowledge Base Article

This article contents is Microsoft Copyrighted material.
Microsoft Corporation. All rights reserved. Terms of Use | Trademarks

You can follow any responses to this entry through the RSS 2.0 feed. You can leave a response, or trackback from your own site.

AddThis Social Bookmark Button

Leave a Reply

To prove that you're not a bot, enter this code
Anti-Spam Image