Funzione WdfDeviceInitAssignWdmIrpPreprocessCallback (wdfdevice.h)

[Si applica solo a KMDF]

Il metodo WdfDeviceInitAssignWdmIrpPreprocessCallback registra una funzione di callback per gestire un codice di funzione principale di IRP e, facoltativamente, uno o più codici di funzione secondari associati al codice della funzione principale.

Sintassi

NTSTATUS WdfDeviceInitAssignWdmIrpPreprocessCallback(
  [in]           PWDFDEVICE_INIT                  DeviceInit,
  [in]           PFN_WDFDEVICE_WDM_IRP_PREPROCESS EvtDeviceWdmIrpPreprocess,
  [in]           UCHAR                            MajorFunction,
  [in, optional] PUCHAR                           MinorFunctions,
  [in]           ULONG                            NumMinorFunctions
);

Parametri

[in] DeviceInit

Puntatore a una struttura WDFDEVICE_INIT .

[in] EvtDeviceWdmIrpPreprocess

Puntatore alla funzione di callback EvtDeviceWdmIrpPreprocess del driver.

[in] MajorFunction

Uno dei codici di funzione principali di IRP definiti in wdm.h.

[in, optional] MinorFunctions

Puntatore a una matrice di uno o più codici di funzione secondaria IRP associati al codice della funzione principale specificato. Questo parametro è facoltativo e può essere NULL. Per ulteriori informazioni, vedere la sezione Osservazioni successiva.

[in] NumMinorFunctions

Numero di codici di funzione secondaria contenuti nella matrice MinorFunctions .

Valore restituito

Se l'operazione ha esito positivo, il metodo restituisce STATUS_SUCCESS. I valori restituiti aggiuntivi includono:

Codice restituito Descrizione
STATUS_INVALID_PARAMETER
Il valore MajorFunction non è valido.
STATUS_INSUFFICIENT_RESOURCES
Memoria insufficiente.
STATUS_INVALID_DEVICE_REQUEST
Il driver ha registrato in precedenza una matrice MinorFunctions per questa funzione principale e sta tentando di specificare nuovamente funzioni secondarie per il codice MajorFunction specificato.
 

Il metodo potrebbe restituire altri valori NTSTATUS.

Commenti

I driver possono chiamare il metodo WdfDeviceInitAssignWdmIrpPreprocessCallback per uno dei due motivi seguenti:

  • Per gestire un codice di funzione principale o secondario di IRP non supportato dal framework.

    Ad esempio, il framework non supporta IRP_MJ_FLUSH_BUFFERS. Se il driver deve supportare questo IRP, deve registrare una funzione di callback EvtDeviceWdmIrpPreprocess che gestisce l'IRP. Il driver deve seguire le regole WDM per l'elaborazione dei provider di integrazione.

  • Per pre-elaborare un IRP prima che il framework lo gestisca.

    In rari casi, potrebbe essere necessario che un driver elabori un IRP prima che il framework lo elabori. In questi casi, la funzione di callback EvtDeviceWdmIrpPreprocess del driver può elaborare l'IRP e quindi chiamare WdfDeviceWdmDispatchPreprocessedIrp per restituire l'IRP al framework. A seconda del codice della funzione di IRP, il framework potrebbe elaborare l'IRP stesso o recapitare nuovamente l'IRP al driver in un oggetto richiesta del framework.

Il framework chiama la funzione di callback EvtDeviceWdmIrpPreprocess ogni volta che riceve un pacchetto di richiesta I/O (IRP) che contiene un codice di funzione principale IRP che corrisponde al parametro MajorFunction e a un codice di funzione secondario che corrisponde a uno dei codici di funzione secondaria presenti nella matrice MinorFunctions .

Se il puntatore alla matrice MinorFunctions è NULL, il framework chiama la funzione di callback per tutti i codici di funzione secondaria associati al codice della funzione principale specificato. Se il puntatore alla matrice MinorFunctions non è NULL, il framework crea una copia della matrice in modo che il driver non deve mantenere definitivamente la matrice.

Se il driver ha ricevuto il puntatore DeviceInit da WdfPdoInitAllocate o da una funzione di callback dell'evento EvtChildListCreateDevice , la funzione di callback EvtDeviceWdmIrpPreprocess del driver non può impostare una routine di completamento per i runtime di integrazione che contengono un codice di funzione principale di IRP_MJ_PNP. In caso contrario, Driver Verifier segnala un errore.

Se il driver chiama WdfDeviceInitAssignWdmIrpPreprocessCallback una o più volte, il framework incrementa il membro StackSize della struttura wdm DEVICE_OBJECT del driver una volta. Di conseguenza, il gestore di I/O aggiunge un percorso dello stack di I/O aggiuntivo a tutti i provider di integrazione in modo che la funzione di callback EvtDeviceWdmIrpPreprocess possa impostare una routine IoCompletion . Si noti che questo percorso aggiuntivo dello stack di I/O viene aggiunto a tutti i provider di integrazione, non solo a quelli che contengono un codice di funzione principale di IRP specificato in una chiamata a WdfDeviceInitAssignWdmIrpPreprocessCallback. Pertanto, per evitare di aumentare inutilmente l'uso del driver del pool di memoria non di paging, è consigliabile evitare di usare WdfDeviceInitAssignWdmIrpPreprocessCallback a meno che non vi sia alcuna alternativa.

