Commit 618bebcd by Olli Etuaho Committed by Commit Bot

Pass texture base level to shaders on D3D11

The base level is passed to shaders in an array included in the driver uniform block. This is done on feature levels above 9_3, which treat samplers as indices to sampler arrays in shaders. A separate uniform block couldn't be used for the sampler metadata, since that would bring the number of available uniform blocks down to below minimum level defined by GLES 3.0. BUG=angleproject:596 TEST=angle_end2end_tests Change-Id: Ie040521402f9996d51a978aeeba9222e9dd761ce Reviewed-on: https://chromium-review.googlesource.com/326290Reviewed-by: 's avatarCorentin Wallez <cwallez@chromium.org> Commit-Queue: Olli Etuaho <oetuaho@nvidia.com>
parent d14e3c45
......@@ -512,6 +512,11 @@ void OutputHLSL::header(TInfoSinkBase &out, const BuiltInFunctionEmulator *built
out << " float2 dx_ViewScale : packoffset(c3);\n";
}
if (mOutputType == SH_HLSL_4_1_OUTPUT)
{
mUniformHLSL->samplerMetadataUniforms(out, "c4");
}
out << "};\n";
}
else
......@@ -614,6 +619,11 @@ void OutputHLSL::header(TInfoSinkBase &out, const BuiltInFunctionEmulator *built
out << " float2 dx_ViewCoords : packoffset(c2);\n";
out << " float2 dx_ViewScale : packoffset(c3);\n";
if (mOutputType == SH_HLSL_4_1_OUTPUT)
{
mUniformHLSL->samplerMetadataUniforms(out, "c4");
}
out << "};\n"
"\n";
}
......
......@@ -246,6 +246,15 @@ void UniformHLSL::uniformsHeader(TInfoSinkBase &out,
}
}
void UniformHLSL::samplerMetadataUniforms(TInfoSinkBase &out, const char *reg)
{
// If mSamplerRegister is 0 the shader doesn't use any textures.
if (mSamplerRegister > 0)
{
out << " int samplerMetadata[" << mSamplerRegister << "] : packoffset(" << reg << ");\n";
}
}
TString UniformHLSL::interfaceBlocksHeader(const ReferencedSymbols &referencedInterfaceBlocks)
{
TString interfaceBlocks;
......
......@@ -31,6 +31,10 @@ class UniformHLSL : angle::NonCopyable
void uniformsHeader(TInfoSinkBase &out,
ShShaderOutput outputType,
const ReferencedSymbols &referencedUniforms);
// Must be called after uniformsHeader
void samplerMetadataUniforms(TInfoSinkBase &out, const char *reg);
TString interfaceBlocksHeader(const ReferencedSymbols &referencedInterfaceBlocks);
// Used for direct index references
......
......@@ -661,7 +661,7 @@ GLenum ProgramD3D::getSamplerTextureType(gl::SamplerType type, unsigned int samp
return GL_TEXTURE_2D;
}
GLint ProgramD3D::getUsedSamplerRange(gl::SamplerType type) const
GLuint ProgramD3D::getUsedSamplerRange(gl::SamplerType type) const
{
switch (type)
{
......@@ -671,7 +671,7 @@ GLint ProgramD3D::getUsedSamplerRange(gl::SamplerType type) const
return mUsedVertexSamplerRange;
default:
UNREACHABLE();
return 0;
return 0u;
}
}
......
......@@ -145,7 +145,7 @@ class ProgramD3D : public ProgramImpl
unsigned int samplerIndex,
const gl::Caps &caps) const;
GLenum getSamplerTextureType(gl::SamplerType type, unsigned int samplerIndex) const;
GLint getUsedSamplerRange(gl::SamplerType type) const;
GLuint getUsedSamplerRange(gl::SamplerType type) const;
void updateSamplerMapping();
bool usesPointSize() const { return mUsesPointSize; }
......
......@@ -282,7 +282,7 @@ gl::Error RendererD3D::generateSwizzles(const gl::Data &data, gl::SamplerType ty
{
ProgramD3D *programD3D = GetImplAs<ProgramD3D>(data.state->getProgram());
unsigned int samplerRange = static_cast<unsigned int>(programD3D->getUsedSamplerRange(type));
unsigned int samplerRange = programD3D->getUsedSamplerRange(type);
for (unsigned int i = 0; i < samplerRange; i++)
{
......
......@@ -14,6 +14,7 @@
#include "libANGLE/AttributeMap.h"
#include "libANGLE/angletypes.h"
#include "libANGLE/renderer/d3d/HLSLCompiler.h"
#include "libANGLE/renderer/d3d/ProgramD3D.h"
#include "libANGLE/renderer/d3d/RendererD3D.h"
#include "libANGLE/renderer/d3d/RenderTargetD3D.h"
#include "libANGLE/renderer/d3d/d3d11/DebugAnnotator11.h"
......@@ -336,6 +337,36 @@ class Renderer11 : public RendererD3D
void updateHistograms();
class SamplerMetadataD3D11 final : angle::NonCopyable
{
public:
SamplerMetadataD3D11();
~SamplerMetadataD3D11();
struct dx_SamplerMetadata
{
int baseLevel[4];
};
void initData(unsigned int samplerCount);
void update(unsigned int samplerIndex, unsigned int baseLevel);
const dx_SamplerMetadata *getData() const;
size_t sizeBytes() const;
bool isDirty() const { return mDirty; }
private:
std::vector<dx_SamplerMetadata> mSamplerMetadata;
bool mDirty;
};
template <class TShaderConstants>
void applyDriverConstantsIfNeeded(TShaderConstants *appliedConstants,
const TShaderConstants &constants,
SamplerMetadataD3D11 *samplerMetadata,
size_t samplerMetadataReferencedBytes,
ID3D11Buffer *driverConstantBuffer);
HMODULE mD3d11Module;
HMODULE mDxgiModule;
HMODULE mDCompModule;
......@@ -395,6 +426,7 @@ class Renderer11 : public RendererD3D
dx_VertexConstants11 mAppliedVertexConstants;
ID3D11Buffer *mDriverConstantBufferVS;
SamplerMetadataD3D11 mSamplerMetadataVS;
ID3D11Buffer *mCurrentVertexConstantBuffer;
unsigned int mCurrentConstantBufferVS[gl::IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS];
GLintptr mCurrentConstantBufferVSOffset[gl::IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS];
......@@ -402,6 +434,7 @@ class Renderer11 : public RendererD3D
dx_PixelConstants11 mAppliedPixelConstants;
ID3D11Buffer *mDriverConstantBufferPS;
SamplerMetadataD3D11 mSamplerMetadataPS;
ID3D11Buffer *mCurrentPixelConstantBuffer;
unsigned int mCurrentConstantBufferPS[gl::IMPLEMENTATION_MAX_FRAGMENT_SHADER_UNIFORM_BUFFERS];
GLintptr mCurrentConstantBufferPSOffset[gl::IMPLEMENTATION_MAX_FRAGMENT_SHADER_UNIFORM_BUFFERS];
......
......@@ -754,21 +754,19 @@ static size_t GetMaximumVertexUniformVectors(D3D_FEATURE_LEVEL featureLevel)
}
}
static size_t GetReservedVertexUniformBuffers()
{
// Reserve one buffer for the application uniforms, and one for driver uniforms
return 2;
}
static size_t GetMaximumVertexUniformBlocks(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
case D3D_FEATURE_LEVEL_11_1:
case D3D_FEATURE_LEVEL_11_0: return D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT - GetReservedVertexUniformBuffers();
case D3D_FEATURE_LEVEL_11_0:
return D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT -
d3d11::RESERVED_CONSTANT_BUFFER_SLOT_COUNT;
case D3D_FEATURE_LEVEL_10_1:
case D3D_FEATURE_LEVEL_10_0: return D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT - GetReservedVertexUniformBuffers();
case D3D_FEATURE_LEVEL_10_0:
return D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT -
d3d11::RESERVED_CONSTANT_BUFFER_SLOT_COUNT;
// Uniform blocks not supported on D3D11 Feature Level 9
case D3D_FEATURE_LEVEL_9_3:
......@@ -871,21 +869,19 @@ static size_t GetMaximumPixelUniformVectors(D3D_FEATURE_LEVEL featureLevel)
}
}
static size_t GetReservedPixelUniformBuffers()
{
// Reserve one buffer for the application uniforms, and one for driver uniforms
return 2;
}
static size_t GetMaximumPixelUniformBlocks(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
case D3D_FEATURE_LEVEL_11_1:
case D3D_FEATURE_LEVEL_11_0: return D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT - GetReservedPixelUniformBuffers();
case D3D_FEATURE_LEVEL_11_0:
return D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT -
d3d11::RESERVED_CONSTANT_BUFFER_SLOT_COUNT;
case D3D_FEATURE_LEVEL_10_1:
case D3D_FEATURE_LEVEL_10_0: return D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT - GetReservedPixelUniformBuffers();
case D3D_FEATURE_LEVEL_10_0:
return D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT -
d3d11::RESERVED_CONSTANT_BUFFER_SLOT_COUNT;
// Uniform blocks not supported on D3D11 Feature Level 9
case D3D_FEATURE_LEVEL_9_3:
......@@ -1501,6 +1497,16 @@ WorkaroundsD3D GenerateWorkarounds(D3D_FEATURE_LEVEL featureLevel)
return workarounds;
}
void InitConstantBufferDesc(D3D11_BUFFER_DESC *constantBufferDescription, size_t byteWidth)
{
constantBufferDescription->ByteWidth = static_cast<UINT>(byteWidth);
constantBufferDescription->Usage = D3D11_USAGE_DYNAMIC;
constantBufferDescription->BindFlags = D3D11_BIND_CONSTANT_BUFFER;
constantBufferDescription->CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
constantBufferDescription->MiscFlags = 0;
constantBufferDescription->StructureByteStride = 0;
}
} // namespace d3d11
TextureHelper11::TextureHelper11()
......
......@@ -343,6 +343,16 @@ void SetBufferData(ID3D11DeviceContext *context, ID3D11Buffer *constantBuffer, c
}
WorkaroundsD3D GenerateWorkarounds(D3D_FEATURE_LEVEL featureLevel);
enum ReservedConstantBufferSlot
{
RESERVED_CONSTANT_BUFFER_SLOT_DEFAULT_UNIFORM_BLOCK = 0,
RESERVED_CONSTANT_BUFFER_SLOT_DRIVER = 1,
RESERVED_CONSTANT_BUFFER_SLOT_COUNT = 2
};
void InitConstantBufferDesc(D3D11_BUFFER_DESC *constantBufferDescription, size_t byteWidth);
} // namespace d3d11
// A helper class which wraps a 2D or 3D texture.
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment