void ShaderReflection()

in Source/Core/ShaderConductor.cpp [329:424]


    void ShaderReflection(Compiler::ReflectionResultDesc& result, IDxcBlob* dxilBlob)
    {
        CComPtr<ID3D12ShaderReflection> shaderReflection;
        IFT(CreateDxcReflectionFromBlob(dxilBlob, shaderReflection));

        D3D12_SHADER_DESC shaderDesc;
        shaderReflection->GetDesc(&shaderDesc);

        std::vector<Compiler::ReflectionDesc> vecReflectionDescs;
        for (uint32_t resourceIndex = 0; resourceIndex < shaderDesc.BoundResources; ++resourceIndex)
        {
            D3D12_SHADER_INPUT_BIND_DESC bindDesc;
            shaderReflection->GetResourceBindingDesc(resourceIndex, &bindDesc);

            Compiler::ReflectionDesc reflectionDesc{};

            if (bindDesc.Type == D3D_SIT_CBUFFER || bindDesc.Type == D3D_SIT_TBUFFER)
            {
                ID3D12ShaderReflectionConstantBuffer* constantBuffer = shaderReflection->GetConstantBufferByName(bindDesc.Name);

                D3D12_SHADER_BUFFER_DESC bufferDesc;
                constantBuffer->GetDesc(&bufferDesc);

                if (strcmp(bufferDesc.Name, "$Globals") == 0)
                {
                    for (uint32_t variableIndex = 0; variableIndex < bufferDesc.Variables; ++variableIndex)
                    {
                        ID3D12ShaderReflectionVariable* variable = constantBuffer->GetVariableByIndex(variableIndex);
                        D3D12_SHADER_VARIABLE_DESC variableDesc;
                        variable->GetDesc(&variableDesc);

                        std::strncpy(reflectionDesc.name, variableDesc.Name,
                                     std::min(std::strlen(variableDesc.Name) + 1, sizeof(reflectionDesc.name)));

                        reflectionDesc.type = ShaderResourceType::Parameter;
                        reflectionDesc.bufferBindPoint = bindDesc.BindPoint;
                        reflectionDesc.bindPoint = variableDesc.StartOffset;
                        reflectionDesc.bindCount = variableDesc.Size;
                    }
                }
                else
                {
                    std::strncpy(reflectionDesc.name, bufferDesc.Name,
                                 std::min(std::strlen(bufferDesc.Name) + 1, sizeof(reflectionDesc.name)));

                    reflectionDesc.type = ShaderResourceType::ConstantBuffer;
                    reflectionDesc.bufferBindPoint = bindDesc.BindPoint;
                    reflectionDesc.bindPoint = 0;
                    reflectionDesc.bindCount = 0;
                }
            }
            else
            {
                switch (bindDesc.Type)
                {
                case D3D_SIT_TEXTURE:
                    reflectionDesc.type = ShaderResourceType::Texture;
                    break;

                case D3D_SIT_SAMPLER:
                    reflectionDesc.type = ShaderResourceType::Sampler;
                    break;

                case D3D_SIT_STRUCTURED:
                case D3D_SIT_BYTEADDRESS:
                    reflectionDesc.type = ShaderResourceType::ShaderResourceView;
                    break;

                case D3D_SIT_UAV_RWTYPED:
                case D3D_SIT_UAV_RWSTRUCTURED:
                case D3D_SIT_UAV_RWBYTEADDRESS:
                case D3D_SIT_UAV_APPEND_STRUCTURED:
                case D3D_SIT_UAV_CONSUME_STRUCTURED:
                case D3D_SIT_UAV_RWSTRUCTURED_WITH_COUNTER:
                    reflectionDesc.type = ShaderResourceType::UnorderedAccessView;
                    break;

                default:
                    llvm_unreachable("Unknown bind type.");
                    break;
                }

                std::strncpy(reflectionDesc.name, bindDesc.Name, std::min(std::strlen(bindDesc.Name) + 1, sizeof(reflectionDesc.name)));

                reflectionDesc.bufferBindPoint = 0;
                reflectionDesc.bindPoint = bindDesc.BindPoint;
                reflectionDesc.bindCount = bindDesc.BindCount;
            }

            vecReflectionDescs.push_back(reflectionDesc);
        }

        result.descCount = static_cast<uint32_t>(vecReflectionDescs.size());
        result.descs.Reset(vecReflectionDescs.data(), sizeof(Compiler::ReflectionDesc) * result.descCount);
        result.instructionCount = shaderDesc.InstructionCount;
    }