[Mesa-dev] [PATCH 20/20] radeonsi: enable gs support for nir backend

Timothy Arceri tarceri at itsqueeze.com
Fri Nov 10 03:13:54 UTC 2017


---
 src/gallium/drivers/radeonsi/si_pipe.c       |  3 +-
 src/gallium/drivers/radeonsi/si_shader_nir.c | 43 ++++++++++++++++------------
 src/mesa/state_tracker/st_glsl_to_nir.cpp    |  3 +-
 3 files changed, 28 insertions(+), 21 deletions(-)

diff --git a/src/gallium/drivers/radeonsi/si_pipe.c b/src/gallium/drivers/radeonsi/si_pipe.c
index 391997db84..9548f10766 100644
--- a/src/gallium/drivers/radeonsi/si_pipe.c
+++ b/src/gallium/drivers/radeonsi/si_pipe.c
@@ -529,21 +529,21 @@ static int si_get_param(struct pipe_screen* pscreen, enum pipe_cap param)
 	case PIPE_CAP_CONSTANT_BUFFER_OFFSET_ALIGNMENT:
 	case PIPE_CAP_TEXTURE_BUFFER_OFFSET_ALIGNMENT:
 	case PIPE_CAP_MAX_TEXTURE_GATHER_COMPONENTS:
 	case PIPE_CAP_MAX_STREAM_OUTPUT_BUFFERS:
 	case PIPE_CAP_MAX_VERTEX_STREAMS:
 	case PIPE_CAP_SHADER_BUFFER_OFFSET_ALIGNMENT:
 		return 4;
 
 	case PIPE_CAP_GLSL_FEATURE_LEVEL:
 		if (sscreen->b.debug_flags & DBG(NIR))
-			return 140; /* no geometry and tessellation shaders yet */
+			return 150; /* no tessellation shaders yet */
 		if (si_have_tgsi_compute(sscreen))
 			return 450;
 		return 420;
 
 	case PIPE_CAP_MAX_TEXTURE_BUFFER_SIZE:
 		return MIN2(sscreen->b.info.max_alloc_size, INT_MAX);
 
 	case PIPE_CAP_VERTEX_BUFFER_OFFSET_4BYTE_ALIGNED_ONLY:
 	case PIPE_CAP_VERTEX_BUFFER_STRIDE_4BYTE_ALIGNED_ONLY:
 	case PIPE_CAP_VERTEX_ELEMENT_SRC_OFFSET_4BYTE_ALIGNED_ONLY:
