Partager via


WdfDmaTransactionExecute, fonction (wdfdmatransaction.h)

[S’applique uniquement à KMDF]

La méthode WdfDmaTransactionExecute commence l’exécution d’une transaction DMA spécifiée.

Syntaxe

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

Paramètres

[in] DmaTransaction

Handle vers un objet de transaction DMA que le pilote a obtenu à partir d’un appel précédent à WdfDmaTransactionCreate.

[in, optional] Context

Informations de contexte définies par le pilote. L’infrastructure transmet la valeur spécifiée pour context, qui peut être un pointeur, à la fonction de rappel d’événement evtProgramDma du pilote. Ce paramètre est facultatif et peut être NULL.

Valeur de retour

WdfDmaTransactionExecute retourne STATUS_SUCCESS si l’opération réussit. Sinon, la méthode peut retourner l’une des valeurs suivantes.

Code de retour Description
STATUS_INSUFFICIENT_RESOURCES
Le pilote appelé précédemment WdfDmaTransactionSetImmediateExecution et les ressources nécessaires à la requête ne sont pas disponibles.
STATUS_INVALID_DEVICE_REQUEST
L’appel à WdfDmaTransactionExecute n’a pas été précédé d’un appel à WdfDmaTransactionInitialize ou WdfDmaTransactionInitializeUsingRequest.
STATUS_WDF_BUSY
L’appareil effectue des transferts à paquet unique et le pilote appelé WdfDmaTransactionExecute pendant l’exécution d’une autre transaction.
STATUS_WDF_TOO_FRAGMENTED
Le nombre d’éléments de nuages/de collecte nécessaires au système d’exploitation pour gérer la taille de transfert spécifiée était supérieur à la valeur que l’appel du pilote à WdfDmaEnablerSetMaximumScatterGatherElements spécifié. Pour plus d’informations, consultez la section Remarques suivante.
 

Cette méthode peut également retourner d’autres valeurs NTSTATUS .

Une vérification de bogue se produit si le pilote fournit un handle d’objet non valide.

Remarques

La méthode WdfDmaTransactionExecute initialise la liste de nuages de points/collecte d’une transaction pour la première de transfert DMA associée au transaction DMA spécifié. (Pour les transferts à paquet unique, la liste de nuages de points/collecte contient un élément unique.) Ensuite, la méthode appelle la fonction de rappel d’événements evtProgramDma du pilote, et la fonction de rappel peut programmer l’appareil pour commencer le transfert.

Les pilotes basés sur l’infrastructure appellent généralement WdfDmaTransactionExecute à partir d’une fonction de rappel d’événements d’E/S .

Une fois qu’un pilote a appelé WdfDmaTransactionInitialize ou WdfDmaTransactionInitializeUsingRequest pour initialiser une transaction DMA, le pilote doit appeler WdfDmaTransactionExecute une seule fois avant fin de la transaction DMA.

Si WdfDmaTransactionInitializeXxx retourne la réussite, mais WdfDmaTransactionExecute retourne une valeur d’erreur, votre pilote doit appeler WdfDmaTransactionRelease.

Dans les versions de framework antérieures à la version 1.11, si l’appareil effectue des transferts à paquet unique, le système d’exploitation ne peut exécuter qu’une seule transaction DMA à la fois. Dans ce cas, WdfDmaTransactionExecute retourne STATUS_WDF_BUSY si une autre transaction est en cours d’exécution.

Dans les versions de framework 1.11 et ultérieures, si le pilote utilise DMA version 3 pour effectuer des transferts à paquet unique, le système d’exploitation peut stocker plusieurs transactions DMA dans une file d’attente interne. Dans ce cas, le pilote peut appeler WdfDmaTransactionExecute pendant l’exécution d’une autre transaction. Pour sélectionner DMA version 3, définissez le membre WdmDmaVersionOverride de WDF_DMA_ENABLER_CONFIG sur 3.

Si l’appareil effectue des transferts de nuages/de collecte, le système d’exploitation peut exécuter plusieurs transactions DMA simultanément. Dans ce cas, le pilote peut appeler WdfDmaTransactionExecute pendant l’exécution d’une autre transaction.

Si le pilote appelle WdfDmaTransactionDmaCompletedWithLength pour signaler un transfert partiel, et si le pilote avait spécifié la mémoire tampon de données de la transaction DMA à l’aide de MDLs qu’il chaînait (à l’aide du membre Suivant de la structure MDL), WdfDmaTransactionExecute peut retourner STATUS_WDF_TOO_FRAGMENTED, car l’infrastructure peut recalculer le nombre et la taille des fragments et peut dépasser le nombre de fragments autorisés.

Le WdfDmaTransactionExecute retourne STATUS_SUCCESS si la transaction a bien démarré. Pour déterminer si l’infrastructure a correctement envoyé tous les transferts de la transaction à la fonction de rappel evtProgramDma du pilote, le pilote doit appeler WdfDmaTransactionDmaCompleted, WdfDmaTransactionDmaTransactionDmaCompletedWithLength, ou WdfDmaTransactionDmaCompletedFinal.

Si la valeur que fournit le paramètre Context est un pointeur ou un handle, la mémoire qu’il référence doit être accessible dans la fonction de rappel d’événements EvtProgramDma du pilote à IRQL = DISPATCH_LEVEL. Vous pouvez utiliser contexte d’objet framework pour répondre à cette exigence.

Le pilote peut appeler WdfDmaTransactionExecute de manière non bloquante s’il a déjà appelé WdfDmaTransactionSetImmediateExecution.

Pour plus d’informations sur les transactions DMA, consultez Démarrage d’une transaction DMA.

Exemples

L’exemple de code suivant provient de l’exemple de pilote PCIDRV . Cet exemple crée et initialise un transfert DMA et commence son exécution.

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;
}

Spécifications

Besoin Valeur
plateforme cible Universel
version minimale de KMDF 1.0
En-tête wdfdmatransaction.h (include Wdf.h)
Bibliothèque Wdf01000.sys (voir Versioning de la bibliothèque Framework.)
IRQL <=DISPATCH_LEVEL
règles de conformité DDI DriverCreate(kmdf), KmdfIrql(kmdf), KmdfIrql2(kmdf), KmdfIrqlExplicit(kmdf)

Voir aussi

EvtProgramDma

WdfDmaEnablerSetMaximumScatterGatherElements

WdfDmaTransactionCreate

WdfDmaTransactionDmaCompleted

WdfDmaTransactionDmaCompletedFinal

WdfDmaTransactionDmaCompletedWithLength

WdfDmaTransactionInitialize

WdfDmaTransactionInitializeUsingRequest

WdfDmaTransactionSetImmediateExecution