mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-05-06 20:18:12 +02:00
tu: Adjust multiview lowering for GS
When there is a GS, run multiview lowering for the VS and multiply the per-primitive varying stride by the view count since all outputs are now per-view. Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/40153>
This commit is contained in:
parent
be84cb6211
commit
f497e3913b
4 changed files with 40 additions and 19 deletions
|
|
@ -17,7 +17,8 @@
|
|||
* gl_Position = ((1ull << gl_ViewIndex) & view_mask) ? gl_Position : vec4(0.);
|
||||
*
|
||||
* Scan backwards until we find the gl_Position write (there should only be
|
||||
* one).
|
||||
* one). This also needs to happen with multi-position, which doesn't respect
|
||||
* the view mask.
|
||||
*/
|
||||
static bool
|
||||
lower_multiview_mask(nir_shader *nir, uint32_t *mask)
|
||||
|
|
@ -70,15 +71,18 @@ lower_multiview_mask(nir_shader *nir, uint32_t *mask)
|
|||
}
|
||||
|
||||
bool
|
||||
tu_nir_lower_multiview(nir_shader *nir, uint32_t mask, struct tu_device *dev)
|
||||
tu_nir_lower_multiview(nir_shader *nir, uint32_t mask, struct tu_device *dev,
|
||||
bool last_stage)
|
||||
{
|
||||
bool progress = false;
|
||||
nir_lower_multiview_options options = {
|
||||
.view_mask = mask,
|
||||
.allowed_per_view_outputs = VARYING_BIT_POS
|
||||
.allowed_per_view_outputs =
|
||||
last_stage ? VARYING_BIT_POS : ~0ull,
|
||||
};
|
||||
|
||||
if (!dev->physical_device->info->props.supports_multiview_mask)
|
||||
if (!dev->physical_device->info->props.supports_multiview_mask &&
|
||||
last_stage)
|
||||
NIR_PASS(progress, nir, lower_multiview_mask, &options.view_mask);
|
||||
|
||||
unsigned num_views = util_logbase2(mask) + 1;
|
||||
|
|
@ -95,10 +99,16 @@ tu_nir_lower_multiview(nir_shader *nir, uint32_t mask, struct tu_device *dev)
|
|||
*/
|
||||
nir_assign_io_var_locations(nir, nir_var_shader_out);
|
||||
|
||||
if (!last_stage) {
|
||||
/* We will store outputs per-view and loop over all active views in the
|
||||
* shader.
|
||||
*/
|
||||
NIR_PASS(progress, nir, nir_lower_multiview, options);
|
||||
|
||||
/* In addition to the generic checks done by NIR, check that we don't
|
||||
* overflow VPC with the extra copies of gl_Position.
|
||||
*/
|
||||
if (!TU_DEBUG(NOMULTIPOS) &&
|
||||
} else if (!TU_DEBUG(NOMULTIPOS) &&
|
||||
num_views <= max_views_for_multipos && nir->num_outputs + (num_views - 1) <= 32 &&
|
||||
nir_can_lower_multiview(nir, options)) {
|
||||
/* It appears that the multiview mask is ignored when multi-position
|
||||
|
|
|
|||
|
|
@ -1304,7 +1304,7 @@ tu6_emit_geom_tess_consts(struct tu_cs *cs,
|
|||
|
||||
if (gs && !hs) {
|
||||
tu6_emit_vs_params(cs, ir3_const_state(vs), vs->constlen,
|
||||
vs->output_size, gs->gs.vertices_in);
|
||||
vs->output_size, gs->gs.vertices_in * vs->view_count);
|
||||
}
|
||||
|
||||
if (hs) {
|
||||
|
|
@ -1312,9 +1312,9 @@ tu6_emit_geom_tess_consts(struct tu_cs *cs,
|
|||
tu_get_tess_iova<CHIP>(dev, &tess_factor_iova, &tess_param_iova);
|
||||
|
||||
uint32_t ds_params[8] = {
|
||||
gs ? ds->output_size * gs->gs.vertices_in * 4 : 0, /* ds primitive stride */
|
||||
ds->output_size * 4, /* ds vertex stride */
|
||||
hs->output_size, /* hs vertex stride (dwords) */
|
||||
gs ? ds->output_size * ds->view_count * gs->gs.vertices_in * 4 : 0, /* ds primitive stride */
|
||||
ds->output_size * 4, /* ds vertex stride */
|
||||
hs->output_size, /* hs vertex stride (dwords) */
|
||||
hs->tess.tcs_vertices_out,
|
||||
tess_param_iova,
|
||||
tess_param_iova >> 32,
|
||||
|
|
@ -1330,8 +1330,8 @@ tu6_emit_geom_tess_consts(struct tu_cs *cs,
|
|||
if (gs) {
|
||||
const struct ir3_shader_variant *prev = ds ? ds : vs;
|
||||
uint32_t gs_params[4] = {
|
||||
prev->output_size * gs->gs.vertices_in * 4, /* gs primitive stride */
|
||||
prev->output_size * 4, /* gs vertex stride */
|
||||
prev->output_size * prev->view_count * gs->gs.vertices_in * 4, /* gs primitive stride */
|
||||
prev->output_size * 4, /* gs vertex stride */
|
||||
0,
|
||||
0,
|
||||
};
|
||||
|
|
@ -1887,8 +1887,12 @@ tu_pipeline_builder_compile_shaders(struct tu_pipeline_builder *builder,
|
|||
|
||||
if (builder->state &
|
||||
VK_GRAPHICS_PIPELINE_LIBRARY_PRE_RASTERIZATION_SHADERS_BIT_EXT) {
|
||||
keys[MESA_SHADER_VERTEX].multiview_mask =
|
||||
builder->graphics_state.mv->view_mask;
|
||||
for (int i = MESA_SHADER_VERTEX; i <= MESA_SHADER_GEOMETRY; i++) {
|
||||
if (nir[i] || stage_infos[i]) {
|
||||
keys[i].multiview_mask =
|
||||
builder->graphics_state.mv->view_mask;
|
||||
}
|
||||
}
|
||||
|
||||
mesa_shader_stage last_pre_rast_stage = MESA_SHADER_VERTEX;
|
||||
for (int i = MESA_SHADER_GEOMETRY; i >= MESA_SHADER_VERTEX; i--) {
|
||||
|
|
@ -4972,7 +4976,7 @@ tu_compute_pipeline_create(VkDevice device,
|
|||
nir_shader_as_str(nir, pipeline->base.executables_mem_ctx) : NULL;
|
||||
|
||||
struct tu_shader_info info = {};
|
||||
tu_lower_nir(dev, nir, &key, &info);
|
||||
tu_lower_nir(dev, nir, &key, &ir3_key, &info);
|
||||
result = tu_shader_create(dev, &shader, nir, &key, &info, &ir3_key,
|
||||
pipeline_blake3, sizeof(pipeline_blake3), layout,
|
||||
executable_info);
|
||||
|
|
|
|||
|
|
@ -2934,6 +2934,7 @@ void
|
|||
tu_lower_nir(struct tu_device *dev,
|
||||
nir_shader *nir,
|
||||
const struct tu_shader_key *key,
|
||||
const struct ir3_shader_key *ir3_key,
|
||||
struct tu_shader_info *info)
|
||||
{
|
||||
const nir_opt_access_options access_options = {
|
||||
|
|
@ -2999,9 +3000,13 @@ tu_lower_nir(struct tu_device *dev,
|
|||
*/
|
||||
ir3_nir_lower_io_vars_to_temporaries(nir);
|
||||
|
||||
if (nir->info.stage == MESA_SHADER_VERTEX && key->multiview_mask) {
|
||||
tu_nir_lower_multiview(nir, key->multiview_mask, dev);
|
||||
}
|
||||
bool is_last_stage =
|
||||
(nir->info.stage == MESA_SHADER_VERTEX && !ir3_key->has_gs && !ir3_key->tessellation);
|
||||
|
||||
if (nir->info.stage == MESA_SHADER_VERTEX && key->multiview_mask)
|
||||
tu_nir_lower_multiview(nir, key->multiview_mask, dev, is_last_stage);
|
||||
if (nir->info.stage == MESA_SHADER_GEOMETRY)
|
||||
nir->info.view_mask = key->multiview_mask;
|
||||
|
||||
if (!key->multiview_mask)
|
||||
tu_nir_lower_view_to_zero(nir);
|
||||
|
|
@ -3347,7 +3352,7 @@ tu_compile_shaders(struct tu_device *device,
|
|||
|
||||
int64_t stage_start = os_time_get_nano();
|
||||
|
||||
tu_lower_nir(device, nir[stage], &keys[stage], &info[stage]);
|
||||
tu_lower_nir(device, nir[stage], &keys[stage], &ir3_key, &info[stage]);
|
||||
|
||||
stage_feedbacks[stage].duration += os_time_get_nano() - stage_start;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -146,7 +146,8 @@ void
|
|||
tu_destroy_softfloat(struct tu_device *device);
|
||||
|
||||
bool
|
||||
tu_nir_lower_multiview(nir_shader *nir, uint32_t mask, struct tu_device *dev);
|
||||
tu_nir_lower_multiview(nir_shader *nir, uint32_t mask, struct tu_device *dev,
|
||||
bool last_stage);
|
||||
|
||||
bool
|
||||
tu_nir_lower_ray_queries(nir_shader *nir);
|
||||
|
|
@ -202,6 +203,7 @@ void
|
|||
tu_lower_nir(struct tu_device *dev,
|
||||
nir_shader *nir,
|
||||
const struct tu_shader_key *key,
|
||||
const struct ir3_shader_key *ir3_key,
|
||||
struct tu_shader_info *info);
|
||||
|
||||
VkResult
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue