Commit 09591b87 by Nicolas Capens Committed by Nicolas Capens

Pass descriptor sets to SPIR-V compilation

The at draw time currently bound descriptors are passed down to the SPIR-V code generation so that we can read the sampler parameters and image view parameters. An important exception is compute shaders, which are currently compiled before the invoke calls. Also still TODO is taking the parameters into account during routine lookup in the cache. This change also eliminates the now unused 'enableMask' from PixelProgram and VertexProgram. Bug b/129523279 Change-Id: I1ea75ec5a7b83783a1efacb238143a419afa5bda Reviewed-on: https://swiftshader-review.googlesource.com/c/SwiftShader/+/28446Tested-by: 's avatarNicolas Capens <nicolascapens@google.com> Reviewed-by: 's avatarBen Clayton <bclayton@google.com> Kokoro-Presubmit: kokoro <noreply+kokoro@google.com>
parent 82eb22e2
...@@ -30,7 +30,7 @@ namespace vk ...@@ -30,7 +30,7 @@ namespace vk
class DescriptorSet; class DescriptorSet;
class ImageView; class ImageView;
class PipelineLayout; class PipelineLayout;
} // namespace vk }
namespace sw namespace sw
{ {
......
...@@ -349,7 +349,7 @@ namespace sw ...@@ -349,7 +349,7 @@ namespace sw
if(!routine) if(!routine)
{ {
QuadRasterizer *generator = new PixelProgram(state, context->pipelineLayout, context->pixelShader); QuadRasterizer *generator = new PixelProgram(state, context->pipelineLayout, context->pixelShader, context->descriptorSets);
generator->generate(); generator->generate();
routine = (*generator)("PixelRoutine_%0.8X", state.shaderID); routine = (*generator)("PixelRoutine_%0.8X", state.shaderID);
delete generator; delete generator;
......
...@@ -142,7 +142,7 @@ namespace sw ...@@ -142,7 +142,7 @@ namespace sw
if(!routine) // Create one if(!routine) // Create one
{ {
VertexRoutine *generator = new VertexProgram(state, context->pipelineLayout, context->vertexShader); VertexRoutine *generator = new VertexProgram(state, context->pipelineLayout, context->vertexShader, context->descriptorSets);
generator->generate(); generator->generate();
routine = (*generator)("VertexRoutine_%0.8X", state.shaderID); routine = (*generator)("VertexRoutine_%0.8X", state.shaderID);
delete generator; delete generator;
......
...@@ -24,11 +24,12 @@ namespace ...@@ -24,11 +24,12 @@ namespace
namespace sw namespace sw
{ {
ComputeProgram::ComputeProgram(SpirvShader const *shader, vk::PipelineLayout const *pipelineLayout) ComputeProgram::ComputeProgram(SpirvShader const *shader, vk::PipelineLayout const *pipelineLayout, const vk::DescriptorSet::Bindings &descriptorSets)
: data(Arg<0>()), : data(Arg<0>()),
routine(pipelineLayout), routine(pipelineLayout),
shader(shader), shader(shader),
pipelineLayout(pipelineLayout) pipelineLayout(pipelineLayout),
descriptorSets(descriptorSets)
{ {
} }
...@@ -157,7 +158,7 @@ namespace sw ...@@ -157,7 +158,7 @@ namespace sw
}); });
// Process numLanes of the workgroup. // Process numLanes of the workgroup.
shader->emit(&routine, activeLaneMask); shader->emit(&routine, activeLaneMask, descriptorSets);
} }
} }
......
...@@ -39,7 +39,7 @@ namespace sw ...@@ -39,7 +39,7 @@ namespace sw
class ComputeProgram : public Function<Void(Pointer<Byte>)> class ComputeProgram : public Function<Void(Pointer<Byte>)>
{ {
public: public:
ComputeProgram(SpirvShader const *spirvShader, vk::PipelineLayout const *pipelineLayout); ComputeProgram(SpirvShader const *spirvShader, vk::PipelineLayout const *pipelineLayout, const vk::DescriptorSet::Bindings &descriptorSets);
virtual ~ComputeProgram(); virtual ~ComputeProgram();
...@@ -74,6 +74,7 @@ namespace sw ...@@ -74,6 +74,7 @@ namespace sw
SpirvRoutine routine; SpirvRoutine routine;
SpirvShader const * const shader; SpirvShader const * const shader;
vk::PipelineLayout const * const pipelineLayout; vk::PipelineLayout const * const pipelineLayout;
const vk::DescriptorSet::Bindings &descriptorSets;
}; };
} // namespace sw } // namespace sw
......
...@@ -29,14 +29,12 @@ namespace sw ...@@ -29,14 +29,12 @@ namespace sw
void PixelProgram::applyShader(Int cMask[4]) void PixelProgram::applyShader(Int cMask[4])
{ {
enableIndex = 0;
routine.descriptorSets = data + OFFSET(DrawData, descriptorSets); routine.descriptorSets = data + OFFSET(DrawData, descriptorSets);
routine.descriptorDynamicOffsets = data + OFFSET(DrawData, descriptorDynamicOffsets); routine.descriptorDynamicOffsets = data + OFFSET(DrawData, descriptorDynamicOffsets);
routine.pushConstants = data + OFFSET(DrawData, pushConstants); routine.pushConstants = data + OFFSET(DrawData, pushConstants);
auto activeLaneMask = SIMD::Int(0xFFFFFFFF); // TODO: Control this. auto activeLaneMask = SIMD::Int(0xFFFFFFFF); // TODO: Control this.
spirvShader->emit(&routine, activeLaneMask); spirvShader->emit(&routine, activeLaneMask, descriptorSets);
spirvShader->emitEpilog(&routine); spirvShader->emitEpilog(&routine);
for(int i = 0; i < RENDERTARGETS; i++) for(int i = 0; i < RENDERTARGETS; i++)
...@@ -232,12 +230,6 @@ namespace sw ...@@ -232,12 +230,6 @@ namespace sw
} }
} }
Int4 PixelProgram::enableMask()
{
Int4 enable = true ? Int4(enableStack[enableIndex]) : Int4(0xFFFFFFFF);
return enable;
}
Float4 PixelProgram::linearToSRGB(const Float4 &x) // Approximates x^(1.0/2.2) Float4 PixelProgram::linearToSRGB(const Float4 &x) // Approximates x^(1.0/2.2)
{ {
Float4 sqrtx = Rcp_pp(RcpSqrt_pp(x)); Float4 sqrtx = Rcp_pp(RcpSqrt_pp(x));
......
...@@ -26,8 +26,9 @@ namespace sw ...@@ -26,8 +26,9 @@ namespace sw
PixelProgram( PixelProgram(
const PixelProcessor::State &state, const PixelProcessor::State &state,
vk::PipelineLayout const *pipelineLayout, vk::PipelineLayout const *pipelineLayout,
SpirvShader const *spirvShader) : SpirvShader const *spirvShader,
PixelRoutine(state, pipelineLayout, spirvShader) const vk::DescriptorSet::Bindings &descriptorSets) :
PixelRoutine(state, pipelineLayout, spirvShader, descriptorSets)
{ {
} }
...@@ -43,15 +44,9 @@ namespace sw ...@@ -43,15 +44,9 @@ namespace sw
// Color outputs // Color outputs
Vector4f c[RENDERTARGETS]; Vector4f c[RENDERTARGETS];
// Per pixel based on conditions reached
Int enableIndex;
Array<Int4, 1 + 24> enableStack;
// Raster operations // Raster operations
void clampColor(Vector4f oC[RENDERTARGETS]); void clampColor(Vector4f oC[RENDERTARGETS]);
Int4 enableMask();
Float4 linearToSRGB(const Float4 &x); Float4 linearToSRGB(const Float4 &x);
}; };
} }
......
...@@ -35,9 +35,11 @@ namespace sw ...@@ -35,9 +35,11 @@ namespace sw
PixelRoutine::PixelRoutine( PixelRoutine::PixelRoutine(
const PixelProcessor::State &state, const PixelProcessor::State &state,
vk::PipelineLayout const *pipelineLayout, vk::PipelineLayout const *pipelineLayout,
SpirvShader const *spirvShader) SpirvShader const *spirvShader,
const vk::DescriptorSet::Bindings &descriptorSets)
: QuadRasterizer(state, spirvShader), : QuadRasterizer(state, spirvShader),
routine(pipelineLayout) routine(pipelineLayout),
descriptorSets(descriptorSets)
{ {
spirvShader->emitProlog(&routine); spirvShader->emitProlog(&routine);
......
...@@ -27,7 +27,8 @@ namespace sw ...@@ -27,7 +27,8 @@ namespace sw
public: public:
PixelRoutine(const PixelProcessor::State &state, PixelRoutine(const PixelProcessor::State &state,
vk::PipelineLayout const *pipelineLayout, vk::PipelineLayout const *pipelineLayout,
SpirvShader const *spirvShader); SpirvShader const *spirvShader,
const vk::DescriptorSet::Bindings &descriptorSets);
virtual ~PixelRoutine(); virtual ~PixelRoutine();
...@@ -37,6 +38,7 @@ namespace sw ...@@ -37,6 +38,7 @@ namespace sw
Float4 rhw; // Reciprocal w Float4 rhw; // Reciprocal w
SpirvRoutine routine; SpirvRoutine routine;
const vk::DescriptorSet::Bindings &descriptorSets;
// Depth output // Depth output
Float4 oDepth; Float4 oDepth;
......
...@@ -19,6 +19,7 @@ ...@@ -19,6 +19,7 @@
#include "Vulkan/VkDebug.hpp" #include "Vulkan/VkDebug.hpp"
#include "Vulkan/VkDescriptorSet.hpp" #include "Vulkan/VkDescriptorSet.hpp"
#include "Vulkan/VkPipelineLayout.hpp" #include "Vulkan/VkPipelineLayout.hpp"
#include "Vulkan/VkDescriptorSetLayout.hpp"
#include "Device/Config.hpp" #include "Device/Config.hpp"
#include <spirv/unified1/spirv.hpp> #include <spirv/unified1/spirv.hpp>
...@@ -1371,11 +1372,9 @@ namespace sw ...@@ -1371,11 +1372,9 @@ namespace sw
} }
} }
void SpirvShader::emit(SpirvRoutine *routine, RValue<SIMD::Int> const &activeLaneMask) const void SpirvShader::emit(SpirvRoutine *routine, RValue<SIMD::Int> const &activeLaneMask, const vk::DescriptorSet::Bindings &descriptorSets) const
{ {
EmitState state; EmitState state(routine, activeLaneMask, descriptorSets);
state.setActiveLaneMask(activeLaneMask);
state.routine = routine;
// Emit everything up to the first label // Emit everything up to the first label
// TODO: Separate out dispatch of block from non-block instructions? // TODO: Separate out dispatch of block from non-block instructions?
......
...@@ -20,6 +20,7 @@ ...@@ -20,6 +20,7 @@
#include "System/Types.hpp" #include "System/Types.hpp"
#include "Vulkan/VkDebug.hpp" #include "Vulkan/VkDebug.hpp"
#include "Vulkan/VkConfig.h" #include "Vulkan/VkConfig.h"
#include "Vulkan/VkDescriptorSet.hpp"
#include "Device/Config.hpp" #include "Device/Config.hpp"
#include <spirv/unified1/spirv.hpp> #include <spirv/unified1/spirv.hpp>
...@@ -480,7 +481,7 @@ namespace sw ...@@ -480,7 +481,7 @@ namespace sw
std::vector<InterfaceComponent> outputs; std::vector<InterfaceComponent> outputs;
void emitProlog(SpirvRoutine *routine) const; void emitProlog(SpirvRoutine *routine) const;
void emit(SpirvRoutine *routine, RValue<SIMD::Int> const &activeLaneMask) const; void emit(SpirvRoutine *routine, RValue<SIMD::Int> const &activeLaneMask, const vk::DescriptorSet::Bindings &descriptorSets) const;
void emitEpilog(SpirvRoutine *routine) const; void emitEpilog(SpirvRoutine *routine) const;
using BuiltInHash = std::hash<std::underlying_type<spv::BuiltIn>::type>; using BuiltInHash = std::hash<std::underlying_type<spv::BuiltIn>::type>;
...@@ -610,6 +611,13 @@ namespace sw ...@@ -610,6 +611,13 @@ namespace sw
class EmitState class EmitState
{ {
public: public:
EmitState(SpirvRoutine *routine, RValue<SIMD::Int> activeLaneMask, const vk::DescriptorSet::Bindings &descriptorSets)
: routine(routine),
activeLaneMaskValue(activeLaneMask.value),
descriptorSets(descriptorSets)
{
}
RValue<SIMD::Int> activeLaneMask() const RValue<SIMD::Int> activeLaneMask() const
{ {
ASSERT(activeLaneMaskValue != nullptr); ASSERT(activeLaneMaskValue != nullptr);
...@@ -638,6 +646,8 @@ namespace sw ...@@ -638,6 +646,8 @@ namespace sw
Block::Set visited; // Blocks already built. Block::Set visited; // Blocks already built.
std::unordered_map<Block::Edge, RValue<SIMD::Int>, Block::Edge::Hash> edgeActiveLaneMasks; std::unordered_map<Block::Edge, RValue<SIMD::Int>, Block::Edge::Hash> edgeActiveLaneMasks;
std::queue<Block::ID> *pending; std::queue<Block::ID> *pending;
const vk::DescriptorSet::Bindings &descriptorSets;
}; };
// EmitResult is an enumerator of result values from the Emit functions. // EmitResult is an enumerator of result values from the Emit functions.
......
...@@ -27,16 +27,11 @@ namespace sw ...@@ -27,16 +27,11 @@ namespace sw
VertexProgram::VertexProgram( VertexProgram::VertexProgram(
const VertexProcessor::State &state, const VertexProcessor::State &state,
vk::PipelineLayout const *pipelineLayout, vk::PipelineLayout const *pipelineLayout,
SpirvShader const *spirvShader) SpirvShader const *spirvShader,
: VertexRoutine(state, pipelineLayout, spirvShader) const vk::DescriptorSet::Bindings &descriptorSets)
: VertexRoutine(state, pipelineLayout, spirvShader),
descriptorSets(descriptorSets)
{ {
ifDepth = 0;
loopRepDepth = 0;
currentLabel = -1;
whileTest = false;
enableStack[0] = Int4(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF);
auto it = spirvShader->inputBuiltins.find(spv::BuiltInInstanceIndex); auto it = spirvShader->inputBuiltins.find(spv::BuiltInInstanceIndex);
if (it != spirvShader->inputBuiltins.end()) if (it != spirvShader->inputBuiltins.end())
{ {
...@@ -57,10 +52,6 @@ namespace sw ...@@ -57,10 +52,6 @@ namespace sw
void VertexProgram::program(UInt &index) void VertexProgram::program(UInt &index)
{ {
// shader->print("VertexShader-%0.8X.txt", state.shaderID);
enableIndex = 0;
auto it = spirvShader->inputBuiltins.find(spv::BuiltInVertexIndex); auto it = spirvShader->inputBuiltins.find(spv::BuiltInVertexIndex);
if (it != spirvShader->inputBuiltins.end()) if (it != spirvShader->inputBuiltins.end())
{ {
...@@ -70,20 +61,8 @@ namespace sw ...@@ -70,20 +61,8 @@ namespace sw
} }
auto activeLaneMask = SIMD::Int(0xFFFFFFFF); // TODO: Control this. auto activeLaneMask = SIMD::Int(0xFFFFFFFF); // TODO: Control this.
spirvShader->emit(&routine, activeLaneMask); spirvShader->emit(&routine, activeLaneMask, descriptorSets);
if(currentLabel != -1)
{
Nucleus::setInsertBlock(returnBlock);
}
spirvShader->emitEpilog(&routine); spirvShader->emitEpilog(&routine);
} }
Int4 VertexProgram::enableMask()
{
Int4 enable = true ? Int4(enableStack[enableIndex]) : Int4(0xFFFFFFFF);
return enable;
}
} }
...@@ -32,31 +32,15 @@ namespace sw ...@@ -32,31 +32,15 @@ namespace sw
VertexProgram( VertexProgram(
const VertexProcessor::State &state, const VertexProcessor::State &state,
vk::PipelineLayout const *pipelineLayout, vk::PipelineLayout const *pipelineLayout,
SpirvShader const *spirvShader); SpirvShader const *spirvShader,
const vk::DescriptorSet::Bindings &descriptorSets);
virtual ~VertexProgram(); virtual ~VertexProgram();
private: private:
Int enableIndex;
Array<Int4, 1 + 24> enableStack;
void program(UInt &index) override; void program(UInt &index) override;
RValue<Pointer<Byte>> uniformAddress(int bufferIndex, unsigned int index);
RValue<Pointer<Byte>> uniformAddress(int bufferIndex, unsigned int index, Int &offset); const vk::DescriptorSet::Bindings &descriptorSets;
Int4 enableMask();
int ifDepth;
int loopRepDepth;
int currentLabel;
bool whileTest;
BasicBlock *ifFalseBlock[24 + 24];
BasicBlock *loopRepTestBlock[4];
BasicBlock *loopRepEndBlock[4];
BasicBlock *labelBlock[2048];
std::vector<BasicBlock*> callRetBlock[2048];
BasicBlock *returnBlock;
bool isConditionalIf[24 + 24];
}; };
} }
......
...@@ -505,10 +505,10 @@ void ComputePipeline::compileShaders(const VkAllocationCallbacks* pAllocator, co ...@@ -505,10 +505,10 @@ void ComputePipeline::compileShaders(const VkAllocationCallbacks* pAllocator, co
ASSERT(shader == nullptr); ASSERT(shader == nullptr);
// FIXME (b/119409619): use allocator. // FIXME(b/119409619): use allocator.
shader = new sw::SpirvShader(code); shader = new sw::SpirvShader(code);
vk::DescriptorSet::Bindings descriptorSets; // FIXME(b/129523279): Delay code generation until invoke time.
sw::ComputeProgram program(shader, layout); sw::ComputeProgram program(shader, layout, descriptorSets);
program.generate(); program.generate();
......
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