Relatando partes e estatísticas de codificação Miracast no Windows 8.1
Observação
A partir do Windows 10 (WDDM 2.0), o sistema operacional é fornecido com uma pilha Miracast interna que pode funcionar em qualquer GPU. Para obter informações sobre a pilha do Microsoft Miracast e os requisitos de drivers e hardware para dar suporte a exibições do Miracast a partir do Windows 10, consulte a seguinte documentação:
Criando as melhores soluções de projeção sem fio da categoria com o Windows 10
A documentação WHLK relevante em Device.Graphics.WDDM13.DisplayRender.WirelessDisplay
Os desenvolvedores de driver não devem mais implementar uma pilha Miracast personalizada. A Microsoft pode remover o suporte para pilhas Miracast personalizadas em uma versão futura do Windows.
No Windows 8.1, o hardware de exibição pode processar cada quadro de vídeo enviado por um link de exibição sem fio Miracast dividindo o quadro em várias partes ou codificando partes. Cada parte tem uma ID de parte exclusiva gerada a partir do número do quadro e do número da parte (ou fatia) do quadro. Cada parte relacionada à mesma atualização de quadro da área de trabalho deve receber o mesmo número de quadro.
Processamento de blocos de relatórios
Um driver pode codificar um quadro a ser enviado por um link sem fio Miracast em várias etapas de processamento, por exemplo, separando a conversão de cores da codificação, ou em uma única etapa. Cada etapa de processamento deve receber um número de peça de quadro exclusivo dentro do quadro.
O driver de modo de usuário Miracast ou o driver de miniporto de exibição deve notificar o sistema operacional sempre que:
- O hardware concluiu uma etapa de processamento de um quadro.
- Imediatamente antes de cada parte do quadro ser enviada para a rede.
A hora de uma etapa de processamento relatada específica é considerada a hora em que o evento foi relatado ao sistema operacional, portanto, é importante relatar os estágios o mais rápido possível.
O sistema operacional não executa nenhuma ação além de registrar esses eventos usando o recurso de rastreamento no nível do kernel ETW (Rastreamento de Eventos para Windows). No entanto, essas informações são importantes para medir e investigar problemas de desempenho.
Um motorista pode fornecer a notificação usando uma das seguintes maneiras possíveis:
- O driver de modo de usuário Miracast chama a função de retorno de chamada ReportStatistic para relatar detalhes com o tipo de MIRACAST_STATISTIC_TYPE_CHUNK_PROCESSING_COMPLETE ou com MIRACAST_STATISTIC_TYPE_CHUNK_SENT para indicar que a parte está prestes a ser enviada para a pilha de rede para transmissão.
- O driver de miniporto de exibição relata detalhes do processamento de partes com o tipo de interrupção DXGK_INTERRUPT_MICACAST_CHUNK_PROCESSING_COMPLETE , embora esse relatório só possa ser feito no momento da interrupção. Além de registrar as informações da parte, um pacote de partes é criado e enfileirado para que o driver do modo de usuário Miracast possa recuperá-lo chamando a função de retorno de chamada GetNextChunkData .
- O driver de miniporto de exibição chama a função de retorno de chamada DxgkCbReportChunkInfo em qualquer nível de IRQL . Essa função registra apenas as informações da parte e não enfileira nenhum pacote de parte.
O mesmo número de quadro e números de peça devem ser usados se a imagem da área de trabalho não for atualizada, mas o driver precisar codificar a imagem da área de trabalho novamente para melhorar a qualidade. As ferramentas de desempenho acionam o segundo evento de codificação concluída para o mesmo quadro e número de peça, indicando que uma segunda codificação do mesmo quadro foi executada.
A última fatia de cada quadro deve ter um número de peça de quadro zero, que indica a última fatia do quadro para as ferramentas de desempenho.
Para garantir a sincronização correta da superfície primária, se o pipeline de pixel executar a codificação, qualquer operação de inversão solicitada em um intervalo VSync não deverá ser relatada antes que a codificação termine de acessar a superfície primária. Esse comportamento impede que o apresentador renderize para a superfície primária enquanto o mecanismo de codificação está lendo a partir dela.
O driver de modo de usuário Miracast deve informar o sistema operacional em cada um dos vários estágios de processamento do quadro:
Quadro inicial, tipo de parte MIRACAST_CHUNK_TYPE_FRAME_START
Representa o ponto em que o sistema operacional solicita que o driver exiba o novo quadro da área de trabalho. Embora tecnicamente o driver de modo de usuário Miracast possa relatar esse estágio, o início do processamento de um novo quadro sempre envolve o driver de miniporto de exibição e, portanto, deve ser relatado por esse driver.
Conversão de cores concluída, tipo de parte MIRACAST_CHUNK_TYPE_COLOR_CONVERT_COMPLETE
Algumas soluções têm estágios separados de conversão e codificação de cores. Nessas soluções, o evento de processamento completo de conversão de cores deve ser relatado o mais rápido possível e o driver deve usar o DXGK_MIRACAST_CHUNK_INFO.ProcessingTime para relatar o tempo necessário para o hardware executar a operação. Se o quadro inteiro for convertido em cores de uma só vez, em vez de em fatias, o número da peça deverá ser zero.
Codificar concluído, tipo de bloco MIRACAST_CHUNK_TYPE_ENCODE_COMPLETE
Indica que a codificação H.264 foi concluída. Os membros ProcessingTime e EncodeRate da estrutura DXGK_MIRACAST_CHUNK_INFO devem ser concluídos.
Frame send, chamando ReportStatistic usando MIRACAST_STATISTIC_TYPE_CHUNK_SENT
Indica que o driver de modo de usuário Miracast está prestes a enviar o pacote de dados para esse número de quadro/peça para a API de rede para transmissão. Se os dados desse quadro/parte forem enviados usando várias chamadas para a API de rede, eles só deverão ser registrados pouco antes do envio do primeiro pacote. A chamada deve ser feita antes de chamar a API de rede. Esse tempo é importante porque, se a API de rede bloquear chamadas, não queremos que o tempo bloqueado conte para o processamento do quadro na pilha de gráficos.
Quadro descartado, tipo de pedaço MIRACAST_CHUNK_TYPE_FRAME_DROPPED
Se a qualquer momento o motorista decidir que não concluirá o processamento do quadro/peça e o enviará para o coletor, ele deverá relatar o quadro descartado. Nesse contexto, um quadro só é considerado descartado se o driver realmente começou a processá-lo registrando MIRACAST_CHUNK_TYPE_FRAME_START. Se um driver calcular que vai ignorar esse quadro sem nenhum processamento, ele poderá registrar MIRACAST_CHUNK_TYPE_FRAME_DROPPED sem registrar MIRACAST_CHUNK_TYPE_FRAME_START.
Tipo de parte definido pelo driver MIRACAST_CHUNK_TYPE_ENCODE_DRIVER_DEFINED_1 ou _2
Esses tipos de partes estão disponíveis para ajudá-lo a entender o desempenho de um cenário. Alguns exemplos incluem:
- O driver usa esses tipos para indicar que um I-Frame foi criado para esse quadro.
- O driver registra outro pacote depois que a última fatia do quadro foi enviada para APIs de rede que continham o tamanho total do quadro codificado.
Exemplos de conversão de cores de quadros
Os exemplos a seguir mostram como a cor do quadro é convertida e como o driver de miniporto de exibição relata a conclusão da conversão de cores.
As referências de tabela aos membros da estrutura MIRACAST_CHUNK_INFO são:
ChunkType é um valor MIRACAST_CHUNK_TYPE_XXX .
FrameNumber e PartNumber são membros da união ChunkId.
ProcessingTime é o tempo em microssegundos.
EncodeRate está em kilobits por segundo.
MIRACAST_STATISTIC_TYPE_CHUNK_SENT é usado em estágios de processamento que envolvem chamadas para ReportStatistic.
Relatando um único quadro sem usar fatias
Estágio de processamento | Tipo de Pedaço | FrameNumber | PartNumber | Tempo de processamento | Taxa de codificação |
---|---|---|---|---|---|
Iniciar o quadro de processamento | FRAME_START | 101 | 0 | 0 | 0 |
A conversão de cores está concluída | COLOR_CONVERT_COMPLETE | 101 | 0 | 950 | 0 |
A codificação está concluída | ENCODE_COMPLETE | 101 | 0 | 1042 | 15000 |
Pouco antes da chamada para enviar dados para a chamada ReportStatistic da rede | N/D | 101 (valor de ChunkSent.ChunkId.FrameNumber) | 0 (valor de ChunkSent.ChunkId.PartNumber) | N/D | N/D |
Relatando um único quadro, processado usando fatias
Estágio de processamento | Tipo de Pedaço | FrameNumber | PartNumber | Tempo de processamento | Taxa de codificação |
---|---|---|---|---|---|
Iniciar o quadro de processamento | FRAME_START | 101 | 0 | 0 | 0 |
A conversão de cores está concluída | COLOR_CONVERT_COMPLETE | 101 | 0 | 950 | 0 |
A codificação da fatia 1 está concluída | ENCODE_COMPLETE | 101 | 1 | 1042 | 15000 |
A codificação da fatia 2 está concluída | ENCODE_COMPLETE | 101 | 0 | 400 | 15000 |
Pouco antes da chamada para enviar dados da fatia 1 para a chamada ReportStatistic da rede | N/D | 101 (valor de ChunkSent.ChunkId.FrameNumber para a fatia 1) | 1 (valor de ChunkSent.ChunkId.PartNumber para a fatia 1) | N/D | N/D |
Pouco antes da chamada para enviar dados da fatia 2 para a chamada ReportStatistic da rede | N/D | 101 (valor de ChunkSent.ChunkId.FrameNumber para a fatia 2) | 0 (valor de ChunkSent.ChunkId.FrameNumber para a fatia 2) | N/D | N/D |
Relatando um quadro original, processado e recodificado sem usar fatias
Estágio de processamento | Tipo de Pedaço | FrameNumber | PartNumber | Tempo de processamento | Taxa de codificação |
---|---|---|---|---|---|
Iniciar o quadro de processamento | FRAME_START | 101 | 0 | 0 | 0 |
A conversão de cores está concluída | COLOR_CONVERT_COMPLETE | 101 | 0 | 950 | 0 |
A codificação está concluída | ENCODE_COMPLETE | 101 | 0 | 1042 | 15000 |
Pouco antes da chamada para enviar dados do quadro original para a chamada ReportStatistic de rede | N/D | 101 (valor de ChunkSent.ChunkId.FrameNumber) | 0 (valor de ChunkSent.ChunkId.PartNumber) | N/D | N/D |
A recodificação está concluída | ENCODE_COMPLETE | 101 | 0 | 500 | 15000 |
Pouco antes da chamada para enviar dados para quadro recodificado para a rede ReportStatistic | N/D | 101 (valor de ChunkSent.ChunkId.FrameNumber) | 0 (valor de ChunkSent.ChunkId.PartNumber) | N/D | N/D |
Relatando eventos de protocolo
Quando o driver do modo de usuário Miracast relata eventos de protocolo chamando a função ReportStatistic com MIRACAST_STATISTIC_DATA. StatisticType definido como MIRACAST_STATISTIC_TYPE_EVENT, o sistema operacional registra o evento, mas não executa nenhuma outra ação. Esses eventos são, no entanto, valiosos para diagnósticos e investigação de desempenho.
A enumeração MIRACAST_PROTOCOL_EVENT inclui possíveis tipos de eventos de protocolo que podem ser relatados.
Relatando erros de protocolo
Enquanto uma sessão conectada do Miracast está em andamento, se um driver de modo de usuário do Miracast descobrir um erro, ele deverá chamar a função de retorno de chamada ReportSessionStatus com informações de status de erro de MIRACAST_STATUS apropriadas no parâmetro MiracastStatus . A sessão de operação sempre destrói a sessão quando um erro é relatado.
Embora o sistema operacional apenas registre o parâmetro ReportSessionStatus Status para diagnóstico e não execute nenhuma ação com base em seu valor, o driver deve usar esse parâmetro para diferenciar entre as diferentes causas do erro.