共用方式為


WdfDmaTransactionExecute 函式 (wdfdmatransaction.h)

[僅適用於 KMDF]

WdfDmaTransactionExecute 方法會開始執行指定的 DMA 交易。

語法

NTSTATUS WdfDmaTransactionExecute(
  [in]           WDFDMATRANSACTION DmaTransaction,
  [in, optional] WDFCONTEXT        Context
);

參數

[in] DmaTransaction

驅動程式從先前呼叫 WdfDmaTransactionCreate取得的 DMA 交易物件的句柄。

[in, optional] Context

驅動程式定義的內容資訊。 架構會將指定給 Context的值傳遞至驅動程式的 EvtProgramDma 事件回呼函式。 這個參數是選擇性的,而且可以 NULL

返回值

如果作業成功,WdfDmaTransactionExecute 會傳回STATUS_SUCCESS。 否則,方法可能會傳回下列其中一個值。

回傳碼 說明
資源不足狀態
驅動程式先前稱為 WdfDmaTransactionSetImmediateExecution,而且要求所需的資源無法使用。
STATUS_INVALID_DEVICE_REQUEST
WdfDmaTransactionExecute 的呼叫之前,沒有呼叫 WdfDmaTransactionInitializeWdfDmaTransactionInitializeUsingRequest
STATUS_WDF_BUSY
裝置會執行單一封包傳輸,而另一個交易執行時稱為 WdfDmaTransactionExecute 的驅動程式
STATUS_WDF_TOO_FRAGMENTED
作系統處理指定之傳輸大小所需的散佈/收集元素數目大於驅動程式呼叫 WdfDmaEnablerSetMaximumScatterGatherElements 的值。 如需詳細資訊,請參閱下列一節。
 

此方法也可能 傳回其他NTSTATUS 值。

如果驅動程式提供無效的物件句柄,就會發生錯誤檢查。

備註

