PMAP_TRANSFER_EX função de retorno de chamada (wdm.h)

A rotina MapTransferEx configura registros de mapa para mapear os endereços físicos em uma lista de dispersão/coleta para os endereços lógicos necessários para fazer uma transferência de DMA.

Sintaxe

PMAP_TRANSFER_EX PmapTransferEx;

NTSTATUS PmapTransferEx(
  [in]            PDMA_ADAPTER DmaAdapter,
  [in]            PMDL Mdl,
  [in]            PVOID MapRegisterBase,
  [in]            ULONGLONG Offset,
  [in]            ULONG DeviceOffset,
  [in, out]       PULONG Length,
  [in]            BOOLEAN WriteToDevice,
  [out, optional] PSCATTER_GATHER_LIST ScatterGatherBuffer,
  [in]            ULONG ScatterGatherBufferLength,
  [in, optional]  PDMA_COMPLETION_ROUTINE DmaCompletionRoutine,
  [in, optional]  PVOID CompletionContext
)
{...}

Parâmetros

[in] DmaAdapter

Um ponteiro para uma estrutura DMA_ADAPTER . Essa estrutura é o objeto do adaptador que representa o dispositivo DMA master do barramento ou o canal DMA do sistema. O chamador obteve esse ponteiro de uma chamada anterior para a rotina IoGetDmaAdapter .

[in] Mdl

Um ponteiro para uma cadeia de MDL que descreve o layout de página física de uma coleção de buffers bloqueados na memória virtual. A lista de dispersão/coleta para a transferência de DMA usará a região dessa memória especificada pelos parâmetros Offset e Length . Para obter mais informações sobre cadeias de MDL, consulte Usando MDLs.

[in] MapRegisterBase

Um identificador para os registros de mapa alocados para o objeto do adaptador. O chamador obteve esse identificador anteriormente da rotina AllocateAdapterChannelEx .

[in] Offset

Um deslocamento de bytes do início da memória descrito pela cadeia de MDL. Esse deslocamento especifica o início do buffer de dados de E/S usado para a transferência de DMA. Se uma lista de dispersão/coleta for fornecida ao chamador, esse deslocamento determinará o endereço inicial do primeiro fragmento de buffer na lista. Se os MDLs na cadeia de MDL descreverem um total de N bytes de memória, os valores válidos de Offset estarão no intervalo de 0 a N-1. Para obter mais informações, consulte Comentários.

[in] DeviceOffset

O deslocamento de bytes do registro de dados do dispositivo de destino ou FIFO do endereço base do dispositivo. Esse parâmetro se aplica a dispositivos que têm vários FIFOs que podem ser acessados por um controlador de DMA do sistema. Esse parâmetro é usado apenas para transferências de DMA do sistema. Para transferências de master de barramento, defina esse parâmetro como zero.

[in, out] Length

Um ponteiro para uma variável que contém o comprimento, em bytes, do buffer de dados de E/S usado para a transferência de DMA. Na entrada, essa variável contém o comprimento solicitado pelo driver de chamada. Antes de retornar, a rotina grava o comprimento real do buffer mapeado nessa variável. O valor de *Length no retorno de MapTransferEx indica quantos bytes foram mapeados. Se o número de registros de mapa e o tamanho do buffer de dispersão/coleta forem suficientes para mapear todo o comprimento solicitado pelo chamador, os valores de entrada e saída de *Length serão idênticos. Se os MDLs na cadeia de MDL descreverem um total de N bytes de memória, os valores válidos de *Length estarão no intervalo de 0 a N–Offset.

[in] WriteToDevice

A direção da transferência de DMA. Defina esse parâmetro como TRUE para uma operação de gravação, que transfere dados para o dispositivo da memória. Defina esse parâmetro como FALSE para uma operação de leitura, que transfere dados do dispositivo para a memória.

[out, optional] ScatterGatherBuffer

Um ponteiro para um buffer alocado pelo chamador no qual a rotina grava a lista de dispersão/coleta para a transferência de DMA. Essa lista começa com uma estrutura SCATTER_GATHER_LIST , que é imediatamente seguida por uma matriz de SCATTER_GATHER_ELEMENT . Para um driver que usa um dispositivo DMA master barramento, ScatterGatherBuffer é um parâmetro necessário. Para um driver que usa um controlador DMA do sistema, o parâmetro ScatterGatherBuffer é opcional e pode ser NULL. Para obter mais informações, consulte Comentários.

