Partilhar via


Criação de perfil de aplicativos DirectX

Isso mostra como medir algumas das medições de tempo de desempenho mais importantes para um aplicativo DirectX usando as ferramentas XPerf e GPUView que são fornecidas como parte do Kit de Ferramentas de Desempenho do Windows. Este não é um guia abrangente para entender as ferramentas, mas sua aplicabilidade específica para analisar o desempenho do aplicativo DirectX. Embora a maioria das técnicas discutidas aqui seja relevante para todos os aplicativos DirectX, ela é mais relevante para aplicativos que usam cadeias de permuta e não para aplicativos DirectX criados em XAML que usam animações SIS/VSIS e XAML. Orientamos você através das principais medições de tempo de desempenho, como adquirir e instalar as ferramentas e fazemos rastreamentos de medição de desempenho e, em seguida, analisamo-los para entender os gargalos do aplicativo.

Sobre as Ferramentas

XPerf

XPerf é um conjunto de ferramentas de análise de desempenho criado com base no Rastreamento de Eventos para Windows (ETW) projetado para medir e analisar o desempenho detalhado do sistema e do aplicativo e o uso de recursos. A partir do Windows 8, essa ferramenta de linha de comando tem uma interface gráfica do usuário e é chamada de Gravador de Desempenho do Windows (WPR) e Analisador de Desempenho do Windows (WPA). Mais informações sobre essas ferramentas podem ser encontradas na página da Web do Windows Performance Toolkit (WPT): Windows Performance Toolkit.

Um ETW coleta eventos do kernel solicitados e os salva em um arquivo chamado ETL (log de rastreamento de eventos). Esses eventos do kernel fornecem informações extensas sobre um aplicativo e as características do sistema ao executar o aplicativo. Os dados são coletados habilitando a captura de rastreamento, executando o cenário de aplicativo desejado que precisa de análise, interrompendo a captura que salva os dados em um arquivo ETL. Em seguida, você pode analisar o arquivo na mesma máquina ou em uma máquina diferente usando a ferramenta de linha de comando xperf.exe ou a ferramenta de análise de rastreamento visual xperfview.exe.

GPUView

GPUView é uma ferramenta de desenvolvimento para determinar o desempenho da unidade de processamento gráfico (GPU) e CPU. Ele observa o desempenho no que diz respeito ao processamento de buffers de acesso direto à memória (DMA) e a todos os outros processamentos de vídeo no hardware de vídeo.

Por aplicativos DirectX que dependem muito da GPU, GPUView é uma ferramenta poderosa para entender a relação entre o trabalho feito na CPU versus GPU. Para obter mais informações sobre GPUViewconsulte Usando GPUView.

Semelhante ao XPerf, um rastreamento ETW é primeiro obtido ao iniciar o serviço de rastreamento, executar o cenário que precisa ser analisado para o aplicativo em questão, interromper o serviço e salvar as informações em um arquivo ETL. GPUView apresenta os dados presentes no arquivo ETL em um formato gráfico.

Depois de instalar a ferramenta GPUView, recomendamos ler o tópico "Ecrã Principal doGPUView" no menu "Ajuda doGPUView". Ele contém informações úteis sobre como interpretar o GPUView UI.

Instalando as ferramentas

Tanto XPerf quanto GPUView estão incluídos no WPT (Kit de Ferramentas de Desempenho do Windows).

XPerf é fornecido como parte do Windows Software Development Kit (SDK) para Windows. Baixe o SDK do Windows.

GPUView está disponível no Kit de Avaliação e Implantação do Windows (Windows ADK). Baixe o Windows ADK.

Após a instalação, você deve adicionar os diretórios que contêm XPerf e GPUView à variável "Path" do sistema.

Clique no botão Iniciar e digite "Variáveis do sistema". A janela Propriedades do sistema é aberta. Clique em "Editar as variáveis de ambiente do sistema". Selecione "Variáveis de ambiente" na caixa de diálogo "Propriedades do sistema". A variável "Path" encontra-se em "System variables". Anexe o diretório que contém xperf.exe e GPUView.exe ao caminho. Esses executáveis são encontrados no diretório "Windows Performance Toolkit" dentro do "Windows Kits". O local padrão é: C:\Program Files (x86)\Windows Kits\10\Windows Performance Toolkit.

