Exemplo de código: ações de Finish-Install em um co-instalador
Observação
Os recursos descritos nesta seção não têm suporte em pacotes de driver universal ou móvel. Consulte Usando um arquivo INF universal.
Neste exemplo, um co-instalador executa as seguintes operações para dar suporte a ações de conclusão de instalação:
Quando o co-instalador recebe uma solicitação DIF_NEWDEVICEWIZARD_FINISHINSTALL , ele chama a função fornecida pelo instalador FinishInstallActionsNeeded para determinar se há ações de instalação final a serem executadas. (O código da função FinishInstallActionsNeeded não é mostrado neste exemplo).
Se FinishInstallActionsNeeded retornarTRUE, o co-instalador chamará SetupDiGetDeviceInstallParams para recuperar os parâmetros de instalação do dispositivo e, em seguida, chamará SetupDiSetDeviceInstallParams para definir o membro FlagsEx da estrutura SP_DEVINSTALL_PARAMS para o dispositivo com o sinalizador DI_FLAGSEX_FINISHINSTALL_ACTION. Definir esse sinalizador faz com que o Windows envie uma solicitação de DIF_FINISHINSTALL_ACTION para todos os instaladores de classe, co-instaladores de classe e co-instaladores de dispositivo envolvidos na instalação deste dispositivo. Essa solicitação é enviada depois que todas as operações de instalação, exceto as ações de conclusão da instalação, forem concluídas.
Quando o co-instalador recebe uma solicitação DIF_FINISHINSTALL_ACTION, o co-instalador novamente chama FinishInstallActionsNeeded para determinar se ele tem ações de instalação final para executar e, nesse caso, executa as ações de conclusão de instalação. O co-instalador notifica o usuário de que as ações de conclusão da instalação estão em andamento e aguarda a conclusão das ações de conclusão da instalação antes de retornar do processamento da solicitação de DIF_FINISHINSTALL_ACTION.
Se as ações concluir a instalação forem bem-sucedidas, o co-instalador notificará o usuário de que as ações de conclusão de instalação foram bem-sucedidas.
Se as ações de instalação final exigirem uma reinicialização do sistema para concluir as ações de instalação final, o co-instalador chamará SetupDiGetDeviceInstallParams para recuperar os parâmetros de instalação do dispositivo para o dispositivo e, em seguida, chamará SetupDiSetDeviceInstallParams para definir o membro Flags da estrutura SP_DEVINSTALL_PARAMS para o dispositivo com o sinalizador DI_NEEDREBOOT. O instalador também notifica o usuário de que uma reinicialização do sistema é necessária.
Se as ações de conclusão de instalação falharem e as ações de concluir a instalação forem tentadas novamente na próxima vez que o dispositivo for enumerado, o co-instalador notificará o usuário sobre essa situação.
Nota Começando no Windows 8 uma ação de conclusão de instalação só é executada uma vez. O Windows não o executará automaticamente novamente, especialmente na próxima vez que o dispositivo for enumerado, pois não é quando as ações de instalação final são executadas.
Se as ações de instalação final falharem e o co-instalador determinar que as ações de conclusão de instalação não poderão ser bem-sucedidas, o co-instalador notificará o usuário sobre essa situação.
Por padrão, o co-instalador retorna NO_ERROR em resposta a uma solicitação de DIF_FINISHINSTALL_ACTION se as ações de instalação de término tiverem sido bem-sucedidas ou se as ações de instalação final falharem e o co-instalador determinar que as ações de conclusão-instalação não devem ser tentadas novamente. O co-instalador retornará um código de erro Win32 somente se as ações de concluir a instalação falharem e as ações de conclusão da instalação forem tentadas novamente na próxima vez que o dispositivo for enumerado no contexto de um administrador.
Nota Começando no Windows 8 uma ação de conclusão de instalação só é executada uma vez. O Windows não o executará automaticamente novamente, especialmente na próxima vez que o dispositivo for enumerado, pois não é quando as ações de instalação final são executadas.
O exemplo de código do co-instalador a seguir mostra a estrutura básica do código do co-instalador que implementa ações de conclusão de instalação:
DWORD CALLBACK
SampleCoInstaller(
IN DI_FUNCTION InstallFunction,
IN HDEVINFO DeviceInfoSet,
IN PSP_DEVINFO_DATA DeviceInfoData,
IN OUT PCOINSTALLER_CONTEXT_DATA Context
)
{
SP_DEVINSTALL_PARAMS DeviceInstallParams;
DWORD ReturnValue = NO_ERROR; // The default return value
switch(InstallFunction)
{
case DIF_NEWDEVICEWIZARD_FINISHINSTALL:
//
// Processing for finish-install wizard pages
//
// Processing for finish-install actions
if (FinishInstallActionsNeeded())
{
// Obtain the device install parameters for the device
// and set the DI_FLAGSEX_FINISHINSTALL_ACTION flag
DeviceInstallParams.cbSize = sizeof(DeviceInstallParams);
if (SetupDiGetDeviceInstallParams(DeviceInfoSet, DeviceInfoData, &DeviceInstallParams))
{
DeviceInstallParams.FlagsEx |= DI_FLAGSEX_FINISHINSTALL_ACTION;
SetupDiSetDeviceInstallParams(DeviceInfoSet, DeviceInfoData, &DeviceInstallParams);
}
}
break;
case DIF_FINISHINSTALL_ACTION:
if (FinishInstallActionsNeeded())
{
//
// Perform the finish-install actions,
// notify the user that finish install actions
// are in progress and wait for
// the finish-install actions to complete
//
// If the finish-install actions succeed, notify the user
//
// If the finish install actions require a system restart:
// notify the user, call SetupDiGetDeviceInstallParams
// to obtain the device install parameters for the device in
// DeviceInstallParams, and call SetupDiSetInstallParams to set
// the DI_NEEDREBOOT flag in DeviceInstallParams.Flags
//
// If the finish install actions failed, but
// should be attempted again: clean up,
// notify the user of the failure, and
// set ReturnValue to an appropriate Win32 error code
//
// If the finish install actions failed and
// should not be attempted again: clean up
// and notify the user of the failure
//
// Starting with Windows 8, a finish-install action
// is only run once. Windows will not automatically
// run it again, especially not the next time
// the device is enumerated because that is not when
// finish-install actions are run.
//
}
break;
}
return ReturnValue;
}