Compartilhar via


Função FsRtlCancellableWaitForMultipleObjects (ntifs.h)

O FsRtlCancellableWaitForMultipleObjects rotina executa uma operação de espera cancelável (uma espera que pode ser encerrada) em um ou mais objetos dispatcher.

Sintaxe

NTSTATUS FsRtlCancellableWaitForMultipleObjects(
  [in]           ULONG          Count,
  [in]           PVOID []       ObjectArray,
  [in]           WAIT_TYPE      WaitType,
  [in, optional] PLARGE_INTEGER Timeout,
  [in, optional] PKWAIT_BLOCK   WaitBlockArray,
  [in, optional] PIRP           Irp
);

Parâmetros

[in] Count

O número de objetos a serem aguardados.

[in] ObjectArray

Um ponteiro para uma matriz de ponteiros para objetos dispatcher (eventos, mutexes, semáforos, threads e temporizadores) para os quais o chamador fornece o armazenamento.

[in] WaitType

WaitAll, que indica que todos os objetos especificados devem atingir um estado sinalizado antes que a espera seja atendida; ou WaitAny, que indica que qualquer um dos objetos deve atingir um estado sinalizado antes que a espera seja atendida.

[in, optional] Timeout

Um ponteiro para um valor de tempo limite opcional. Esse parâmetro especifica o tempo absoluto ou relativo, em 100 unidades nanossegundos, nas quais a espera deve ser concluída.

Se Tempo Limite apontar para um valor zero (ou seja, *Tempo limite == 0), a rotina retornará sem esperar. Se o chamador fornecer um ponteiro NULL (ou seja, Tempo limite == NULL), a rotina aguardará indefinidamente até que qualquer um ou todos os objetos do dispatcher sejam definidos como o estado sinalizado.

Um valor positivo especifica um tempo absoluto em relação a 1º de janeiro de 1601. Um valor negativo especifica um intervalo relativo à hora atual. Os tempos de expiração absolutos acompanham as alterações na hora do sistema; os tempos de expiração relativos não são afetados pelas alterações de tempo do sistema.

Se tempo limite for especificado, a espera será atendida automaticamente se nenhuma das condições de espera especificadas for atendida quando o intervalo especificado expirar.

Um valor de tempo limite zero (ou seja, *Tempo limite == 0) permite testar um conjunto de condições de espera e executar condicionalmente quaisquer ações adicionais se a espera puder ser atendida imediatamente, como na aquisição de um mutex.

[in, optional] WaitBlockArray

Se Contagem<= THREAD_WAIT_OBJECTS, WaitBlockArray poderá ser NULL. Caso contrário, esse parâmetro deve apontar para um buffer de memória de sizeof(KWAIT_BLOCK * Count) bytes. A rotina usa esse buffer para manter registros enquanto executa a operação de espera.

[in, optional] Irp

Um ponteiro para o IRP original que corresponde à operação de E/S emitida pelo usuário e que pode ser cancelada pelo usuário. O chamador deve garantir que o IRP permanecerá válido durante essa rotina e que o IRP não deve ter um conjunto de rotina de cancelamento (por exemplo, IoSetCancelRoutine não deve ter sido chamado no IRP). Observe que o IRP deve ser mantido pelo chamador, ele não pode ser passado para um driver de nível inferior.

Valor de retorno

FsRtlCancellableWaitForMultipleObjects pode retornar um dos seguintes valores:

Código de retorno Descrição
STATUS_SUCCESS O chamador especificado WaitAll para o parâmetro WaitType e todos os objetos dispatcher na matriz ObjectArray foram definidos como o estado sinalizado.
STATUS_TIMEOUT Ocorreu um tempo limite antes que o conjunto especificado de condições de espera fosse atendido. Esse valor pode ser retornado quando o conjunto especificado de condições de espera não puder ser atendido imediatamente e Tempo Limite estiver definido como zero.
STATUS_WAIT_0 through STATUS_WAIT_63 O chamador especificado WaitAny para WaitType e um dos objetos dispatcher na matriz ObjectArray foi definido como o estado sinalizado. Os seis bits inferiores do valor retornado codificam o índice baseado em zero do objeto que satisfize a espera.
STATUS_ABANDONED_WAIT_0 through STATUS_ABANDONED_WAIT_63 O chamador tentou esperar por um mutex que foi abandonado. Os seis bits inferiores do valor retornado codificam o índice baseado em zero do mutex na matriz ObjectArray.
STATUS_CANCELLED A espera foi interrompida por uma solicitação de cancelamento pendente no IRP especificado. Observe que esse valor será retornado somente se um IRP válido for passado para FsRtlCancellableWaitForMultipleObjects e o IRP tiver sido cancelado por CancelSynchronousIo.
STATUS_THREAD_IS_TERMINATING A espera foi interrompida porque o thread foi encerrado por um aplicativo ou pelo usuário.

O valor retornado indica apenas o status da espera. Se aplicável, o status real da solicitação de E/S deve ser obtido diretamente de outro IRP gerado no processo de manipulação do IRP do modo de usuário original.

Observe que a macro NT_SUCCESS retorna FALSE ("failure") para os valores de status STATUS_CANCELLED e STATUS_THREAD_IS_TERMINATING e TRUE ("success") para todos os outros valores de status.

Observações

