vk/graphics_state, tu: Rewrite renderpass flags handling

Before this, the render pass code or the driver combined the pipeline
create flags and the implicit flags from the render pass, but the
pipeline create flags will need to be sanitized when they are dynamic
state, so we need to do it in vk_graphics_state where we know that
information.

We also weren't combining pipeline flags correctly when linking, which
on turnip was being hidden by the lack of sanitizing for driver-provided
flags. We can't combine them correctly if they're part of the render
pass state, so they need to be pulled out into the overall pipeline
state.

For drivers using emulated renderpasses or tracking feedback loop
information themselves, this won't make a difference, but we have to
adapt turnip to not pass pipeline flags. This also means that we can
drop all handling of feedback_loop_input_only in turnip and just set it
in the runtime.

Reviewed-by: Lionel Landwerlin <lionel.g.landwerlin@intel.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/25436>
This commit is contained in:
Connor Abbott 2023-05-24 19:33:38 +02:00 committed by Marge Bot
parent 2b62d90158
commit 55f3f952aa
12 changed files with 112 additions and 81 deletions

View file

@ -298,7 +298,7 @@ radv_pipeline_uses_vrs_attachment(const struct radv_graphics_pipeline *pipeline,
{
VkPipelineCreateFlags2KHR create_flags = pipeline->base.create_flags;
if (state->rp)
create_flags |= state->rp->pipeline_flags;
create_flags |= state->pipeline_flags;
return (create_flags & VK_PIPELINE_CREATE_2_RENDERING_FRAGMENT_SHADING_RATE_ATTACHMENT_BIT_KHR) != 0;
}
@ -697,7 +697,7 @@ radv_pipeline_import_graphics_info(struct radv_device *device, struct radv_graph
pipeline->active_stages |= sinfo->stage;
}
result = vk_graphics_pipeline_state_fill(&device->vk, state, pCreateInfo, NULL, NULL, NULL,
result = vk_graphics_pipeline_state_fill(&device->vk, state, pCreateInfo, NULL, 0, NULL, NULL,
VK_SYSTEM_ALLOCATION_SCOPE_OBJECT, &pipeline->state_data);
if (result != VK_SUCCESS)
return result;
@ -821,7 +821,7 @@ radv_pipeline_uses_ds_feedback_loop(const struct radv_graphics_pipeline *pipelin
{
VkPipelineCreateFlags2KHR create_flags = pipeline->base.create_flags;
if (state->rp)
create_flags |= state->rp->pipeline_flags;
create_flags |= state->pipeline_flags;
return (create_flags & VK_PIPELINE_CREATE_2_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT) != 0;
}

View file

@ -3774,7 +3774,7 @@ tu_pipeline_builder_parse_rasterization_order(
* setting the SINGLE_PRIM_MODE field to the same value that the blob does
* for advanced_blend in sysmem mode if a feedback loop is detected.
*/
if (builder->graphics_state.rp->pipeline_flags &
if (builder->graphics_state.pipeline_flags &
(VK_PIPELINE_CREATE_2_COLOR_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT |
VK_PIPELINE_CREATE_2_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT)) {
sysmem_prim_mode = FLUSH_PER_OVERLAP_AND_OVERWRITE;
@ -3966,15 +3966,13 @@ tu_pipeline_builder_build(struct tu_pipeline_builder *builder,
vk_dynamic_graphics_state_fill(&gfx_pipeline->dynamic_state,
&builder->graphics_state);
gfx_pipeline->feedback_loop_color =
(builder->graphics_state.rp->pipeline_flags &
(builder->graphics_state.pipeline_flags &
VK_PIPELINE_CREATE_2_COLOR_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT);
gfx_pipeline->feedback_loop_ds =
(builder->graphics_state.rp->pipeline_flags &
(builder->graphics_state.pipeline_flags &
VK_PIPELINE_CREATE_2_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT);
gfx_pipeline->feedback_loop_may_involve_textures =
(gfx_pipeline->feedback_loop_color ||
gfx_pipeline->feedback_loop_ds) &&
!builder->graphics_state.rp->feedback_loop_input_only;
builder->graphics_state.feedback_loop_not_input_only;
}
return VK_SUCCESS;
@ -3993,7 +3991,6 @@ tu_fill_render_pass_state(struct vk_render_pass_state *rp,
{
rp->view_mask = subpass->multiview_mask;
rp->color_attachment_count = subpass->color_count;
rp->pipeline_flags = 0;
const uint32_t a = subpass->depth_stencil_attachment.attachment;
rp->depth_attachment_format = VK_FORMAT_UNDEFINED;
@ -4094,6 +4091,7 @@ tu_pipeline_builder_init_graphics(
struct vk_render_pass_state rp_state = {};
const struct vk_render_pass_state *driver_rp = NULL;
VkPipelineCreateFlags2KHR rp_flags = 0;
builder->unscaled_input_fragcoord = 0;
@ -4114,8 +4112,6 @@ tu_pipeline_builder_init_graphics(
tu_fill_render_pass_state(&rp_state, pass, subpass);
rp_state.feedback_loop_input_only = true;
for (unsigned i = 0; i < subpass->input_count; i++) {
/* Input attachments stored in GMEM must be loaded with unscaled
* FragCoord.
@ -4124,29 +4120,18 @@ tu_pipeline_builder_init_graphics(
builder->unscaled_input_fragcoord |= 1u << i;
}
/* Feedback loop flags can come from either the user (in which case they
* may involve textures) or from the driver (in which case they don't).
*/
VkPipelineCreateFlags feedback_flags = builder->create_flags &
(VK_PIPELINE_CREATE_2_COLOR_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT |
VK_PIPELINE_CREATE_2_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT);
if (feedback_flags) {
rp_state.feedback_loop_input_only = false;
rp_state.pipeline_flags |= feedback_flags;
}
if (subpass->feedback_loop_color) {
rp_state.pipeline_flags |=
rp_flags |=
VK_PIPELINE_CREATE_2_COLOR_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT;
}
if (subpass->feedback_loop_ds) {
rp_state.pipeline_flags |=
rp_flags |=
VK_PIPELINE_CREATE_2_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT;
}
if (pass->fragment_density_map.attachment != VK_ATTACHMENT_UNUSED) {
rp_state.pipeline_flags |=
rp_flags |=
VK_PIPELINE_CREATE_2_RENDERING_FRAGMENT_DENSITY_MAP_ATTACHMENT_BIT_EXT;
}
@ -4166,12 +4151,13 @@ tu_pipeline_builder_init_graphics(
&builder->graphics_state,
builder->create_info,
driver_rp,
rp_flags,
&builder->all_state,
NULL, VK_SYSTEM_ALLOCATION_SCOPE_OBJECT,
NULL);
if (builder->graphics_state.rp) {
builder->fragment_density_map = (builder->graphics_state.rp->pipeline_flags &
builder->fragment_density_map = (builder->graphics_state.pipeline_flags &
VK_PIPELINE_CREATE_2_RENDERING_FRAGMENT_DENSITY_MAP_ATTACHMENT_BIT_EXT) ||
TU_DEBUG(FDM);
}

View file

@ -853,7 +853,7 @@ lvp_graphics_pipeline_init(struct lvp_pipeline *pipeline,
result = vk_graphics_pipeline_state_fill(&device->vk,
&pipeline->graphics_state,
pCreateInfo, NULL, NULL, NULL,
pCreateInfo, NULL, 0, NULL, NULL,
VK_SYSTEM_ALLOCATION_SCOPE_OBJECT,
&pipeline->state_data);
if (result != VK_SUCCESS)

View file

@ -2297,6 +2297,7 @@ pvr_graphics_pipeline_init(struct pvr_device *device,
&state,
pCreateInfo,
&rp_state,
0,
&all_state,
NULL,
0,

View file

@ -3050,7 +3050,8 @@ anv_graphics_lib_pipeline_create(struct anv_device *device,
result = vk_graphics_pipeline_state_fill(&device->vk,
&pipeline->state, pCreateInfo,
NULL /* sp_info */,
NULL /* driver_rp */,
0 /* driver_rp_flags */,
&pipeline->all_state, NULL, 0, NULL);
if (result != VK_SUCCESS) {
anv_pipeline_finish(&pipeline->base.base, device);
@ -3166,7 +3167,8 @@ anv_graphics_pipeline_create(struct anv_device *device,
}
result = vk_graphics_pipeline_state_fill(&device->vk, &state, pCreateInfo,
NULL /* sp_info */,
NULL /* driver_rp */,
0 /* driver_rp_flags */,
&all, NULL, 0, NULL);
if (result != VK_SUCCESS) {
anv_pipeline_finish(&pipeline->base.base, device);

View file

@ -1484,9 +1484,9 @@ emit_3dstate_gs(struct anv_graphics_pipeline *pipeline)
}
static bool
rp_has_ds_self_dep(const struct vk_render_pass_state *rp)
state_has_ds_self_dep(const struct vk_graphics_pipeline_state *state)
{
return rp->pipeline_flags &
return state->pipeline_flags &
VK_PIPELINE_CREATE_2_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT;
}
@ -1608,7 +1608,7 @@ emit_3dstate_ps(struct anv_graphics_pipeline *pipeline,
static void
emit_3dstate_ps_extra(struct anv_graphics_pipeline *pipeline,
const struct vk_rasterization_state *rs,
const struct vk_render_pass_state *rp)
const struct vk_graphics_pipeline_state *state)
{
const struct brw_wm_prog_data *wm_prog_data = get_wm_prog_data(pipeline);
@ -1633,7 +1633,7 @@ emit_3dstate_ps_extra(struct anv_graphics_pipeline *pipeline,
* around to fetching from the input attachment and we may get the depth
* or stencil value from the current draw rather than the previous one.
*/
ps.PixelShaderKillsPixel = rp_has_ds_self_dep(rp) ||
ps.PixelShaderKillsPixel = state_has_ds_self_dep(state) ||
wm_prog_data->uses_kill;
ps.PixelShaderComputesStencil = wm_prog_data->computed_stencil;
@ -1678,7 +1678,7 @@ emit_3dstate_vf_statistics(struct anv_graphics_pipeline *pipeline)
static void
compute_kill_pixel(struct anv_graphics_pipeline *pipeline,
const struct vk_multisample_state *ms,
const struct vk_render_pass_state *rp)
const struct vk_graphics_pipeline_state *state)
{
if (!anv_pipeline_has_stage(pipeline, MESA_SHADER_FRAGMENT)) {
pipeline->kill_pixel = false;
@ -1702,7 +1702,7 @@ compute_kill_pixel(struct anv_graphics_pipeline *pipeline,
* of an alpha test.
*/
pipeline->kill_pixel =
rp_has_ds_self_dep(rp) ||
state_has_ds_self_dep(state) ||
wm_prog_data->uses_kill ||
wm_prog_data->uses_omask ||
(ms && ms->alpha_to_coverage_enable);
@ -1905,7 +1905,7 @@ genX(graphics_pipeline_emit)(struct anv_graphics_pipeline *pipeline,
emit_rs_state(pipeline, state->ia, state->rs, state->ms, state->rp,
urb_deref_block_size);
emit_ms_state(pipeline, state->ms);
compute_kill_pixel(pipeline, state->ms, state->rp);
compute_kill_pixel(pipeline, state->ms, state);
emit_3dstate_clip(pipeline, state->ia, state->vp, state->rs);
@ -2003,7 +2003,7 @@ genX(graphics_pipeline_emit)(struct anv_graphics_pipeline *pipeline,
emit_3dstate_wm(pipeline, state->ia, state->rs,
state->ms, state->cb, state->rp);
emit_3dstate_ps(pipeline, state->ms, state->cb);
emit_3dstate_ps_extra(pipeline, state->rs, state->rp);
emit_3dstate_ps_extra(pipeline, state->rs, state);
}
#if GFX_VERx10 >= 125

View file

@ -1867,7 +1867,8 @@ anv_graphics_pipeline_create(struct anv_device *device,
struct vk_graphics_pipeline_all_state all;
struct vk_graphics_pipeline_state state = { };
result = vk_graphics_pipeline_state_fill(&device->vk, &state, pCreateInfo,
NULL /* sp_info */,
NULL /* driver_rp */,
0 /* driver_rp_flags */,
&all, NULL, 0, NULL);
if (result != VK_SUCCESS) {
vk_free2(&device->vk.alloc, pAllocator, pipeline);

View file

@ -1541,9 +1541,9 @@ emit_3dstate_gs(struct anv_graphics_pipeline *pipeline,
}
static bool
rp_has_ds_self_dep(const struct vk_render_pass_state *rp)
state_has_ds_self_dep(const struct vk_graphics_pipeline_state *state)
{
return rp->pipeline_flags &
return state->pipeline_flags &
VK_PIPELINE_CREATE_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT;
}
@ -1553,7 +1553,7 @@ emit_3dstate_wm(struct anv_graphics_pipeline *pipeline,
const struct vk_rasterization_state *rs,
const struct vk_multisample_state *ms,
const struct vk_color_blend_state *cb,
const struct vk_render_pass_state *rp)
const struct vk_graphics_pipeline_state *state)
{
const struct brw_wm_prog_data *wm_prog_data = get_wm_prog_data(pipeline);
@ -1612,7 +1612,7 @@ emit_3dstate_wm(struct anv_graphics_pipeline *pipeline,
* may get the depth or stencil value from the current draw rather
* than the previous one.
*/
wm.PixelShaderKillsPixel = rp_has_ds_self_dep(rp) ||
wm.PixelShaderKillsPixel = state_has_ds_self_dep(state) ||
wm_prog_data->uses_kill ||
wm_prog_data->uses_omask;
@ -1744,7 +1744,7 @@ emit_3dstate_ps(struct anv_graphics_pipeline *pipeline,
static void
emit_3dstate_ps_extra(struct anv_graphics_pipeline *pipeline,
const struct vk_rasterization_state *rs,
const struct vk_render_pass_state *rp)
const struct vk_graphics_pipeline_state *state)
{
const struct brw_wm_prog_data *wm_prog_data = get_wm_prog_data(pipeline);
@ -1769,7 +1769,7 @@ emit_3dstate_ps_extra(struct anv_graphics_pipeline *pipeline,
* around to fetching from the input attachment and we may get the depth
* or stencil value from the current draw rather than the previous one.
*/
ps.PixelShaderKillsPixel = rp_has_ds_self_dep(rp) ||
ps.PixelShaderKillsPixel = state_has_ds_self_dep(state) ||
wm_prog_data->uses_kill;
ps.PixelShaderUsesInputCoverageMask = wm_prog_data->uses_sample_mask;
@ -1788,7 +1788,7 @@ emit_3dstate_vf_statistics(struct anv_graphics_pipeline *pipeline)
static void
compute_kill_pixel(struct anv_graphics_pipeline *pipeline,
const struct vk_multisample_state *ms,
const struct vk_render_pass_state *rp)
const struct vk_graphics_pipeline_state *state)
{
if (!anv_pipeline_has_stage(pipeline, MESA_SHADER_FRAGMENT)) {
pipeline->kill_pixel = false;
@ -1812,7 +1812,7 @@ compute_kill_pixel(struct anv_graphics_pipeline *pipeline,
* of an alpha test.
*/
pipeline->kill_pixel =
rp_has_ds_self_dep(rp) ||
state_has_ds_self_dep(state) ||
wm_prog_data->uses_kill ||
wm_prog_data->uses_omask ||
(ms && ms->alpha_to_coverage_enable);
@ -1830,7 +1830,7 @@ genX(graphics_pipeline_emit)(struct anv_graphics_pipeline *pipeline,
urb_deref_block_size);
emit_ms_state(pipeline, state->ms);
emit_cb_state(pipeline, state->cb, state->ms);
compute_kill_pixel(pipeline, state->ms, state->rp);
compute_kill_pixel(pipeline, state->ms, state);
emit_3dstate_clip(pipeline, state->ia, state->vp, state->rs);
@ -1865,10 +1865,10 @@ genX(graphics_pipeline_emit)(struct anv_graphics_pipeline *pipeline,
emit_3dstate_sbe(pipeline);
emit_3dstate_wm(pipeline, state->ia, state->rs,
state->ms, state->cb, state->rp);
state->ms, state->cb, state);
emit_3dstate_ps(pipeline, state->ms, state->cb);
#if GFX_VER >= 8
emit_3dstate_ps_extra(pipeline, state->rs, state->rp);
emit_3dstate_ps_extra(pipeline, state->rs, state);
#endif
}

View file

@ -44,11 +44,11 @@ emit_pipeline_rs_state(struct nv_push *p,
static void
nvk_populate_fs_key(struct nvk_fs_key *key,
const struct vk_multisample_state *ms,
const struct vk_render_pass_state *rp)
const struct vk_graphics_pipeline_state *state)
{
memset(key, 0, sizeof(*key));
if (rp->pipeline_flags &
if (state->pipeline_flags &
VK_PIPELINE_CREATE_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT)
key->zs_self_dep = true;
@ -321,7 +321,7 @@ nvk_graphics_pipeline_create(struct nvk_device *dev,
struct vk_graphics_pipeline_all_state all;
struct vk_graphics_pipeline_state state = {};
result = vk_graphics_pipeline_state_fill(&dev->vk, &state, pCreateInfo,
NULL, &all, NULL, 0, NULL);
NULL, 0, &all, NULL, 0, NULL);
assert(result == VK_SUCCESS);
nir_shader *nir[MESA_SHADER_STAGES] = {};
@ -358,7 +358,7 @@ nvk_graphics_pipeline_create(struct nvk_device *dev,
struct nvk_fs_key fs_key_tmp, *fs_key = NULL;
if (stage == MESA_SHADER_FRAGMENT) {
nvk_populate_fs_key(&fs_key_tmp, state.ms, state.rp);
nvk_populate_fs_key(&fs_key_tmp, state.ms, &state);
fs_key = &fs_key_tmp;
}

View file

@ -5,6 +5,7 @@
#include "vk_common_entrypoints.h"
#include "vk_device.h"
#include "vk_log.h"
#include "vk_pipeline.h"
#include "vk_render_pass.h"
#include "vk_standard_sample_locations.h"
#include "vk_util.h"
@ -1032,11 +1033,11 @@ vk_render_pass_state_is_complete(const struct vk_render_pass_state *rp)
}
static void
vk_render_pass_state_init(struct vk_render_pass_state *rp,
const struct vk_render_pass_state *old_rp,
const struct vk_render_pass_state *driver_rp,
const VkGraphicsPipelineCreateInfo *info,
VkGraphicsPipelineLibraryFlagsEXT lib)
vk_pipeline_flags_init(struct vk_graphics_pipeline_state *state,
VkPipelineCreateFlags2KHR driver_rp_flags,
bool has_driver_rp,
const VkGraphicsPipelineCreateInfo *info,
VkGraphicsPipelineLibraryFlagsEXT lib)
{
VkPipelineCreateFlags2KHR valid_pipeline_flags = 0;
if (lib & VK_GRAPHICS_PIPELINE_LIBRARY_FRAGMENT_SHADER_BIT_EXT) {
@ -1049,22 +1050,43 @@ vk_render_pass_state_init(struct vk_render_pass_state *rp,
VK_PIPELINE_CREATE_2_COLOR_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT |
VK_PIPELINE_CREATE_2_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT;
}
const VkPipelineCreateFlags2KHR pipeline_flags =
(driver_rp ? driver_rp->pipeline_flags :
const VkPipelineCreateFlags2KHR renderpass_flags =
(has_driver_rp ? driver_rp_flags :
vk_get_pipeline_rendering_flags(info)) & valid_pipeline_flags;
const VkPipelineCreateFlags2KHR pipeline_flags =
vk_graphics_pipeline_create_flags(info) & valid_pipeline_flags;
bool pipeline_feedback_loop = pipeline_flags &
(VK_PIPELINE_CREATE_2_COLOR_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT |
VK_PIPELINE_CREATE_2_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT);
bool renderpass_feedback_loop = renderpass_flags &
(VK_PIPELINE_CREATE_2_COLOR_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT |
VK_PIPELINE_CREATE_2_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT);
state->pipeline_flags |= renderpass_flags | pipeline_flags;
state->feedback_loop_not_input_only |=
pipeline_feedback_loop || (!has_driver_rp && renderpass_feedback_loop);
}
static void
vk_render_pass_state_init(struct vk_render_pass_state *rp,
const struct vk_render_pass_state *old_rp,
const struct vk_render_pass_state *driver_rp,
const VkGraphicsPipelineCreateInfo *info,
VkGraphicsPipelineLibraryFlagsEXT lib)
{
/* If we already have render pass state and it has attachment info, then
* it's complete and we don't need a new one. The one caveat here is that
* we may need to add in some rendering flags.
*/
if (old_rp != NULL && vk_render_pass_state_is_complete(old_rp)) {
*rp = *old_rp;
rp->pipeline_flags |= pipeline_flags;
return;
}
*rp = (struct vk_render_pass_state) {
.pipeline_flags = pipeline_flags,
.depth_attachment_format = VK_FORMAT_UNDEFINED,
.stencil_attachment_format = VK_FORMAT_UNDEFINED,
};
@ -1228,6 +1250,7 @@ vk_graphics_pipeline_state_fill(const struct vk_device *device,
struct vk_graphics_pipeline_state *state,
const VkGraphicsPipelineCreateInfo *info,
const struct vk_render_pass_state *driver_rp,
VkPipelineCreateFlags2KHR driver_rp_flags,
struct vk_graphics_pipeline_all_state *all,
const VkAllocationCallbacks *alloc,
VkSystemAllocationScope scope,
@ -1360,6 +1383,11 @@ vk_graphics_pipeline_state_fill(const struct vk_device *device,
state->rp = NULL;
}
if (lib & (VK_GRAPHICS_PIPELINE_LIBRARY_FRAGMENT_SHADER_BIT_EXT |
VK_GRAPHICS_PIPELINE_LIBRARY_FRAGMENT_OUTPUT_INTERFACE_BIT_EXT)) {
vk_pipeline_flags_init(state, driver_rp_flags, !!driver_rp, info, lib);
}
if (lib & VK_GRAPHICS_PIPELINE_LIBRARY_PRE_RASTERIZATION_SHADERS_BIT_EXT) {
/* From the Vulkan 1.3.218 spec:
*
@ -1599,6 +1627,9 @@ vk_graphics_pipeline_state_merge(struct vk_graphics_pipeline_state *dst,
dst->shader_stages |= src->shader_stages;
dst->pipeline_flags |= src->pipeline_flags;
dst->feedback_loop_not_input_only |= src->feedback_loop_not_input_only;
/* Render pass state needs special care because a render pass state may be
* incomplete (view mask only). See vk_render_pass_state_init().
*/
@ -1690,6 +1721,10 @@ vk_graphics_pipeline_state_copy(const struct vk_device *device,
#undef COPY_STATE_IF_NEEDED
state->pipeline_flags = old_state->pipeline_flags;
state->feedback_loop_not_input_only =
old_state->feedback_loop_not_input_only;
vk_graphics_pipeline_state_validate(state);
return VK_SUCCESS;
}

View file

@ -675,16 +675,6 @@ struct vk_render_pass_state {
/** VkPipelineRenderingCreateInfo::viewMask */
uint32_t view_mask;
/** Render pass flags from VkGraphicsPipelineCreateInfo::flags
*
* For drivers which use vk_render_pass, this will also include flags
* generated based on subpass self-dependencies and fragment density map.
*/
VkPipelineCreateFlags2KHR pipeline_flags;
/* True if any feedback loops only involve input attachments. */
bool feedback_loop_input_only;
/** VkPipelineRenderingCreateInfo::colorAttachmentCount */
uint8_t color_attachment_count;
@ -858,6 +848,23 @@ struct vk_graphics_pipeline_state {
VkShaderStageFlags shader_stages;
/** Flags from VkGraphicsPipelineCreateInfo::flags that are considered part
* of a stage and need to be merged when linking libraries.
*
* For drivers which use vk_render_pass, this will also include flags
* generated based on subpass self-dependencies and fragment density map.
*/
VkPipelineCreateFlags2KHR pipeline_flags;
/* True if there are feedback loops that do not involve input attachments
* managed by the driver. This is set to true by the runtime if there
* are loops indicated by a pipeline flag (which may involve any image
* rather than only input attachments under the control of the driver) or
* there was no driver-provided render pass info struct (because input
* attachments for emulated renderpasses cannot be managed by the driver).
*/
bool feedback_loop_not_input_only;
/** Vertex input state */
const struct vk_vertex_input_state *vi;
@ -922,6 +929,10 @@ struct vk_graphics_pipeline_state {
* passes itself. This should be NULL for drivers
* that use the common render pass infrastructure
* built on top of dynamic rendering.
* :param driver_rp_flags: |in| Pipeline create flags implied by the
* renderpass or subpass if the driver implements
* render passes itself. This is only used if
* driver_rp is non-NULL.
* :param all: |in| The vk_graphics_pipeline_all_state to use to
* back any newly needed states. If NULL, newly
* needed states will be dynamically allocated
@ -938,7 +949,8 @@ VkResult
vk_graphics_pipeline_state_fill(const struct vk_device *device,
struct vk_graphics_pipeline_state *state,
const VkGraphicsPipelineCreateInfo *info,
const struct vk_render_pass_state *rp_info,
const struct vk_render_pass_state *driver_rp,
VkPipelineCreateFlags2KHR driver_rp_flags,
struct vk_graphics_pipeline_all_state *all,
const VkAllocationCallbacks *alloc,
VkSystemAllocationScope scope,

View file

@ -30,7 +30,6 @@
#include "vk_format.h"
#include "vk_framebuffer.h"
#include "vk_image.h"
#include "vk_pipeline.h"
#include "vk_util.h"
#include "util/log.h"
@ -842,12 +841,7 @@ vk_get_pipeline_rendering_create_info(const VkGraphicsPipelineCreateInfo *info)
VkPipelineCreateFlags2KHR
vk_get_pipeline_rendering_flags(const VkGraphicsPipelineCreateInfo *info)
{
VkPipelineCreateFlags2KHR rendering_flags =
vk_graphics_pipeline_create_flags(info) &
(VK_PIPELINE_CREATE_2_COLOR_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT |
VK_PIPELINE_CREATE_2_DEPTH_STENCIL_ATTACHMENT_FEEDBACK_LOOP_BIT_EXT |
VK_PIPELINE_CREATE_2_RENDERING_FRAGMENT_SHADING_RATE_ATTACHMENT_BIT_KHR |
VK_PIPELINE_CREATE_2_RENDERING_FRAGMENT_DENSITY_MAP_ATTACHMENT_BIT_EXT);
VkPipelineCreateFlags2KHR rendering_flags = 0;
VK_FROM_HANDLE(vk_render_pass, render_pass, info->renderPass);
if (render_pass != NULL) {