Retired Microsoft Blog disclaimer

This directory is a mirror of retired "Windows PKI Team" TechNet blog and is provided as is. All posting authorship and copyrights belong to respective authors.

Posts on this page:

Original URL: https://blogs.technet.microsoft.com/pki/2010/05/12/certificate-path-validation-in-bridge-ca-and-cross-certification-environments/
Post name: Certificate Path Validation in Bridge CA and Cross-Certification Environments
Original author: siadukia
Posting date: 2010-05-12T17:09:00+00:00


Recently, we’ve had a deluge of questions regarding chain building and selection, especially in the presence of cross-certified certificates. Hopefully, this post will make Crypto API 2 (CAPI2) chaining logic clearer and help enterprise admins design and troubleshoot their public key infrastructure.

While trying to validate an end entity, CAPI2 tries to select the best quality chain leading up to a certificate that the user trusts. Where multiple valid chains exist, this may not be the shortest chain found. It is also possible that CAPI2 could not construct complete chains – this can happen when intermediate CAs are not available on the client, and the client could not retrieve the certificates (due to server issues, proxy authentication failures, insufficient rights to access the network, and other issues).

Consider the following chain: the Contoso Root CA has issued an intermediate CA, Contoso InterCA, which in turn issues a signing cert to Bob. Now, another root CA, Super Root has issued an intermediate CA called Bridge CA, which cross certifies the Contoso Root CA.


Contoso Root CA ->
Contoso InterCA ->
Bob


Bridge CA cross certifies Contoso Root CA, resulting in


Super Root ->
Bridge CA ->
X-Cert Contoso Root CA->
Contoso InterCA ->
Bob


There are two possible valid chains here – the original chain Contoso Root CA -> Contoso InterCA -> Bob, and the cross certified chain Super Root -> Bridge CA -> X-Cert Contoso Root CA -> Contoso InterCA -> Bob. Which chain will CAPI2 return? This isn’t as simple as returning the shortest chain. It is also affected by certificate discovery – can the client access all certificates in the chain?


Consider the simple case, in which the client has all certificates available. This means that it either performed a network retrieval to get the certificates, or they were already installed into the relevant certificate stores, or were available in the cache. Since the client now has two valid chains, CAPI2 need to select and return the “best” chain. Simply returning the shortest chain isn’t an option – the longer chain can be a “better” chain. The process of selecting a chain can be explained as follows.

CAPI2 starts by calculating the “quality” of each chain. The quality of the chain is derived from a number of factors, including:
1. Certificate signatures are valid
2. Certificate chain ends at a trusted root
3. Chain has valid basic constraints
4. Successful revocation check / not revoked
5.Chain has name constraint policies
6. Chain has certificate policies
7. Chain has extended key usages
8. Chain has SubjectKeyIdentifier / AuthorityKeyIdentifier match


In a nutshell, if a chain provides more information (i.e. valid policy constraints, revocation check succeeded) its quality increases; conversely, if it encounters errors (certificate is revoked / revocation status unknown, invalid name constraints) its quality decreases.

If there are multiple chains with the same quality score, CAPI2 uses the following tie breakers:
1. Starting with the certificate of the end entity’s issuer on both chains, compare the NotBefore dates and NotAfter dates of certificates in the same position in the chain. The first chain with a later NotBefore date, or if the NotBefore dates are identical, the chain with the later NotAfter date is selected.
2. If both chains have identical validity periods, then the shorter chain is selected.


When there are multiple valid chains possible, the above heuristics are used only when CAPI2 can successfully build the various valid chains. However, due to various issues during path discovery, CAPI2 may not even be able to build a certificate chain up to a particular root. For example, if the intermediate certificates or cross-certificates cannot be discovered, CAPI2 may only completely build one of the two valid chains in the example above. There are however some general guidelines which are recommended for a majority of PKI scenarios commonly encountered in the enterprise.


In order to facilitate a successful path discovery, you should use group policies to deploy cross-certificates and intermediate CA certificates in your environment. This would eliminate the need to perform network retrievals during path discovery (and potentially result in performance improvements).

Selection of particular chains can be forced by correct management of trusted roots and certificate policies. If you want a chain up to a particular root be always picked, you need to make sure that is the only trusted valid chain that can be built and remove the ambiguity. In the example above, if you want the chain up to the Contoso Root to be built, then it needs to be only valid chain possible. If Super Root is distributed through automatic root update service, then you can either disable the Auto Root Update program in clients and push the selected third party roots via Group Policy, or place Super Root in the “Untrusted Certificates” store.