Medições de Tempo de Desempenho

A maioria dos aplicativos espera ser executada sem problemas e responder à entrada do usuário. No entanto, dependendo do cenário desejado, um aspeto do desempenho pode ser mais importante do que outro. Por exemplo, para um aplicativo leitor de notícias executado em um tablet PC sensível ao toque, o aspeto mais importante é visualizar um único artigo de cada vez e mover / zoom / rolar pelo mesmo artigo ou um artigo diferente. Nesse cenário, a capacidade de renderizar todo o conteúdo de cada quadro não é necessária. No entanto, a capacidade de percorrer o artigo suavemente após um gesto de toque é extremamente importante.

Em outro caso, um jogo ou um aplicativo de renderização de vídeo que usa muitas animações falha se os quadros forem descartados. Neste caso, a capacidade de apresentar conteúdo na tela sem interrupção da entrada do usuário é extremamente importante.

Para entender qual parte do aplicativo é problemática, o primeiro passo é decidir sobre os cenários mais importantes. Uma vez que os principais aspetos do aplicativo são compreendidos e como eles serão exercitados, procurar problemas usando as ferramentas torna-se mais fácil.

Algumas das métricas de tempo de desempenho mais comuns são as seguintes:

Tempo de arranque

Tempo medido desde o lançamento do processo até o primeiro aparecimento no ecrã. Essa medição é mais útil quando o sistema está quente, o que significa que a medição é feita depois que o aplicativo é iniciado algumas vezes.

Tempo de CPU por quadro

O tempo pelo qual a CPU processa ativamente a carga de trabalho da aplicação por quadro. Se o aplicativo estiver funcionando sem problemas, todo o processamento necessário para um quadro acontece dentro de um intervalo v-sync. Com a taxa de atualização do monitor de 60Hz, isso chega a 16ms por quadro. Se o tempo/quadro da CPU for maior que 16ms, otimizações de CPU podem ser necessárias para produzir uma experiência de utilização da aplicação sem problemas.

Tempo de GPU por quadro

O tempo pelo qual a GPU processa ativamente a carga de trabalho da aplicação para um fotograma. Um aplicativo é vinculado à GPU quando o tempo necessário para processar um quadro de dados é superior a 16ms.

Ser capaz de entender se um aplicativo está vinculado à CPU ou GPU reduzirá a parte problemática do código.

Rastreio de medição do tempo de desempenho

Execute estas etapas para fazer um rastreamento:

  1. Abra uma janela de comando como administrador.
  2. Feche o aplicativo se ele já estiver em execução.
  3. Altere os diretórios para o diretório gpuview dentro da pasta Kit de Ferramentas de Desempenho do Windows.
  4. Digite "log.cmd" para iniciar o rastreamento de eventos. Esta opção regista os eventos mais interessantes. Outras opções disponíveis registram diferentes âmbitos dos eventos. Por exemplo, o modo de registo 'v' ou modo detalhado capta todos os eventos que o GPUView regista.
  5. Inicie o exemplo e exercite-o de uma maneira que abranja o caminho de desempenho que você precisa analisar.
  6. Volte para as janelas de comando e digite "log.cmd" novamente para parar de registrar.
  7. Isso gera um arquivo chamado "merged.etl" na pasta gpuview. Você pode salvar esse arquivo em outro local e analisá-lo na mesma máquina ou em uma máquina diferente. Para visualizar os detalhes da captura da pilha, salve o arquivo de símbolo (.pdb) associado ao aplicativo.

Medições

Observação

As medições para a amostra de realização de geometria são feitas em uma máquina Quad Core com uma placa gráfica DirectX11 integrada. As medidas variam dependendo da configuração da máquina.

 

Esta seção demonstra como medir o tempo de inicialização, o tempo por quadro da CPU e da GPU. Você pode capturar um rastreamento de desempenho para a mesma amostra em sua máquina e ver as diferenças nas várias medições.