@@ -733,20 +733,21 @@ static int si_get_shader_param(struct pipe_screen* pscreen,
 		return SI_NUM_SAMPLERS;
 	case PIPE_SHADER_CAP_MAX_SHADER_BUFFERS:
 		return SI_NUM_SHADER_BUFFERS;
 	case PIPE_SHADER_CAP_MAX_SHADER_IMAGES:
 		return SI_NUM_IMAGES;
 	case PIPE_SHADER_CAP_MAX_UNROLL_ITERATIONS_HINT:
 		return 32;
 	case PIPE_SHADER_CAP_PREFERRED_IR:
 		if (sscreen->b.debug_flags & DBG(NIR) &&
 		    (shader == PIPE_SHADER_VERTEX ||
+		     shader == PIPE_SHADER_GEOMETRY ||
 		     shader == PIPE_SHADER_FRAGMENT))
 			return PIPE_SHADER_IR_NIR;
 		return PIPE_SHADER_IR_TGSI;
 	case PIPE_SHADER_CAP_LOWER_IF_THRESHOLD:
 		return 4;
 
 	/* Supported boolean features. */
 	case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
 	case PIPE_SHADER_CAP_TGSI_SQRT_SUPPORTED:
 	case PIPE_SHADER_CAP_INDIRECT_TEMP_ADDR:
diff --git a/src/gallium/drivers/radeonsi/si_shader_nir.c b/src/gallium/drivers/radeonsi/si_shader_nir.c
index 1933c8c770..ca67967083 100644
--- a/src/gallium/drivers/radeonsi/si_shader_nir.c
+++ b/src/gallium/drivers/radeonsi/si_shader_nir.c
@@ -145,20 +145,21 @@ static void scan_instruction(struct tgsi_shader_info *info,
 	}
 }
 
 void si_nir_scan_shader(const struct nir_shader *nir,
 			struct tgsi_shader_info *info)
 {
 	nir_function *func;
 	unsigned i;
 
 	assert(nir->info.stage == MESA_SHADER_VERTEX ||
+	       nir->info.stage == MESA_SHADER_GEOMETRY ||
 	       nir->info.stage == MESA_SHADER_FRAGMENT);
 
 	info->processor = pipe_shader_type_from_mesa(nir->info.stage);
 	info->num_tokens = 2; /* indicate that the shader is non-empty */
 	info->num_instructions = 2;
 
 	info->num_inputs = nir->num_inputs;
 	info->num_outputs = nir->num_outputs;
 
 	if (nir->info.stage == MESA_SHADER_GEOMETRY) {
@@ -166,29 +167,30 @@ void si_nir_scan_shader(const struct nir_shader *nir,
 		info->properties[TGSI_PROPERTY_GS_MAX_OUTPUT_VERTICES] = nir->info.gs.vertices_out;
 		info->properties[TGSI_PROPERTY_GS_INVOCATIONS] = nir->info.gs.invocations;
 	}
 
 	i = 0;
 	nir_foreach_variable(variable, &nir->inputs) {
 		unsigned semantic_name, semantic_index;
 		unsigned attrib_count = glsl_count_attribute_slots(variable->type,
 								   nir->info.stage == MESA_SHADER_VERTEX);
 
-		assert(attrib_count == 1 && "not implemented");
-
 		/* Vertex shader inputs don't have semantics. The state
 		 * tracker has already mapped them to attributes via
 		 * variable->data.driver_location.
 		 */
 		if (nir->info.stage == MESA_SHADER_VERTEX)
 			continue;
 
+		assert(nir->info.stage != MESA_SHADER_FRAGMENT ||
+		       (attrib_count == 1 && "not implemented"));
+
 		/* Fragment shader position is a system value. */
 		if (nir->info.stage == MESA_SHADER_FRAGMENT &&
 		    variable->data.location == VARYING_SLOT_POS) {
 			if (variable->data.pixel_center_integer)
 				info->properties[TGSI_PROPERTY_FS_COORD_PIXEL_CENTER] =
 					TGSI_FS_COORD_PIXEL_CENTER_INTEGER;
 			continue;
 		}
 
 		tgsi_get_gl_varying_semantic(variable->data.location, true,
@@ -563,37 +565,40 @@ si_nir_load_sampler_desc(struct ac_shader_abi *abi,
 	index = LLVMBuildAdd(ctx->gallivm.builder, index,
 			     LLVMConstInt(ctx->i32, SI_NUM_IMAGES / 2, 0), "");
 
 	return si_load_sampler_desc(ctx, list, index, desc_type);
 }
 
 bool si_nir_build_llvm(struct si_shader_context *ctx, struct nir_shader *nir)
 {
 	struct tgsi_shader_info *info = &ctx->shader->selector->info;
 
-	unsigned fs_attr_idx = 0;
-	nir_foreach_variable(variable, &nir->inputs) {
-		unsigned attrib_count = glsl_count_attribute_slots(variable->type,
-								   nir->info.stage == MESA_SHADER_VERTEX);
-		unsigned input_idx = variable->data.driver_location;
-
-		for (unsigned i = 0; i < attrib_count; ++i) {
-			LLVMValueRef data[4];
-
-			if (nir->info.stage == MESA_SHADER_VERTEX)
-				declare_nir_input_vs(ctx, variable, i, data);
-			else if (nir->info.stage == MESA_SHADER_FRAGMENT)
-				declare_nir_input_fs(ctx, variable, i, &fs_attr_idx, data);
-
-			for (unsigned chan = 0; chan < 4; chan++) {
-				ctx->inputs[input_idx + chan] =
-					LLVMBuildBitCast(ctx->ac.builder, data[chan], ctx->ac.i32, "");
+	if (nir->info.stage == MESA_SHADER_VERTEX ||
+	    nir->info.stage == MESA_SHADER_FRAGMENT) {
+		unsigned fs_attr_idx = 0;
+		nir_foreach_variable(variable, &nir->inputs) {
+			unsigned attrib_count = glsl_count_attribute_slots(variable->type,
+									   nir->info.stage == MESA_SHADER_VERTEX);
+			unsigned input_idx = variable->data.driver_location;
+
+			for (unsigned i = 0; i < attrib_count; ++i) {
+				LLVMValueRef data[4];
+
+				if (nir->info.stage == MESA_SHADER_VERTEX)
+					declare_nir_input_vs(ctx, variable, i, data);
+				else if (nir->info.stage == MESA_SHADER_FRAGMENT)
+					declare_nir_input_fs(ctx, variable, i, &fs_attr_idx, data);
+
+				for (unsigned chan = 0; chan < 4; chan++) {
+					ctx->inputs[input_idx + chan] =
+						LLVMBuildBitCast(ctx->ac.builder, data[chan], ctx->ac.i32, "");
+				}
 			}
 		}
 	}
 
 	ctx->abi.inputs = &ctx->inputs[0];
 	ctx->abi.load_sampler_desc = si_nir_load_sampler_desc;
 	ctx->abi.clamp_shadow_reference = true;
 
 	ctx->num_samplers = util_last_bit(info->samplers_declared);
 	ctx->num_images = util_last_bit(info->images_declared);
diff --git a/src/mesa/state_tracker/st_glsl_to_nir.cpp b/src/mesa/state_tracker/st_glsl_to_nir.cpp
index d478725fbe..a167d5dffb 100644
--- a/src/mesa/state_tracker/st_glsl_to_nir.cpp
+++ b/src/mesa/state_tracker/st_glsl_to_nir.cpp
@@ -375,21 +375,22 @@ st_finalize_nir(struct st_context *st, struct gl_program *prog,
       /* Needs special handling so drvloc matches the vbo state: */
       st_nir_assign_vs_in_locations(prog, nir);
       /* Re-lower global vars, to deal with any dead VS inputs. */
       NIR_PASS_V(nir, nir_lower_global_vars_to_local);
 
       sort_varyings(&nir->outputs);
       nir_assign_var_locations(&nir->outputs,
                                &nir->num_outputs,
                                type_size);
       st_nir_fixup_varying_slots(st, &nir->outputs);
-   } else if (nir->info.stage == MESA_SHADER_FRAGMENT) {
+   } else if (nir->info.stage == MESA_SHADER_GEOMETRY ||
+              nir->info.stage == MESA_SHADER_FRAGMENT) {
       sort_varyings(&nir->inputs);
       nir_assign_var_locations(&nir->inputs,
                                &nir->num_inputs,
                                type_size);
       st_nir_fixup_varying_slots(st, &nir->inputs);
       nir_assign_var_locations(&nir->outputs,
                                &nir->num_outputs,
                                type_size);
    } else if (nir->info.stage == MESA_SHADER_COMPUTE) {
        /* TODO? */
-- 
2.14.3



More information about the mesa-dev mailing list