Visão geral dos descritores

Os descritores são criados por chamadas de API e identificam recursos.

Dados do descritor

Um descritor é um bloco relativamente pequeno de dados que descreve totalmente um objeto para a GPU, em um formato opaco específico da GPU. Há vários tipos diferentes de descritores: RTVs (exibições de destino de renderização), DSVs (exibições de estêncil de profundidade), SRVs (exibições de recurso de sombreador), UAVs (exibições de acesso não ordenadas), CBVs (exibições de buffer constantes) e amostras.

Os descritores variam de tamanho, dependendo do hardware da GPU. Você pode consultar o tamanho de um SRV, UAV ou CBV chamando ID3D12Device::GetDescriptorHandleIncrementSize. Os descritores são mostrados nesta documentação como unidades indivisíveis; aqui está um exemplo.

srv, cbv, uav, and sampler

Os descritores são criados por chamadas de API e incluirão informações como o recurso e os mip-maps que você quer que o descritor contenha.

O driver não rastreia ou mantém referências a descritores, cabe ao aplicativo garantir que o tipo de descritor correto esteja em uso e que as informações sejam atuais. Há uma pequena exceção para isso; o driver inspeciona as associações de destino de renderização para garantir que as cadeias de troca funcionem corretamente.

Os descritores de objeto não precisam ser liberados. Os drivers não anexam alocações à criação de um descritor. No entanto, um descritor pode codificar referências a outras alocações para as quais o aplicativo possui o tempo de vida. Por exemplo, um descritor para um SRV deve conter o endereço virtual do recurso D3D (por exemplo, uma textura) ao qual o SRV se refere. É responsabilidade do aplicativo garantir que ele não use um descritor SRV quando o recurso D3D subjacente do qual ele depende foi destruído ou está sendo modificado (como ser declarado como não identificador).

A principal maneira de usar descritores é colocá-los em heaps de descritor, que estão fazendo backup de memória para descritores.

Identificadores de descritor

Um identificador de descritor é o endereço exclusivo do descritor. Ele é semelhante a um ponteiro, mas é opaco, pois sua implementação é específica de hardware. O identificador é exclusivo em heaps de descritor. Por exemplo, uma matriz de identificadores pode referenciar descritores em vários heaps.

Identificadores de CPU são para uso imediato, como copiar onde a origem e o destino precisam ser identificados. Imediatamente após o uso (por exemplo, uma chamada para ID3D12GraphicsCommandList::OMSetRenderTargets), eles podem ser reutilizados ou seu heap subjacente pode ser descartado.

Os identificadores de GPU não são para uso imediato: eles identificam locais de uma lista de comandos, para uso no tempo de execução da GPU. Eles devem ser preservados até que todas as listas de comandos referenciadas tenham sido totalmente executadas.

Para criar um identificador de descritor para o início de um heap, depois de criar o heap do descritor em si, chame um dos seguintes métodos:

Esses métodos retornam as seguintes estruturas:

Como o tamanho dos descritores varia de acordo com o hardware, para obter o incremento entre cada descritor em um uso de heap:

É seguro deslocar um local inicial com vários incrementos, copiar identificadores e passar identificadores para chamadas à API. Não é seguro desreferenciar um identificador como se fosse um ponteiro de CPU válido, nem analisar os bits dentro de um identificador.

Algumas estruturas auxiliares foram adicionadas, com membros de inicialização, para facilitar um pouco o gerenciamento de identificadores.

Descritores nulos

Ao criar descritores usando chamadas de API, os aplicativos passam NULL para o ponteiro de recurso na definição do descritor para alcançar o efeito de nada associado quando acessado por um sombreador.

O restante do descritor deve ser preenchido o máximo possível. Por exemplo, no caso de SRVs (Exibições de Recurso de Sombreador), o descritor pode ser usado para distinguir o tipo de exibição que é (Texture1D, Texture2D e assim por diante). Parâmetros numéricos no descritor de exibição, como o número de mipmaps, devem ser definidos como valores válidos para um recurso.

Em muitos casos, há um comportamento definido para acessar um recurso não associado, como SRVs que retornam valores padrão. Eles serão respeitados ao acessar um descritor NULL, desde que o tipo de acesso de sombreador seja compatível com o tipo de descritor. Por exemplo, se um sombreador espera um SRV Texture2D e acessa um SRV NULL definido como texture1D, o comportamento é indefinido e pode resultar na redefinição do dispositivo.

Em resumo, para criar um descritor nulo, passe null para o parâmetro pResource ao criar a exibição com métodos como CreateShaderResourceView. Para o parâmetro de descrição da exibição pDesc, defina uma configuração que funcionaria se o recurso não fosse nulo (caso contrário, poderá ocorrer uma falha em alguns hardwares).

No entanto, os descritores raiz não devem ser definidos como nulos.

No hardware de Camada1 (confira Camadas de Hardware, todos os descritores associados (por meio de tabelas de descritor) devem ser inicializados, seja como descritores reais ou descritores nulos, mesmo que não sejam acessados pelo hardware, caso contrário, o comportamento será indefinido.

No hardware de Camada2, isso se aplica a descritores CBV e UAV associados, mas não aos descritores SRV.

No hardware da Camada3, não há nenhuma restrição sobre isso, desde que descritores não inicializados nunca sejam acessados.

Descritores padrão

Para criar um descritor padrão para uma determinada exibição, passe um parâmetro pResource válido para o método de criação de exibição (como CreateShaderResourceView), mas passe NULL para o parâmetro pDesc. Por exemplo, se o recurso contiver 14 mips, o modo de exibição conterá 14 mips. O caso padrão abrange o mapeamento mais óbvio de um recurso para uma exibição. Isso requer que o recurso seja alocado com um nome de formato totalmente qualificado (como DXGI_FORMAT_R8G8B8A8_UNORM_SRGB em vez de DXGI_FORMAT_R8G8B8A8_TYPELESS).

Os descritores padrão não podem ser usados com uma exibição de estrutura de aceleração de raytracing, porque o parâmetro pResource fornecido deve ser NULL, e o local deve ser passado por meio de um D3D12_RAYTRACING_ACCELERATION_STRUCTURE_SRV.

Descritores