Para analisar o rastreamento em GPUView, abra o arquivo "merged.elt" usando GPUView.exe.

Tempo de arranque

O tempo de inicialização é medido pelo tempo total gasto desde o início do aplicativo até que o conteúdo apareça pela primeira vez na tela.

A medição do tempo de inicialização é melhor feita seguindo as etapas listadas na seção anterior com estas variações:

  • Se você fizer as medições de inicialização na primeira vez que iniciar o aplicativo, isso é chamado de inicialização fria. Isso pode variar das medidas tomadas depois que você inicia o aplicativo algumas vezes em um pequeno período de tempo. Isso é chamado de inicialização quente. Dependendo de quantos recursos um aplicativo cria no lançamento, pode haver uma grande diferença entre os dois tempos de inicialização. Dependendo dos objetivos do aplicativo, medir um ou outro pode ser desejável.
  • Quando você registrar informações de desempenho, encerre o aplicativo assim que o primeiro quadro aparecer na tela.

Calculando o tempo de inicialização usando GPUView

  1. Em GPUView, role para baixo até o processo relevante, neste caso GeometryRealization.exe.

    Captura de tela que mostra um exemplo de processos em GPUView.

  2. A fila de contexto da CPU representa a carga de trabalho gráfica que está enfileirada para o hardware, mas que não está necessariamente a ser processada por ele. Quando o arquivo de rastreamento é aberto, ele mostra todos os eventos registrados entre o momento em que o rastreamento foi feito. Para calcular o tempo de inicialização, selecione a região de interesse, amplie a parte inicial da primeira Fila de CPU de Contexto (esta é a que mostra a atividade) usando Ctrl + Z. Mais informações sobre GPUView Controls podem ser encontradas na seção GPUView arquivo de Ajuda "Resumo de GPUView Controls". A figura abaixo mostra apenas o processo de GeometryRealization.exe ampliado para a primeira parte da Fila de CPU de Contexto. A cor da Fila de CPU de Contexto é indicada pelo retângulo imediatamente abaixo da fila, e pacotes de dados da mesma cor na fila indicam o trabalho da GPU enfileirado no hardware. O pacote de padrão hatch na fila de contexto mostra o pacote atual, o que significa que o aplicativo deseja que o hardware apresente o conteúdo na tela.

    Captura de tela que mostra exemplos da 'Fila de Contexto C P U'.

  3. O tempo de inicialização é o momento em que o aplicativo é iniciado pela primeira vez (neste caso, o módulo de ponto de entrada de thread da interface do usuário SHCORE.dll) até o momento em que o contexto aparece pela primeira vez (marcado por um pacote hatch). A figura aqui destaca a área de interesse.

    Observação

    A informação efetivamente atual é representada na fila de inversão e, portanto, o tempo requerido é estendido até que o pacote atual seja realmente concluído na fila de inversão.

     

    A barra de status completa não é visível na figura abaixo, que também mostra o tempo decorrido entre as partes destacadas. Este é o momento de inicialização do aplicativo. Neste caso, para a máquina mencionada acima, ficou em torno de 240 ms.

    Captura de tela que mostra as áreas de interesse relacionadas ao tempo de inicialização no 'Contexto C P U Queue'.

Tempo de CPU e GPU por quadro

Há algumas coisas a considerar ao medir o tempo da CPU. Procure as áreas no traço onde você exerceu o cenário a ser analisado. Por exemplo, no exemplo de realização de geometria, um dos cenários que foi analisado é a transição entre renderizar 2048 e 8192 primitivas, todas não concretizadas (como, por exemplo, a geometria não ser tesselada em cada frame). O rastreio mostra claramente a diferença na atividade da CPU e GPU antes e depois da transição no número de primitivos.

Dois cenários estão sendo analisados para calcular o tempo de CPU e GPU por quadro. São os seguintes.

  • Transição da renderização de 2048 primitivos não realizados para 8192 primitivos não realizados.
  • Transição da renderização de 8192 primitivos concretizados para 8192 primitivos não concretizados.

