Extensibilidade de configuração declarada

O registro de configuração declarada do Windows (WinDC) oferece extensibilidade por meio de provedores WMI nativos. Esse recurso instancia e faz interface com um provedor WMI (Instrumentação de Gerenciamento do Windows) que implementa uma interface de MI (infraestrutura de gerenciamento). A interface deve implementar os métodos GetTargetResource, TestTargetResource e SetTargetResource e pode implementar qualquer número de propriedades de cadeia de caracteres.

Observação

No momento, apenas propriedades de cadeia de caracteres têm suporte de provedores de extensibilidade.

[static, Description ("Get resource state based on input configuration file." )]
uint32 GetTargetResource(
    [in, EmbeddedInstance ("MSFT_FileDirectoryConfiguration"), Description ("Configuration document that is to be applied.")]
    string InputResource,
    [in, Description ("Flags passed to the provider. Reserved for future use." )]
    uint32 Flags,
    [out, EmbeddedInstance ("MSFT_FileDirectoryConfiguration"), Description ("The current state of the specified configuration resources." )]
    string OutputResource
);

[static, Description ("Test resource state based on input configuration file." )]
uint32 TestTargetResource(
    [in, EmbeddedInstance("MSFT_FileDirectoryConfiguration"), Description ("Configuration document to be applied." )]
    string InputResource,
    [in, Description ("Flags passed to the provider. reserved for future use." )]
    uint32 Flags,
    [out, Description ("True if identical. False otherwise." )]
    boolean Result,
    [out, Description ("Context information the provider can use to optimize the set. This is optional." )]
    uint64 ProviderContext
);

[static, Description ("Set resource state based on input configuration file." )]
uint32 SetTargetResource(
    [in, EmbeddedInstance ("MSFT_FileDirectoryConfiguration"),
    Description ("Configuration document to be applied." )]
    string InputResource,
    [in, Description ("Context information the provider can use to optimize the set from SetTargetResource. This is optional." )]
    uint64 ProviderContext,
    [in, Description ("Flags passed to the provider. reserved for future use." )]
    uint32 Flags
);

Autor: recursos de configuração de estado desejados

Para criar um provedor WMI nativo, siga as etapas descritas em Como implementar um provedor MI. Essas etapas incluem como gerar o código-fonte para uma interface de MI usando a Convert-MofToProvider.exe ferramenta para gerar a DLL e prepará-la para posicionamento.

  1. Crie um arquivo MOF (Managed Object Format) que defina o esquema para o recurso de configuração de estado desejado, incluindo parâmetros e métodos. Esse arquivo inclui os parâmetros necessários para o recurso.
  2. Copie o arquivo MOF do esquema junto com quaisquer arquivos necessários para o diretório de ferramentas do provedor, por exemplo: ProviderGenerationTool.
  3. Edite os arquivos necessários e inclua os nomes de arquivo e os nomes de classe corretos.
  4. Invoque a ferramenta geradora de provedor para gerar os arquivos de projeto do provedor.
  5. Copie os arquivos gerados para a pasta do projeto do provedor.
  6. Inicie o processo de desenvolvimento.

Exemplo de provedor de MI

Este exemplo fornece mais detalhes sobre cada etapa para demonstrar como implementar um recurso nativo de exemplo chamado MSFT_FileDirectoryConfiguration.

Etapa 1: Criar o arquivo MOF do esquema de recursos

Crie um arquivo MOF de esquema de exemplo usado para gerar o código-fonte inicial para o MSFT_FileDirectoryConfiguration recurso nativo. Coloque-o no diretório do projeto chamado MSFT_FileDirectoryConfiguration.

#pragma include ("cim_schema_2.26.0.mof")
#pragma include ("OMI_BaseResource.mof")
#pragma include ("MSFT_Credential.mof")

[ClassVersion("1.0.0"), Description("The configuration provider for files and directories.")]
class MSFT_FileDirectoryConfiguration : OMI_BaseResource
{
    [Key, Description("File name and path on target node to copy or create.")]
    string DestinationPath;

    [Write, Description("The name and path of the file to copy from.")]
    string SourcePath;

    [Write, Description("Contains a string that represents the contents of the file. To create an empty file, the string must be empty. The contents will be written and compared using UTF-8 character encoding.")]
    string Contents;

