Compartilhar via


Protegendo o arquivo MOF

Aplica-se a: Windows PowerShell 4.0, Windows PowerShell 5.0

A DSC gerencia a configuração de nós de servidor aplicando informações armazenadas em um arquivo MOF, em que o LCM (Gerenciador de Configurações Local) implementa o estado final desejado. Como esse arquivo contém os detalhes da configuração, é importante mantê-lo seguro. Este artigo descreve como garantir que o nó de destino tenha criptografado o arquivo.

A partir do PowerShell versão 5.0, todo o arquivo MOF é criptografado por padrão quando é aplicado ao nó usando o Start-DSCConfiguration cmdlet. O processo descrito neste artigo é necessário somente ao implementar uma solução usando o protocolo de serviço de pull se os certificados não forem gerenciados, para garantir que as configurações baixadas pelo nó de destino possam ser descriptografadas e lidas pelo sistema antes de serem aplicadas (por exemplo, o serviço de pull disponível no Windows Server). Os nós registrados no DSC de Automação do Azure terão automaticamente certificados instalados e gerenciados pelo serviço sem a necessidade de sobrecarga administrativa.

Observação

Este tópico discute os certificados usados para criptografia. Para criptografia, um certificado autoassinado é suficiente, pois a chave privada é sempre mantida em segredo e a criptografia não implica confiança no documento. Os certificados autoassinados não devem ser usados para fins de autenticação. Você deve usar um certificado de uma Autoridade de Certificação (CA) confiável para fins de autenticação.

Pré-requisitos

Para criptografar com êxito as credenciais usadas para proteger uma configuração de DSC, verifique se você tem o seguinte:

  • Alguns meios de emissão e distribuição de certificados. Este tópico e seus exemplos pressupõem que você esteja usando a Autoridade de Certificação do Active Directory. Para obter mais informações básicas sobre os Serviços de Certificados do Active Directory, consulte Visão geral dos Serviços de Certificados do Active Directory.
  • Acesso administrativo ao nó ou nós de destino.
  • Cada nó de destino tem um certificado com capacidade de criptografia salvo em seu Repositório Pessoal. No Windows PowerShell, o caminho para o repositório é Cert:\LocalMachine\My. Os exemplos neste tópico usam o modelo de "autenticação de estação de trabalho", que você pode encontrar (junto com outros modelos de certificado) em Modelos de Certificado Padrão.
  • Se você estiver executando essa configuração em um computador diferente do nó de destino, exporte a chave pública do certificado e importe-a para o computador do qual você executará a configuração. Certifique-se de exportar apenas a chave pública ; Mantenha a chave privada segura.

Observação

Os recursos de script têm limitações quando se trata de criptografia. Para obter mais informações, consulte Recurso de script

Processo geral

  1. Configure os certificados, chaves e impressões digitais, certificando-se de que cada nó de destino tenha cópias do certificado e que o computador de configuração tenha a chave pública e a impressão digital.
  2. Crie um bloco de dados de configuração que contenha o caminho e a impressão digital da chave pública.
  3. Crie um script de configuração que defina a configuração desejada para o nó de destino e configure a descriptografia nos nós de destino comandando o Gerenciador de configuração local para descriptografar os dados de configuração usando o certificado e sua impressão digital.
  4. Execute a configuração, que definirá as configurações do Gerenciador de Configurações Local e iniciará a configuração do DSC.

Fluxo de processo para criptografia de credenciais

Requisitos de certificado

Para executar a criptografia de credenciais, um certificado de chave pública deve estar disponível no Nó de Destinoconfiável para o computador que está sendo usado para criar a configuração de DSC. Esse certificado de chave pública tem requisitos específicos para ser usado para criptografia de credencial DSC:

  1. Uso da chave:
    • Deve conter: 'KeyEncipherment' e 'DataEncipherment'.
    • Não deve conter: 'Assinatura Digital'.
  2. Uso aprimorado da chave:
    • Deve conter: Criptografia de documentos (1.3.6.1.4.1.311.80.1).
    • Não deve conter: Autenticação de Cliente (1.3.6.1.5.5.7.3.2) e Autenticação de Servidor (1.3.6.1.5.5.7.3.1).
  3. A chave privada do certificado está disponível no Node_ *Target.
  4. O provedor do certificado deve ser "Microsoft RSA SChannel Cryptographic Provider".

Importante