Em ambos os casos, observou-se que o framerate caiu drasticamente. Medir o tempo da CPU e GPU, a relação entre os dois, bem como alguns outros padrões no rastreamento, pode fornecer informações úteis sobre áreas problemáticas no aplicativo.

Calculando o tempo de CPU e GPU ao renderizar 2048 primitivas não finalizadas

  1. Abra o arquivo de rastreamento usando GPUView.exe.

  2. Desloque-se para baixo até ao processo GeometryRealization.exe.

  3. Selecione uma área para calcular o tempo da CPU e aumente o zoom nela usando CTRL + Z.

    Captura de tela que mostra uma área selecionada para calcular o tempo de C P U na 'Fila de CPU de contexto'.

  4. Mostrar informações de V-sync ao alternar com a tecla F8. Continue a ampliar até que seja fácil ver claramente uma quantidade de dados de um vsync. As linhas azuis indicam os momentos de v-sync. Normalmente, eles ocorrem uma vez a cada 16 ms (60 fps), mas se o DWM estiver encontrando um problema de desempenho, ele é executado mais lentamente, então eles ocorrerão uma vez a cada 32 ms (30 fps). Para ter uma noção do tempo, selecione de uma barra azul para a barra seguinte e, em seguida, olhe para o número de ms relatado no canto inferior direito da janela GPUView.

    Captura de tela que mostra um exemplo de tempos de v-sync.

  5. Para medir o tempo da CPU por quadro, meça o tempo gasto por todos os threads envolvidos na renderização. Pode valer a pena restringir o tópico que se espera que seja mais relevante do ponto de vista do desempenho. Por exemplo, no exemplo de realização de geometria, o conteúdo é animado e precisa ser renderizado na tela a cada frame, tornando o thread da UI o mais relevante. Depois de determinar qual thread examinar, meça o comprimento das barras nesse thread. A média de alguns deles produz tempo de CPU por quadro. A figura abaixo mostra o tempo gasto no thread da interface do usuário. Também mostra que este tempo se encaixa bem entre dois síncronos verticais consecutivos, o que significa que está atingindo os 60FPS.

    Captura de tela que mostra o tempo gasto no tópico U I.

    Você também pode verificar olhando para a fila de inversão para o período de tempo correspondente, o que mostra que o DWM é capaz de apresentar todos os quadros.

    Captura de tela que mostra um exemplo da 'Fila de inversão'.

  6. O tempo da GPU pode ser medido da mesma forma que o tempo da CPU. Aumente o zoom na área relevante, como no caso de medir o tempo da CPU. Meça o comprimento das barras na Fila de hardware da GPU com a mesma cor da Fila de Contexto da CPU. Contanto que as barras caibam em v-syncs consecutivas, o aplicativo está funcionando sem problemas a 60FPS.

    Captura de tela que mostra um exemplo da 'Fila de hardware da GPU' exibindo informações de que um aplicativo está sendo executado a 60 F P S.