    [static, Description ("Get resource states based on input configuration file." )]
    uint32 GetTargetResource(
        [in, EmbeddedInstance ("MSFT_FileDirectoryConfiguration"), Description ("Configuration document that is to be applied." )]
        string InputResource,

        [in,Description ("Flags passed to the providers. Reserved for future use." )]
        uint32 Flags,

        [out, EmbeddedInstance ("MSFT_FileDirectoryConfiguration"), Description ("The current state of the specified configuration resources." )]
        string OutputResource
    );

    [static, Description ("Test resource states based on input configuration file." )]
    uint32 TestTargetResource(
        [in, EmbeddedInstance("MSFT_FileDirectoryConfiguration"), Description ("Configuration document that to be applied." )]
        string InputResource,

        [in, Description ("Flags passed to the providers. reserved for future use." )]
        uint32 Flags,

        [out, Description ("True if identical. False otherwise." )]
        boolean Result,

        [out, Description ("Context information that the provider can use to optimize the set, This is optional." )]
        uint64 ProviderContext
    );

    [static, Description ("Set resource states based on input configuration file." )]
    uint32 SetTargetResource(
        [in, EmbeddedInstance ("MSFT_FileDirectoryConfiguration"), Description ("Configuration document that to be applied." )]
        string InputResource,

        [in, Description ("Context information that the provider can use to optimize the set from TestTargetResource, This is optional." )]
        uint64 ProviderContext,

        [in, Description ("Flags passed to the providers. reserved for future use." )]
        uint32 Flags
    );
};

Observação

  • O nome da classe e o nome do arquivo DLL devem ser os mesmos, conforme definido no Provider.DEF arquivo.

  • O qualificador [Key] de tipo em uma propriedade indica que ele identifica exclusivamente a instância do recurso. Pelo menos uma [Key] propriedade é obrigatória.

  • O [Required] qualificador indica que a propriedade é obrigatória. Em outras palavras, um valor deve ser especificado em qualquer script de configuração que use esse recurso.

  • O [write] qualificador indica que a propriedade é opcional ao usar o recurso personalizado em um script de configuração. O [read] qualificador indica que uma propriedade não pode ser definida por uma configuração e é apenas para fins de relatório.

  • O [Values] qualificador restringe os valores que podem ser atribuídos à propriedade. Definir a lista de valores permitidos em [ValueMap]. Para obter mais informações, consulte ValueMap e qualificadores de valor.

  • Qualquer novo arquivo MOF deve incluir as seguintes linhas na parte superior do arquivo:

    #pragma include ("cim_schema_2.26.0.mof")
    #pragma include ("OMI_BaseResource.mof")
    #pragma include ("MSFT_Credential.mof")
    
  • Os nomes de método e seus parâmetros devem ser os mesmos para cada recurso. Altere MSFT_FileDirectoryConfiguration do valor EmbeddedInstance para o nome da classe do provedor desejado. Deve haver apenas um provedor por arquivo MOF.

Etapa 2: Copiar os arquivos MOF do esquema

Copie esses arquivos e pastas necessários para o diretório do projeto que você criou na etapa 1:

  • CIM-2.26.0
  • codegen.cmd
  • Convert-MofToProvider.exe
  • MSFT_Credential.mof
  • MSFT_DSCResource.mof
  • OMI_BaseResource.mof
  • OMI_Errors.mof
  • Provider.DEF
  • wmicodegen.dll

Para obter mais informações sobre como obter os arquivos necessários, consulte Como implementar um provedor de MI.

Etapa 3: Edite os arquivos necessários

Modifique os seguintes arquivos no diretório do projeto:

  • MSFT_FileDirectoryConfiguration.mof: você criou este arquivo na etapa 1.

  • Provider.DEF: este arquivo contém o nome da DLL, por exemplo, MSFT_FileDirectoryConfiguration.dll.

  • codegen.cmd: Este arquivo contém o comando para invocar convert-moftoprovider.exe.

    "convert-moftoprovider.exe" ^
       -MofFile MSFT_FileDirectoryConfiguration.mof ^
                MSFT_DSCResource.mof ^
                OMI_Errors.mof ^
       -ClassList MSFT_FileDirectoryConfiguration ^
       -IncludePath CIM-2.26.0 ^
       -ExtraClass OMI_Error ^
                   MSFT_DSCResource ^
       -OutPath temp
    

