Merge pull request #3424 from ReinUsesLisp/spirv-layer

vk_shader_decompiler: Implement Layer output attribute
This commit is contained in:
bunnei 2020-02-22 23:45:16 -05:00 committed by GitHub
commit 2b4cdb73b6
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -86,6 +86,7 @@ struct AttributeType {
struct VertexIndices { struct VertexIndices {
std::optional<u32> position; std::optional<u32> position;
std::optional<u32> layer;
std::optional<u32> viewport; std::optional<u32> viewport;
std::optional<u32> point_size; std::optional<u32> point_size;
std::optional<u32> clip_distances; std::optional<u32> clip_distances;
@ -284,9 +285,11 @@ public:
AddExtension("SPV_KHR_variable_pointers"); AddExtension("SPV_KHR_variable_pointers");
AddExtension("SPV_KHR_shader_draw_parameters"); AddExtension("SPV_KHR_shader_draw_parameters");
if (ir.UsesViewportIndex()) { if (ir.UsesLayer() || ir.UsesViewportIndex()) {
AddCapability(spv::Capability::MultiViewport); if (ir.UsesViewportIndex()) {
if (device.IsExtShaderViewportIndexLayerSupported()) { AddCapability(spv::Capability::MultiViewport);
}
if (stage != ShaderType::Geometry && device.IsExtShaderViewportIndexLayerSupported()) {
AddExtension("SPV_EXT_shader_viewport_index_layer"); AddExtension("SPV_EXT_shader_viewport_index_layer");
AddCapability(spv::Capability::ShaderViewportIndexLayerEXT); AddCapability(spv::Capability::ShaderViewportIndexLayerEXT);
} }
@ -928,13 +931,22 @@ private:
VertexIndices indices; VertexIndices indices;
indices.position = AddBuiltIn(t_float4, spv::BuiltIn::Position, "position"); indices.position = AddBuiltIn(t_float4, spv::BuiltIn::Position, "position");
if (ir.UsesLayer()) {
if (stage != ShaderType::Vertex || device.IsExtShaderViewportIndexLayerSupported()) {
indices.layer = AddBuiltIn(t_int, spv::BuiltIn::Layer, "layer");
} else {
LOG_ERROR(
Render_Vulkan,
"Shader requires Layer but it's not supported on this stage with this device.");
}
}
if (ir.UsesViewportIndex()) { if (ir.UsesViewportIndex()) {
if (stage != ShaderType::Vertex || device.IsExtShaderViewportIndexLayerSupported()) { if (stage != ShaderType::Vertex || device.IsExtShaderViewportIndexLayerSupported()) {
indices.viewport = AddBuiltIn(t_int, spv::BuiltIn::ViewportIndex, "viewport_index"); indices.viewport = AddBuiltIn(t_int, spv::BuiltIn::ViewportIndex, "viewport_index");
} else { } else {
LOG_ERROR(Render_Vulkan, LOG_ERROR(Render_Vulkan, "Shader requires ViewportIndex but it's not supported on "
"Shader requires ViewportIndex but it's not supported on this " "this stage with this device.");
"stage with this device.");
} }
} }
@ -1296,6 +1308,13 @@ private:
} }
case Attribute::Index::LayerViewportPointSize: case Attribute::Index::LayerViewportPointSize:
switch (element) { switch (element) {
case 1: {
if (!out_indices.layer) {
return {};
}
const u32 index = out_indices.layer.value();
return {AccessElement(t_out_int, out_vertex, index), Type::Int};
}
case 2: { case 2: {
if (!out_indices.viewport) { if (!out_indices.viewport) {
return {}; return {};
@ -1366,6 +1385,11 @@ private:
UNIMPLEMENTED(); UNIMPLEMENTED();
} }
if (!target.id) {
// On failure we return a nullptr target.id, skip these stores.
return {};
}
OpStore(target.id, As(Visit(src), target.type)); OpStore(target.id, As(Visit(src), target.type));
return {}; return {};
} }