Пример кода: действия Finish-Install в установщике классов
Примечание
Функции, описанные в этом разделе, не поддерживаются в универсальных или мобильных пакетах драйверов. См . раздел Использование универсального INF-файла.
В этом примере установщик класса выполняет следующие операции для поддержки действий завершения установки:
Когда установщик класса получает запрос DIF_NEWDEVICEWIZARD_FINISHINSTALL , он вызывает предоставленную установщиком функцию FinishInstallActionsNeeded , чтобы определить, нужно ли выполнить действия завершения установки. (Код функции FinishInstallActionsNeeded в этом примере не показан.)
Если Метод FinishInstallActionsNeeded возвращает значение TRUE, установщик класса вызывает SetupDiGetDeviceInstallParams , чтобы получить параметры установки устройства для устройства. Затем он вызывает SetupDiSetDeviceInstallParams , чтобы задать элемент FlagsExструктуры SP_DEVINSTALL_PARAMS для устройства с флагом DI_FLAGSEX_FINISHINSTALL_ACTION. Установка этого флага приводит к тому, что Windows отправляет запрос DIF_FINISHINSTALL_ACTION всем установщикам классов, соустановкам классов и совместному установщику устройств, участвующим в установке этого устройства. Этот запрос отправляется после завершения всех операций установки, кроме действий завершения установки.
Когда установщик класса получает запрос DIF_FINISHINSTALL_ACTION, он снова вызывает FinishInstallActionsNeeded, чтобы определить, есть ли у него действия завершения и установки, и, если да, выполняет действия завершения установки. Установщик класса уведомляет пользователя о выполнении действий по завершению установки и ожидает завершения действий завершения установки, прежде чем вернуться из обработки запроса DIF_FINISHINSTALL_ACTION.
Если действия завершения установки выполнены успешно, установщик класса уведомляет пользователя о том, что действия по завершению установки выполнены успешно.
Если для выполнения действий завершения установки требовался перезапуск системы, установщик класса вызывает SetupDiGetDeviceInstallParams для получения параметров установки устройства, а затем вызывает SetupDiSetDeviceInstallParams, чтобы задать элемент Flags структуры SP_DEVINSTALL_PARAMS для устройства с флагом DI_NEEDREBOOT. Установщик также уведомляет пользователя о необходимости перезагрузки системы.
Если действия завершения и установки завершаются сбоем, но при следующем перечислении устройства необходимо повторить попытку выполнения действий завершения установки, установщик класса уведомляет пользователя об этой ситуации.
Примечание Начиная с Windows 8 действие завершения установки выполняется только один раз. Windows не будет автоматически запускать его снова, особенно при следующем перечислении устройства, так как это не происходит при выполнении действий завершения установки.
Если действия завершения и установки завершаются сбоем и установщик класса определяет, что действия завершения и установки не могут быть выполнены, установщик класса уведомляет пользователя об этой ситуации.
По умолчанию установщик класса возвращает ERROR_DI_DO_DEFAULT в ответ на запрос DIF_FINISHINSTALL_ACTION, если действия завершения установки выполнены успешно или если действия завершения установки завершилися ошибкой, и установщик определяет, что действия завершения установки не должны выполняться повторно. Установщик возвращает код ошибки Win32 только в том случае, если действия завершения установки завершаются сбоем, и при следующем перечислении устройства в контексте администратора необходимо повторить попытку выполнения действий завершения установки.
Примечание Начиная с Windows 8 действие завершения установки выполняется только один раз. Windows не будет автоматически запускать его снова, особенно при следующем перечислении устройства, так как это не происходит при выполнении действий завершения установки.
В следующем примере кода установщика класса показана базовая структура кода установщика класса, реализующая действия завершения установки:
DWORD CALLBACK
SampleClassInstaller(
IN DI_FUNCTION InstallFunction,
IN HDEVINFO DeviceInfoSet,
IN PSP_DEVINFO_DATA DeviceInfoData,
)
{
SP_DEVINSTALL_PARAMS DeviceInstallParams;
DWORD ReturnValue = ERROR_DI_DO_DEFAULT; // The default return value
switch(InstallFunction)
{
case DIF_NEWDEVICEWIZARD_FINISHINSTALL:
//
// Processing for finish-install wizard pages
// If the class installer has wizard pages,
// set ReturnValue to NO_ERROR
//
// 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:
// Processing for finish-install actions
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;
}