Etapa 4: Executar a ferramenta geradora de provedor

Execute codegen.cmd, que executa o convert-moftoprovider.exe comando. Como alternativa, você pode executar o comando diretamente.

Etapa 5: copiar os arquivos de origem gerados

O comando na etapa 3 especifica o -OutPath parâmetro, que neste exemplo é uma pasta chamada temp. Quando você executa a ferramenta na etapa 4, ela cria novos arquivos nessa pasta. Copie os arquivos gerados desta temp pasta para o diretório do projeto. Você criou o diretório do projeto na etapa 1, que neste exemplo é MSFT_FileDirectoryConfiguration.

Observação

Sempre que você atualizar o arquivo MOF do esquema, execute o codegen.cmd script para regenerar os arquivos de origem. Executar novamente a ferramenta geradora substitui todos os arquivos de origem existentes. Para evitar esse comportamento, este exemplo usa uma pasta temporária. Minimize as atualizações no arquivo MOF do esquema, pois a implementação principal deve ser mesclada com os arquivos de origem gerados automaticamente mais recentes.

Sobre o MSFT_FileDirectoryConfiguration recurso

Depois de executar a ferramenta geradora de provedores, ela cria vários arquivos de origem e de cabeçalho:

  • MSFT_FileDirectoryConfiguration.c
  • MSFT_FileDirectoryConfiguration.h
  • module.c
  • schema.c
  • WMIAdapter.c

Nessa lista, você só precisa modificar MSFT_FileDirectoryConfiguration.c e MSFT_FileDirectoryConfiguration.h. Você também pode alterar a extensão dos arquivos de .c origem de para .cpp, que é o caso deste recurso. A lógica de negócios para esse recurso é implementada no MSFT_FileDirectoryConfigurationImp.cpp e MSFT_FileDirectoryConfigurationImp.h. Esses novos arquivos são adicionados ao diretório do MSFT_FileDirectoryConfiguration projeto depois que você executa a ferramenta geradora de provedores.

Para um recurso nativo de configuração de estado desejado, você precisa implementar três funções geradas automaticamente em MSFT_FileDirectoryConfiguration.cpp:

  • MSFT_FileDirectoryConfiguration_Invoke_GetTargetResource
  • MSFT_FileDirectoryConfiguration_Invoke_TestTargetResource
  • MSFT_FileDirectoryConfiguration_Invoke_SetTargetResource

Dessas três funções, somente MSFT_FileDirectoryConfiguration_Invoke_GetTargetResource é necessário para um cenário Get. MSFT_FileDirectoryConfiguration_Invoke_TestTargetResource e MSFT_FileDirectoryConfiguration_Invoke_SetTargetResource são usados quando a correção é necessária.

Há várias outras funções MSFT_FileDirectoryConfiguration.cpp geradas automaticamente que não precisam de implementação para um recurso nativo de configuração de estado desejado. Você não precisa modificar as seguintes funções:

  • MSFT_FileDirectoryConfiguration_Load
  • MSFT_FileDirectoryConfiguration_Unload
  • MSFT_FileDirectoryConfiguration_EnumerateInstances
  • MSFT_FileDirectoryConfiguration_GetInstance
  • MSFT_FileDirectoryConfiguration_CreateInstance
  • MSFT_FileDirectoryConfiguration_ModifyInstance
  • MSFT_FileDirectoryConfiguration_DeleteInstance

Sobre nós MSFT_FileDirectoryConfiguration_Invoke_GetTargetResource

A MSFT_FileDirectoryConfiguration_Invoke_GetTargetResource função executa as seguintes etapas para concluir sua tarefa:

  1. Valide o recurso de entrada.

  2. Certifique-se de que as chaves e os parâmetros necessários estejam presentes.

  3. Crie uma instância de recurso que seja usada como a saída do método Get. Esta instância é do tipo MSFT_FileDirectoryConfiguration, que é derivado de MI_Instance.

  4. Crie a instância do recurso de saída da instância do recurso modificada e retorne-a ao cliente MI chamando estas funções:

    • MSFT_FileDirectoryConfiguration_GetTargetResource_Construct
    • MSFT_FileDirectoryConfiguration_GetTargetResource_SetPtr_OutputResource
    • MSFT_FileDirectoryConfiguration_GetTargetResource_Set_MIReturn
    • MSFT_FileDirectoryConfiguration_GetTargetResource_Post
    • MSFT_FileDirectoryConfiguration_GetTargetResource_Destruct
  5. Limpe os recursos, por exemplo, liberar memória alocada.