WdfDmaTransactionExecute 方法會針對與指定 DMA 交易相關聯的第一個 DMA 傳輸,初始化交易的散佈/收集清單。 (對於單一封包傳輸,散佈/收集清單包含單一元素。然後,方法會呼叫驅動程式的 EvtProgramDma 事件回呼函式,而且回呼函式可以程式設計裝置開始傳輸。

架構型驅動程式通常會從 I/O 佇列事件回呼函式內呼叫 WdfDmaTransactionExecute

在驅動程式呼叫 WdfDmaTransactionInitializeWdfDmaTransactionInitializeUsingRequest 初始化 DMA 交易 之後,驅動程式必須先呼叫 WdfDmaTransactionExecute,才能完成 DMA 交易

如果 WdfDmaTransactionInitializeXxx 傳回成功,但 WdfDmaTransactionExecute 傳回錯誤值,您的驅動程式必須呼叫 WdfDmaTransactionRelease

在 1.11 之前的架構版本中,如果裝置執行單一封包傳輸,作系統一次只能執行一個 DMA 交易。 在此情況下,WdfDmaTransactionExecute 在另一個交易執行時傳回STATUS_WDF_BUSY。

在 Framework 1.11 版和更新版本中,如果驅動程式使用 DMA 第 3 版來執行單一封包傳輸,作系統可以在內部佇列中儲存多個 DMA 交易。 在此情況下,驅動程式可以在另一筆交易執行時呼叫 WdfDmaTransactionExecute。 若要選取 DMA 第 3 版,請將 WdmDmaVersionOverrideWDF_DMA_ENABLER_CONFIG 成員設為 3。

如果裝置執行散佈/收集傳輸,作系統可以同時執行多個 DMA 交易。 在此情況下,驅動程式可以在另一筆交易執行時呼叫 WdfDmaTransactionExecute

如果驅動程式呼叫 WdfDmaTransactionDmaCompletedWithLength 來報告部分傳輸, 如果驅動程式已使用鏈結在一起的 MDL 來指定 DMA 交易的數據緩衝區(使用 MDL 結構的成員),WdfDmaTransactionExecute 可以傳回STATUS_WDF_TOO_FRAGMENTED,因為架構可能會重新計算片段的數目和大小,而且可能超過允許的片段數目。

如果交易成功啟動,WdfDmaTransactionExecute 會傳回STATUS_SUCCESS。 若要判斷架構是否成功將所有交易的傳輸傳送傳送至驅動程式的 EvtProgramDma 回呼函式, 驅動程式必須呼叫 WdfDmaTransactionDmaCompletedWdfDmaTransactionDmaCompletedWithLengthWdfDmaTransactionDmaCompletedFinal

如果 Context 參數提供的值是指針或句柄,則必須在 IRQL = DISPATCH_LEVEL 的驅動程式 EvtProgramDma 事件回呼函式中存取它所參考的記憶體。 您可以使用 架構物件內容 來符合這項需求。

如果驅動程式先前呼叫 WdfDmaTransactionSetImmediateExecution,則驅動程式可以以非封鎖方式呼叫 WdfDmaTransactionExecute

如需 DMA 交易的詳細資訊,請參閱 啟動 DMA 交易

範例

下列程式代碼範例來自 PCIDRV 範例驅動程式。 此範例會建立並初始化 DMA 傳輸,並開始執行。

NTSTATUS
NICInitiateDmaTransfer(
    IN PFDO_DATA  FdoData,
    IN WDFREQUEST  Request
    )
{
    WDFDMATRANSACTION  dmaTransaction;
    NTSTATUS  status;
    BOOLEAN  bCreated = FALSE;
 
    do {
        status = WdfDmaTransactionCreate(
                                         FdoData->WdfDmaEnabler,
                                         WDF_NO_OBJECT_ATTRIBUTES,
                                         &dmaTransaction
                                         );
        if(!NT_SUCCESS(status)) {
            TraceEvents(TRACE_LEVEL_ERROR, DBG_WRITE, 
                        "WdfDmaTransactionCreate failed %X\n", status);
            break;
        }

        bCreated = TRUE;

        status = WdfDmaTransactionInitializeUsingRequest( 
                                     dmaTransaction,
                                     Request,
                                     NICEvtProgramDmaFunction,
                                     WdfDmaDirectionWriteToDevice
                                     );
        if(!NT_SUCCESS(status)) {
            TraceEvents(
                        TRACE_LEVEL_ERROR,
                        DBG_WRITE, 
                        "WdfDmaTransactionInitalizeUsingRequest failed %X\n", 
                        status
                        );
            break;
        }

        status = WdfDmaTransactionExecute(
                                          dmaTransaction,
                                          dmaTransaction
                                          );

        if(!NT_SUCCESS(status)) {
            TraceEvents(
                        TRACE_LEVEL_ERROR,
                        DBG_WRITE, 
                        "WdfDmaTransactionExecute failed %X\n",
                        status
                        );
            break;
        }
    } while (FALSE);

    if(!NT_SUCCESS(status)){
 
        if(bCreated) {
            WdfObjectDelete(dmaTransaction);
        }
    }
    return status;
}

需求

要求 價值
目標平臺 普遍
最低 KMDF 版本 1.0
標題 wdfdmatransaction.h (包括 Wdf.h)
程式庫 Wdf01000.sys (請參閱架構連結庫版本控制。)
IRQL <=DISPATCH_LEVEL
DDI 合規性規則 DriverCreate(kmdf)KmdfIrql(kmdf)KmdfIrql2(kmdf),KmdfIrqlExplicit(kmdf)

另請參閱

EvtProgramDma

WdfDmaEnablerSetMaximumScatterGatherElements

WdfDmaTransactionCreate

WdfDmaTransactionDmaCompleted

WdfDmaTransactionDmaCompletedFinal

WdfDmaTransactionDmaCompletedWithLength

WdfDmaTransactionInitialize

WdfDmaTransactionInitializeUsingRequest

WdfDmaTransactionSetImmediateExecution