From ac89a8ae740e5d3003e326d1344f353026a0cc2b Mon Sep 17 00:00:00 2001 From: Gert Wollny Date: Thu, 12 Aug 2021 14:59:03 +0200 Subject: [PATCH] shader: rework handling of num_clip and num_cull Let the value found in the properties takes preference. This fixes all compilation and link errors with KHR-GL43.cull_distance.functional Signed-off-by: Gert Wollny Reviewed-by: Rohan Garg --- src/vrend_renderer.c | 14 ++++ src/vrend_shader.c | 169 ++++++++++++++++++++++--------------------- src/vrend_shader.h | 6 +- 3 files changed, 105 insertions(+), 84 deletions(-) diff --git a/src/vrend_renderer.c b/src/vrend_renderer.c index 4ce699e..a0892b1 100644 --- a/src/vrend_renderer.c +++ b/src/vrend_renderer.c @@ -3423,6 +3423,12 @@ static inline void vrend_sync_shader_io(struct vrend_sub_context *sub_ctx, && key->fs.prim_is_points ? sub_ctx->rs_state.sprite_coord_enable : 0x0; + + if (prev_type != -1 && sub_ctx->shaders[prev_type]) { + key->num_clip = sub_ctx->shaders[prev_type]->current->var_sinfo.num_clip; + key->num_cull = sub_ctx->shaders[prev_type]->current->var_sinfo.num_cull; + } + } else { if (sub_ctx->shaders[PIPE_SHADER_FRAGMENT]) { struct vrend_shader *fs = @@ -3459,6 +3465,14 @@ static inline void vrend_sync_shader_io(struct vrend_sub_context *sub_ctx, if (next_type != -1 && sub_ctx->shaders[next_type]) { key->output = sub_ctx->shaders[next_type]->sinfo.in; + /* FS gets the clip/cull info in the key from this shader, so + * we can avoid re-translating this shader by not updating the + * info in the key */ + if (next_type != PIPE_SHADER_FRAGMENT) { + key->num_clip = sub_ctx->shaders[next_type]->current->var_sinfo.num_clip; + key->num_cull = sub_ctx->shaders[next_type]->current->var_sinfo.num_cull; + } + if (type == PIPE_SHADER_VERTEX && next_type == PIPE_SHADER_FRAGMENT) { if (sub_ctx->shaders[type]) { uint32_t fog_input = sub_ctx->shaders[next_type]->sinfo.fog_input_mask; diff --git a/src/vrend_shader.c b/src/vrend_shader.c index 83efcb0..d536b9c 100644 --- a/src/vrend_shader.c +++ b/src/vrend_shader.c @@ -2024,6 +2024,9 @@ static void emit_clip_dist_movs(const struct dump_ctx *ctx, { int i; bool has_prop = (ctx->num_clip_dist_prop + ctx->num_cull_dist_prop) > 0; + int num_clip = has_prop ? ctx->num_clip_dist_prop : ctx->key->num_clip; + int num_cull = has_prop ? ctx->num_cull_dist_prop : ctx->key->num_cull; + int ndists; const char *prefix=""; @@ -2037,7 +2040,7 @@ static void emit_clip_dist_movs(const struct dump_ctx *ctx, } ndists = ctx->num_clip_dist; if (has_prop) - ndists = ctx->num_clip_dist_prop + ctx->num_cull_dist_prop; + ndists = num_clip + num_cull; for (i = 0; i < ndists; i++) { int clipidx = i < 4 ? 0 : 1; char swiz = i & 3; @@ -2050,13 +2053,19 @@ static void emit_clip_dist_movs(const struct dump_ctx *ctx, case 3: wm = 'w'; break; } bool is_cull = false; - if (has_prop) { - if (i >= ctx->num_clip_dist_prop && i < ctx->num_clip_dist_prop + ctx->num_cull_dist_prop) + const char *clip_cull = "Clip"; + + if (i >= num_clip) { + if (i < ndists) { is_cull = true; + clip_cull = "Cull"; + } else { + clip_cull = "ERROR"; + } } - const char *clip_cull = is_cull ? "Cull" : "Clip"; + emit_buff(glsl_strbufs, "%sgl_%sDistance[%d] = clip_dist_temp[%d].%c;\n", prefix, clip_cull, - is_cull ? i - ctx->num_clip_dist_prop : i, clipidx, wm); + is_cull ? i - num_clip : i, clipidx, wm); } } @@ -2999,11 +3008,15 @@ create_swizzled_clipdist(const struct dump_ctx *ctx, char clip_indirect[32] = ""; - bool has_prev_vals = (ctx->key->input.num_cull + ctx->key->input.num_clip) > 0; - int num_culls = has_prev_vals ? ctx->key->input.num_cull : 0; - int num_clips = has_prev_vals ? ctx->key->input.num_clip : ctx->num_in_clip_dist; + bool has_prop = (ctx->num_cull_dist_prop + ctx->num_clip_dist_prop) > 0; + int num_culls = has_prop ? ctx->num_cull_dist_prop : ctx->key->num_cull; + int num_clips = has_prop ? ctx->num_clip_dist_prop : ctx->key->num_clip; + int base_idx = ctx->inputs[input_idx].sid * 4; + // This doesn't work for indirect adressing + int base_offset = (src->Register.Index - offset) * 4; + /* With arrays enabled , but only when gl_ClipDistance or gl_CullDistance are emitted (>4) * then we need to add indirect addressing */ if (src->Register.Indirect && ((num_clips > 4 && base_idx < num_clips) || num_culls > 4)) @@ -3024,18 +3037,12 @@ create_swizzled_clipdist(const struct dump_ctx *ctx, idx += src->Register.SwizzleW; if (num_culls) { - if (idx >= num_clips) { + if (idx + base_offset >= num_clips) { idx -= num_clips; cc_name = "gl_CullDistance"; } - if (ctx->key->input.num_cull) - if (idx >= ctx->key->input.num_cull) - idx = 0; - } else { - if (ctx->key->input.num_clip) - if (idx >= ctx->key->input.num_clip) - idx = 0; } + if (gl_in) snprintf(clipdistvec[cc], 80, "%sgl_in%s.%s[%s %d]", prefix, arrayname, cc_name, clip_indirect, idx); else @@ -4710,7 +4717,7 @@ void emit_fs_clipdistance_load(const struct dump_ctx *ctx, if (!ctx->fs_uses_clipdist_input) return; - int prev_num = ctx->key->input.num_clip + ctx->key->input.num_cull; + int prev_num = ctx->key->num_clip + ctx->key->num_cull; int ndists; const char *prefix=""; @@ -4734,12 +4741,12 @@ void emit_fs_clipdistance_load(const struct dump_ctx *ctx, } bool is_cull = false; if (prev_num > 0) { - if (i >= ctx->key->input.num_clip && i < prev_num) + if (i >= ctx->key->num_clip && i < prev_num) is_cull = true; } const char *clip_cull = is_cull ? "Cull" : "Clip"; emit_buff(glsl_strbufs, "clip_dist_temp[%d].%c = %sgl_%sDistance[%d];\n", clipidx, wm, prefix, clip_cull, - is_cull ? i - ctx->key->input.num_clip : i); + is_cull ? i - ctx->key->num_clip : i); } } @@ -5662,7 +5669,7 @@ static void emit_header(const struct dump_ctx *ctx, struct vrend_glsl_strbufs *g if (ctx->ubo_used_mask) emit_ext(glsl_strbufs, "ARB_uniform_buffer_object", "require"); - if (ctx->num_cull_dist_prop || ctx->key->input.num_cull) + if (ctx->num_cull_dist_prop || ctx->key->num_cull) emit_ext(glsl_strbufs, "ARB_cull_distance", "require"); if (ctx->ssbo_used_mask) emit_ext(glsl_strbufs, "ARB_shader_storage_buffer_object", "require"); @@ -6443,7 +6450,8 @@ static void emit_ios_vs(const struct dump_ctx *ctx, if (ctx->key->clip_plane_enable) { emit_hdr(glsl_strbufs, "uniform vec4 clipp[8];\n"); } - if ((ctx->key->gs_present || ctx->key->tes_present) && ctx->key->output.use_pervertex) { + + if (ctx->key->gs_present || ctx->key->tes_present) { emit_hdrf(glsl_strbufs, "out gl_PerVertex {\n vec4 gl_Position;\n %s%s};\n", clip_buf, cull_buf); } else { emit_hdrf(glsl_strbufs, "%s%s", clip_buf, cull_buf); @@ -6586,14 +6594,14 @@ static void emit_ios_fs(const struct dump_ctx *ctx, } if (ctx->num_in_clip_dist) { - if (ctx->key->input.num_clip) { - emit_hdrf(glsl_strbufs, "in float gl_ClipDistance[%d];\n", ctx->key->input.num_clip); - } else if (ctx->num_in_clip_dist > 4 && !ctx->key->input.num_cull) { + if (ctx->key->num_clip) { + emit_hdrf(glsl_strbufs, "in float gl_ClipDistance[%d];\n", ctx->key->num_clip); + } else if (ctx->num_in_clip_dist > 4 && !ctx->key->num_cull) { emit_hdrf(glsl_strbufs, "in float gl_ClipDistance[%d];\n", ctx->num_in_clip_dist); } - if (ctx->key->input.num_cull) { - emit_hdrf(glsl_strbufs, "in float gl_CullDistance[%d];\n", ctx->key->input.num_cull); + if (ctx->key->num_cull) { + emit_hdrf(glsl_strbufs, "in float gl_CullDistance[%d];\n", ctx->key->num_cull); } if(ctx->fs_uses_clipdist_input) emit_hdr(glsl_strbufs, "vec4 clip_dist_temp[2];\n"); @@ -6606,6 +6614,50 @@ can_emit_generic_geom(const struct vrend_shader_io *io) return io->stream == 0; } +static void emit_ios_per_vertex_in(const struct dump_ctx *ctx, + struct vrend_glsl_strbufs *glsl_strbufs, + bool *has_pervertex) +{ + if (ctx->num_in_clip_dist || ctx->key->clip_plane_enable) { + int clip_dist, cull_dist; + char clip_var[64] = ""; + char cull_var[64] = ""; + + clip_dist = ctx->num_clip_dist_prop ? ctx->num_clip_dist_prop : ctx->key->num_clip; + cull_dist = ctx->num_cull_dist_prop ? ctx->num_cull_dist_prop : ctx->key->num_cull; + + if (clip_dist) + snprintf(clip_var, 64, "float gl_ClipDistance[%d];\n", clip_dist); + if (cull_dist) + snprintf(cull_var, 64, "float gl_CullDistance[%d];\n", cull_dist); + + (*has_pervertex) = true; + emit_hdrf(glsl_strbufs, "in gl_PerVertex {\n vec4 gl_Position; \n %s%s\n} gl_in[];\n", clip_var, cull_var); + } +} + + +static void emit_ios_per_vertex_out(const struct dump_ctx *ctx, + struct vrend_glsl_strbufs *glsl_strbufs) +{ + if (ctx->num_clip_dist || ctx->num_cull_dist_prop) { + if (ctx->key->output.use_pervertex) { + + int clip_dist = ctx->num_clip_dist_prop ? ctx->num_clip_dist_prop : ctx->key->num_clip; + int cull_dist = ctx->num_cull_dist_prop ? ctx->num_cull_dist_prop : ctx->key->num_cull; + + char clip_var[64] = "", cull_var[64] = ""; + if (cull_dist) + snprintf(cull_var, 64, "float gl_CullDistance[%d];\n", cull_dist); + + if (clip_dist) + snprintf(clip_var, 64, "float gl_ClipDistance[%d];\n", clip_dist); + emit_hdrf(glsl_strbufs, "out gl_PerVertex {\n vec4 gl_Position;\n %s%s\n} gl_out[];\n", clip_var, cull_var); + } + emit_hdr(glsl_strbufs, "vec4 clip_dist_temp[2];\n"); + } +} + static void emit_ios_geom(const struct dump_ctx *ctx, struct vrend_glsl_strbufs *glsl_strbufs, struct vrend_generic_ios *generic_ios, @@ -6660,22 +6712,8 @@ static void emit_ios_geom(const struct dump_ctx *ctx, emit_winsys_correction(glsl_strbufs); - if (ctx->num_in_clip_dist || ctx->key->clip_plane_enable) { - int clip_dist, cull_dist; - char clip_var[64] = ""; - char cull_var[64] = ""; - - clip_dist = ctx->key->input.num_clip ? ctx->key->input.num_clip : ctx->num_in_clip_dist; - cull_dist = ctx->key->input.num_cull; - - if (clip_dist) - snprintf(clip_var, 64, "float gl_ClipDistance[%d];\n", clip_dist); - if (cull_dist) - snprintf(cull_var, 64, "float gl_CullDistance[%d];\n", cull_dist); + emit_ios_per_vertex_in(ctx, glsl_strbufs, has_pervertex); - (*has_pervertex) = true; - emit_hdrf(glsl_strbufs, "in gl_PerVertex {\n vec4 gl_Position; \n %s%s\n} gl_in[];\n", clip_var, cull_var); - } if (ctx->num_clip_dist) { bool has_prop = (ctx->num_clip_dist_prop + ctx->num_cull_dist_prop) > 0; int num_clip_dists = ctx->num_clip_dist ? ctx->num_clip_dist : 8; @@ -6738,25 +6776,8 @@ static void emit_ios_tcs(const struct dump_ctx *ctx, } } - if (ctx->num_in_clip_dist) { - int clip_dist, cull_dist; - char clip_var[64] = "", cull_var[64] = ""; - - clip_dist = ctx->key->input.num_clip ? ctx->key->input.num_clip : ctx->num_in_clip_dist; - cull_dist = ctx->key->input.num_cull; - - if (clip_dist) - snprintf(clip_var, 64, "float gl_ClipDistance[%d];\n", clip_dist); - if (cull_dist) - snprintf(cull_var, 64, "float gl_CullDistance[%d];\n", cull_dist); - - *has_pervertex = true; - emit_hdrf(glsl_strbufs, "in gl_PerVertex {\n vec4 gl_Position; \n %s%s} gl_in[];\n", clip_var, cull_var); - } - if (ctx->num_clip_dist && ctx->key->output.use_pervertex) { - emit_hdrf(glsl_strbufs, "out gl_PerVertex {\n vec4 gl_Position;\n float gl_ClipDistance[%d];\n} gl_out[];\n", ctx->num_clip_dist); - emit_hdr(glsl_strbufs, "vec4 clip_dist_temp[2];\n"); - } + emit_ios_per_vertex_in(ctx, glsl_strbufs, has_pervertex); + emit_ios_per_vertex_out(ctx, glsl_strbufs); } static void emit_ios_tes(const struct dump_ctx *ctx, @@ -6797,25 +6818,8 @@ static void emit_ios_tes(const struct dump_ctx *ctx, emit_winsys_correction(glsl_strbufs); - if (ctx->num_in_clip_dist) { - int clip_dist, cull_dist; - char clip_var[64] = "", cull_var[64] = ""; - - clip_dist = ctx->key->input.num_clip ? ctx->key->input.num_clip : ctx->num_in_clip_dist; - cull_dist = ctx->key->input.num_cull; - - if (clip_dist) - snprintf(clip_var, 64, "float gl_ClipDistance[%d];\n", clip_dist); - if (cull_dist) - snprintf(cull_var, 64, "float gl_CullDistance[%d];\n", cull_dist); - - *has_pervertex = true; - emit_hdrf(glsl_strbufs, "in gl_PerVertex {\n vec4 gl_Position; \n %s%s} gl_in[];\n", clip_var, cull_var); - } - if (ctx->num_clip_dist && ctx->key->output.use_pervertex) { - emit_hdrf(glsl_strbufs, "out gl_PerVertex {\n vec4 gl_Position;\n float gl_ClipDistance[%d];\n} gl_out[];\n", ctx->num_clip_dist); - emit_hdr(glsl_strbufs, "vec4 clip_dist_temp[2];\n"); - } + emit_ios_per_vertex_in(ctx, glsl_strbufs, has_pervertex); + emit_ios_per_vertex_out(ctx, glsl_strbufs); } @@ -6971,14 +6975,15 @@ static void fill_var_sinfo(const struct dump_ctx *ctx, struct vrend_variable_sha sinfo->fs_info.has_sample_input = ctx->has_sample_input; sinfo->fs_info.num_interps = ctx->num_interps; sinfo->fs_info.glsl_ver = ctx->glsl_ver_required; + bool has_prop = (ctx->num_clip_dist_prop + ctx->num_cull_dist_prop) > 0; + + sinfo->num_clip = has_prop ? ctx->num_clip_dist_prop : ctx->key->num_clip; + sinfo->num_cull = has_prop ? ctx->num_cull_dist_prop : ctx->key->num_cull; } static void fill_sinfo(const struct dump_ctx *ctx, struct vrend_shader_info *sinfo) { sinfo->in.use_pervertex = ctx->has_pervertex; - bool has_prop = (ctx->num_clip_dist_prop + ctx->num_cull_dist_prop) > 0; - sinfo->out.num_clip = has_prop ? ctx->num_clip_dist_prop : (ctx->num_clip_dist ? ctx->num_clip_dist : 8); - sinfo->out.num_cull = has_prop ? ctx->num_cull_dist_prop : 0; sinfo->samplers_used_mask = ctx->samplers_used; sinfo->images_used_mask = ctx->images_used_mask; sinfo->num_consts = ctx->num_consts; diff --git a/src/vrend_shader.h b/src/vrend_shader.h index fa33254..ec5c693 100644 --- a/src/vrend_shader.h +++ b/src/vrend_shader.h @@ -81,8 +81,6 @@ struct vrend_fs_shader_info { }; struct vrend_shader_info_out { - uint64_t num_clip : 8; - uint64_t num_cull : 8; uint64_t num_indirect_generic : 8; uint64_t num_indirect_patch : 8; uint64_t num_generic_and_patch : 8; @@ -134,6 +132,8 @@ struct vrend_shader_info { struct vrend_variable_shader_info { struct vrend_fs_shader_info fs_info; int num_ucp; + int num_clip; + int num_cull; }; struct vrend_shader_key { @@ -170,6 +170,8 @@ struct vrend_shader_key { uint8_t alpha_test; uint8_t clip_plane_enable; + uint8_t num_cull : 4; + uint8_t num_clip : 4; uint8_t pstipple_tex : 1; uint8_t add_alpha_test : 1; uint8_t color_two_side : 1;