Documento WinDC

Importante

O destino das configurações de cenário só pode ser em todo o dispositivo para extensibilidade. O escopo do CSP definido no <LocURI>contexto do WinDC deve ser Device.

O valor do Document nó folha no CSP DeclaredConfiguration é um documento XML que descreve a solicitação. Aqui está um documento WinDC de exemplo com os dados de configuração especificados para extensibilidade.

<DeclaredConfiguration schema="1.0" context="Device" id="27FEA311-68B9-4320-9FC4-296F6FDFAFE2" checksum="99925209110918B67FE962460137AA3440AFF4DB6ABBE15C8F499682457B9999" osdefinedscenario="MSFTExtensibilityMIProviderConfig">
    <DSC namespace="root/Microsoft/Windows/DesiredStateConfiguration" className="MSFT_FileDirectoryConfiguration">
        <Key name="DestinationPath">c:\data\test\bin\ut_extensibility.tmp</Key>
        <Value name="Contents">TestFileContent1</Value>
    </DSC>
</DeclaredConfiguration>

Somente valores com suporte para osdefinedscenario podem ser usados. Valores sem suporte resultam em uma mensagem de erro semelhante a Invalid scenario name.

OSDdefinedScenario Descrição
MSFTExtensibilityMIProviderConfig Usado para definir as configurações do provedor de MI.
MSFTExtensibilityMIProviderInventory Usado para recuperar valores de configuração do provedor de MI.

Ambos MSFTExtensibilityMIProviderConfig e MSFTExtensibilityMIProviderInventory cenários que exigem as mesmas marcas e atributos.

  • A <DSC> marca XML descreve o provedor WMI de destino expresso por um namespace e um nome de classe, juntamente com os valores a serem aplicados ao dispositivo ou consultados pelo provedor MI.

    Esta marca tem os seguintes atributos:

    Atributo Descrição
    namespace Especifica o namespace do provedor de MI de destino.
    classname O provedor de MI de destino.
  • A <Key> marca XML descreve o nome e o valor do parâmetro necessário. Ele só precisa de um valor para configuração. O nome é um atributo e o valor é <Key> conteúdo.

    Esta marca tem os seguintes atributos:

    Atributo Descrição
    name Especifica o nome de um parâmetro do provedor MI.
  • A <Value> marca XML descreve o nome e o valor do parâmetro opcional. Ele só precisa de um valor para configuração. O nome é um atributo e o valor é <Value> conteúdo.

    Esta marca tem os seguintes atributos:

    Atributo Descrição
    name Especifica o nome de um parâmetro do provedor MI.

Exemplos de SyncML

A sintaxe padrão SyncML do OMA-DM é usada para especificar as operações do CSP DeclaredConfiguration, como Substituir, Adicionar e Excluir. A carga do elemento do <Data> SyncML deve ser codificada em XML. Para essa codificação XML, há vários codificadores online que você pode usar. Para evitar a codificação da carga, você pode usar a Seção CDATA conforme mostrado nos exemplos de SyncML a seguir.

Solicitação de configuração

Este exemplo demonstra como enviar uma solicitação de configuração usando o MSFT_FileDirectoryConfiguration provedor MI com o MSFTExtensibilityMIProviderConfig cenário.

<?xml version="1.0" encoding="utf-8"?>
<SyncML xmlns="SYNCML:SYNCML1.1">
  <SyncBody>
    <Replace>
      <CmdID>14</CmdID>
      <Item>
        <Target>
          <LocURI>./Device/Vendor/MSFT/DeclaredConfiguration/Host/Complete/Documents/27FEA311-68B9-4320-9FC4-296F6FDFAFE2/Document</LocURI>
        </Target>
        <Data><![CDATA[
            <DeclaredConfiguration schema="1.0" context="Device" id="27FEA311-68B9-4320-9FC4-296F6FDFAFE2" checksum="99925209110918B67FE962460137AA3440AFF4DB6ABBE15C8F499682457B9999" osdefinedscenario="MSFTExtensibilityMIProviderConfig">
                <DSC namespace="root/Microsoft/Windows/DesiredStateConfiguration" className="MSFT_FileDirectoryConfiguration">
                    <Key name="DestinationPath">c:\data\test\bin\ut_extensibility.tmp</Key>
                    <Value name="Contents">TestFileContent1</Value>
                </DSC>
            </DeclaredConfiguration>
        ]]></Data>
      </Item>
    </Replace>
  </SyncBody>
</SyncML>

Solicitação de inventário

Este exemplo demonstra como enviar uma solicitação de inventário usando o provedor MSFT_FileDirectoryConfiguration MI com o cenário MSFTExtensibilityMIProviderInventory.

<?xml version="1.0" encoding="utf-8"?>
<SyncML xmlns="SYNCML:SYNCML1.1">
  <SyncBody>
    <Replace>
      <CmdID>15</CmdID>
      <Item>
        <Target>
          <LocURI>./Device/Vendor/MSFT/DeclaredConfiguration/Host/Inventory/Documents/12345678-1234-1234-1234-123456789012/Document</LocURI>
        </Target>
        <Data><![CDATA[
            <DeclaredConfiguration schema="1.0" context="Device" id="12345678-1234-1234-1234-123456789012" checksum="1234567890ABCDEF1234567890ABCDEF1234567890ABCDEF1234567890ABCDEF" osdefinedscenario="MSFTExtensibilityMIProviderInventory">
                <DSC namespace="root/Microsoft/Windows/DesiredStateConfiguration" className="MSFT_FileDirectoryConfiguration">
                    <Key name="DestinationPath">c:\data\test\bin\ut_extensibility.tmp</Key>
                </DSC>
            </DeclaredConfiguration>
        ]]></Data>
      </Item>
    </Replace>
  </SyncBody>
</SyncML>

Recuperar resultados

Este exemplo recupera os resultados de uma solicitação de configuração ou inventário:

Solicitação:

<SyncML xmlns="SYNCML:SYNCML1.1">
    <SyncBody>
    <Get>
        <CmdID>2</CmdID>
        <Item>
        <Meta>
            <Format>chr</Format>
            <Type>text/plain</Type>
        </Meta>
        <Target>
            <LocURI>./Device/Vendor/MSFT/DeclaredConfiguration/Host/Complete/Results/27FEA311-68B9-4320-9FC4-296F6FDFAFE2/Document</LocURI>
        </Target>
        </Item>
    </Get>
    <Final />
    </SyncBody>
</SyncML>

Resposta:

<Status>
    <CmdID>2</CmdID>
    <MsgRef>1</MsgRef>
    <CmdRef>2</CmdRef>
    <Cmd>Get</Cmd>
    <Data>200</Data>
</Status>
<Results>
    <CmdID>3</CmdID>
    <MsgRef>1</MsgRef>
    <CmdRef>2</CmdRef>
    <Item>
        <Source>
            <LocURI>./Device/Vendor/MSFT/DeclaredConfiguration/Host/Complete/Results/27FEA311-68B9-4320-9FC4-296F6FDFAFE2/Document</LocURI>
        </Source>
        <Data>
            <DeclaredConfigurationResult context="Device" schema="1.0" id="99988660-9080-3433-96e8-f32e85011999" osdefinedscenario="MSFTPolicies" checksum="99925209110918B67FE962460137AA3440AFF4DB6ABBE15C8F499682457B9999" result_checksum="EE4F1636201B0D39F71654427E420E625B9459EED17ACCEEE1AC9B358F4283FD" operation="Set" state="60">
                <DSC namespace="root/Microsoft/Windows/DesiredStateConfiguration" className="MSFT_FileDirectoryConfiguration" status="200" state="60">
                    <Key name="DestinationPath" />
                    <Value name="Contents" />
                </DSC>
            </DeclaredConfigurationResult>
        </Data>
    </Item>
</Results>

Referências de implementação de MI