mirror of
https://github.com/EduApps-CDG/OpenDX
synced 2024-12-30 09:45:37 +01:00
[dxbc] Implemented shader resource declaration for images
This commit is contained in:
parent
939faeaf27
commit
7c03495d74
@ -1438,7 +1438,7 @@ namespace dxvk {
|
|||||||
: VK_PIPELINE_BIND_POINT_GRAPHICS;
|
: VK_PIPELINE_BIND_POINT_GRAPHICS;
|
||||||
|
|
||||||
const uint32_t slotId = computeResourceSlotId(
|
const uint32_t slotId = computeResourceSlotId(
|
||||||
ShaderStage, DxbcBindingType::ImageSampler,
|
ShaderStage, DxbcBindingType::ShaderResource,
|
||||||
StartSlot + i);
|
StartSlot + i);
|
||||||
|
|
||||||
if (resView != nullptr) {
|
if (resView != nullptr) {
|
||||||
|
@ -24,6 +24,9 @@ namespace dxvk {
|
|||||||
case DxbcOpcode::DclConstantBuffer:
|
case DxbcOpcode::DclConstantBuffer:
|
||||||
return this->dclConstantBuffer(ins);
|
return this->dclConstantBuffer(ins);
|
||||||
|
|
||||||
|
case DxbcOpcode::DclResource:
|
||||||
|
return this->dclResource(ins);
|
||||||
|
|
||||||
case DxbcOpcode::DclSampler:
|
case DxbcOpcode::DclSampler:
|
||||||
return this->dclSampler(ins);
|
return this->dclSampler(ins);
|
||||||
|
|
||||||
@ -39,7 +42,7 @@ namespace dxvk {
|
|||||||
return this->dclInterfaceVar(ins);
|
return this->dclInterfaceVar(ins);
|
||||||
|
|
||||||
case DxbcOpcode::DclTemps:
|
case DxbcOpcode::DclTemps:
|
||||||
return this->dclTemps(ins);
|
return this->dclTemps(ins);
|
||||||
|
|
||||||
case DxbcOpcode::Add:
|
case DxbcOpcode::Add:
|
||||||
return this->opAdd(ins);
|
return this->opAdd(ins);
|
||||||
@ -81,6 +84,9 @@ namespace dxvk {
|
|||||||
|
|
||||||
|
|
||||||
void DxbcCompiler::dclConstantBuffer(const DxbcInstruction& ins) {
|
void DxbcCompiler::dclConstantBuffer(const DxbcInstruction& ins) {
|
||||||
|
// dclConstantBuffer takes two operands:
|
||||||
|
// 1. The buffer register ID
|
||||||
|
// 2. The number of 4x32-bit constants
|
||||||
auto op = ins.operand(0);
|
auto op = ins.operand(0);
|
||||||
|
|
||||||
if (op.token().indexDimension() != 2)
|
if (op.token().indexDimension() != 2)
|
||||||
@ -93,7 +99,46 @@ namespace dxvk {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void DxbcCompiler::dclSampler(const DxbcInstruction& ins) {
|
void DxbcCompiler::dclResource(const DxbcInstruction& ins) {
|
||||||
|
// dclResource takes two operands:
|
||||||
|
// 1. The resource register ID
|
||||||
|
// 2. The resource return type
|
||||||
|
auto op = ins.operand(0);
|
||||||
|
|
||||||
|
if (op.token().indexDimension() != 1)
|
||||||
|
throw DxvkError("DXBC: dclResource: Invalid index dimension");
|
||||||
|
|
||||||
|
const uint32_t index = op.index(0).immPart();
|
||||||
|
|
||||||
|
// Defines the type of the resource (texture2D, ...)
|
||||||
|
auto resourceDim = static_cast<DxbcResourceDim>(
|
||||||
|
bit::extract(ins.token().control(), 0, 4));
|
||||||
|
|
||||||
|
// Defines the type of a read operation. DXBC has the ability
|
||||||
|
// to define four different types whereas SPIR-V only allows
|
||||||
|
// one, but in practice this should not be much of a problem.
|
||||||
|
const uint32_t ofs = op.length();
|
||||||
|
|
||||||
|
auto xType = static_cast<DxbcResourceReturnType>(
|
||||||
|
bit::extract(ins.arg(ofs), 0, 3));
|
||||||
|
auto yType = static_cast<DxbcResourceReturnType>(
|
||||||
|
bit::extract(ins.arg(ofs), 4, 7));
|
||||||
|
auto zType = static_cast<DxbcResourceReturnType>(
|
||||||
|
bit::extract(ins.arg(ofs), 8, 11));
|
||||||
|
auto wType = static_cast<DxbcResourceReturnType>(
|
||||||
|
bit::extract(ins.arg(ofs), 12, 15));
|
||||||
|
|
||||||
|
if ((xType != yType) || (xType != zType) || (xType != wType))
|
||||||
|
Logger::warn("DXBC: dclResource: Ignoring resource return types");
|
||||||
|
|
||||||
|
m_gen->dclResource(index, resourceDim, xType);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void DxbcCompiler::dclSampler(const DxbcInstruction& ins) {
|
||||||
|
// dclSampler takes one operand:
|
||||||
|
// 1. The sampler register ID
|
||||||
|
// TODO implement sampler mode (default / comparison / mono)
|
||||||
auto op = ins.operand(0);
|
auto op = ins.operand(0);
|
||||||
|
|
||||||
if (op.token().indexDimension() != 1)
|
if (op.token().indexDimension() != 1)
|
||||||
@ -163,6 +208,9 @@ namespace dxvk {
|
|||||||
|
|
||||||
|
|
||||||
void DxbcCompiler::dclTemps(const DxbcInstruction& ins) {
|
void DxbcCompiler::dclTemps(const DxbcInstruction& ins) {
|
||||||
|
// dclTemps takes one operand:
|
||||||
|
// 1. The number of temporary registers to
|
||||||
|
// declare, as an immediate 32-bit integer.
|
||||||
m_gen->dclTemps(ins.arg(0));
|
m_gen->dclTemps(ins.arg(0));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -35,6 +35,9 @@ namespace dxvk {
|
|||||||
void dclConstantBuffer(
|
void dclConstantBuffer(
|
||||||
const DxbcInstruction& ins);
|
const DxbcInstruction& ins);
|
||||||
|
|
||||||
|
void dclResource(
|
||||||
|
const DxbcInstruction& ins);
|
||||||
|
|
||||||
void dclSampler(
|
void dclSampler(
|
||||||
const DxbcInstruction& ins);
|
const DxbcInstruction& ins);
|
||||||
|
|
||||||
|
@ -80,6 +80,99 @@ namespace dxvk {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void DxbcCodeGen::dclResource(
|
||||||
|
uint32_t registerId,
|
||||||
|
DxbcResourceDim resourceType,
|
||||||
|
DxbcResourceReturnType returnType) {
|
||||||
|
uint32_t sampledTypeId = 0;
|
||||||
|
|
||||||
|
switch (returnType) {
|
||||||
|
default: Logger::err(str::format("DXBC: Invalid sampled type: ", returnType));
|
||||||
|
case DxbcResourceReturnType::Float: sampledTypeId = m_module.defFloatType(32); break;
|
||||||
|
case DxbcResourceReturnType::Sint: sampledTypeId = m_module.defIntType (32, 1); break;
|
||||||
|
case DxbcResourceReturnType::Uint: sampledTypeId = m_module.defIntType (32, 0); break;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint32_t resourceTypeId = 0;
|
||||||
|
|
||||||
|
switch (resourceType) {
|
||||||
|
default:
|
||||||
|
Logger::err(str::format(
|
||||||
|
"DXBC: Invalid resource type: ",
|
||||||
|
resourceType));
|
||||||
|
|
||||||
|
case DxbcResourceDim::Texture1D:
|
||||||
|
resourceTypeId = m_module.defImageType(
|
||||||
|
sampledTypeId, spv::Dim1D, 2, 0, 0, 1,
|
||||||
|
spv::ImageFormatUnknown);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case DxbcResourceDim::Texture1DArr:
|
||||||
|
resourceTypeId = m_module.defImageType(
|
||||||
|
sampledTypeId, spv::Dim1D, 2, 1, 0, 1,
|
||||||
|
spv::ImageFormatUnknown);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case DxbcResourceDim::Texture2D:
|
||||||
|
resourceTypeId = m_module.defImageType(
|
||||||
|
sampledTypeId, spv::Dim2D, 2, 0, 0, 1,
|
||||||
|
spv::ImageFormatUnknown);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case DxbcResourceDim::Texture2DArr:
|
||||||
|
resourceTypeId = m_module.defImageType(
|
||||||
|
sampledTypeId, spv::Dim2D, 2, 1, 0, 1,
|
||||||
|
spv::ImageFormatUnknown);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case DxbcResourceDim::Texture3D:
|
||||||
|
resourceTypeId = m_module.defImageType(
|
||||||
|
sampledTypeId, spv::Dim3D, 2, 0, 0, 1,
|
||||||
|
spv::ImageFormatUnknown);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case DxbcResourceDim::TextureCube:
|
||||||
|
resourceTypeId = m_module.defImageType(
|
||||||
|
sampledTypeId, spv::DimCube, 2, 0, 0, 1,
|
||||||
|
spv::ImageFormatUnknown);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case DxbcResourceDim::TextureCubeArr:
|
||||||
|
resourceTypeId = m_module.defImageType(
|
||||||
|
sampledTypeId, spv::DimCube, 2, 1, 0, 1,
|
||||||
|
spv::ImageFormatUnknown);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint32_t resourcePtrType = m_module.defPointerType(
|
||||||
|
resourceTypeId, spv::StorageClassUniformConstant);
|
||||||
|
|
||||||
|
uint32_t varId = m_module.newVar(resourcePtrType,
|
||||||
|
spv::StorageClassUniformConstant);
|
||||||
|
|
||||||
|
m_module.setDebugName(varId,
|
||||||
|
str::format("t", registerId).c_str());
|
||||||
|
|
||||||
|
m_resources.at(registerId).varId = varId;
|
||||||
|
m_resources.at(registerId).sampledTypeId = sampledTypeId;
|
||||||
|
m_resources.at(registerId).resourceTypeId = resourceTypeId;
|
||||||
|
|
||||||
|
// Compute the DXVK binding slot index for the resource.
|
||||||
|
// D3D11 needs to bind the actual resource to this slot.
|
||||||
|
uint32_t bindingId = computeResourceSlotId(m_shaderStage,
|
||||||
|
DxbcBindingType::ShaderResource, registerId);
|
||||||
|
|
||||||
|
m_module.decorateDescriptorSet(varId, 0);
|
||||||
|
m_module.decorateBinding(varId, bindingId);
|
||||||
|
|
||||||
|
// Store descriptor info for the shader interface
|
||||||
|
DxvkResourceSlot resource;
|
||||||
|
resource.slot = bindingId;
|
||||||
|
resource.type = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE;
|
||||||
|
m_resourceSlots.push_back(resource);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void DxbcCodeGen::dclSampler(uint32_t samplerId) {
|
void DxbcCodeGen::dclSampler(uint32_t samplerId) {
|
||||||
// The sampler type is opaque, but we still have to
|
// The sampler type is opaque, but we still have to
|
||||||
// define a pointer and a variable in oder to use it
|
// define a pointer and a variable in oder to use it
|
||||||
|
@ -45,6 +45,18 @@ namespace dxvk {
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* \brief Shader resource binding
|
||||||
|
*
|
||||||
|
* Stores the sampler variable as well as
|
||||||
|
*/
|
||||||
|
struct DxbcShaderResource {
|
||||||
|
uint32_t varId = 0;
|
||||||
|
uint32_t sampledTypeId = 0;
|
||||||
|
uint32_t resourceTypeId = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* \brief DXBC code generator
|
* \brief DXBC code generator
|
||||||
*
|
*
|
||||||
@ -64,11 +76,16 @@ namespace dxvk {
|
|||||||
void dclTemps(uint32_t n);
|
void dclTemps(uint32_t n);
|
||||||
|
|
||||||
void dclConstantBuffer(
|
void dclConstantBuffer(
|
||||||
uint32_t bufferId,
|
uint32_t registerId,
|
||||||
uint32_t elementCount);
|
uint32_t elementCount);
|
||||||
|
|
||||||
|
void dclResource(
|
||||||
|
uint32_t registerId,
|
||||||
|
DxbcResourceDim resourceType,
|
||||||
|
DxbcResourceReturnType returnType);
|
||||||
|
|
||||||
void dclSampler(
|
void dclSampler(
|
||||||
uint32_t samplerId);
|
uint32_t registerId);
|
||||||
|
|
||||||
DxbcValue defConstScalar(uint32_t v);
|
DxbcValue defConstScalar(uint32_t v);
|
||||||
|
|
||||||
@ -172,8 +189,9 @@ namespace dxvk {
|
|||||||
|
|
||||||
std::vector<DxbcPointer> m_rRegs;
|
std::vector<DxbcPointer> m_rRegs;
|
||||||
|
|
||||||
std::array<DxbcConstantBuffer, 16> m_constantBuffers;
|
std::array<DxbcConstantBuffer, 16> m_constantBuffers;
|
||||||
std::array<DxbcSampler, 16> m_samplers;
|
std::array<DxbcSampler, 16> m_samplers;
|
||||||
|
std::array<DxbcShaderResource, 128> m_resources;
|
||||||
|
|
||||||
std::vector<DxvkResourceSlot> m_resourceSlots;
|
std::vector<DxvkResourceSlot> m_resourceSlots;
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user