[in] ScatterGatherBufferLength

O tamanho, em bytes, do buffer para o qual o parâmetro ScatterGatherBuffer aponta. O tamanho do buffer alocado deve ser grande o suficiente para conter a lista de dispersão/coleta, além de dados internos que o sistema operacional armazena nesse buffer. Para determinar o tamanho do buffer necessário, chame a rotina GetDmaTransferInfo ou CalculateScatterGatherList . Se ScatterGatherBuffer for NULL, defina ScatterGatherBufferLength como zero.

[in, optional] DmaCompletionRoutine

Um ponteiro para uma rotina DmaCompletionRoutine fornecida pelo chamador a ser chamada quando a transferência de DMA for concluída. Essa rotina é chamada se o dispositivo de destino usa um controlador DMA do sistema que gera uma interrupção de conclusão de DMA. A rotina DmaCompletionRoutine é chamada em DISPATCH_LEVEL após a conclusão da transferência de DMA. Para um adaptador de DMA do sistema, esse parâmetro é opcional e pode ser NULL. Para um adaptador de master de barramento, defina esse parâmetro como NULL.

[in, optional] CompletionContext

O contexto determinado pelo driver para a rotina DmaCompletionRoutine . Esse contexto é fornecido como o parâmetro CompletionContext para a rotina DmaCompletionRoutine . Se o parâmetro DmaCompletionRoutine for NULL, defina CompletionContext como NULL.

Retornar valor

MapTransferEx retornará STATUS_SUCCESS se a chamada for bem-sucedida. Os valores de retorno de erro possíveis incluem os seguintes códigos de status.

Código de retorno Descrição
STATUS_INVALID_PARAMETERS
A rotina falhou devido a valores de parâmetro inválidos passados pelo chamador.
STATUS_BUFFER_TOO_SMALL
O buffer fornecido pelo chamador em ScatterGatherBuffer é muito pequeno para conter a lista de dispersão/coleta.
STATUS_INSUFFICIENT_RESOURCES
A rotina não conseguiu alocar recursos necessários para a transferência de DMA.
STATUS_CANCELLED
Essa transferência foi cancelada.

Comentários

MapTransferEx não é uma rotina do sistema que pode ser chamada diretamente pelo nome. Essa rotina só pode ser chamada por ponteiro do endereço retornado em uma estrutura DMA_OPERATIONS. Os drivers obtêm o endereço dessa rotina chamando IoGetDmaAdapter com o membro Version do parâmetro DeviceDescription definido como DEVICE_DESCRIPTION_VERSION3. Se IoGetDmaAdapter retornar NULL, a rotina não estará disponível em sua plataforma.

Para uma transferência que usa um controlador DMA do sistema, o chamador pode, como opção, fornecer uma rotina de retorno de chamada DmaCompletionRoutine que é chamada quando a transferência é concluída. O sistema operacional agenda esse retorno de chamada em resposta à interrupção de conclusão do DMA do controlador de DMA do sistema.

O número de registros de mapa que podem ser configurados por MapTransferEx não pode exceder o máximo obtido pelo driver de IoGetDmaAdapter.

Os parâmetros Mdl, Offset e Length descrevem o buffer de dados de E/S para a transferência de DMA solicitada. O número de registros de mapa alocados pode não ser suficiente para mapear toda a memória nesse buffer ou o buffer de dispersão/coleta apontado por ScatterGatherBuffer pode não ser grande o suficiente para descrever todo o buffer. MapTransferEx grava um valor de saída em *Length para informar ao driver quanto da memória do buffer para a transferência de DMA solicitada foi mapeada pela rotina. A rotina grava uma lista de dispersão/coleta no buffer apontado por ScatterGatherBuffer. Esta lista descreve os fragmentos de buffer mapeados com êxito pela rotina.

Se uma chamada para MapTransferEx for bem-sucedida, MapTransferEx gravará o *Valor de saída de comprimento antes de retornar. Se o chamador especificar um DmaCompletionRoutine, o valor de saída *Length atualizado será sempre gravado antes da execução de DmaCompletionRoutine . Para obter mais informações, consulte Várias chamadas para MapTransferEx.

O parâmetro Offset especifica o deslocamento inicial na cadeia de MDL que descreve a memória no buffer de dados de E/S. Por exemplo, suponha que a cadeia MDL contenha dois MDLs, MDL₁ e MDL₂ e que MDL₁ descreve N₁ bytes de memória e MDL₂ descreve N₂ bytes. Se Offset = N, em que N₁ < N < N₁ + N₂, o buffer não contém nenhuma memória descrita por MDL₁ e começa em um deslocamento de N - N₁ bytes na memória descrita por MDL₂.

Se a transferência usar um controlador DMA do sistema, o chamador poderá definir ScatterGatherBuffer = NULL; nesse caso, MapTransferEx usa um buffer padrão alocado internamente para manter a lista de dispersão/coleta. O buffer padrão tem a garantia de ser grande o suficiente para conter uma lista de dispersão/coleta de pelo menos um elemento. Se o buffer padrão for usado para uma transferência de dispersão/coleta de muitos elementos, muitas chamadas para MapTransferEx poderão ser necessárias para concluir a transferência. Se o hardware do controlador DMA der suporte a transferências de dispersão/coleta, o uso do buffer padrão poderá prejudicar o desempenho.

Se ScatterGatherBuffer não for NULL e ScatterGatherBufferSize especificar um tamanho muito pequeno para conter uma lista de dispersão/coleta de pelo menos um elemento, MapTransferEx falhará e retornará STATUS_INVALID_PARAMETER.

MapTransferEx é uma versão estendida da rotina MapTransfer . A versão estendida tem estas vantagens:

  • MapTransferEx pode processar todos os fragmentos de buffer em uma cadeia de MDL em uma chamada, mas MapTransfer pode processar apenas um fragmento de buffer fisicamente contíguo por chamada.
  • MapTransferEx pode gerar uma lista de dispersão/coleta inteira em uma chamada, mas MapTransfer pode gerar apenas um elemento de lista de dispersão/coleta por chamada.
  • MapTransferEx pode mapear todos os fragmentos de buffer em uma lista de dispersão/coleta em uma chamada, mas MapTransfer pode mapear apenas um fragmento de buffer fisicamente contíguo por chamada.
  • MapTransferEx requer apenas o deslocamento inicial para toda a lista de dispersão/coleta, mas MapTransfer requer um endereço virtual inicial para cada fragmento de buffer fisicamente contíguo.
  • Uma chamada MapTransferEx pode mapear um buffer que se estende por um ou mais MDLs, mas uma chamada mapTransfer pode mapear apenas um fragmento de buffer fisicamente contíguo na memória descrito por um MDL.
  • Para uma transferência de DMA do sistema, MapTransferEx permite que o chamador forneça uma rotina de retorno de chamada DmaCompletionRoutine para receber notificação após a conclusão da transferência, mas MapTransfer não fornece uma maneira de notificar o chamador quando uma transferência de DMA for concluída.
Cada chamada bem-sucedida para MapTransferEx deve ser seguida por uma chamada correspondente para a rotina FlushAdapterBuffersEx . A chamada FlushAdapterBuffersEx que segue uma chamada MapTransferEx deve ocorrer antes que a próxima chamada MapTransferEx ocorra. A chamada FlushAdapterBuffersEx é necessária mesmo que uma chamada para a rotina CancelMappedTransfer tenha êxito em cancelar a transferência mapeada solicitada pela chamada MapTransferEx anterior.

Para obter mais informações, consulte Usando a rotina MapTransferEx.

Requisitos

Requisito Valor
Cliente mínimo com suporte Disponível a partir do Windows 8.
Plataforma de Destino Área de Trabalho
Cabeçalho wdm.h (include Wdm.h, Ntddk.h, Ntifs.h)
IRQL <= DISPATCH_LEVEL

Confira também

AllocateAdapterChannelEx

CalculateScatterGatherList

CancelMappedTransfer

DMA_ADAPTER

DMA_OPERATIONS

DmaCompletionRoutine

FlushAdapterBuffersEx

GetDmaTransferInfo

IoGetDmaAdapter

SCATTER_GATHER_LIST