Se il driver chiama WdfDeviceInitAssignWdmIrpPreprocessCallback più volte per lo stesso codice principale, il framework mantiene solo la funzione di callback EvtDeviceWdmIrpPreprocess impostata più di recente per questo codice principale. Il driver non può registrare più callback di pre-elaborazione per un singolo codice principale.

Per altre informazioni sul metodo WdfDeviceInitAssignWdmIrpPreprocessCallback, vedere Handling WDM IRPs Outside of the Framework.For more information about the WdfDeviceInitAssignWdmIrpPreprocessCallback method, see Handling WDM IRPs Outside of the Framework.

Esempio

L'esempio di codice seguente definisce una funzione di callback dell'evento EvtDeviceWdmIrpPreprocess e quindi registra la funzione di callback per gestire IRP_MJ_QUERY_INFORMATION IRP.

NTSTATUS
SerialQueryInformationFile(
    IN WDFDEVICE Device,
    IN PIRP Irp
    )

/*++

Routine Description:

    This routine is used to query the end of file information on
    the opened serial port.  Any other file information request
    is returned with an invalid parameter.

    This routine always returns an end of file of 0.

Arguments:

    DeviceObject - Pointer to the device object for this device

    Irp - Pointer to the IRP for the current request

Return Value:

    The function value is the final status of the call

--*/

{
    NTSTATUS Status;
    PIO_STACK_LOCATION IrpSp;

    SerialDbgPrintEx(TRACE_LEVEL_INFORMATION, DBG_PNP, ">SerialQueryInformationFile(%p, %p)\n", Device, Irp);

    PAGED_CODE();


    IrpSp = IoGetCurrentIrpStackLocation(Irp);
    Irp->IoStatus.Information = 0L;
    Status = STATUS_SUCCESS;

    if (IrpSp->Parameters.QueryFile.FileInformationClass ==
        FileStandardInformation) {

        if (IrpSp->Parameters.DeviceIoControl.OutputBufferLength <
                sizeof(FILE_STANDARD_INFORMATION))
        {
                Status = STATUS_BUFFER_TOO_SMALL;
        }
        else
        {
            PFILE_STANDARD_INFORMATION Buf = Irp->AssociatedIrp.SystemBuffer;

            Buf->AllocationSize.QuadPart = 0;
            Buf->EndOfFile = Buf->AllocationSize;
            Buf->NumberOfLinks = 0;
            Buf->DeletePending = FALSE;
            Buf->Directory = FALSE;
            Irp->IoStatus.Information = sizeof(FILE_STANDARD_INFORMATION);
        }

    } else if (IrpSp->Parameters.QueryFile.FileInformationClass ==
               FilePositionInformation) {

        if (IrpSp->Parameters.DeviceIoControl.OutputBufferLength <
                sizeof(FILE_POSITION_INFORMATION))
        {
                Status = STATUS_BUFFER_TOO_SMALL;
        }
        else
        {

            ((PFILE_POSITION_INFORMATION)Irp->AssociatedIrp.SystemBuffer)->
                CurrentByteOffset.QuadPart = 0;
            Irp->IoStatus.Information = sizeof(FILE_POSITION_INFORMATION);
        }

    } else {
        Status = STATUS_INVALID_PARAMETER;
    }

    Irp->IoStatus.Status = Status;

    IoCompleteRequest(Irp, IO_NO_INCREMENT);

    return Status;

}

NTSTATUS
SerialEvtDeviceAdd(
    IN WDFDRIVER Driver,
    IN PWDFDEVICE_INIT DeviceInit
    )
{
...
    status = WdfDeviceInitAssignWdmIrpPreprocessCallback(
                                                 DeviceInit,
                                                 SerialQueryInformationFile,
                                                 IRP_MJ_QUERY_INFORMATION,
                                                 NULL, // Pointer to the minor function table
                                                 0 // Number of entries in the table
                                                 ); 
    if (!NT_SUCCESS(status)) {
        return status;
    }
...
}

Requisiti

Requisito Valore
Piattaforma di destinazione Universale
Versione KMDF minima 1.0
Intestazione wdfdevice.h (include Wdf.h)
Libreria Wdf01000.sys (vedere Controllo delle versioni della libreria framework).
IRQL <= DISPATCH_LEVEL
Regole di conformità DDI ChildDeviceInitAPI(kmdf), ControlDeviceInitAPI(kmdf), DeviceInitAPI(kmdf), DriverCreate(kmdf), InitFreeDeviceCallback(kmdf), InitFreeDeviceCreate(kmdf), InitFreeNull(kmdf), KmdfIrql(kmdf), KmdfIrql2(kmdf), KmdfIrqlExplicit(kmdf), PdoDeviceInitAPI(kmdf), PdoInitFreeDeviceCallback(kmdf), PdoInitFreeDeviceCreate(kmdf)

Vedi anche

WdfDeviceWdmDispatchPreprocessedIrp