Embora você possa usar um certificado contendo um uso de chave de 'assinatura digital' ou um dos EKU de autenticação, isso permitirá que a chave de criptografia seja mais facilmente mal utilizada e vulnerável a ataques. Portanto, é uma prática recomendada usar um certificado criado especificamente com a finalidade de proteger as credenciais de DSC que omitem esses EKUs e uso de chave.

Qualquer certificado existente no Nó de Destino que atenda a esses critérios pode ser usado para proteger credenciais de DSC.

Criação de certificado

Há duas abordagens que você pode adotar para criar e usar o Certificado de Criptografia necessário (par de chaves pública-privada).

  1. Crie-o no Nó de Destino e exporte apenas a chave pública para o Nó de Criação
  2. Crie-o no Nó de Criação e exporte todo o par de chaves para o Nó de Destino

O método 1 é recomendado porque a chave privada usada para descriptografar credenciais no MOF permanece no nó de destino o tempo todo.

Criando o certificado no nó de destino

A chave privada deve ser mantida em segredo, pois é usada para descriptografar o MOF no Nó de Destino A maneira mais fácil de fazer isso é criar o certificado de chave privada no Nó de Destino e copiar o certificado de chave pública para o computador que está sendo usado para criar a configuração de DSC em um arquivo MOF. O exemplo a seguir:

  1. cria um certificado no nó Destino
  2. exporta o certificado de chave pública no nó de destino.
  3. importa o certificado de chave pública para o repositório de certificados my no nó Authoring.

No nó de destino: criar e exportar o certificado

Nó de destino: Windows Server 2016 e Windows 10

# note: These steps need to be performed in an Administrator PowerShell session
$cert = New-SelfSignedCertificate -Type DocumentEncryptionCertLegacyCsp -DnsName 'DscEncryptionCert' -HashAlgorithm SHA256
# export the public key certificate
$cert | Export-Certificate -FilePath "$env:temp\DscPublicKey.cer" -Force

Depois de exportado, o DscPublicKey.cer precisaria ser copiado para o nó de criação.

No nó de criação: importe a chave pública do certificado

# Import to the my store
Import-Certificate -FilePath "$env:temp\DscPublicKey.cer" -CertStoreLocation Cert:\LocalMachine\My

Criando o certificado no nó de autoria

Como alternativa, o certificado de criptografia pode ser criado no Nó de Criação, exportado com a chave privada como um arquivo PFX e, em seguida, importado no Nó de Destino. Esse é o método atual para implementar a criptografia de credenciais DSC no Nano Server. Embora o PFX seja protegido com uma senha, ele deve ser mantido seguro durante o trânsito. O exemplo a seguir:

  1. cria um certificado no nó Criação.
  2. exporta o certificado, incluindo a chave privada no nó Criação.
  3. remove a chave privada do nó Criação, mas mantém o certificado de chave pública no meu repositório.
  4. importa o certificado de chave privada para o repositório de certificados My(Personal) no nó Destino.
    • ele deve ser adicionado ao repositório raiz para que seja confiável para o nó de destino.

No Nó de Criação: criar e exportar o certificado

Nó de destino: Windows Server 2016 e Windows 10

# note: These steps need to be performed in an Administrator PowerShell session
$cert = New-SelfSignedCertificate -Type DocumentEncryptionCertLegacyCsp -DnsName 'DscEncryptionCert' -HashAlgorithm SHA256
# export the private key certificate
$mypwd = ConvertTo-SecureString -String "YOUR_PFX_PASSWD" -Force -AsPlainText
$cert | Export-PfxCertificate -FilePath "$env:temp\DscPrivateKey.pfx" -Password $mypwd -Force
# remove the private key certificate from the node but keep the public key certificate
$cert | Export-Certificate -FilePath "$env:temp\DscPublicKey.cer" -Force
$cert | Remove-Item -Force
Import-Certificate -FilePath "$env:temp\DscPublicKey.cer" -CertStoreLocation Cert:\LocalMachine\My

Depois de exportado, o DscPrivateKey.pfx precisaria ser copiado para o nó de destino.

No nó de destino: importe a chave privada do certificado como uma raiz confiável

# Import to the root store so that it is trusted
$mypwd = ConvertTo-SecureString -String "YOUR_PFX_PASSWD" -Force -AsPlainText
Import-PfxCertificate -FilePath "$env:temp\DscPrivateKey.pfx" -CertStoreLocation Cert:\LocalMachine\My -Password $mypwd > $null

Dados de configuração

