+ unsigned num_elements;
+ struct svga_vertex_shader new_vs;
+ struct ureg_src src[PIPE_MAX_SHADER_INPUTS];
+ struct ureg_dst dst[PIPE_MAX_SHADER_OUTPUTS];
+ struct ureg_program *ureg;
+ struct svga_compile_key key;
+ enum pipe_error ret;
+
+ assert(svga_have_vgpu10(svga));
+ assert(fs);
+
+ num_inputs = fs->base.info.num_inputs;
+
+ ureg = ureg_create(PIPE_SHADER_VERTEX);
+ if (!ureg)
+ return PIPE_ERROR_OUT_OF_MEMORY;
+
+ /* draw will always add position */
+ dst[0] = ureg_DECL_output(ureg, TGSI_SEMANTIC_POSITION, 0);
+ src[0] = ureg_DECL_vs_input(ureg, 0);
+ num_elements = 1;
+
+ /**
+ * swtnl backend redefines the input layout based on the
+ * fragment shader's inputs. So we only need to passthrough
+ * those inputs that will be consumed by the fragment shader.
+ * Note: DX10 requires the number of vertex elements
+ * specified in the input layout to be no less than the
+ * number of inputs to the vertex shader.
+ */
+ for (i = 0; i < num_inputs; i++) {
+ switch (fs->base.info.input_semantic_name[i]) {
+ case TGSI_SEMANTIC_COLOR:
+ case TGSI_SEMANTIC_GENERIC:
+ case TGSI_SEMANTIC_FOG:
+ dst[num_elements] = ureg_DECL_output(ureg,
+ fs->base.info.input_semantic_name[i],
+ fs->base.info.input_semantic_index[i]);
+ src[num_elements] = ureg_DECL_vs_input(ureg, num_elements);
+ num_elements++;
+ break;
+ default:
+ break;
+ }
+ }
+
+ for (i = 0; i < num_elements; i++) {
+ ureg_MOV(ureg, dst[i], src[i]);
+ }
+
+ ureg_END(ureg);
+
+ memset(&new_vs, 0, sizeof(new_vs));
+ new_vs.base.tokens = ureg_get_tokens(ureg, NULL);
+ tgsi_scan_shader(new_vs.base.tokens, &new_vs.base.info);
+
+ memset(&key, 0, sizeof(key));
+ key.vs.undo_viewport = 1;
+
+ ret = compile_vs(svga, &new_vs, &key, &variant);
+ if (ret != PIPE_OK)
+ return ret;
+
+ ureg_free_tokens(new_vs.base.tokens);
+ ureg_destroy(ureg);
+
+ /* Overwrite the variant key to indicate it's a pass-through VS */
+ memset(&variant->key, 0, sizeof(variant->key));
+ variant->key.vs.passthrough = 1;
+ variant->key.vs.undo_viewport = 1;
+
+ *out_variant = variant;
+
+ return PIPE_OK;
+}
+
+
+static enum pipe_error
+emit_hw_vs(struct svga_context *svga, unsigned dirty)
+{
+ struct svga_shader_variant *variant;
+ struct svga_vertex_shader *vs = svga->curr.vs;
+ struct svga_fragment_shader *fs = svga->curr.fs;
+ enum pipe_error ret = PIPE_OK;
+ struct svga_compile_key key;
+
+ SVGA_STATS_TIME_PUSH(svga_sws(svga), SVGA_STATS_TIME_EMITVS);
+
+ /* If there is an active geometry shader, and it has stream output
+ * defined, then we will skip the stream output from the vertex shader
+ */
+ if (!svga_have_gs_streamout(svga)) {
+ /* No GS stream out */
+ if (svga_have_vs_streamout(svga)) {
+ /* Set VS stream out */
+ ret = svga_set_stream_output(svga, vs->base.stream_output);
+ }
+ else {
+ /* turn off stream out */
+ ret = svga_set_stream_output(svga, NULL);
+ }
+ if (ret != PIPE_OK) {
+ goto done;
+ }
+ }