mirror of
https://github.com/baldurk/renderdoc.git
synced 2026-05-05 09:30:44 +00:00
Implement Get*Descriptor for virtual descriptor storage in D3D11 & GL
This commit is contained in:
@@ -783,6 +783,24 @@ struct State
|
||||
)");
|
||||
Shader computeShader;
|
||||
|
||||
DOCUMENT(R"(The virtual descriptor storage.
|
||||
|
||||
:type: ResourceId
|
||||
)");
|
||||
ResourceId descriptorStore;
|
||||
|
||||
DOCUMENT(R"(The number of descriptors in the virtual descriptor storage.
|
||||
|
||||
:type: int
|
||||
)");
|
||||
uint32_t descriptorCount;
|
||||
|
||||
DOCUMENT(R"(The byte size of a descriptor in the virtual descriptor storage.
|
||||
|
||||
:type: int
|
||||
)");
|
||||
uint32_t descriptorByteSize;
|
||||
|
||||
DOCUMENT(R"(The stream-out pipeline stage.
|
||||
|
||||
:type: D3D11StreamOut
|
||||
|
||||
@@ -913,6 +913,24 @@ struct State
|
||||
)");
|
||||
rdcarray<ImageLoadStore> images;
|
||||
|
||||
DOCUMENT(R"(The virtual descriptor storage.
|
||||
|
||||
:type: ResourceId
|
||||
)");
|
||||
ResourceId descriptorStore;
|
||||
|
||||
DOCUMENT(R"(The number of descriptors in the virtual descriptor storage.
|
||||
|
||||
:type: int
|
||||
)");
|
||||
uint32_t descriptorCount;
|
||||
|
||||
DOCUMENT(R"(The byte size of a descriptor in the virtual descriptor storage.
|
||||
|
||||
:type: int
|
||||
)");
|
||||
uint32_t descriptorByteSize;
|
||||
|
||||
DOCUMENT(R"(The transform feedback stage.
|
||||
|
||||
:type: GLFeedback
|
||||
|
||||
@@ -33,6 +33,54 @@ class WrappedID3D11Device;
|
||||
class WrappedID3D11DeviceContext;
|
||||
class D3D11ResourceManager;
|
||||
|
||||
// mapping of 'index in descriptor store' to fixed bindings, linearly in a given stage's members
|
||||
enum class D3D11DescriptorMapping : uint32_t
|
||||
{
|
||||
CBs = 0,
|
||||
SRVs = CBs + D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT,
|
||||
Samplers = SRVs + D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT,
|
||||
UAVs = Samplers + D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT,
|
||||
Count = UAVs + D3D11_1_UAV_SLOT_COUNT,
|
||||
Invalid = ~0U,
|
||||
};
|
||||
|
||||
struct D3D11DescriptorLocation
|
||||
{
|
||||
ShaderStage stage;
|
||||
D3D11DescriptorMapping type;
|
||||
uint32_t idx;
|
||||
};
|
||||
|
||||
inline D3D11DescriptorLocation DecodeD3D11DescriptorIndex(uint32_t idx)
|
||||
{
|
||||
ShaderStage stage = ShaderStage(idx / (uint32_t)D3D11DescriptorMapping::Count);
|
||||
|
||||
idx %= (uint32_t)D3D11DescriptorMapping::Count;
|
||||
|
||||
if((uint32_t)stage > (uint32_t)ShaderStage::Compute)
|
||||
return {stage, D3D11DescriptorMapping::Invalid, 0};
|
||||
|
||||
// go in reverse order to handle each case with a >=
|
||||
#define HANDLE_TYPE(type) \
|
||||
else if(idx >= (uint32_t)D3D11DescriptorMapping::type) return { \
|
||||
stage, \
|
||||
D3D11DescriptorMapping::type, \
|
||||
idx - (uint32_t)D3D11DescriptorMapping::type, \
|
||||
}
|
||||
HANDLE_TYPE(UAVs);
|
||||
HANDLE_TYPE(Samplers);
|
||||
HANDLE_TYPE(SRVs);
|
||||
HANDLE_TYPE(CBs);
|
||||
#undef HANDLE_TYPE
|
||||
|
||||
return {stage, D3D11DescriptorMapping::Invalid, 0};
|
||||
}
|
||||
|
||||
inline uint32_t EncodeD3D11DescriptorIndex(const D3D11DescriptorLocation &idx)
|
||||
{
|
||||
return (uint32_t)idx.stage * (uint32_t)D3D11DescriptorMapping::Count + (uint32_t)idx.type + idx.idx;
|
||||
}
|
||||
|
||||
struct D3D11RenderState
|
||||
{
|
||||
enum EmptyInit
|
||||
|
||||
@@ -741,6 +741,11 @@ void D3D11Replay::SavePipelineState(uint32_t eventId)
|
||||
|
||||
D3D11ResourceManager *rm = m_pDevice->GetResourceManager();
|
||||
|
||||
ret.descriptorStore = m_pImmediateContext->GetDescriptorsID();
|
||||
ret.descriptorCount =
|
||||
EncodeD3D11DescriptorIndex({ShaderStage::Compute, D3D11DescriptorMapping::Count, 0});
|
||||
ret.descriptorByteSize = 1;
|
||||
|
||||
ret.inputAssembly.bytecode = NULL;
|
||||
ret.inputAssembly.resourceId = ResourceId();
|
||||
ret.inputAssembly.layouts.clear();
|
||||
@@ -1671,14 +1676,243 @@ rdcarray<Descriptor> D3D11Replay::GetDescriptors(ResourceId descriptorStore,
|
||||
|
||||
if(descriptorStore != m_pImmediateContext->GetDescriptorsID())
|
||||
{
|
||||
RDCERR("Descriptors query for invalid descriptor store on fixed bindings API (D3D11)");
|
||||
RDCERR(
|
||||
"Descriptors query for invalid descriptor descriptorStore on fixed bindings API (D3D11)");
|
||||
return ret;
|
||||
}
|
||||
|
||||
D3D11RenderState *rs = m_pDevice->GetImmediateContext()->GetCurrentPipelineState();
|
||||
D3D11ResourceManager *rm = m_pDevice->GetResourceManager();
|
||||
|
||||
size_t count = 0;
|
||||
for(const DescriptorRange &r : ranges)
|
||||
count += r.count;
|
||||
ret.resize(count);
|
||||
|
||||
const D3D11RenderState::Shader *srcArr[] = {&rs->VS, &rs->HS, &rs->DS, &rs->GS, &rs->PS, &rs->CS};
|
||||
|
||||
size_t dst = 0;
|
||||
for(const DescriptorRange &r : ranges)
|
||||
{
|
||||
uint32_t descriptorId = r.offset;
|
||||
|
||||
for(uint32_t i = 0; i < r.count; i++, dst++, descriptorId++)
|
||||
{
|
||||
D3D11DescriptorLocation idx = DecodeD3D11DescriptorIndex(descriptorId);
|
||||
const D3D11RenderState::Shader &src = *srcArr[(uint32_t)idx.stage];
|
||||
|
||||
if(idx.type == D3D11DescriptorMapping::CBs)
|
||||
{
|
||||
ret[dst].type = DescriptorType::ConstantBuffer;
|
||||
|
||||
ret[dst].resource = rm->GetOriginalID(GetIDForDeviceChild(src.ConstantBuffers[idx.idx]));
|
||||
ret[dst].byteOffset = src.CBOffsets[idx.idx] * sizeof(Vec4f);
|
||||
ret[dst].byteSize = src.CBCounts[idx.idx] * sizeof(Vec4f);
|
||||
}
|
||||
else if(idx.type == D3D11DescriptorMapping::SRVs)
|
||||
{
|
||||
ID3D11ShaderResourceView *view = src.SRVs[idx.idx];
|
||||
|
||||
ret[dst].view = rm->GetOriginalID(GetIDForDeviceChild(view));
|
||||
|
||||
ret[dst].type = DescriptorType::Image;
|
||||
if(ret[dst].view != ResourceId())
|
||||
{
|
||||
D3D11_SHADER_RESOURCE_VIEW_DESC desc;
|
||||
view->GetDesc(&desc);
|
||||
|
||||
ret[dst].format = MakeResourceFormat(desc.Format);
|
||||
|
||||
ID3D11Resource *res = NULL;
|
||||
view->GetResource(&res);
|
||||
|
||||
ret[dst].elementByteSize =
|
||||
desc.Format == DXGI_FORMAT_UNKNOWN ? 1 : GetByteSize(1, 1, 1, desc.Format, 0);
|
||||
|
||||
ret[dst].resource = rm->GetOriginalID(GetIDForDeviceChild(res));
|
||||
|
||||
ret[dst].textureType = MakeTextureDim(desc.ViewDimension);
|
||||
|
||||
if(desc.ViewDimension == D3D11_SRV_DIMENSION_BUFFER)
|
||||
{
|
||||
ret[dst].type = DescriptorType::TypedBuffer;
|
||||
|
||||
D3D11_BUFFER_DESC bufdesc;
|
||||
((ID3D11Buffer *)res)->GetDesc(&bufdesc);
|
||||
|
||||
if(bufdesc.StructureByteStride > 0 && desc.Format == DXGI_FORMAT_UNKNOWN)
|
||||
{
|
||||
ret[dst].elementByteSize = bufdesc.StructureByteStride;
|
||||
ret[dst].type = DescriptorType::Buffer;
|
||||
}
|
||||
|
||||
ret[dst].byteOffset = desc.Buffer.FirstElement * ret[dst].elementByteSize;
|
||||
ret[dst].byteSize = desc.Buffer.NumElements * ret[dst].elementByteSize;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_SRV_DIMENSION_BUFFEREX)
|
||||
{
|
||||
ret[dst].type = DescriptorType::TypedBuffer;
|
||||
|
||||
ret[dst].flags = DescriptorFlags(desc.BufferEx.Flags);
|
||||
|
||||
D3D11_BUFFER_DESC bufdesc;
|
||||
((ID3D11Buffer *)res)->GetDesc(&bufdesc);
|
||||
|
||||
if(bufdesc.StructureByteStride > 0 && desc.Format == DXGI_FORMAT_UNKNOWN)
|
||||
{
|
||||
ret[dst].elementByteSize = bufdesc.StructureByteStride;
|
||||
ret[dst].type = DescriptorType::Buffer;
|
||||
}
|
||||
|
||||
ret[dst].byteOffset = desc.BufferEx.FirstElement * ret[dst].elementByteSize;
|
||||
ret[dst].byteSize = desc.BufferEx.NumElements * ret[dst].elementByteSize;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_SRV_DIMENSION_TEXTURE1D)
|
||||
{
|
||||
ret[dst].firstMip = desc.Texture1D.MostDetailedMip & 0xff;
|
||||
ret[dst].numMips = desc.Texture1D.MipLevels & 0xff;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_SRV_DIMENSION_TEXTURE1DARRAY)
|
||||
{
|
||||
ret[dst].firstMip = desc.Texture1DArray.MostDetailedMip & 0xff;
|
||||
ret[dst].numMips = desc.Texture1DArray.MipLevels & 0xff;
|
||||
ret[dst].numSlices = desc.Texture1DArray.ArraySize & 0xffff;
|
||||
ret[dst].firstSlice = desc.Texture1DArray.FirstArraySlice & 0xffff;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_SRV_DIMENSION_TEXTURE2D)
|
||||
{
|
||||
ret[dst].firstMip = desc.Texture2D.MostDetailedMip & 0xff;
|
||||
ret[dst].numMips = desc.Texture2D.MipLevels & 0xff;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_SRV_DIMENSION_TEXTURE2DARRAY)
|
||||
{
|
||||
ret[dst].firstMip = desc.Texture2DArray.MostDetailedMip & 0xff;
|
||||
ret[dst].numMips = desc.Texture2DArray.MipLevels & 0xff;
|
||||
ret[dst].firstSlice = desc.Texture2DArray.FirstArraySlice & 0xffff;
|
||||
ret[dst].numSlices = desc.Texture2DArray.ArraySize & 0xffff;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_SRV_DIMENSION_TEXTURE2DMS)
|
||||
{
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_SRV_DIMENSION_TEXTURE2DMSARRAY)
|
||||
{
|
||||
ret[dst].numSlices = desc.Texture2DMSArray.ArraySize & 0xffff;
|
||||
ret[dst].firstSlice = desc.Texture2DMSArray.FirstArraySlice & 0xffff;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_SRV_DIMENSION_TEXTURE3D)
|
||||
{
|
||||
ret[dst].firstMip = desc.Texture3D.MostDetailedMip & 0xff;
|
||||
ret[dst].numMips = desc.Texture3D.MipLevels & 0xff;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_SRV_DIMENSION_TEXTURECUBE)
|
||||
{
|
||||
ret[dst].firstMip = desc.TextureCube.MostDetailedMip & 0xff;
|
||||
ret[dst].numMips = desc.TextureCube.MipLevels & 0xff;
|
||||
ret[dst].numSlices = 6;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_SRV_DIMENSION_TEXTURECUBEARRAY)
|
||||
{
|
||||
ret[dst].firstMip = desc.TextureCubeArray.MostDetailedMip & 0xff;
|
||||
ret[dst].numMips = desc.TextureCubeArray.MipLevels & 0xff;
|
||||
ret[dst].firstSlice = desc.TextureCubeArray.First2DArrayFace & 0xffff;
|
||||
ret[dst].numSlices = (desc.TextureCubeArray.NumCubes * 6) & 0xffff;
|
||||
}
|
||||
|
||||
SAFE_RELEASE(res);
|
||||
}
|
||||
}
|
||||
else if(idx.type == D3D11DescriptorMapping::UAVs)
|
||||
{
|
||||
ID3D11UnorderedAccessView *view = NULL;
|
||||
|
||||
if(idx.stage == ShaderStage::Compute)
|
||||
view = rs->CSUAVs[idx.idx];
|
||||
else if(idx.idx >= rs->OM.UAVStartSlot)
|
||||
view = rs->OM.UAVs[idx.idx - rs->OM.UAVStartSlot];
|
||||
|
||||
ret[dst].view = rm->GetOriginalID(GetIDForDeviceChild(view));
|
||||
|
||||
ret[dst].type = DescriptorType::ReadWriteImage;
|
||||
if(ret[dst].view != ResourceId())
|
||||
{
|
||||
D3D11_UNORDERED_ACCESS_VIEW_DESC desc;
|
||||
view->GetDesc(&desc);
|
||||
|
||||
ID3D11Resource *res = NULL;
|
||||
view->GetResource(&res);
|
||||
|
||||
ret[dst].bufferStructCount = 0;
|
||||
|
||||
ret[dst].elementByteSize =
|
||||
desc.Format == DXGI_FORMAT_UNKNOWN ? 1 : GetByteSize(1, 1, 1, desc.Format, 0);
|
||||
|
||||
ret[dst].textureType = MakeTextureDim(desc.ViewDimension);
|
||||
|
||||
ret[dst].secondary = ResourceId();
|
||||
|
||||
if(desc.ViewDimension == D3D11_UAV_DIMENSION_BUFFER &&
|
||||
(desc.Buffer.Flags & (D3D11_BUFFER_UAV_FLAG_APPEND | D3D11_BUFFER_UAV_FLAG_COUNTER)))
|
||||
{
|
||||
ret[dst].bufferStructCount = GetDebugManager()->GetStructCount(view);
|
||||
|
||||
ret[dst].secondary = GetDebugManager()->GetCounterBufferID(view);
|
||||
}
|
||||
|
||||
ret[dst].resource = rm->GetOriginalID(GetIDForDeviceChild(res));
|
||||
|
||||
ret[dst].format = MakeResourceFormat(desc.Format);
|
||||
|
||||
if(desc.ViewDimension == D3D11_UAV_DIMENSION_BUFFER)
|
||||
{
|
||||
ret[dst].type = DescriptorType::ReadWriteBuffer;
|
||||
|
||||
if(desc.Format != DXGI_FORMAT_UNKNOWN)
|
||||
ret[dst].type = DescriptorType::ReadWriteTypedBuffer;
|
||||
|
||||
ret[dst].flags = DescriptorFlags(desc.Buffer.Flags);
|
||||
|
||||
D3D11_BUFFER_DESC bufdesc;
|
||||
((ID3D11Buffer *)res)->GetDesc(&bufdesc);
|
||||
|
||||
if(bufdesc.StructureByteStride > 0 && desc.Format == DXGI_FORMAT_UNKNOWN)
|
||||
ret[dst].elementByteSize = bufdesc.StructureByteStride;
|
||||
|
||||
ret[dst].byteOffset = desc.Buffer.FirstElement * ret[dst].elementByteSize;
|
||||
ret[dst].byteSize = desc.Buffer.NumElements * ret[dst].elementByteSize;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_UAV_DIMENSION_TEXTURE1D)
|
||||
{
|
||||
ret[dst].firstMip = desc.Texture1D.MipSlice & 0xff;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_UAV_DIMENSION_TEXTURE1DARRAY)
|
||||
{
|
||||
ret[dst].numSlices = desc.Texture1DArray.ArraySize & 0xffff;
|
||||
ret[dst].firstSlice = desc.Texture1DArray.FirstArraySlice & 0xffff;
|
||||
ret[dst].firstMip = desc.Texture1DArray.MipSlice & 0xff;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_UAV_DIMENSION_TEXTURE2D)
|
||||
{
|
||||
ret[dst].firstMip = desc.Texture2D.MipSlice & 0xff;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_UAV_DIMENSION_TEXTURE2DARRAY)
|
||||
{
|
||||
ret[dst].numSlices = desc.Texture2DArray.ArraySize & 0xffff;
|
||||
ret[dst].firstSlice = desc.Texture2DArray.FirstArraySlice & 0xffff;
|
||||
ret[dst].firstMip = desc.Texture2DArray.MipSlice & 0xff;
|
||||
}
|
||||
else if(desc.ViewDimension == D3D11_UAV_DIMENSION_TEXTURE3D)
|
||||
{
|
||||
ret[dst].numSlices = desc.Texture3D.WSize & 0xffff;
|
||||
ret[dst].firstSlice = desc.Texture3D.FirstWSlice & 0xffff;
|
||||
ret[dst].firstMip = desc.Texture3D.MipSlice & 0xff;
|
||||
}
|
||||
|
||||
SAFE_RELEASE(res);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -1689,14 +1923,62 @@ rdcarray<SamplerDescriptor> D3D11Replay::GetSamplerDescriptors(ResourceId descri
|
||||
|
||||
if(descriptorStore != m_pImmediateContext->GetDescriptorsID())
|
||||
{
|
||||
RDCERR("Descriptors query for invalid descriptor store on fixed bindings API (D3D11)");
|
||||
RDCERR(
|
||||
"Descriptors query for invalid descriptor descriptorStore on fixed bindings API (D3D11)");
|
||||
return ret;
|
||||
}
|
||||
|
||||
D3D11RenderState *rs = m_pDevice->GetImmediateContext()->GetCurrentPipelineState();
|
||||
D3D11ResourceManager *rm = m_pDevice->GetResourceManager();
|
||||
|
||||
size_t count = 0;
|
||||
for(const DescriptorRange &r : ranges)
|
||||
count += r.count;
|
||||
ret.resize(count);
|
||||
|
||||
const D3D11RenderState::Shader *srcArr[] = {&rs->VS, &rs->HS, &rs->DS, &rs->GS, &rs->PS, &rs->CS};
|
||||
|
||||
size_t dst = 0;
|
||||
for(const DescriptorRange &r : ranges)
|
||||
{
|
||||
uint32_t descriptorId = r.offset;
|
||||
|
||||
for(uint32_t i = 0; i < r.count; i++, dst++, descriptorId++)
|
||||
{
|
||||
D3D11DescriptorLocation idx = DecodeD3D11DescriptorIndex(descriptorId);
|
||||
|
||||
if(idx.type != D3D11DescriptorMapping::Samplers)
|
||||
continue;
|
||||
|
||||
ID3D11SamplerState *samp = srcArr[(uint32_t)idx.stage]->Samplers[idx.idx];
|
||||
|
||||
ret[dst].type = DescriptorType::Sampler;
|
||||
ret[dst].object = rm->GetOriginalID(GetIDForDeviceChild(samp));
|
||||
|
||||
if(ret[dst].object != ResourceId())
|
||||
{
|
||||
D3D11_SAMPLER_DESC desc;
|
||||
samp->GetDesc(&desc);
|
||||
|
||||
ret[dst].addressU = MakeAddressMode(desc.AddressU);
|
||||
ret[dst].addressV = MakeAddressMode(desc.AddressV);
|
||||
ret[dst].addressW = MakeAddressMode(desc.AddressW);
|
||||
|
||||
ret[dst].borderColorValue.floatValue = desc.BorderColor;
|
||||
ret[dst].borderColorType = CompType::Float;
|
||||
|
||||
ret[dst].compareFunction = MakeCompareFunc(desc.ComparisonFunc);
|
||||
ret[dst].filter = MakeFilter(desc.Filter);
|
||||
ret[dst].maxAnisotropy = 0;
|
||||
if(ret[dst].filter.mip == FilterMode::Anisotropic)
|
||||
ret[dst].maxAnisotropy = (float)desc.MaxAnisotropy;
|
||||
ret[dst].maxLOD = desc.MaxLOD;
|
||||
ret[dst].minLOD = desc.MinLOD;
|
||||
ret[dst].mipBias = desc.MipLODBias;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
@@ -68,6 +68,72 @@ struct PixelUnpackState : public PixelStorageState
|
||||
void ResetPixelPackState(bool compressed, GLint alignment);
|
||||
void ResetPixelUnpackState(bool compressed, GLint alignment);
|
||||
|
||||
// mapping of 'index in descriptor store' to fixed bindings, linearly in GLRenderState members
|
||||
enum class GLDescriptorMapping : uint32_t
|
||||
{
|
||||
Tex1D = 0,
|
||||
Tex2D = Tex1D + 128,
|
||||
Tex3D = Tex2D + 128,
|
||||
Tex1DArray = Tex3D + 128,
|
||||
Tex2DArray = Tex1DArray + 128,
|
||||
TexCubeArray = Tex2DArray + 128,
|
||||
TexRect = TexCubeArray + 128,
|
||||
TexBuffer = TexRect + 128,
|
||||
TexCube = TexBuffer + 128,
|
||||
Tex2DMS = TexCube + 128,
|
||||
Tex2DMSArray = Tex2DMS + 128,
|
||||
Images = Tex2DMSArray + 128,
|
||||
AtomicCounter = Images + 8,
|
||||
ShaderStorage = AtomicCounter + 8,
|
||||
UniformBinding = ShaderStorage + 96,
|
||||
BareUniforms = UniformBinding + 84,
|
||||
Count = BareUniforms + 6,
|
||||
Invalid = ~0U,
|
||||
};
|
||||
|
||||
struct GLDescriptorLocation
|
||||
{
|
||||
GLDescriptorMapping type;
|
||||
uint32_t idx;
|
||||
};
|
||||
|
||||
inline GLDescriptorLocation DecodeGLDescriptorIndex(uint32_t idx)
|
||||
{
|
||||
if(idx >= (uint32_t)GLDescriptorMapping::Count)
|
||||
return {GLDescriptorMapping::Invalid, 0};
|
||||
|
||||
// go in reverse order to handle each case with a >=
|
||||
#define HANDLE_TYPE(type) \
|
||||
else if(idx >= (uint32_t)GLDescriptorMapping::type) return { \
|
||||
GLDescriptorMapping::type, \
|
||||
idx - (uint32_t)GLDescriptorMapping::type, \
|
||||
}
|
||||
HANDLE_TYPE(BareUniforms);
|
||||
HANDLE_TYPE(UniformBinding);
|
||||
HANDLE_TYPE(ShaderStorage);
|
||||
HANDLE_TYPE(AtomicCounter);
|
||||
HANDLE_TYPE(Images);
|
||||
HANDLE_TYPE(Tex2DMSArray);
|
||||
HANDLE_TYPE(Tex2DMS);
|
||||
HANDLE_TYPE(TexCube);
|
||||
HANDLE_TYPE(TexBuffer);
|
||||
HANDLE_TYPE(TexRect);
|
||||
HANDLE_TYPE(TexCubeArray);
|
||||
HANDLE_TYPE(Tex2DArray);
|
||||
HANDLE_TYPE(Tex1DArray);
|
||||
HANDLE_TYPE(Tex3D);
|
||||
HANDLE_TYPE(Tex2D);
|
||||
HANDLE_TYPE(Tex1D);
|
||||
#undef HANDLE_TYPE
|
||||
|
||||
return {GLDescriptorMapping::Invalid, 0};
|
||||
}
|
||||
|
||||
inline uint32_t EncodeGLDescriptorIndex(const GLDescriptorLocation &idx)
|
||||
{
|
||||
return (uint32_t)idx.type + idx.idx;
|
||||
}
|
||||
|
||||
struct GLRenderState
|
||||
{
|
||||
GLRenderState();
|
||||
|
||||
@@ -848,6 +848,10 @@ void GLReplay::SavePipelineState(uint32_t eventId)
|
||||
|
||||
ContextPair &ctx = drv.GetCtx();
|
||||
|
||||
pipe.descriptorStore = m_pDriver->m_DescriptorsID;
|
||||
pipe.descriptorCount = EncodeGLDescriptorIndex({GLDescriptorMapping::Count, 0});
|
||||
pipe.descriptorByteSize = 1;
|
||||
|
||||
GLuint vao = 0;
|
||||
drv.glGetIntegerv(eGL_VERTEX_ARRAY_BINDING, (GLint *)&vao);
|
||||
pipe.vertexInput.vertexArrayObject = rm->GetOriginalID(rm->GetResID(VertexArrayRes(ctx, vao)));
|
||||
@@ -2131,10 +2135,244 @@ rdcarray<Descriptor> GLReplay::GetDescriptors(ResourceId descriptorStore,
|
||||
return ret;
|
||||
}
|
||||
|
||||
MakeCurrentReplayContext(&m_ReplayCtx);
|
||||
WrappedOpenGL &drv = *m_pDriver;
|
||||
GLResourceManager *rm = m_pDriver->GetResourceManager();
|
||||
|
||||
ContextPair &ctx = drv.GetCtx();
|
||||
|
||||
GLRenderState rs;
|
||||
rs.FetchState(&drv);
|
||||
|
||||
size_t count = 0;
|
||||
for(const DescriptorRange &r : ranges)
|
||||
count += r.count;
|
||||
ret.resize(count);
|
||||
|
||||
size_t dst = 0;
|
||||
for(const DescriptorRange &r : ranges)
|
||||
{
|
||||
uint32_t descriptorId = r.offset;
|
||||
|
||||
for(uint32_t i = 0; i < r.count; i++, dst++, descriptorId++)
|
||||
{
|
||||
GLDescriptorLocation idx = DecodeGLDescriptorIndex(descriptorId);
|
||||
|
||||
if(idx.type == GLDescriptorMapping::Invalid)
|
||||
{
|
||||
}
|
||||
else if(idx.type == GLDescriptorMapping::BareUniforms)
|
||||
{
|
||||
// not feasible to emulate backing store for bare uniforms. We could synthesise our own byte
|
||||
// layout and query uniform values into a buffer but... let's not.
|
||||
ret[dst].type = DescriptorType::ConstantBuffer;
|
||||
ret[dst].byteSize = 16 * 1024;
|
||||
}
|
||||
else if(idx.type == GLDescriptorMapping::UniformBinding)
|
||||
{
|
||||
ret[dst].type = DescriptorType::ConstantBuffer;
|
||||
if(rs.UniformBinding[idx.idx].res.name != 0)
|
||||
{
|
||||
ret[dst].resource = rm->GetOriginalID(rm->GetResID(rs.UniformBinding[idx.idx].res));
|
||||
ret[dst].byteOffset = rs.UniformBinding[idx.idx].start;
|
||||
ret[dst].byteSize = rs.UniformBinding[idx.idx].size;
|
||||
}
|
||||
}
|
||||
else if(idx.type == GLDescriptorMapping::AtomicCounter)
|
||||
{
|
||||
ret[dst].type = DescriptorType::ReadWriteBuffer;
|
||||
if(rs.AtomicCounter[idx.idx].res.name != 0)
|
||||
{
|
||||
ret[dst].resource = rm->GetOriginalID(rm->GetResID(rs.AtomicCounter[idx.idx].res));
|
||||
ret[dst].byteOffset = rs.AtomicCounter[idx.idx].start;
|
||||
ret[dst].byteSize = rs.AtomicCounter[idx.idx].size;
|
||||
}
|
||||
}
|
||||
else if(idx.type == GLDescriptorMapping::ShaderStorage)
|
||||
{
|
||||
ret[dst].type = DescriptorType::ReadWriteBuffer;
|
||||
if(rs.ShaderStorage[idx.idx].res.name != 0)
|
||||
{
|
||||
ret[dst].resource = rm->GetOriginalID(rm->GetResID(rs.ShaderStorage[idx.idx].res));
|
||||
ret[dst].byteOffset = rs.ShaderStorage[idx.idx].start;
|
||||
ret[dst].byteSize = rs.ShaderStorage[idx.idx].size;
|
||||
}
|
||||
}
|
||||
else if(idx.type == GLDescriptorMapping::Images)
|
||||
{
|
||||
ret[dst].type = DescriptorType::ReadWriteImage;
|
||||
if(rs.Images[idx.idx].res.name != 0)
|
||||
{
|
||||
ResourceId id = rm->GetResID(rs.Images[idx.idx].res);
|
||||
ret[dst].resource = rm->GetOriginalID(id);
|
||||
ret[dst].firstMip = rs.Images[idx.idx].level & 0xff;
|
||||
ret[dst].numMips = 1;
|
||||
ret[dst].firstSlice = rs.Images[idx.idx].layer & 0xffff;
|
||||
if(rs.Images[idx.idx].access == eGL_READ_ONLY)
|
||||
{
|
||||
ret[dst].flags = DescriptorFlags::ReadOnlyAccess;
|
||||
}
|
||||
else if(rs.Images[idx.idx].access == eGL_WRITE_ONLY)
|
||||
{
|
||||
ret[dst].flags = DescriptorFlags::WriteOnlyAccess;
|
||||
}
|
||||
ret[dst].format = MakeResourceFormat(eGL_TEXTURE_2D, rs.Images[idx.idx].format);
|
||||
|
||||
CacheTexture(id);
|
||||
|
||||
ret[dst].textureType = m_CachedTextures[id].type;
|
||||
if(ret[dst].textureType == TextureType::Texture3D)
|
||||
ret[dst].numSlices = rs.Images[idx.idx].layered
|
||||
? (m_CachedTextures[id].depth >> ret[dst].firstMip) & 0xffff
|
||||
: 1;
|
||||
else
|
||||
ret[dst].numSlices =
|
||||
rs.Images[idx.idx].layered ? m_CachedTextures[id].arraysize & 0xffff : 1;
|
||||
|
||||
if(ret[dst].textureType == TextureType::Buffer)
|
||||
ret[dst].type = DescriptorType::ReadWriteTypedBuffer;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
ret[dst].type = DescriptorType::ImageSampler;
|
||||
if(idx.type == GLDescriptorMapping::TexBuffer)
|
||||
ret[dst].type = DescriptorType::TypedBuffer;
|
||||
|
||||
drv.glActiveTexture(GLenum(eGL_TEXTURE0 + idx.idx));
|
||||
|
||||
GLuint tex = 0;
|
||||
GLenum target = eGL_NONE;
|
||||
|
||||
if(idx.type == GLDescriptorMapping::TexCubeArray && !HasExt[ARB_texture_cube_map_array])
|
||||
{
|
||||
tex = 0;
|
||||
target = eGL_TEXTURE_CUBE_MAP_ARRAY;
|
||||
}
|
||||
else
|
||||
{
|
||||
switch(idx.type)
|
||||
{
|
||||
case GLDescriptorMapping::Tex1D:
|
||||
target = eGL_TEXTURE_1D;
|
||||
ret[dst].textureType = TextureType::Texture1D;
|
||||
break;
|
||||
case GLDescriptorMapping::Tex2D:
|
||||
target = eGL_TEXTURE_2D;
|
||||
ret[dst].textureType = TextureType::Texture2D;
|
||||
break;
|
||||
case GLDescriptorMapping::Tex3D:
|
||||
target = eGL_TEXTURE_3D;
|
||||
ret[dst].textureType = TextureType::Texture3D;
|
||||
break;
|
||||
case GLDescriptorMapping::Tex1DArray:
|
||||
target = eGL_TEXTURE_1D_ARRAY;
|
||||
ret[dst].textureType = TextureType::Texture1DArray;
|
||||
break;
|
||||
case GLDescriptorMapping::Tex2DArray:
|
||||
target = eGL_TEXTURE_2D_ARRAY;
|
||||
ret[dst].textureType = TextureType::Texture2DArray;
|
||||
break;
|
||||
case GLDescriptorMapping::TexCubeArray:
|
||||
target = eGL_TEXTURE_CUBE_MAP_ARRAY;
|
||||
ret[dst].textureType = TextureType::TextureCubeArray;
|
||||
break;
|
||||
case GLDescriptorMapping::TexRect:
|
||||
target = eGL_TEXTURE_RECTANGLE;
|
||||
ret[dst].textureType = TextureType::TextureRect;
|
||||
break;
|
||||
case GLDescriptorMapping::TexBuffer:
|
||||
target = eGL_TEXTURE_BUFFER;
|
||||
ret[dst].textureType = TextureType::Buffer;
|
||||
break;
|
||||
case GLDescriptorMapping::TexCube:
|
||||
target = eGL_TEXTURE_CUBE_MAP;
|
||||
ret[dst].textureType = TextureType::TextureCube;
|
||||
break;
|
||||
case GLDescriptorMapping::Tex2DMS:
|
||||
target = eGL_TEXTURE_2D_MULTISAMPLE;
|
||||
ret[dst].textureType = TextureType::Texture2DMS;
|
||||
break;
|
||||
case GLDescriptorMapping::Tex2DMSArray:
|
||||
target = eGL_TEXTURE_2D_MULTISAMPLE_ARRAY;
|
||||
ret[dst].textureType = TextureType::Texture2DMSArray;
|
||||
break;
|
||||
case GLDescriptorMapping::AtomicCounter:
|
||||
case GLDescriptorMapping::ShaderStorage:
|
||||
case GLDescriptorMapping::BareUniforms:
|
||||
case GLDescriptorMapping::UniformBinding:
|
||||
case GLDescriptorMapping::Images:
|
||||
case GLDescriptorMapping::Invalid:
|
||||
case GLDescriptorMapping::Count: target = eGL_NONE; break;
|
||||
}
|
||||
}
|
||||
|
||||
if(target == eGL_NONE)
|
||||
continue;
|
||||
|
||||
GLenum binding = TextureBinding(target);
|
||||
|
||||
drv.glGetIntegerv(binding, (GLint *)&tex);
|
||||
|
||||
if(tex == 0)
|
||||
continue;
|
||||
|
||||
GLint firstMip = 0, numMips = 1;
|
||||
|
||||
if(target != eGL_TEXTURE_BUFFER)
|
||||
{
|
||||
drv.glGetTextureParameterivEXT(tex, target, eGL_TEXTURE_BASE_LEVEL, &firstMip);
|
||||
drv.glGetTextureParameterivEXT(tex, target, eGL_TEXTURE_MAX_LEVEL, &numMips);
|
||||
|
||||
numMips = numMips - firstMip + 1;
|
||||
}
|
||||
|
||||
ResourceId id = rm->GetResID(TextureRes(ctx, tex));
|
||||
ret[dst].resource = rm->GetOriginalID(id);
|
||||
ret[dst].firstMip = firstMip & 0xff;
|
||||
ret[dst].numMips = numMips & 0xff;
|
||||
|
||||
GLenum levelQueryType =
|
||||
target == eGL_TEXTURE_CUBE_MAP ? eGL_TEXTURE_CUBE_MAP_POSITIVE_X : target;
|
||||
GLenum fmt = eGL_NONE;
|
||||
drv.glGetTexLevelParameteriv(levelQueryType, 0, eGL_TEXTURE_INTERNAL_FORMAT, (GLint *)&fmt);
|
||||
ret[dst].format = MakeResourceFormat(target, fmt);
|
||||
if(IsDepthStencilFormat(fmt))
|
||||
{
|
||||
GLint depthMode = eGL_DEPTH_COMPONENT;
|
||||
|
||||
if(HasExt[ARB_stencil_texturing])
|
||||
drv.glGetTextureParameterivEXT(tex, target, eGL_DEPTH_STENCIL_TEXTURE_MODE, &depthMode);
|
||||
|
||||
ret[dst].format = ResourceFormat();
|
||||
ret[dst].format.type = ResourceFormatType::Regular;
|
||||
ret[dst].format.compByteWidth = 1;
|
||||
ret[dst].format.compCount = 1;
|
||||
if(depthMode == eGL_DEPTH_COMPONENT)
|
||||
ret[dst].format.compType = CompType::Depth;
|
||||
else if(depthMode == eGL_STENCIL_INDEX)
|
||||
ret[dst].format.compType = CompType::UInt;
|
||||
}
|
||||
|
||||
GLenum swizzles[4] = {eGL_RED, eGL_GREEN, eGL_BLUE, eGL_ALPHA};
|
||||
if(target != eGL_TEXTURE_BUFFER &&
|
||||
(HasExt[ARB_texture_swizzle] || HasExt[EXT_texture_swizzle]))
|
||||
GetTextureSwizzle(tex, target, swizzles);
|
||||
|
||||
ret[dst].swizzle.red = MakeSwizzle(swizzles[0]);
|
||||
ret[dst].swizzle.green = MakeSwizzle(swizzles[1]);
|
||||
ret[dst].swizzle.blue = MakeSwizzle(swizzles[2]);
|
||||
ret[dst].swizzle.alpha = MakeSwizzle(swizzles[3]);
|
||||
|
||||
GLuint samp = 0;
|
||||
if(HasExt[ARB_sampler_objects])
|
||||
drv.glGetIntegerv(eGL_SAMPLER_BINDING, (GLint *)&samp);
|
||||
|
||||
ret[dst].secondary = rm->GetOriginalID(rm->GetResID(SamplerRes(ctx, samp)));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -2149,10 +2387,190 @@ rdcarray<SamplerDescriptor> GLReplay::GetSamplerDescriptors(ResourceId descripto
|
||||
return ret;
|
||||
}
|
||||
|
||||
MakeCurrentReplayContext(&m_ReplayCtx);
|
||||
WrappedOpenGL &drv = *m_pDriver;
|
||||
GLResourceManager *rm = m_pDriver->GetResourceManager();
|
||||
|
||||
ContextPair &ctx = drv.GetCtx();
|
||||
|
||||
size_t count = 0;
|
||||
for(const DescriptorRange &r : ranges)
|
||||
count += r.count;
|
||||
ret.resize(count);
|
||||
|
||||
size_t dst = 0;
|
||||
for(const DescriptorRange &r : ranges)
|
||||
{
|
||||
uint32_t descriptorId = r.offset;
|
||||
|
||||
for(uint32_t i = 0; i < r.count; i++, dst++, descriptorId++)
|
||||
{
|
||||
GLDescriptorLocation idx = DecodeGLDescriptorIndex(descriptorId);
|
||||
|
||||
if(idx.type == GLDescriptorMapping::Invalid || idx.type == GLDescriptorMapping::Images ||
|
||||
idx.type == GLDescriptorMapping::AtomicCounter ||
|
||||
idx.type == GLDescriptorMapping::ShaderStorage ||
|
||||
idx.type == GLDescriptorMapping::UniformBinding)
|
||||
continue;
|
||||
|
||||
drv.glActiveTexture(GLenum(eGL_TEXTURE0 + idx.idx));
|
||||
|
||||
GLuint tex = 0;
|
||||
GLenum target = eGL_NONE;
|
||||
|
||||
if(idx.type == GLDescriptorMapping::TexCubeArray && !HasExt[ARB_texture_cube_map_array])
|
||||
{
|
||||
tex = 0;
|
||||
target = eGL_TEXTURE_CUBE_MAP_ARRAY;
|
||||
}
|
||||
else
|
||||
{
|
||||
switch(idx.type)
|
||||
{
|
||||
case GLDescriptorMapping::Tex1D: target = eGL_TEXTURE_1D; break;
|
||||
case GLDescriptorMapping::Tex2D: target = eGL_TEXTURE_2D; break;
|
||||
case GLDescriptorMapping::Tex3D: target = eGL_TEXTURE_3D; break;
|
||||
case GLDescriptorMapping::Tex1DArray: target = eGL_TEXTURE_1D_ARRAY; break;
|
||||
case GLDescriptorMapping::Tex2DArray: target = eGL_TEXTURE_2D_ARRAY; break;
|
||||
case GLDescriptorMapping::TexCubeArray: target = eGL_TEXTURE_CUBE_MAP_ARRAY; break;
|
||||
case GLDescriptorMapping::TexRect: target = eGL_TEXTURE_RECTANGLE; break;
|
||||
case GLDescriptorMapping::TexBuffer: target = eGL_TEXTURE_BUFFER; break;
|
||||
case GLDescriptorMapping::TexCube: target = eGL_TEXTURE_CUBE_MAP; break;
|
||||
case GLDescriptorMapping::Tex2DMS: target = eGL_TEXTURE_2D_MULTISAMPLE; break;
|
||||
case GLDescriptorMapping::Tex2DMSArray: target = eGL_TEXTURE_2D_MULTISAMPLE_ARRAY; break;
|
||||
case GLDescriptorMapping::AtomicCounter:
|
||||
case GLDescriptorMapping::ShaderStorage:
|
||||
case GLDescriptorMapping::BareUniforms:
|
||||
case GLDescriptorMapping::UniformBinding:
|
||||
case GLDescriptorMapping::Images:
|
||||
case GLDescriptorMapping::Invalid:
|
||||
case GLDescriptorMapping::Count: target = eGL_NONE; break;
|
||||
}
|
||||
}
|
||||
|
||||
if(target == eGL_NONE)
|
||||
continue;
|
||||
|
||||
GLenum binding = TextureBinding(target);
|
||||
|
||||
GLuint samp = 0;
|
||||
if(HasExt[ARB_sampler_objects])
|
||||
drv.glGetIntegerv(eGL_SAMPLER_BINDING, (GLint *)&samp);
|
||||
|
||||
drv.glGetIntegerv(binding, (GLint *)&tex);
|
||||
|
||||
if(samp == 0 && tex == 0)
|
||||
continue;
|
||||
|
||||
ret[dst].object = rm->GetOriginalID(rm->GetResID(SamplerRes(ctx, samp)));
|
||||
|
||||
// GL has separate sampler objects but they don't exist as separate sampler descriptors
|
||||
ret[dst].type = DescriptorType::ImageSampler;
|
||||
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameterfv(samp, eGL_TEXTURE_BORDER_COLOR,
|
||||
ret[dst].borderColorValue.floatValue.data());
|
||||
else
|
||||
drv.glGetTextureParameterfvEXT(tex, target, eGL_TEXTURE_BORDER_COLOR,
|
||||
ret[dst].borderColorValue.floatValue.data());
|
||||
|
||||
ret[dst].borderColorType = CompType::Float;
|
||||
|
||||
GLint v;
|
||||
v = 0;
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameteriv(samp, eGL_TEXTURE_WRAP_S, &v);
|
||||
else
|
||||
drv.glGetTextureParameterivEXT(tex, target, eGL_TEXTURE_WRAP_S, &v);
|
||||
ret[dst].addressU = MakeAddressMode((GLenum)v);
|
||||
|
||||
v = 0;
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameteriv(samp, eGL_TEXTURE_WRAP_T, &v);
|
||||
else
|
||||
drv.glGetTextureParameterivEXT(tex, target, eGL_TEXTURE_WRAP_T, &v);
|
||||
ret[dst].addressV = MakeAddressMode((GLenum)v);
|
||||
|
||||
v = 0;
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameteriv(samp, eGL_TEXTURE_WRAP_R, &v);
|
||||
else
|
||||
drv.glGetTextureParameterivEXT(tex, target, eGL_TEXTURE_WRAP_R, &v);
|
||||
ret[dst].addressW = MakeAddressMode((GLenum)v);
|
||||
|
||||
// GLES 3 is always seamless
|
||||
if(IsGLES && GLCoreVersion > 30)
|
||||
{
|
||||
ret[dst].seamlessCubemaps = true;
|
||||
}
|
||||
else if(!IsGLES)
|
||||
{
|
||||
// on GLES 2 this is always going to be false, GL has a toggle
|
||||
ret[dst].seamlessCubemaps = drv.glIsEnabled(eGL_TEXTURE_CUBE_MAP_SEAMLESS) != GL_FALSE;
|
||||
}
|
||||
|
||||
v = 0;
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameteriv(samp, eGL_TEXTURE_COMPARE_FUNC, &v);
|
||||
else
|
||||
drv.glGetTextureParameterivEXT(tex, target, eGL_TEXTURE_COMPARE_FUNC, &v);
|
||||
ret[dst].compareFunction = MakeCompareFunc((GLenum)v);
|
||||
|
||||
GLint minf = 0;
|
||||
GLint magf = 0;
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameteriv(samp, eGL_TEXTURE_MIN_FILTER, &minf);
|
||||
else
|
||||
drv.glGetTextureParameterivEXT(tex, target, eGL_TEXTURE_MIN_FILTER, &minf);
|
||||
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameteriv(samp, eGL_TEXTURE_MAG_FILTER, &magf);
|
||||
else
|
||||
drv.glGetTextureParameterivEXT(tex, target, eGL_TEXTURE_MAG_FILTER, &magf);
|
||||
|
||||
if(HasExt[ARB_texture_filter_anisotropic])
|
||||
{
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameterfv(samp, eGL_TEXTURE_MAX_ANISOTROPY, &ret[dst].maxAnisotropy);
|
||||
else
|
||||
drv.glGetTextureParameterfvEXT(tex, target, eGL_TEXTURE_MAX_ANISOTROPY,
|
||||
&ret[dst].maxAnisotropy);
|
||||
}
|
||||
else
|
||||
{
|
||||
ret[dst].maxAnisotropy = 0.0f;
|
||||
}
|
||||
|
||||
ret[dst].filter = MakeFilter((GLenum)minf, (GLenum)magf, ret[dst].maxAnisotropy);
|
||||
|
||||
v = 0;
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameteriv(samp, eGL_TEXTURE_COMPARE_MODE, &v);
|
||||
else
|
||||
drv.glGetTextureParameterivEXT(tex, target, eGL_TEXTURE_COMPARE_MODE, &v);
|
||||
ret[dst].filter.filter = (GLenum)v == eGL_COMPARE_REF_TO_TEXTURE ? FilterFunction::Comparison
|
||||
: FilterFunction::Normal;
|
||||
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameterfv(samp, eGL_TEXTURE_MAX_LOD, &ret[dst].maxLOD);
|
||||
else
|
||||
drv.glGetTextureParameterfvEXT(tex, target, eGL_TEXTURE_MAX_LOD, &ret[dst].maxLOD);
|
||||
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameterfv(samp, eGL_TEXTURE_MIN_LOD, &ret[dst].minLOD);
|
||||
else
|
||||
drv.glGetTextureParameterfvEXT(tex, target, eGL_TEXTURE_MIN_LOD, &ret[dst].minLOD);
|
||||
|
||||
if(!IsGLES)
|
||||
{
|
||||
if(samp != 0)
|
||||
drv.glGetSamplerParameterfv(samp, eGL_TEXTURE_LOD_BIAS, &ret[dst].mipBias);
|
||||
else
|
||||
drv.glGetTextureParameterfvEXT(tex, target, eGL_TEXTURE_LOD_BIAS, &ret[dst].mipBias);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
@@ -2052,9 +2052,9 @@ GLint CubeTargetIndex(GLenum face)
|
||||
return 0;
|
||||
}
|
||||
|
||||
GLenum TextureTarget(GLenum target)
|
||||
GLenum TextureTarget(GLenum binding)
|
||||
{
|
||||
switch(target)
|
||||
switch(binding)
|
||||
{
|
||||
case eGL_TEXTURE_BINDING_1D: return eGL_TEXTURE_1D;
|
||||
case eGL_TEXTURE_BINDING_1D_ARRAY: return eGL_TEXTURE_1D_ARRAY;
|
||||
@@ -2076,7 +2076,7 @@ GLenum TextureTarget(GLenum target)
|
||||
default: break;
|
||||
}
|
||||
|
||||
return target;
|
||||
return binding;
|
||||
}
|
||||
|
||||
bool IsProxyTarget(GLenum target)
|
||||
|
||||
@@ -61,7 +61,7 @@ GLenum GetViewCastedFormat(GLenum internalFormat, CompType typeCast);
|
||||
bool IsCubeFace(GLenum target);
|
||||
GLint CubeTargetIndex(GLenum face);
|
||||
GLenum TextureBinding(GLenum target);
|
||||
GLenum TextureTarget(GLenum target);
|
||||
GLenum TextureTarget(GLenum binding);
|
||||
bool IsProxyTarget(GLenum target);
|
||||
|
||||
GLenum BufferBinding(GLenum target);
|
||||
|
||||
@@ -1435,6 +1435,10 @@ void DoSerialise(SerialiserType &ser, D3D11Pipe::State &el)
|
||||
SERIALISE_MEMBER(pixelShader);
|
||||
SERIALISE_MEMBER(computeShader);
|
||||
|
||||
SERIALISE_MEMBER(descriptorStore);
|
||||
SERIALISE_MEMBER(descriptorCount);
|
||||
SERIALISE_MEMBER(descriptorByteSize);
|
||||
|
||||
SERIALISE_MEMBER(streamOut);
|
||||
|
||||
SERIALISE_MEMBER(rasterizer);
|
||||
@@ -1442,7 +1446,7 @@ void DoSerialise(SerialiserType &ser, D3D11Pipe::State &el)
|
||||
|
||||
SERIALISE_MEMBER(predication);
|
||||
|
||||
SIZE_CHECK(2088);
|
||||
SIZE_CHECK(2104);
|
||||
}
|
||||
|
||||
#pragma endregion D3D11 pipeline state
|
||||
@@ -2026,6 +2030,10 @@ void DoSerialise(SerialiserType &ser, GLPipe::State &el)
|
||||
SERIALISE_MEMBER(shaderStorageBuffers);
|
||||
SERIALISE_MEMBER(images);
|
||||
|
||||
SERIALISE_MEMBER(descriptorStore);
|
||||
SERIALISE_MEMBER(descriptorCount);
|
||||
SERIALISE_MEMBER(descriptorByteSize);
|
||||
|
||||
SERIALISE_MEMBER(transformFeedback);
|
||||
|
||||
SERIALISE_MEMBER(rasterizer);
|
||||
@@ -2036,7 +2044,7 @@ void DoSerialise(SerialiserType &ser, GLPipe::State &el)
|
||||
|
||||
SERIALISE_MEMBER(hints);
|
||||
|
||||
SIZE_CHECK(1952);
|
||||
SIZE_CHECK(1968);
|
||||
}
|
||||
|
||||
#pragma endregion OpenGL pipeline state
|
||||
|
||||
Reference in New Issue
Block a user