O bloco de dados de configuração define em quais nós de destino operar, se devem ou não criptografar as credenciais, os meios de criptografia e outras informações. Para obter mais informações sobre o bloco de dados de configuração, consulte Separando dados de configuração e ambiente.

Os elementos que podem ser configurados para cada nó relacionados à criptografia de credenciais são:

  • NodeName - o nome do nó de destino para o qual a criptografia de credencial está sendo configurada.
  • PsDscAllowPlainTextPassword - se as credenciais não criptografadas poderão ser passadas para esse nó. Isso não é recomendado.
  • Impressão digital – a impressão digital do certificado que será usado para descriptografar as credenciais na Configuração de DSC no Nó de Destino. Esse certificado deve existir no repositório de certificados do Computador Local no Nó de Destino.
  • CertificateFile - o arquivo de certificado (contendo somente a chave pública) que deve ser usado para criptografar as credenciais do Nó de Destino. Deve ser um arquivo de certificado de formato X.509 binário codificado em DER ou X.509 codificado em Base-64.

Este exemplo mostra um bloco de dados de configuração que especifica um nó de destino para atuar no nome targetNode, o caminho para o arquivo de certificado de chave pública (chamado targetNode.cer) e a impressão digital da chave pública.

$ConfigData = @{
    AllNodes = @(
        @{
            # The name of the node we are describing
            NodeName        = "targetNode"

            # The path to the .cer file containing the
            # public key of the Encryption Certificate
            # used to encrypt credentials for this node
            CertificateFile = "C:\publicKeys\targetNode.cer"


            # The thumbprint of the Encryption Certificate
            # used to decrypt the credentials on target node
            Thumbprint      = "AC23EA3A9E291A75757A556D0B71CBBF8C4F6FD8"
        }
    )
}

Script de configuração

No próprio script de configuração, use o PsCredential parâmetro para garantir que as credenciais sejam armazenadas pelo menor tempo possível. Quando você executar o exemplo fornecido, a DSC solicitará credenciais e, em seguida, criptografará o arquivo MOF usando o CertificateFile associado ao nó de destino no bloco de dados de configuração. Este exemplo de código copia um arquivo de um compartilhamento protegido para um usuário.

configuration CredentialEncryptionExample
{
    param(
        [Parameter(Mandatory=$true)]
        [ValidateNotNullorEmpty()]
        [PsCredential] $credential
    )

    Node $AllNodes.NodeName
    {
        File exampleFile
        {
            SourcePath = "\\Server\share\path\file.ext"
            DestinationPath = "C:\destinationPath"
            Credential = $credential
        }
    }
}

Configurando a descriptografia

Antes que Start-DscConfiguration possa funcionar, você precisa informar ao Gerenciador de Configurações Local em cada nó de destino qual certificado usar para descriptografar as credenciais, usando o recurso CertificateID para verificar a impressão digital do certificado. Esta função de exemplo encontrará o certificado local apropriado (talvez seja necessário personalizá-lo para que ele encontre o certificado exato que deseja usar):

# Get the certificate that works for encryption
function Get-LocalEncryptionCertificateThumbprint
{
    (dir Cert:\LocalMachine\my) | %{
        # Verify the certificate is for Encryption and valid
        if ($_.PrivateKey.KeyExchangeAlgorithm -and $_.Verify())
        {
            return $_.Thumbprint
        }
    }
}

Com o certificado identificado por sua impressão digital, o script de configuração pode ser atualizado para usar o valor:

configuration CredentialEncryptionExample
{
    param(
        [Parameter(Mandatory=$true)]
        [ValidateNotNullorEmpty()]
        [PsCredential] $credential
    )

    Node $AllNodes.NodeName
    {
        File exampleFile
        {
            SourcePath = "\\Server\share\path\file.ext"
            DestinationPath = "C:\destinationPath"
            Credential = $credential
        }

        LocalConfigurationManager
        {
             CertificateId = $node.Thumbprint
        }
    }
}

Executando a configuração

Neste ponto, você pode executar a configuração, que produzirá dois arquivos:

  • Um *.meta.mof arquivo que configura o Gerenciador de Configurações Local para descriptografar as credenciais usando o certificado armazenado no repositório do computador local e identificado por sua impressão digital. Set-DscLocalConfigurationManager aplica o *.meta.mof arquivo.
  • Um arquivo MOF que realmente aplica a configuração. Start-DscConfiguration aplica a configuração.

Esses comandos realizarão essas etapas:

