[適用於 KMDF 和 UMDF]
DriverEntry 是載入驅動程序之後呼叫的第一個驅動程式提供的例程。 負責初始化驅動程式。
語法
NTSTATUS DriverEntry(
_In_ PDRIVER_OBJECT DriverObject,
_In_ PUNICODE_STRING RegistryPath
);
參數
DriverObject [in]
代表驅動程式 WDM 驅動程式物件的 DRIVER_OBJECT 結構的指標。
RegistryPath [in]
UNICODE_STRING 結構的指標,指定登錄中驅動程式 Parameters 機碼 的路徑。
返回值
如果例程成功,則必須傳回STATUS_SUCCESS。 否則,它必須傳回 ntstatus.h中定義的其中一個錯誤狀態值。
備註
如同所有 WDM 驅動程式,架構型驅動程式必須具有 DriverEntry 例程,此例程會在載入驅動程式之後呼叫。 以架構為基礎的驅動程式 DriverEntry 例程必須:
啟動 WPP 軟體追蹤。
DriverEntry 應該包含可啟動軟體追蹤的 WPP_INIT_TRACING 巨集。
呼叫 WdfDriverCreate。
呼叫 WdfDriverCreate 可讓驅動程式使用 Windows Driver Framework 介面。 (驅動程式在呼叫 WdfDriverCreate之前,無法呼叫其他架構例程。
配置任何非裝置特定的系統資源和可能需要的全域變數。
一般而言,驅動程式會將系統資源與個別裝置產生關聯。 因此,架構型驅動程式會在偵測到個別裝置時呼叫的 EvtDriverDeviceAdd 回呼中配置大部分資源。
由於 UMDF 驅動程式的多個實例可能由 Wudfhost 的個別實例裝載,因此全域變數可能無法在 UMDF 驅動程式的所有實例中使用。
從登錄取得驅動程式特定的參數。
某些驅動程式會從登錄取得參數。 這些驅動程式可以呼叫 WdfDriverOpenParametersRegistryKey,以開啟包含這些參數的登錄機碼。
提供DriverEntry 傳回值。
注意 UMDF 驅動程式會在使用者模式主機進程中執行,而 KMDF 驅動程式則會在系統進程中以核心模式執行。 架構可能會將 UMDF 驅動程式的多個實例載入主機進程的個別實例。 因此:
- 如果架構在不同的主機進程中載入驅動程序的實例,架構可能會多次呼叫 UMDF 驅動程式的 DriverEntry 例程。 相反地,架構只會呼叫 KMDF 驅動程式的 DriverEntry 例程一次。
- 如果 UMDF 驅動程式在其 DriverEntry 例程中建立全域變數,該變數可能無法供驅動程式的所有實例使用。 不過,KMDF 驅動程式在其 DriverEntry 例程中建立的全域變數可供驅動程式的所有實例使用。
如需何時呼叫架構驅動程式 DriverEntry 例程的詳細資訊,請參閱 建置和載入 WDF 驅動程式。
DriverEntry 例程不會在 WDK 標頭中宣告。 靜態驅動程式驗證器 (SDV) 和其他驗證工具可能需要宣告,如下所示:
DRIVER_INITIALIZE MyDriverEntry;
NTSTATUS
DriverEntry(
IN PDRIVER_OBJECT DriverObject,
IN PUNICODE_STRING RegistryPath
)
{
// Function body
}
範例
下列程式代碼範例顯示 Serial (KMDF) 範例驅動程式的 DriverEntry 例程。
NTSTATUS
DriverEntry(
IN PDRIVER_OBJECT DriverObject,
IN PUNICODE_STRING RegistryPath
)
{
WDF_DRIVER_CONFIG config;
WDFDRIVER hDriver;
NTSTATUS status;
WDF_OBJECT_ATTRIBUTES attributes;
SERIAL_FIRMWARE_DATA driverDefaults;
//
// Initialize WPP tracing.
//
WPP_INIT_TRACING(
DriverObject,
RegistryPath
);
SerialDbgPrintEx(
TRACE_LEVEL_INFORMATION,
DBG_INIT,
"Serial Sample (WDF Version) - Built %s %s\n",
__DATE__, __TIME__
);
//
// Register a cleanup callback function (which calls WPP_CLEANUP)
// for the framework driver object. The framework will call
// the cleanup callback function when it deletes the driver object,
// before the driver is unloaded.
//
WDF_OBJECT_ATTRIBUTES_INIT(&attributes);
attributes.EvtCleanupCallback = SerialEvtDriverContextCleanup;
WDF_DRIVER_CONFIG_INIT(
&config,
SerialEvtDeviceAdd
);
status = WdfDriverCreate(
DriverObject,
RegistryPath,
&attributes,
&config,
&hDriver
);
if (!NT_SUCCESS(status)) {
SerialDbgPrintEx(
TRACE_LEVEL_ERROR,
DBG_INIT,
"WdfDriverCreate failed with status 0x%x\n",
status
);
//
// Clean up tracing here because WdfDriverCreate failed.
//
WPP_CLEANUP(DriverObject);
return status;
}
//
// Call an internal routine to obtain registry values
// to use for all the devices that the driver
// controls, including whether or not to break on entry.
//
SerialGetConfigDefaults(
&driverDefaults,
hDriver
);
//
// Break on entry if requested bt registry value.
//
if (driverDefaults.ShouldBreakOnEntry) {
DbgBreakPoint();
}
return status;
}