Windows Certificate Management
A command reference for managing X.509 certificates on Windows using PowerShell, certutil, and MMC. All commands assume an elevated PowerShell session unless noted otherwise.
Generate a Self-Signed Certificate
The New-SelfSignedCertificate cmdlet creates a certificate in the local machine personal store. The example below includes Subject Alternative Names (SANs), key usage, and a two-year validity period.
Create a self-signed certificate with SANs:
$cert = New-SelfSignedCertificate \
-DnsName "myapp.local", "localhost", "127.0.0.1" \
-CertStoreLocation "Cert:\LocalMachine\My" \
-NotAfter (Get-Date).AddYears(2) \
-KeyUsage DigitalSignature, KeyEncipherment \
-TextExtension @(
"2.5.29.37={text}1.3.6.1.5.5.7.3.1", # Server Authentication
"2.5.29.17={text}DNS=myapp.local&DNS=localhost&IPAddress=127.0.0.1"
) \
-KeyAlgorithm RSA \
-KeyLength 2048 \
-FriendlyName "My App Dev Cert"
Write-Host "Thumbprint: $($cert.Thumbprint)"Tip
Use -KeyExportPolicy Exportable if you plan to export the private key later as a PFX.
Export Certificates
Export as PFX (with private key)
Export certificate and private key to a PFX file:
$password = ConvertTo-SecureString -String "P@ssw0rd!" -Force -AsPlainText
Export-PfxCertificate \
-Cert "Cert:\LocalMachine\My\$($cert.Thumbprint)" \
-FilePath "C:\certs\myapp.pfx" \
-Password $passwordExport public certificate only (DER / CER)
Export the public certificate without the private key:
Export-Certificate \
-Cert "Cert:\LocalMachine\My\$($cert.Thumbprint)" \
-FilePath "C:\certs\myapp.cer" \
-Type CERTImport Certificates
Import a PFX into the local machine personal store:
$password = ConvertTo-SecureString -String "P@ssw0rd!" -Force -AsPlainText
Import-PfxCertificate \
-FilePath "C:\certs\myapp.pfx" \
-CertStoreLocation "Cert:\LocalMachine\My" \
-Password $password \
-ExportableImport a public certificate into the trusted root store:
Import-Certificate \
-FilePath "C:\certs\myapp.cer" \
-CertStoreLocation "Cert:\LocalMachine\Root"Warning
Importing into LocalMachine\Root makes the certificate trusted for all users on the machine. Use CurrentUser\Root to limit trust to the current user only.
MMC Certificate Snap-ins
Windows provides two management console shortcuts for certificates:
Open the local machine certificate manager:
certlm.mscOpen the current user certificate manager:
certmgr.mscUse certlm.msc for server certificates (IIS, Kestrel, services) and certmgr.msc for personal user certificates and client certs.
certutil Commands
Dump full certificate details:
certutil -dump "C:\certs\myapp.cer"Verify a certificate chain:
certutil -verify "C:\certs\myapp.cer"Encode a file to Base64 (PEM):
certutil -encode "C:\certs\myapp.cer" "C:\certs\myapp.pem"Decode a Base64 file back to DER:
certutil -decode "C:\certs\myapp.pem" "C:\certs\myapp.der".NET Dev Certificates
Generate and trust the ASP.NET Core development HTTPS certificate:
dotnet dev-certs https --trustClean and regenerate if the dev cert is corrupted:
dotnet dev-certs https --clean
dotnet dev-certs https --trustTrust Store Locations
Windows organizes certificates into stores. The most commonly used:
Cert:\LocalMachine\My # Server personal certs (IIS, Kestrel)
Cert:\LocalMachine\Root # Trusted Root CAs (machine-wide)
Cert:\LocalMachine\CA # Intermediate CAs
Cert:\CurrentUser\My # Current user personal certs
Cert:\CurrentUser\Root # Trusted Root CAs (current user only)List certificates in a store:
Get-ChildItem Cert:\LocalMachine\My | Format-Table Subject, Thumbprint, NotAfterFind a certificate by thumbprint:
Get-ChildItem Cert:\LocalMachine\My | Where-Object {
$_.Thumbprint -eq "A1B2C3D4E5F6..."
}IIS Certificate Binding
Use netsh to bind a certificate to a port for IIS or HTTP.sys.
Bind a certificate to port 443:
netsh http add sslcert \
ipport=0.0.0.0:443 \
certhash=A1B2C3D4E5F6... \
appid={00000000-0000-0000-0000-000000000000}View existing SSL bindings:
netsh http show sslcertRemove an SSL binding:
netsh http delete sslcert ipport=0.0.0.0:443Tip
The appid is any GUID that identifies your application. For IIS, use the GUID found in applicationHost.config. For custom apps, generate one with [guid]::NewGuid().