Write-Host "Generate DSC Configuration..."
CredentialEncryptionExample -ConfigurationData $ConfigData -OutputPath .\CredentialEncryptionExample

Write-Host "Setting up LCM to decrypt credentials..."
Set-DscLocalConfigurationManager .\CredentialEncryptionExample -Verbose

Write-Host "Starting Configuration..."
Start-DscConfiguration .\CredentialEncryptionExample -wait -Verbose

Este exemplo enviaria a configuração de DSC para o nó de destino. A configuração de DSC também pode ser aplicada usando um Servidor de Pull de DSC, se houver um disponível.

Consulte Configurando um cliente de pull de DSC para obter mais informações sobre como aplicar configurações de DSC usando um Servidor de Pull de DSC.

Exemplo de módulo de criptografia de credenciais

Aqui está um exemplo completo que incorpora todas essas etapas, além de um cmdlet auxiliar que exporta e copia as chaves públicas:

# A simple example of using credentials
configuration CredentialEncryptionExample
{
    param(
        [Parameter(Mandatory=$true)]
        [ValidateNotNullorEmpty()]
        [PsCredential] $credential
    )

    Node $AllNodes.NodeName
    {
        File exampleFile
        {
            SourcePath = "\\server\share\file.txt"
            DestinationPath = "C:\Users\user"
            Credential = $credential
        }

        LocalConfigurationManager
        {
            CertificateId = $node.Thumbprint
        }
    }
}

# A Helper to invoke the configuration, with the correct public key
# To encrypt the configuration credentials
function Start-CredentialEncryptionExample
{
    [CmdletBinding()]
    param ($computerName)

    [string] $thumbprint = Get-EncryptionCertificate -computerName $computerName -Verbose
    Write-Verbose "using cert: $thumbprint"

    $certificatePath = join-path -Path "$env:SystemDrive\$script:publicKeyFolder" -childPath "$computername.EncryptionCertificate.cer"

    $ConfigData=    @{
        AllNodes = @(
                        @{
                            # The name of the node we are describing
                            NodeName = "$computerName"

                            # The path to the .cer file containing the
                            # public key of the Encryption Certificate
                            CertificateFile = "$certificatePath"

                            # The thumbprint of the Encryption Certificate
                            # used to decrypt the credentials
                            Thumbprint = $thumbprint
                        };
                    );
    }

    Write-Verbose "Generate DSC Configuration..."
    CredentialEncryptionExample -ConfigurationData $ConfigData -OutputPath .\CredentialEncryptionExample `
        -credential (Get-Credential -UserName "$env:USERDOMAIN\$env:USERNAME" -Message "Enter credentials for configuration")

    Write-Verbose "Setting up LCM to decrypt credentials..."
    Set-DscLocalConfigurationManager .\CredentialEncryptionExample -Verbose

    Write-Verbose "Starting Configuration..."
    Start-DscConfiguration .\CredentialEncryptionExample -wait -Verbose
}

#region HelperFunctions

# The folder name for the exported public keys
$script:publicKeyFolder = "publicKeys"

# Get the certificate that works for encryptions
function Get-EncryptionCertificate
{
    [CmdletBinding()]
    param ($computerName)

    $returnValue= Invoke-Command -ComputerName $computerName -ScriptBlock {
        $certificates = dir Cert:\LocalMachine\my

        $certificates | %{
                    # Verify the certificate is for Encryption and valid
            if ($_.PrivateKey.KeyExchangeAlgorithm -and $_.Verify())
            {
                # Create the folder to hold the exported public key
                $folder= Join-Path -Path $env:SystemDrive\ -ChildPath $using:publicKeyFolder
                if (! (Test-Path $folder))
                {
                    md $folder | Out-Null
                }

                # Export the public key to a well known location
                $certPath = Export-Certificate -Cert $_ -FilePath (Join-Path -path $folder -childPath "EncryptionCertificate.cer")

                # Return the thumbprint, and exported certificate path
                return @($_.Thumbprint,$certPath);
            }
        }
    }

    Write-Verbose "Identified and exported cert..."
    # Copy the exported certificate locally
    $destinationPath = join-path -Path "$env:SystemDrive\$script:publicKeyFolder" -childPath "$computername.EncryptionCertificate.cer"
    Copy-Item -Path (join-path -path \\$computername -childPath $returnValue[1].FullName.Replace(":","$"))  $destinationPath | Out-Null

    # Return the thumbprint
    return $returnValue[0]
}

Start-CredentialEncryptionExample