Browse Source

[vk] Line rasterization and Alpha features adjusments (again)

pull/3115/head
CamilleLaVey 4 weeks ago
parent
commit
a6fd8c82ca
  1. 47
      src/video_core/renderer_vulkan/vk_graphics_pipeline.cpp
  2. 52
      src/video_core/renderer_vulkan/vk_rasterizer.cpp
  3. 39
      src/video_core/vulkan_common/vulkan_device.cpp
  4. 55
      src/video_core/vulkan_common/vulkan_device.h

47
src/video_core/renderer_vulkan/vk_graphics_pipeline.cpp

@ -735,13 +735,18 @@ void GraphicsPipeline::MakePipeline(VkRenderPass render_pass) {
.lineWidth = 1.0f, .lineWidth = 1.0f,
// TODO(alekpop): Transfer from regs // TODO(alekpop): Transfer from regs
}; };
const bool smooth_lines_supported =
device.IsExtLineRasterizationSupported() && device.SupportsSmoothLines();
const bool stippled_lines_supported =
device.IsExtLineRasterizationSupported() && device.SupportsStippledRectangularLines();
VkPipelineRasterizationLineStateCreateInfoEXT line_state{ VkPipelineRasterizationLineStateCreateInfoEXT line_state{
.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_LINE_STATE_CREATE_INFO_EXT, .sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_LINE_STATE_CREATE_INFO_EXT,
.pNext = nullptr, .pNext = nullptr,
.lineRasterizationMode = key.state.smooth_lines != 0
.lineRasterizationMode = key.state.smooth_lines != 0 && smooth_lines_supported
? VK_LINE_RASTERIZATION_MODE_RECTANGULAR_SMOOTH_EXT ? VK_LINE_RASTERIZATION_MODE_RECTANGULAR_SMOOTH_EXT
: VK_LINE_RASTERIZATION_MODE_RECTANGULAR_EXT, : VK_LINE_RASTERIZATION_MODE_RECTANGULAR_EXT,
.stippledLineEnable = dynamic.line_stipple_enable ? VK_TRUE : VK_FALSE,
.stippledLineEnable =
(dynamic.line_stipple_enable && stippled_lines_supported) ? VK_TRUE : VK_FALSE,
.lineStippleFactor = key.state.line_stipple_factor, .lineStippleFactor = key.state.line_stipple_factor,
.lineStipplePattern = static_cast<uint16_t>(key.state.line_stipple_pattern), .lineStipplePattern = static_cast<uint16_t>(key.state.line_stipple_pattern),
}; };
@ -773,6 +778,7 @@ void GraphicsPipeline::MakePipeline(VkRenderPass render_pass) {
} }
const bool supports_alpha_output = fragment_has_color0_output; const bool supports_alpha_output = fragment_has_color0_output;
const bool alpha_to_one_supported = device.SupportsAlphaToOne();
const VkPipelineMultisampleStateCreateInfo multisample_ci{ const VkPipelineMultisampleStateCreateInfo multisample_ci{
.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO, .sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO,
.pNext = nullptr, .pNext = nullptr,
@ -783,8 +789,8 @@ void GraphicsPipeline::MakePipeline(VkRenderPass render_pass) {
.pSampleMask = nullptr, .pSampleMask = nullptr,
.alphaToCoverageEnable = .alphaToCoverageEnable =
supports_alpha_output && key.state.alpha_to_coverage_enabled != 0 ? VK_TRUE : VK_FALSE, supports_alpha_output && key.state.alpha_to_coverage_enabled != 0 ? VK_TRUE : VK_FALSE,
.alphaToOneEnable =
supports_alpha_output && key.state.alpha_to_one_enabled != 0 ? VK_TRUE : VK_FALSE,
.alphaToOneEnable = supports_alpha_output && alpha_to_one_supported &&
key.state.alpha_to_one_enabled != 0 ? VK_TRUE : VK_FALSE,
}; };
const VkPipelineDepthStencilStateCreateInfo depth_stencil_ci{ const VkPipelineDepthStencilStateCreateInfo depth_stencil_ci{
.sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO, .sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO,
@ -899,18 +905,29 @@ void GraphicsPipeline::MakePipeline(VkRenderPass render_pass) {
dynamic_states.insert(dynamic_states.end(), extended3.begin(), extended3.end()); dynamic_states.insert(dynamic_states.end(), extended3.begin(), extended3.end());
} }
// EDS3 - Enables (composite: 9 states)
// EDS3 - Enables (composite: per-feature)
if (key.state.extended_dynamic_state_3_enables) { if (key.state.extended_dynamic_state_3_enables) {
static constexpr std::array extended3{
VK_DYNAMIC_STATE_DEPTH_CLAMP_ENABLE_EXT,
VK_DYNAMIC_STATE_LOGIC_OP_ENABLE_EXT,
VK_DYNAMIC_STATE_LINE_RASTERIZATION_MODE_EXT,
VK_DYNAMIC_STATE_CONSERVATIVE_RASTERIZATION_MODE_EXT,
VK_DYNAMIC_STATE_LINE_STIPPLE_ENABLE_EXT,
VK_DYNAMIC_STATE_ALPHA_TO_COVERAGE_ENABLE_EXT,
VK_DYNAMIC_STATE_ALPHA_TO_ONE_ENABLE_EXT,
};
dynamic_states.insert(dynamic_states.end(), extended3.begin(), extended3.end());
if (device.SupportsDynamicState3DepthClampEnable()) {
dynamic_states.push_back(VK_DYNAMIC_STATE_DEPTH_CLAMP_ENABLE_EXT);
}
if (device.SupportsDynamicState3LogicOpEnable()) {
dynamic_states.push_back(VK_DYNAMIC_STATE_LOGIC_OP_ENABLE_EXT);
}
if (device.SupportsDynamicState3LineRasterizationMode()) {
dynamic_states.push_back(VK_DYNAMIC_STATE_LINE_RASTERIZATION_MODE_EXT);
}
if (device.SupportsDynamicState3ConservativeRasterizationMode()) {
dynamic_states.push_back(VK_DYNAMIC_STATE_CONSERVATIVE_RASTERIZATION_MODE_EXT);
}
if (device.SupportsDynamicState3LineStippleEnable()) {
dynamic_states.push_back(VK_DYNAMIC_STATE_LINE_STIPPLE_ENABLE_EXT);
}
if (device.SupportsDynamicState3AlphaToCoverageEnable()) {
dynamic_states.push_back(VK_DYNAMIC_STATE_ALPHA_TO_COVERAGE_ENABLE_EXT);
}
if (device.SupportsDynamicState3AlphaToOneEnable()) {
dynamic_states.push_back(VK_DYNAMIC_STATE_ALPHA_TO_ONE_ENABLE_EXT);
}
} }
const VkPipelineDynamicStateCreateInfo dynamic_state_ci{ const VkPipelineDynamicStateCreateInfo dynamic_state_ci{

52
src/video_core/renderer_vulkan/vk_rasterizer.cpp

@ -1430,6 +1430,10 @@ void RasterizerVulkan::UpdateConservativeRasterizationMode(Tegra::Engines::Maxwe
return; return;
} }
if (!device.SupportsDynamicState3ConservativeRasterizationMode()) {
return;
}
scheduler.Record([enable = regs.conservative_raster_enable](vk::CommandBuffer cmdbuf) { scheduler.Record([enable = regs.conservative_raster_enable](vk::CommandBuffer cmdbuf) {
cmdbuf.SetConservativeRasterizationModeEXT( cmdbuf.SetConservativeRasterizationModeEXT(
enable ? VK_CONSERVATIVE_RASTERIZATION_MODE_OVERESTIMATE_EXT enable ? VK_CONSERVATIVE_RASTERIZATION_MODE_OVERESTIMATE_EXT
@ -1442,6 +1446,10 @@ void RasterizerVulkan::UpdateLineStippleEnable(Tegra::Engines::Maxwell3D::Regs&
return; return;
} }
if (!device.SupportsDynamicState3LineStippleEnable()) {
return;
}
scheduler.Record([enable = regs.line_stipple_enable](vk::CommandBuffer cmdbuf) { scheduler.Record([enable = regs.line_stipple_enable](vk::CommandBuffer cmdbuf) {
cmdbuf.SetLineStippleEnableEXT(enable); cmdbuf.SetLineStippleEnableEXT(enable);
}); });
@ -1455,9 +1463,30 @@ void RasterizerVulkan::UpdateLineRasterizationMode(Tegra::Engines::Maxwell3D::Re
return; return;
} }
const VkLineRasterizationModeEXT mode =
regs.line_anti_alias_enable != 0 ? VK_LINE_RASTERIZATION_MODE_RECTANGULAR_SMOOTH_EXT
: VK_LINE_RASTERIZATION_MODE_RECTANGULAR_EXT;
if (!device.SupportsDynamicState3LineRasterizationMode()) {
static std::once_flag warn_missing_rect;
std::call_once(warn_missing_rect, [] {
LOG_WARNING(Render_Vulkan,
"Driver lacks rectangular line rasterization support; skipping dynamic "
"line state updates");
});
return;
}
const bool wants_smooth = regs.line_anti_alias_enable != 0;
VkLineRasterizationModeEXT mode = VK_LINE_RASTERIZATION_MODE_RECTANGULAR_EXT;
if (wants_smooth) {
if (device.SupportsSmoothLines()) {
mode = VK_LINE_RASTERIZATION_MODE_RECTANGULAR_SMOOTH_EXT;
} else {
static std::once_flag warn_missing_smooth;
std::call_once(warn_missing_smooth, [] {
LOG_WARNING(Render_Vulkan,
"Line anti-aliasing requested but smoothLines feature unavailable; "
"using rectangular rasterization");
});
}
}
scheduler.Record([mode](vk::CommandBuffer cmdbuf) { scheduler.Record([mode](vk::CommandBuffer cmdbuf) {
cmdbuf.SetLineRasterizationModeEXT(mode); cmdbuf.SetLineRasterizationModeEXT(mode);
}); });
@ -1502,6 +1531,9 @@ void RasterizerVulkan::UpdateLogicOpEnable(Tegra::Engines::Maxwell3D::Regs& regs
if (!state_tracker.TouchLogicOpEnable()) { if (!state_tracker.TouchLogicOpEnable()) {
return; return;
} }
if (!device.SupportsDynamicState3LogicOpEnable()) {
return;
}
scheduler.Record([enable = regs.logic_op.enable](vk::CommandBuffer cmdbuf) { scheduler.Record([enable = regs.logic_op.enable](vk::CommandBuffer cmdbuf) {
cmdbuf.SetLogicOpEnableEXT(enable != 0); cmdbuf.SetLogicOpEnableEXT(enable != 0);
}); });
@ -1511,6 +1543,9 @@ void RasterizerVulkan::UpdateDepthClampEnable(Tegra::Engines::Maxwell3D::Regs& r
if (!state_tracker.TouchDepthClampEnable()) { if (!state_tracker.TouchDepthClampEnable()) {
return; return;
} }
if (!device.SupportsDynamicState3DepthClampEnable()) {
return;
}
bool is_enabled = !(regs.viewport_clip_control.geometry_clip == bool is_enabled = !(regs.viewport_clip_control.geometry_clip ==
Maxwell::ViewportClipControl::GeometryClip::Passthrough || Maxwell::ViewportClipControl::GeometryClip::Passthrough ||
regs.viewport_clip_control.geometry_clip == regs.viewport_clip_control.geometry_clip ==
@ -1525,6 +1560,9 @@ void RasterizerVulkan::UpdateAlphaToCoverageEnable(Tegra::Engines::Maxwell3D::Re
if (!state_tracker.TouchAlphaToCoverageEnable()) { if (!state_tracker.TouchAlphaToCoverageEnable()) {
return; return;
} }
if (!device.SupportsDynamicState3AlphaToCoverageEnable()) {
return;
}
GraphicsPipeline* const pipeline = pipeline_cache.CurrentGraphicsPipeline(); GraphicsPipeline* const pipeline = pipeline_cache.CurrentGraphicsPipeline();
const bool enable = pipeline != nullptr && pipeline->SupportsAlphaToCoverage() && const bool enable = pipeline != nullptr && pipeline->SupportsAlphaToCoverage() &&
regs.anti_alias_alpha_control.alpha_to_coverage != 0; regs.anti_alias_alpha_control.alpha_to_coverage != 0;
@ -1537,6 +1575,14 @@ void RasterizerVulkan::UpdateAlphaToOneEnable(Tegra::Engines::Maxwell3D::Regs& r
if (!state_tracker.TouchAlphaToOneEnable()) { if (!state_tracker.TouchAlphaToOneEnable()) {
return; return;
} }
if (!device.SupportsDynamicState3AlphaToOneEnable()) {
static std::once_flag warn_alpha_to_one;
std::call_once(warn_alpha_to_one, [] {
LOG_WARNING(Render_Vulkan,
"Alpha-to-one is not supported on this device; forcing it disabled");
});
return;
}
GraphicsPipeline* const pipeline = pipeline_cache.CurrentGraphicsPipeline(); GraphicsPipeline* const pipeline = pipeline_cache.CurrentGraphicsPipeline();
const bool enable = pipeline != nullptr && pipeline->SupportsAlphaToOne() && const bool enable = pipeline != nullptr && pipeline->SupportsAlphaToOne() &&
regs.anti_alias_alpha_control.alpha_to_one != 0; regs.anti_alias_alpha_control.alpha_to_one != 0;

39
src/video_core/vulkan_common/vulkan_device.cpp

@ -1259,26 +1259,45 @@ void Device::RemoveUnsuitableExtensions() {
features.extended_dynamic_state3.extendedDynamicState3LogicOpEnable; features.extended_dynamic_state3.extendedDynamicState3LogicOpEnable;
const bool supports_line_raster_mode = const bool supports_line_raster_mode =
features.extended_dynamic_state3.extendedDynamicState3LineRasterizationMode && features.extended_dynamic_state3.extendedDynamicState3LineRasterizationMode &&
extensions.line_rasterization;
extensions.line_rasterization && features.line_rasterization.rectangularLines;
const bool supports_conservative_raster_mode = const bool supports_conservative_raster_mode =
features.extended_dynamic_state3.extendedDynamicState3ConservativeRasterizationMode && features.extended_dynamic_state3.extendedDynamicState3ConservativeRasterizationMode &&
extensions.conservative_rasterization; extensions.conservative_rasterization;
const bool supports_line_stipple_enable = const bool supports_line_stipple_enable =
features.extended_dynamic_state3.extendedDynamicState3LineStippleEnable && features.extended_dynamic_state3.extendedDynamicState3LineStippleEnable &&
extensions.line_rasterization;
extensions.line_rasterization && features.line_rasterization.stippledRectangularLines;
const bool supports_alpha_to_coverage = const bool supports_alpha_to_coverage =
features.extended_dynamic_state3.extendedDynamicState3AlphaToCoverageEnable; features.extended_dynamic_state3.extendedDynamicState3AlphaToCoverageEnable;
const bool supports_alpha_to_one = const bool supports_alpha_to_one =
features.extended_dynamic_state3.extendedDynamicState3AlphaToOneEnable;
dynamic_state3_enables = supports_depth_clamp_enable && supports_logic_op_enable &&
supports_line_raster_mode && supports_conservative_raster_mode &&
supports_line_stipple_enable && supports_alpha_to_coverage &&
supports_alpha_to_one;
features.extended_dynamic_state3.extendedDynamicState3AlphaToOneEnable &&
features.features.alphaToOne;
dynamic_state3_depth_clamp_enable = supports_depth_clamp_enable;
dynamic_state3_logic_op_enable = supports_logic_op_enable;
dynamic_state3_line_raster_mode = supports_line_raster_mode;
dynamic_state3_conservative_raster_mode = supports_conservative_raster_mode;
dynamic_state3_line_stipple_enable = supports_line_stipple_enable;
dynamic_state3_alpha_to_coverage = supports_alpha_to_coverage;
dynamic_state3_alpha_to_one = supports_alpha_to_one;
dynamic_state3_enables = dynamic_state3_depth_clamp_enable || dynamic_state3_logic_op_enable ||
dynamic_state3_line_raster_mode ||
dynamic_state3_conservative_raster_mode ||
dynamic_state3_line_stipple_enable ||
dynamic_state3_alpha_to_coverage || dynamic_state3_alpha_to_one;
extensions.extended_dynamic_state3 = dynamic_state3_blending || dynamic_state3_enables; extensions.extended_dynamic_state3 = dynamic_state3_blending || dynamic_state3_enables;
dynamic_state3_blending = dynamic_state3_blending && extensions.extended_dynamic_state3;
dynamic_state3_enables = dynamic_state3_enables && extensions.extended_dynamic_state3;
if (!extensions.extended_dynamic_state3) {
dynamic_state3_blending = false;
dynamic_state3_enables = false;
dynamic_state3_depth_clamp_enable = false;
dynamic_state3_logic_op_enable = false;
dynamic_state3_line_raster_mode = false;
dynamic_state3_conservative_raster_mode = false;
dynamic_state3_line_stipple_enable = false;
dynamic_state3_alpha_to_coverage = false;
dynamic_state3_alpha_to_one = false;
}
RemoveExtensionFeatureIfUnsuitable(extensions.extended_dynamic_state3, RemoveExtensionFeatureIfUnsuitable(extensions.extended_dynamic_state3,
features.extended_dynamic_state3, features.extended_dynamic_state3,
VK_EXT_EXTENDED_DYNAMIC_STATE_3_EXTENSION_NAME); VK_EXT_EXTENDED_DYNAMIC_STATE_3_EXTENSION_NAME);

55
src/video_core/vulkan_common/vulkan_device.h

@ -638,6 +638,50 @@ public:
return extensions.line_rasterization; return extensions.line_rasterization;
} }
bool SupportsRectangularLines() const {
return features.line_rasterization.rectangularLines != VK_FALSE;
}
bool SupportsSmoothLines() const {
return features.line_rasterization.smoothLines != VK_FALSE;
}
bool SupportsStippledRectangularLines() const {
return features.line_rasterization.stippledRectangularLines != VK_FALSE;
}
bool SupportsAlphaToOne() const {
return features.features.alphaToOne != VK_FALSE;
}
bool SupportsDynamicState3DepthClampEnable() const {
return dynamic_state3_depth_clamp_enable;
}
bool SupportsDynamicState3LogicOpEnable() const {
return dynamic_state3_logic_op_enable;
}
bool SupportsDynamicState3LineRasterizationMode() const {
return dynamic_state3_line_raster_mode;
}
bool SupportsDynamicState3ConservativeRasterizationMode() const {
return dynamic_state3_conservative_raster_mode;
}
bool SupportsDynamicState3LineStippleEnable() const {
return dynamic_state3_line_stipple_enable;
}
bool SupportsDynamicState3AlphaToCoverageEnable() const {
return dynamic_state3_alpha_to_coverage;
}
bool SupportsDynamicState3AlphaToOneEnable() const {
return dynamic_state3_alpha_to_one;
}
/// Returns true if the device supports VK_EXT_vertex_input_dynamic_state. /// Returns true if the device supports VK_EXT_vertex_input_dynamic_state.
bool IsExtVertexInputDynamicStateSupported() const { bool IsExtVertexInputDynamicStateSupported() const {
return extensions.vertex_input_dynamic_state; return extensions.vertex_input_dynamic_state;
@ -986,8 +1030,15 @@ private:
bool cant_blit_msaa{}; ///< Does not support MSAA<->MSAA blitting. bool cant_blit_msaa{}; ///< Does not support MSAA<->MSAA blitting.
bool must_emulate_scaled_formats{}; ///< Requires scaled vertex format emulation bool must_emulate_scaled_formats{}; ///< Requires scaled vertex format emulation
bool must_emulate_bgr565{}; ///< Emulates BGR565 by swizzling RGB565 format. bool must_emulate_bgr565{}; ///< Emulates BGR565 by swizzling RGB565 format.
bool dynamic_state3_blending{}; ///< Has all blending features of dynamic_state3.
bool dynamic_state3_enables{}; ///< Has all enables features of dynamic_state3.
bool dynamic_state3_blending{}; ///< Has blending features of dynamic_state3.
bool dynamic_state3_enables{}; ///< Has at least one enable feature of dynamic_state3.
bool dynamic_state3_depth_clamp_enable{};
bool dynamic_state3_logic_op_enable{};
bool dynamic_state3_line_raster_mode{};
bool dynamic_state3_conservative_raster_mode{};
bool dynamic_state3_line_stipple_enable{};
bool dynamic_state3_alpha_to_coverage{};
bool dynamic_state3_alpha_to_one{};
bool supports_conditional_barriers{}; ///< Allows barriers in conditional control flow. bool supports_conditional_barriers{}; ///< Allows barriers in conditional control flow.
u64 device_access_memory{}; ///< Total size of device local memory in bytes. u64 device_access_memory{}; ///< Total size of device local memory in bytes.
u32 sets_per_pool{}; ///< Sets per Description Pool u32 sets_per_pool{}; ///< Sets per Description Pool

Loading…
Cancel
Save