O FsRtlCancellableWaitForMultipleObjects rotina executa uma operação de espera cancelável em objetos dispatcher. Se o thread for encerrado pelo usuário ou pelo aplicativo ou se CancelSynchronousIo postará uma solicitação de cancelamento em um IRP threaded (IRP síncrono) associado ao thread, a espera será cancelada.

A rotina de FsRtlCancellableWaitForMultipleObjects foi projetada para dar suporte às diretrizes de conclusão/cancelamento de E/S começando com o Windows Vista. A meta dessas diretrizes é permitir que os usuários (ou aplicativos) encerrem rapidamente os aplicativos. Isso, por sua vez, requer que os aplicativos tenham a capacidade de encerrar rapidamente threads que estão executando E/S, bem como quaisquer operações de E/S atuais. Essa rotina fornece uma maneira de os threads do usuário bloquearem (ou seja, aguardar) no kernel para conclusão de E/S, objetos dispatcher ou variáveis de sincronização de uma maneira que permita que a espera seja prontamente cancelada. Essa rotina também permite que a espera do thread seja encerrada se o thread for encerrado por um usuário ou um aplicativo.

Por exemplo, um redirecionador pode precisar criar um ou mais IRPs secundários para processar um IRP no modo de usuário e aguardar síncronamente até que os IRPs secundários sejam concluídos. Uma maneira de fazer isso é configurar um evento que será sinalizado pela rotina de conclusão do IRP secundário e aguardar que o evento seja sinalizado. Em seguida, para executar uma operação de espera cancelável, FsRtlCancellableWaitForMultipleObjects é chamado de passar o evento associado ao IRP secundário, bem como o IRP do modo de usuário original. A espera do thread para que o evento seja sinalizado será cancelada se ocorrer um evento de encerramento pendente ou se o IRP do modo de usuário original for cancelado.

Observe que encerrar a espera não cancela automaticamente nenhuma operação de E/S emitida pelo chamador , que deve ser tratada separadamente pelo chamador.

Cada objeto thread tem uma matriz interna de blocos de espera que podem ser usados para aguardar vários objetos simultaneamente. Sempre que possível, a matriz interna de blocos de espera deve ser usada em uma operação de espera múltipla porque nenhum armazenamento de bloco de espera adicional precisa ser alocado e desalocado posteriormente. No entanto, se o número de objetos que devem ser aguardados simultaneamente for maior do que o número de blocos de espera internos, use o parâmetro WaitBlockArray para especificar um conjunto alternativo de blocos de espera a serem usados na operação de espera. Os drivers só precisam alocar um buffer de memória suficientemente grande para WaitBlockArray. O buffer não precisa ser inicializado e os drivers podem tratá-lo como uma estrutura opaca. O buffer pode ser liberado quando a rotina é retornada.

Se Contagem for maior que MAXIMUM_WAIT_OBJECTS ou se WaitBlockArray for NULL e Contagem for maior que THREAD_WAIT_OBJECTS, o sistema emitirá 0xC de Verificação de Bugs: MAXIMUM_WAIT_OBJECTS_EXCEEDED.

Uma consideração especial se aplica quando o parâmetro ObjectArray passado para FsRtlCancellableWaitForMultipleObjects é um mutex. Se o objeto dispatcher que é aguardado for um mutex, a entrega do APC será a mesma que para todos os outros objetos dispatcher durante a espera. No entanto, uma vez FsRtlCancellableWaitForMultipleObjects retorna com STATUS_SUCCESS e o thread realmente contém o mutex, somente APCs especiais no modo kernel são entregues. A entrega de todas as outras APCs, no modo kernel e no modo de usuário, está desabilitada. Essa restrição na entrega de APCs persiste até que o mutex seja liberado.

Um mutex pode ser adquirido recursivamente apenas por tempo MINLONG. Se esse limite for excedido, a rotina gerará uma exceção STATUS_MUTANT_LIMIT_EXCEEDED.

FsRtlCancellableWaitForMultipleObjects deverá ser chamado no IRQL PASSIVE_LEVEL se o parâmetro irp opcional apontar para um IRP válido. Se o parâmetro Irp não for usado, a rotina poderá ser chamada em IRQL menor ou igual a APC_LEVEL. As APCs de kernel normais podem ser desabilitadas pelo chamador, se necessário, chamando a KeEnterCriticalRegion ou rotinas de FsRtlEnterFileSystem. No entanto, APCs especiais de kernel não devem ser desabilitadas.

FsRtlCancellableWaitForMultipleObjects afirmará em builds de depuração se o IRQL for maior ou igual a APC_LEVEL e o parâmetro irp apontar para um IRP válido.

Requisitos

Requisito Valor
de cliente com suporte mínimo Windows Vista
da Plataforma de Destino Universal
cabeçalho ntifs.h (inclua Ntifs.h)
biblioteca NtosKrnl.lib
de DLL NtosKrnl.exe
IRQL Consulte a seção Comentários.
regras de conformidade de DDI HwStorPortProhibitedDIs(storport), PowerIrpDDis(wdm), SpNoWait(storport)

Consulte também

ExInitializeFastMutex

FsRtlCancellableWaitForSingleObject

KeInitializeEvent

KeInitializeMutex

KeInitializeSemaphore

KeInitializeTimer

KeWaitForMultipleObjects

KeWaitForSingleObject

KeWaitForMutexObject