What if you can’t do either, because Super Root is required to be trusted for a different application? That’s where policy and name constraints come into play. By specifying these on the CA certificates, you can provide additional context for the chain validation client, thereby making a stronger case to restrict to a particular chain (assuming, of course, the constraints are valid throughout the chain). In our example, this could mean specifying a nameConstraint on the Contoso Root CA, which is satisfied by all certificates in the chain. The additional context provided by the shorter chain would cause CAPI2 to return the more restrictive chain.


-----


Siddarth Adukia
Windows Core Security Team


Original URL: https://blogs.technet.microsoft.com/pki/2010/05/12/powershell-crl-copy/
Post name: Powershell CRL Copy
Original author: MS2065 [MSFT]
Posting date: 2010-05-12T04:49:16+00:00


This script writes a Certification Authority's Certificate Revocation List to HTTP based CRL Distribution Points via a UNC path. It checks to make sure that the copy was successful and that the CDPs have not and are not about to expire. Alerts/status messages are sent via SMTP and eventlog entries.

Performs the following steps:

  1. Determines if the Active Directory Certificate Services are running on the system. In the case of a cluster make sure to set the $Cluster variable to '$TRUE'
  2. Reads the CA's CRL from %windir%\system32\certsrv\certenroll (defined by $crl_master_path + $crl_name variables). I'll refer to this CRL as "Master CRL."
  3. Checks the NextUpdate value of the Master CRL to make sure is has not expired. (Note that the Mono library adds hours to the NextUpdate and ThisUpdate values, control this time difference with the $creep variable)
  4. Copy Master CRL to CDP UNC locations if Master CRL's ThisUpdate is greater than CDP CRLs' ThisUpdate
  5. Compare the hash values of the CRLs to make sure the copy was successful. If they do not match override the $SMTP variable to send email alert message.
  6. When Master CRL's ThisUpdate is greater than NextCRLPublish and NextUpdate we want to be alerted when the Master CRL is approaching end of life. Use the $threshold variable to define (in hours, .5 = 30 minutes) how far from NextUpdate you want to receive warnings that the CRLs are soon to expire.

Output:

  1. Run script initially as local administrator to register with the system's application eventlog
  2. Send SMTP message if $STMP = True. Set variable section containing SMTP settings for your environment
  3. To run this script with debug output set powershell $DebugPreference = "Continue"
  4. The 'results' function is used to write to the eventlog and send SMTP messages. Event levels are controlled in the variable section. For example a failed CRL copy you want to make sure the eventlog show "Error" ($EventHigh)

Requirements:

  1. Windows Powershell v2 included in the Windows Management Framework http://support.microsoft.com/kb/968929
  2. Powershell Community Extensions for the Get-Hash commandlet http://pscx.codeplex.com
  3. This powershell script uses a third party, open source .Net reference called 'Mono.' More information can be found at http://www.mono-project.com/Main_Page (Note: the Mono assembly Mono.Security.x509.x509CRL adds 4 hours to the .NextUpdate, .ThisUpdate and .IsCurrent function)
  4. Don't forget to set the powershell set-executionpolicy
  5. Run the script as a scheduled task every 30 minutes
    1. Start Task Scheduler
    2. Select Create Basic Task
    3. Select Daily
    4. Set Repeat task every: 30 minutes for the duration of: Indefinitely
    5. Select Start a program
    6. Set Program/script = %SystemRoot%\system32\WindowsPowerShell\v1.0\powershell.exe
    7. Set Argument = <full_path>crl_copy.ps1
    8. Within the Task’s Properties -> General tab select the following Security Options
      1. Select Change User or Group
      2. Add service account used to perform backups, make sure it has sufficient rights (remember to run the script as local administrator the first time to register with the eventlog)
      3. Select Run whether user is logged on or not
      4. Select Run with highest privileges

ToDos:

If you have any ideas, please share them. A couple of thoughts about future improvements:

  1. Bind to an LDAP directory to retrieve CRL (e.g. ldap://fpkia.gsa.gov/CommonPolicy/CommonPolicy(1).crl)
  2. Use multidimensional arrays to store CDP HTTP and UNC addresses
  3. Improve error handling

Variables:

Make sure to set for your environment

$crl_master_path

Location where the CA writes the Master CRL

$CRL_Name

Name of the CRL

$CDP1_UNC

UNC path to CDP1 make sure the path ends with “\”

$CDP2_UNC

UNC path to CDP2 make sure the path ends with “\”

$CDP1_HTTP

HTTP path to CDP1 make sure the path ends with “/”

$CDP2_HTTP

HTTP path to CDP2 make sure the path ends with “/”

$SMTP

Boolean value to determine if SMTP message is sent via the ‘results’ function

$SmtpServer

Hostname (name, FQDN or IP) of SMTP server

$From

From address of SMTP based message

$To

Recipients of SMTP message

$Title

Subject of SMTP message

$CRL_Evt_Source

Source field of Application eventlog entry

$threshold

# of hours before the reaching the Master CRL’s NextUpdate time (early warning)

$creep

# of hours that the Mono library adds to NextUpdate and ThisUpdate values

$Cluster

Set to ‘true’ if your Certification Authority is clustered

 

################################################
#
# Title:     CRLCopy.ps1
# Date:     4/28/2010
# Author: Paul Fox (MCS)
# Copyright Microsoft Corporation @2010
#
# Description:     This script writes a Certification Authority's Certificate Revocation List to HTTP based CRL Distribution Points via a UNC path.
#               Performs the following steps:
#                 1) Determines if the Active Directory Certificate Services are running on the system. In the case of a cluster make sure to set the $Cluster variable to '$TRUE'
#                 2) Reads the CA's CRL from %windir%\system32\certsrv\certenroll (defined by $crl_master_path + $crl_name variables). I'll refer to this CRL as "Master CRL."
#                 3) Checks the NextUpdate value of the Master CRL to make sure is has not expired. (Note that the Mono library adds hours to the NextUpdate and EffectiveDate values, control this time difference with the $creep variable)
#                 4) Copy Master CRL to CDP UNC locations if Master CRL's ThisUpdate is greater than CDP CRLs' ThisUpdate
#                 5) Compare the hash values of the CRLs to make sure the copy was successful. If they do not match override the $SMTP variable to send email alert message.
#                 6) When Master CRL's ThisUpdate is greater than NextCRLPublish and NextUpdate we want to be alerted when the Master CRL is approaching end of life. Use the $threshold variable to define (in hours) how far from
#                    NextUpdate you want to receive warnings that the CRLs are soon to expire.              
#
# Output: 1) Run script initially as local administrator to register with the system's application eventlog
#         2) Send SMTP message if $STMP = True. Set variable section containing SMTP settings for your environment
#         3) To run this script with debug output set powershell $DebugPreference = "Continue"
#         4) The 'results' function is used to write to the eventlog and send SMTP messages. Event levels are controlled in the variable section. For example a failed CRL copy you want to make sure the eventlog show "Error" ($EventHigh)
#      
# Requirements: 1) Windows Powershell v2 included in the Windows Management Framework http://support.microsoft.com/kb/968929
#                 2)Powershell Community Extensions for the Get-Hash commandlet http://pscx.codeplex.com
#                 3) This powershell script uses a third party, open source .Net reference called 'Mono'    More information can be found at http://www.mono-project.com/Main_Page
#                             Note: the Mono assembly Mono.Security.x509.x509CRL adds 4 hours to the .NextUpdate, .ThisUpdate and .IsCurrent function
#                         4) Don't forget to set the powershell set-executionpolicy
#
# ToDos: Bind to an LDAP directory to retrieve CRL (e.g. ldap://fpkia.gsa.gov/CommonPolicy/CommonPolicy(1).crl)
#        Use multidimensional arrays to store CDP HTTP and UNC addresses
#
# Debug: To run this script with debug output set powershell $DebugPreference = "Continue"
#
################################################

################################################
#
# Function:     Results
# Description:    Writes the $evt_string to the Application eventlog and sends
#                SMTP message to recipients if $SMTP = [bool]$true
#   
#
################################################
function results([string]$evt_string, [int]$level ,[bool]$sendsmtp)
{
write-debug "******** Inside results function ********"
write-debug "SMTP = $sendsmtp"
write-debug "Evtstring = $evt_string"
write-debug "Level: $level"
###############
#if eventlog does not exist create it (must run script as local administrator once to create)
###############
if(![system.diagnostics.eventlog]::sourceExists($CRL_Evt_Source))
    {
        $evtlog = [system.diagnostics.eventlog]::CreateEventSource($CRL_Evt_Source,"Application")
    }

###############
# set eventlog object
###############
$evtlog = new-object system.diagnostics.eventlog("application",".")
$evtlog.source = $CRL_Evt_Source

###############
# write to eventlog
###############
$evtlog.writeEntry($evt_string, $level, $EventID)

if($sendsmtp)
    {
    $SmtpClient = new-object system.net.mail.smtpClient
    $SmtpClient.host = $SmtpServer
    $Body = $evt_string
    $SmtpClient.Send($from,$to,$title,$Body)
    }
}

################################################
#
# Main program
#
################################################

################################################
#
# Add Mono .Net References
# If running on an x64 system make sure the path is correct
#
################################################
Add-Type -Path "C:\Program Files (x86)\Mono-2.6.4\lib\mono\2.0\Mono.Security.dll"

################################################
#
# Variables
#
################################################
$crl_master_path = "c:\windows\system32\certsrv\certenroll\"
$CRL_Name = "master.crl"
$CDP1_UNC = "\\cdp1\cdp1\"
$CDP2_UNC = "\\cdp2\cdp2\"
$CDP1_HTTP = "http://keys1.your.domain/"
$CDP2_HTTP = "http://keys2.your.domain/"

$SMTP = [bool]$false
$SmtpServer = "your.mx.mail.server"
$From = "crlcopy@your.domain"
$To = "CAAdmins@your.domain"
$Title = "CRL Copy Process Results"

$CRL_Evt_Source = "CRL Copy Process"
$EventID = "5000"
$EventHigh = "1"
$EventWarning = "2"
$EventInformation = "4"

$newline = [System.Environment]::NewLine
$time = Get-Date
$threshold = 1
$creep = -4
$Cluster =  [bool]$false

################################################
#
# Is certsrv running? Is it a clustered CA?
# If clustered it is not running don't send an SMTP message
#
################################################
$service = get-service | where-Object {$_.name -eq "certsvc"}

if (!($service.Status -eq "Running"))
    {
    if($Cluster)
        {
       $evt_string = "Active Directory Certificate Services is not running on this node of the cluster. Exiting program."
       write-debug "ADCS is not running. This is a clustered node. Exiting"
       results $evt_string $EventInformation $SMTP
       exit
       }
    else
        {
        $evt_string = "**** IMPORTANT **** IMPORTANT **** IMPORTANT ****" +  $newline + "Certsvc status is: " + $service.status + $newline
        write-debug "ADCS is not running and not a clustered node. Not good."
        results $evt_string $EventHigh $SMTP
        exit
        }
      }
else
     {
     write-debug "Certsvc is running. Continue."
     }

################################################
#
# Pull CRLs from Master and HTTP CDP locations
# Not going to bother with Active Directory since this
# is probably a Windows Enterprise CA (todo)
#
################################################
$CRL_Master = [Mono.Security.X509.X509Crl]::CreateFromFile($crl_master_path + $CRL_Name)
$web_client = New-Object System.Net.WebClient
$CDP1_CRL = [Mono.Security.X509.X509Crl]$web_client.DownloadData($CDP1_HTTP + $CRL_Name)
$CDP2_CRL = [Mono.Security.X509.X509Crl]$web_client.DownloadData($CDP2_HTTP + $CRL_Name)

################################################
#
# Debug section to give you the time/dates of the CRLs
#
################################################
if($debugpreference -eq "continue")
    {
    write-debug $newline
    write-debug "Master CRL Values"
    $debug_out = $CRL_Master.ThisUpdate.AddHours($creep)
    write-debug "Master ThisUpdate $debug_out"
    $debug_out = $CDP1_CRL.ThisUpdate.AddHours($creep)
    write-debug "CDP1_CRL ThisUpdate: $debug_out"
    $debug_out = $CDP2_CRL.ThisUpdate.AddHours($creep)
    write-debug "CDP2_CRL ThisUpdate: $debug_out"
    $debug_out = $CRL_Master.NextUpdate.AddHours($creep)
    write-debug "Master NextUpdate: $debug_out"
    $debug_out = $CDP1_CRL.NextUpdate.AddHours($creep)
    write-debug "CDP1_CRL NextUpdate: $debug_out"
    $debug_out = $CDP2_CRL.NextUpdate.AddHours($creep)
    write-debug "CDP2_CRL NextUpdate: $debug_out"
    write-debug $newline
    }

################################################
#
# Determine the status of the master CRL
# Master and CDP CRLs have the same EffectiveDate (Mono = ThisUpdate)   
#
################################################
if($CRL_Master.NextUpdate.AddHours($creep) -gt $time)
        {
        # This is healthy Master CRL
        write-debug "Master CRL EffectiveDate: "
        write-debug $CRL_Master.ThisUpdate.AddHours($creep)
        write-debug "Time now is: "
        write-debug $time
        write-debug $newline
        }
else
        {
        # Everything has gone stale, not good. Alert.
        write-debug "Master CRL has gone stale"
        $evt_string = "**** IMPORTANT **** IMPORTANT **** IMPORTANT ****" + $newline + "Master CRL: " + $CRL_Name + " has an EffectiveDate of: " + $CRL_Master.ThisUpdate.AddHours($creep) + " and an NextUpdate of: " + $CRL_Master.NextUpdate.AddHours($creep) + $newline + "Certsvc status is: " + $service.status
        results $evt_string $EventHigh $SMTP
        exit
        }
################################################
#   
# Determine what the status of the CDPs
# Does the Master and the CDP CRLs match up?
#
################################################
if (($CRL_Master.ThisUpdate -eq $CDP1_CRL.ThisUpdate) -and ($CRL_Master.ThisUpdate -eq $CDP2_CRL.ThisUpdate))
    {
    write-debug "All CRLs EffectiveDates match"
write-debug $CRL_Master.ThisUpdate
        write-debug $CDP1_CRL.ThisUpdate
        write-debug $CDP2_CRL.ThisUpdate
        write-debug $newline
        }
################################################
#
# New Master CRL, Update CDP CRLs if or or both are old
# would be nice to use the 'CRL Number'
# Compare the hash values of the Master CRL and CDP CRLs
# after the copy command to make sure the copy completed
#
################################################
elseif (($CRL_Master.ThisUpdate -gt $CDP1_CRL.ThisUpdate) -or ($CRL_Master.ThisUpdate -gt $CDP2_CRL.ThisUpdate))
    {
    # There is a new master CRL, copy to CDPs
    write-debug "New master crl. Copy out to CDPs"
    $source = Get-Item $crl_master_path$CRL_Name
    Copy-Item $source $CDP1_UNC$CRL_Name
    Copy-Item $source $CDP2_UNC$CRL_Name
    # Compare the hash values of the master CRL to the CDP CRL
    # If they do not equal alert via SMTP by setting the $SMTP boolian value to '$true'
    $master_hash = get-hash $source
    $cdp1_hash = get-hash $CDP1_UNC$CRL_Name
    $cdp2_hash = get-hash $CDP2_UNC$CRL_Name
    if(($master_hash.HashString -ne $cdp1_hash.HashString) -or ($master_hash.HashString -ne $cdp2_hash.HashString))
        {
        $evt_string = "CRL copy to CDP location failed:" +$newline +"Master CRL Hash: " +$master_hash.HashString +$newline + "CPD1  Hash:" +$cdp1_hash.HashString +$newline + "CDP2 Hash:" +$cdp2_hash.HashString +$newline
        # Make sure the email alert goes out. Override the $SMTP variable
        write-debug $newline
        write-debug "CRLs copied to CDPs hash values do not match Master CRL Hash"
        write-debug "Master CRL Hash value"
        write-debug $master_hash.HashString
        write-debug "CDP1 CRL Hash value"
        write-debug $cdp1_hash.HashString
        write-debug "CDP2 CRL Hash value"
        write-debug $cdp2_hash.HashString
        $SMTP = [bool]$true
        results $evt_string $EventHigh $SMTP
        exit
        }
    else
        {
        $evt_string = "New Master CRL published to CDPs. " + $CRL_Name + " has an EffectiveDate of: " + $CRL_Master.ThisUpdate.AddHours($creep) + " and an NextUpdate of: " + $CRL_Master.NextUpdate.AddHours($creep)
        results $evt_string $EventInformation $SMTP
        }
    }
else
    {
     write-debug "logic bomb, can't determine where the Master CRL is in relationship to the CDP CRLs"
     }
################################################
#
# Master CRL’s ThisUpdate time is in between the NextCRLPublish time and NextUpdate.
# Note Mono does not have a method to read 'NextCRLPublish'
# The CA Operator can define the '$threshold' at which that want to start receiving alerts
#
################################################
if (($CRL_Master.NextUpdate.AddHours($creep) -gt $time) -and ($CRL_Master.ThisUpdate.AddHours($creep) -lt $time))
    {
    write-debug "checking threshold"
    # Is the Master CRL NextUpdate within the defined alert threshold?
    if($CRL_Master.NextUpdate.AddHours(-($threshold - $creep)) -lt $time)
        {
        write-debug "***** WARNING ****** Master CRL NextUpdate has a life less than threshold."
        write-debug $CRL_Master.NextUpdate.AddHours(-($threshold - $creep))
        $evt_string = "***** WARNING ****** Master CRL NextUpdate has a life less than threshold of: " + $threshold + " hour(s)" + $newline + "Master CRLs NextUpdate is: " + $CRL_Master.NextUpdate.AddHours($creep) + $newline +"Certsvc service is: " + $service.Status
        results $evt_string $EventWarning $SMTP
        }
    else
        {
        write-debug "Within the Master CRLs NextCRLPublish and NextUpdate period. Within threshold period."
        write-debug $CRL_Master.NextUpdate.AddHours(-($threshold - $creep))
        # Uncomment the following if you want notification on the CRLs
        #$evt_string = "Within the Master CRLs NextCRLPublish and NextUpdate period. Alerts will be send at " + $threshold + " hour(s) before NextUpdate period is reached."
        #results $evt_string $EventInformation $SMTP
        }
    }
else
    {
     write-debug "logic bomb, can't determine where we are in the threshold"
    }

Original URL: https://blogs.technet.microsoft.com/pki/2010/04/22/how-to-request-a-certificate-with-a-custom-subject-alternative-name/
Post name: How to Request a Certificate With a Custom Subject Alternative Name
Original author: Alex Radutskiy [MSFT]
Posting date: 2010-04-22T13:30:00+00:00


Today many servers require some sort of SSL certificate to be deployed and in many cases custom names are involved. My colleague just published a document How to Request a Certificate With a Custom Subject Alternative Name that I strongly recommend reading.

Original URL: https://blogs.technet.microsoft.com/pki/2010/04/20/disaster-recovery-procedures-for-active-directory-certificate-services-adcs/
Post name: Disaster Recovery Procedures for Active Directory Certificate Services (ADCS)
Original author: Amerk [MSFT]
Posting date: 2010-04-20T05:34:00+00:00


Introduction:

When designing a public key infrastructure (PKI) for your organization, you must develop an effective disaster recovery plan to ensure that, in the event of failure of the computer hosting Certificate Services, you can recover in a timely manner with little effect on your organization.

Common Reasons that Make a Disaster Recovery Plan Necessary Include:

Failed services. If Certificate Services fails to start on the certification authority (CA) computer, no certificate can be issued and certificate revocation lists (CRLs) cannot be published. Your disaster plan for recovery should include performing either System State or manual CA backups and testing recovery (on a different system) on a regular basis.

Hardware failure. Disaster plan options for recovering after hardware failure include:

· Maintaining duplicate hardware (such as spare motherboards or spare computers);

· Implementing fault-tolerant RAID 1 or RAID 5 volumes to prevent CA failure due to a single disk failure.

Network infrastructure failure. Disaster recovery plans must account for network infrastructure failures. If an application implements CRL checking and network infrastructure failure prevents the application from accessing the most recent version of the CRL, an application will not validate the certificates presentedto the application. Your disaster recovery should include methods of diagnosing network infrastructure failures and developing methods of publishing CRL information that are redundant to protect against network failure.

Developing Required Documentation

One of the most important tasks during the design and deployment of a PKI is to ensure that your network and configuration documentation is updated continually. When you undergo disaster recovery, this documentation is the most important source of information regarding the previous Certificate Services configuration.

You should maintain the following documentation to ensure that you can apply all required configuration of Certificate Services successfully. The backup and recovery procedure for each of these items is explained later in this document.

All certificate template definitions. In the worst case, you might have to rebuild Active Directory, which requires the redefinition of all certificate templates. By documenting the individual settings for each certificate template on a tab-by-tab basis, you can easily re-create each certificate template.

All certificate templates published at the CA. You can create a custom script file that implements the certutil –SetCAtemplates +<TemplateName> to publish certificate templates and certutil –SetCAtemplates –<TemplateName> to remove certificate templates from the CA.

All permissions and user rights assignments. CA permissions define which users or groups hold the CA administrator and certificate manager Common Criteria roles, which groups or users can read the CA configuration, and which groups or users can request certificates from the CA. In addition, the Local Security Policy or domain-based Group Policy objects (GPOs) applied to the CA’s computer account defines the user rights assigned to the computer account, including the Common Criteria backup operators and auditor role holders.

All names used for the CA. Includes the CA’s logical name, the NetBIOS name of the computer hosting Certificate Services, and the domain or workgroup membership. The certificate information is based on the CA’s specific names and must be restored exactly.

All specific settings in the properties of the CA in the Certification Authority console. Be sure to identify which certificates are designated for key recovery, if implemented, as well as certificate manager restrictions.

Any post- or preinstallation script files used to configure the CA. For example, if you run a batch file consisting of certutil commands that define the CA’s registry settings, you should store a copy of the batch file for documentation and recovery purposes. Likewise, you should keep a copy of a batch file that publishes the CA’s CRL on an externally accessible Web server.

The CA data paths. When you restore the CA, the previous file locations for the CA database, CA log files, and CA configuration information must be maintained to match the restored registry values.

The CRL and Authority Information Access (AIA) publication points. Once the CA is restored, you must publish an updated CRL and, possibly, an updated CA certificate to the designated publication points. Ensure that no previous publication points are omitted.

The cryptographic service provider (CSP) used to protect the CA’s privatekey. The same CSP must be used to restore the previous key pair for theCA. The CSP might require additional software.

The key length of the CA’s certificate. If you are reinstalling the CA orrenewing the CA certificate, you should maintain the same key length as originallydeployed.

The logical disk-partitioning scheme for the CA computer. When you restore Certificate Services configuration, the disk volumes must implement the same drive letters. Disk volumes can be different sizes or implement different RAID levels, but the drive letters and locations must remain the same for theCA database, CA logs, CA configuration folder (if implemented), and operating system.

A copy of the CAPolicy.inf file deployed in the %windir% of the CA computer. The CAPolicy.inf must be in place when renewing the CA’s certificate.

Disaster Recovery Procedures:

There are two methods to backup and restore the Certification Authority. The methods are:

1- System State Backup

2- Certutil command line in combination of registry export

Update: It just came to my attention that System State Backup in Windows 2008 and 2008 R2 will not backup the private key of the CA. The private key will be stored in hidden folder structure "%systemdrive\ProgramData\Microsoft\Crypto\Keys" which will be linked and accessible via "%systemdrive%\users\all users\microsoft\crypto\keys". %systemdrive%\ProgramData\Microsoft\Crypto\Keys" is not included inSystem Statebackupas it's not in system writers metadata and so will be empty when doing a System State restore.

If you prefer to have System State Backup, then you should consider applying the following hotfixhttp://support.microsoft.com/kb/2603469 on your CAs running Windows Server 2008 or 2008 R2 to backup the Private Key.

Advantages and Disadvantages of Each Procedure:

Each method has advantages and disadvantages. The main advantage of System State backup is simplicity, where the administrator has to join an identical piece of hardware to the domain where the CA existed and restore System State Backup. The main disadvantage of System State is dependence on identical hardware

The Certutil command in combination with the registry export allows the administrator to restore the Certification Authority to any server – hardware agnostic. The main disadvantage of the Certutil command is the amount of steps required to perform the restore.

The document hereafter will only discuss the backup and restore methods using the Certutil command. In addition the document assumes Web Enrollment Pages are installed at the Certification Authority.


Back Up the Certification Authority:

Any proper backup of a CA should include the Certificate Security Protocol, Templates published at the CA, Private Key, Certificate Database and logs in addition to the configuration of the CA stored in HKLM\System\CurrentControlSet\Services\Certsvc\Configuration. The script below combines all of these steps

1- Log on as user who has CA administrator rights.

2- Create a folder under %Homedrive% called Backup.

3- Create a new text document under C:\scripts

4- Paste the following text:

Echo Backup Certification Authority, Certificates, Templates and CSP

c:

cd \scripts

Echo Y| del C:\backup\database

rd C:\backup\database

Echo Y| del c:\backup

Echo Backing up the Certification Authority and Certificates

certutil -backup -p Password c:\backup

Echo Backing up the registry keys

reg export HKLM\System\CurrentControlSet\Services\CertSvc\Configuration c:\backup\regkey.reg

Certutil –getreg CA\CSP > C:\Backup\CSP.txt

Echo Documenting all certificate templates published at the CA

Certutil –catemplates > C:\Backup\CATemplates.txt

*Note* You need to enter a valid Password in the script where noted. The immediate line following the Certification Authority backup will back up the registry

5- Save the file as “BackupCertificates.cmd”

6- Schedule a task to run every day using an administrative account.

7- Schedule your regular backup software job to backup the System State and the C:\Backup folder every day or copy the folder to a safe location.

Steps to Restore the Certification Authority:

Restoring the CA will require using the backup files taken from the Certification Authority, in addition to rebuilding a new server. The steps required are:

1- Extending the life of the CRL file

2- Decommission the Old Certification Authority

3- Install Active Directory Certificate Services (ADCS) at the new server

4- Restore the Certification Authority Configuration

5- Restore the Database and Templates to the Certification Authority

Extending the Life of the CRL file:

This step is necessary to ensure clients’ revocation files are processed in a timely manner,

1- Log on to a any machine in your domain as an administrator

2- Restore the CA's Private key to the machine

3- Obtain a CRL or certificate issued by the CA being tested. The CRL or certificate must correspond to the CA key and certificate being tested where you are restoring multiple keys.

4- Extend the life of the CRL by running Certutil –sign <CRLFileName.crl> ++dd, and when prompted , select the CA certificate (imported in the previous procedure) as the signing certificate.

Example:

Certutil -sign Contoso-Issuing-CA.crl ++03

5- Publish the CRL file to all distribution points as follows:

a. Copy the CRL file to the http distribution points

b. Log on to any machine in the domain as an enterprise admin and run the Certutil –f –dspublish <CRLFileName.crl>

You must now clean the keys from the test system. To clean the keys from the system

1. Log on as a member of local Administrators and delete the user profile of the administrator account using Advanced Properties in My Computer.

2. Delete the administrator account.

3. Securely erase unallocated areas of the disk to permanently remove traces of the keys by running the following command.

Cipher /W:%AllUsersProfile%

Note:Specifying %allusersprofile% as the path ensures that the cipher.exe command operates on the drive holding the user profiles. It clears the whole drive, not just the indicated path, hence making the machine unusable.

Decommission the Old Certification Authority:

This procedure is explained in details in a support article. Refer tohttp://support.microsoft.com/kb/889250for the steps required to decommissions the old Certification Authority

Install Active Directory Certificate Services at the New Server:

The new server must have the same computer name as the old server. Furthermore, it should have the same Operating System of the failed server

1- Partition the server with the same volume names

2- Copy or restore the files from the Backup folder. You should have the database, PKCS12 (*.P12) file, the registry, CATemplates.txt, and CSP.txt to the new server.

3- In Server Manager, click Add Roles.

4- In the Select Role Services window, select Certification Authority and Certification Authority Web Enrollment – if installed previously , and then click Next

5- In the Specify CA Type dialog box, click the appropriate CA type based on the failed server CA type.

6- Click Use custom settings to generate the key pair and CA certificate, and then click Next.

7- In the Set Up Private Key windows, select Use existing private key and then select the option select a certificate and use its associated private key. Click Next

8- In the Select Existing Certificate, choose the Import option and browse to the PKCS12 file in the backup folder, type the password you used during the backup, and click OK, then click Install

9- Follow the setup screens until the CA is restored

Restore the Certification Authority Configuration:

1- Stop the Certificate Services service.

2- Locate the registry file that you restored, and then double-click it to import the registry settings. If the path that is shown in the registry export from the old CA differs from the new path, you must adjust your registry export accordingly. By default, the new path is C:\Windows in Windows Server 2003.

Restore the Database and Templates to the Certification Authority:

Use the Certification Authority snap-in to restore the CA database. To do this, follow these steps:

1- In the Certification Authority snap-in, right-click the CA name, click All Tasks, and then click Restore CA. The Certification Authority Restore Wizard starts.

2- Click Next

3- Click Certificate database and certificate database log.

4- Type the backup folder location, and then click Next.

5- Verify the backup settings. The Issued Log and Pending Requests settings should be displayed.

6- Click Finish, and then click Yes to restart Certificate Services when the CA database is restored.

7- In the Certification Authority snap-in, manually add or remove certificate templates based on the templates published at the CA using the CAtemplates.txt file

Original URL: https://blogs.technet.microsoft.com/pki/2010/03/19/windows-server-2008-r2-ad-cs-migration-guide/
Post name: Windows Server 2008 R2 AD CS Migration Guide
Original author: ltalbot
Posting date: 2010-03-19T10:28:00+00:00


The official version of the new 2008 R2 ADCS Migration Guide is now available at http://technet.microsoft.com/en-us/library/ee126170(WS.10).aspx.


The guide describes the necessary steps for a successful migration of both enterprise and standalone CAs to Windows Server 2008 R2 from;



  • Windows Server 2003 SP2

  • Windows Server 2003 R2

  • Windows Server 2008

  • Windows Server 2008 R2

Also included are steps for migration to Server Core.