Calculando o tempo da CPU e GPU quando primitivos 8192 estão sendo renderizados não realizados

  1. Se seguires os mesmos passos novamente, o rastreio mostra que todo o trabalho da CPU para um quadro não cabe entre um v-sync e o seguinte. Isso significa que o aplicativo está vinculado à CPU. O thread da interface do usuário está saturando a CPU.

    Captura de tela que mostra um exemplo do thread da interface do usuário saturando o C P U.

    Olhando para a fila de flip, também fica claro que o DWM não é capaz de apresentar todos os quadros.

    Captura de ecrã que mostra um exemplo do D W M incapaz de apresentar todos os frames.

  2. Para analisar onde o tempo está a ser gasto, abra o traço em XPerf. Para analisar o tempo de inicialização em XPerf, primeiro encontre o intervalo de tempo em GPUView. Passe o mouse sobre a esquerda do intervalo e a direita e tome nota do tempo absoluto mostrado na parte inferior da janela GPUView. Em seguida, abra o mesmo arquivo .etl em XPerf e, role para baixo até o gráfico "CPU Sampling by CPU", clique com o botão direito do mouse e selecione "Select Interval..." Isso permite digitar o intervalo de interesse que foi descoberto observando o rastreamento da GPU.

    Captura de ecrã que mostra 'C P U sampling by C P U' em 'Windows Performance Analysis'.

  3. Vá para o menu Rastrear e verifique se a opção "Carregar símbolos" está marcada. Além disso, abra Rastreamento -> Configurar Caminhos de Símbolos, e digite o caminho dos símbolos do aplicativo. Um arquivo de símbolo contém informações de depuração sobre um executável compilado em um banco de dados separado (.pdb). Este ficheiro é normalmente referido como um PDB. Mais informações sobre arquivos de símbolos podem ser encontradas aqui: Symbol Files. Esse arquivo pode ser localizado na pasta "Depurar" do diretório do aplicativo.

  4. Para obter o detalhamento de onde o tempo está sendo gasto no aplicativo, clique com o botão direito do mouse no intervalo selecionado na etapa anterior e clique em Tabela de Resumo. Para obter uma visão geral do tempo gasto em cada DLL, desmarque "Pilha" no menu "Colunas". Observe que a coluna "Contagem" aqui mostra quantas amostras estão dentro da dll/função fornecida. Como aproximadamente uma amostra é colhida por ms, esse número pode ser usado como uma melhor estimativa de quanto tempo é gasto em cada dll/função. Selecionar a "Pilha" no menu Colunas mostrará o tempo inclusivo gasto em cada função no gráfico de chamadas. Isso ajudará a decompor ainda mais os pontos problemáticos.

  5. As informações de rastreio da pilha para 2048 primitivos não realizados revelam que 30% do tempo da CPU são gastos no processo de realização geométrica. Desse total, cerca de 36% do tempo está a ser gasto em tesselação de geometria e acariciamento.

  6. Informações de rastreamento de pilha para primitivos não realizados 8192 revelam que cerca de 60% do tempo da CPU (4 núcleos) é gasto na realização da geometria.

    Captura de tela que mostra informações de rastreamento de pilha para o tempo C P U.

Calculando o tempo da CPU quando os 8192 primitivos estão a ser renderizados

Fica claro nos perfis que o aplicativo está vinculado à CPU. Para reduzir o tempo gasto pela CPU, as geometrias podem ser criadas uma vez e armazenadas em cache. O conteúdo armazenado em cache pode ser renderizado a cada quadro sem incorrer no custo de tesselação de geometria por quadro. Ao analisar o rastreamento em GPUView para a parte executada da aplicação, fica claro que o DWM consegue apresentar todos os fotogramas e o tempo de CPU reduziu drasticamente.

Captura de ecrã que mostra um exemplo de rastreamento no GPUView mostrando que o D W M consegue apresentar todos os fotogramas.

A primeira parte do gráfico mostra 8192 primitivas realizadas. O tempo de CPU correspondente por quadro cabe em duas sincronizações verticais consecutivas. Na parte posterior do gráfico, isso não é verdade.

Olhando no XPerf , a CPU está ociosa por um longo período, com apenas cerca de 25% do tempo da CPU a ser gasto na aplicação de realização geométrica.

captura de tela do gpuview.

Resumo

Tanto GPUView quanto XPerf são ferramentas poderosas para analisar o desempenho de aplicações DirectX. Este artigo é uma cartilha para usar essas ferramentas e entender as medições básicas de desempenho e as características do aplicativo. Além de entender o uso das ferramentas, primeiro é importante entender o aplicativo que está sendo analisado. Comece encontrando respostas para perguntas como o que o aplicativo está tentando alcançar? Quais threads no sistema são mais importantes? Que compensações está disposto a fazer? Ao analisar traços de desempenho, comece olhando para lugares problemáticos óbvios. O desempenho da aplicação está limitado pela CPU ou pela GPU? O aplicativo é capaz de apresentar todos os quadros? As ferramentas, juntamente com uma compreensão do aplicativo, podem fornecer informações muito úteis para entender, encontrar e, finalmente, resolver problemas de desempenho.