共用方式為


使用__sdv_save_adapter_coNtext來追蹤配接器內容欄位

當 NDIS 呼叫迷你埠驅動程式的 MiniportInitializeEx 回呼函式來初始化迷你埠配接器時,驅動程式會建立自己的內部資料結構來代表迷你埠配接器。 驅動程式會使用此結構,稱為 迷你埠介面卡內容,來維護驅動程式為了管理迷你埠介面卡所需的裝置特定狀態資訊。 驅動程式會將控制碼傳遞至 NDIS。

當 NDIS 呼叫與迷你埠介面卡相關的其中一個迷你埠驅動程式 MiniportXxx 函式時,NDIS 會將迷你埠配接器內容傳遞至驅動程式,以識別正確的迷你埠介面卡。 迷你埠配接器內容是由迷你埠驅動程式所擁有和維護,而且與 NDIS 和通訊協定驅動程式不透明。

因為迷你埠配接器內容會維護 NDIS 呼叫之間的迷你埠驅動程式狀態,所以靜態驅動程式驗證器 (SDV) 必須能夠識別這個 結構的指標。 若要讓 SDV 追蹤迷你埠驅動程式的狀態,您必須使用 __sdv_save_adapter_coNtext 函式,將控制碼儲存到迷你埠配接器內容。

__sdv_save_adapter_coNtext函式具有下列語法:

__sdv_save_adapter_context( &adapter_context ) 

其中 adapter_coNtext 是迷你埠驅動程式所定義之迷你埠配接器內容的控制碼。 此函式應該只在迷你埠驅動程式的內容中呼叫一次。

__sdv_save_adapter_coNtext函式僅供靜態分析工具使用。 編譯器會忽略此函式。

下列程式碼範例示範何時呼叫 __sdv_save_adapter_coNtext,以及 SDV 如何追蹤 迷你埠配接器內容中的資訊。

下列程式碼範例顯示迷你埠配接器內容範例結構的簡化版本,MP_Adapter。

typedef struct _MP_ADAPTER
{
    NDIS_HANDLE             AdapterHandle;

    BOOLEAN                 InterruptRegistered;
    NDIS_HANDLE             InterruptHandle;

    /* ..................... */

} MP_ADAPTER, *PMP_ADAPTER;

在執行 MiniportInitializeEx期間,會配置MP_ADAPER結構的記憶體。 緊接在記憶體配置之後, 會呼叫 __sdv_save_adapter_coNtext

當您有迷你埠配接器內容結構的有效指標時,必須立即呼叫 __sdv_save_adapter_coNtext 函式。

NDIS_STATUS 
MPInitialize(
    IN  NDIS_HANDLE                        MiniportAdapterHandle,
    IN  NDIS_HANDLE                        MiniportDriverContext,
    IN  PNDIS_MINIPORT_INIT_PARAMETERS     MiniportInitParameters
    )
{
    NDIS_STATUS     Status = NDIS_STATUS_SUCCESS;
    PMP_ADAPTER     pAdapter = NULL;
 
    /* ..................... */
 
    do
    {
   // allocate the memory for the AdapterContext
        pAdapter = NdisAllocateMemoryWithTagPriority(
            MiniportAdapterHandle,
            sizeof(MP_ADAPTER),
            NIC_TAG,
            LowPoolPriority
            );

   // save the adapter context, even before we check whether it is NULL or not 
 __sdv_save_adapter_context(&pAdapter);

        if (pAdapter == NULL)
        {
            Status = NDIS_STATUS_RESOURCES;
            break;
        }
 
        NdisZeroMemory(pAdapter, sizeof(MP_ADAPTER));
 
        pAdapter->AdapterHandle = MiniportAdapterHandle;
        pAdapter->PauseState = NicPaused;

   /* ..................... */

下列程式碼範例示範 SDV 如何追蹤迷你埠配接器內容中的值。 在此範例中,驅動程式會藉由呼叫 Miniport 提供的函式 MpRegisterInterrupt來註冊中斷。 如果呼叫成功,驅動程式會將結果儲存到迷你埠配接器內容中, (pAdapter) 欄位 InterruptRegistered。

//
// Register the interrupt
   //
        Status = MpRegisterInterrupt(pAdapter);
        if (Status != NDIS_STATUS_SUCCESS)
        {
            break;
        }
 
   // save the value of the result into the AdapterContext
        pAdapter->InterruptRegistered = TRUE;

當迷你埠驅動程式必須停止時,NDIS 會藉由將控制碼傳遞至迷你埠配接器內容來呼叫驅動程式的 MiniportHaltEx 函 式。 因為 SDV 也有這個控制碼,所以從先前呼叫 __sdv_save_adapter_coNtext,SDV 可以追蹤 InterruptRegistered 欄位的值。

VOID MPHalt(
    IN  NDIS_HANDLE             MiniportAdapterContext,
    IN  NDIS_HALT_ACTION        HaltAction
    )
{
    PMP_ADAPTER     pAdapter = (PMP_ADAPTER) MiniportAdapterContext;
 
    /* ..................... */

    if (pAdapter->InterruptRegistered)
    {
        NdisMDeregisterInterruptEx(pAdapter->InterruptHandle);
        pAdapter->InterruptRegistered = FALSE;
    }

/* ..................... */