[PATCH vkd3d 3/5] vkd3d-shader: Propagate errors from vkd3d_dxbc_compiler_emit_control_flow_instruction().

Józef Kucia joseph.kucia at gmail.com
Fri Oct 26 08:06:53 CDT 2018


From: Józef Kucia <jkucia at codeweavers.com>

Signed-off-by: Józef Kucia <jkucia at codeweavers.com>
---
 include/private/vkd3d_shader.h           |  3 +-
 libs/vkd3d-shader/spirv.c                | 35 +++++++++++++++---------
 libs/vkd3d-shader/vkd3d_shader_main.c    |  7 +++--
 libs/vkd3d-shader/vkd3d_shader_private.h |  2 +-
 4 files changed, 30 insertions(+), 17 deletions(-)

diff --git a/include/private/vkd3d_shader.h b/include/private/vkd3d_shader.h
index ac163583b65a..b9472a2432e5 100644
--- a/include/private/vkd3d_shader.h
+++ b/include/private/vkd3d_shader.h
@@ -34,7 +34,8 @@ enum vkd3d_result
     VKD3D_ERROR = -1, /* unspecified failure */
     VKD3D_ERROR_OUT_OF_MEMORY = -2,
     VKD3D_ERROR_INVALID_ARGUMENT = -3,
-    VKD3D_ERROR_NOT_IMPLEMENTED = -4,
+    VKD3D_ERROR_INVALID_SHADER = -4,
+    VKD3D_ERROR_NOT_IMPLEMENTED = -5,
 
     VKD3D_FORCE_32_BIT_ENUM(VKD3D_RESULT),
 };
diff --git a/libs/vkd3d-shader/spirv.c b/libs/vkd3d-shader/spirv.c
index f2ed8b888dbf..13631a07fd1b 100644
--- a/libs/vkd3d-shader/spirv.c
+++ b/libs/vkd3d-shader/spirv.c
@@ -5079,7 +5079,7 @@ static struct vkd3d_control_flow_info *vkd3d_dxbc_compiler_find_innermost_breaka
     return NULL;
 }
 
-static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_compiler *compiler,
+static int vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_compiler *compiler,
         const struct vkd3d_shader_instruction *instruction)
 {
     uint32_t loop_header_block_id, loop_body_block_id, continue_block_id;
@@ -5095,7 +5095,7 @@ static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_
     {
         case VKD3DSIH_IF:
             if (!(cf_info = vkd3d_dxbc_compiler_push_control_flow_level(compiler)))
-                return;
+                return VKD3D_ERROR_OUT_OF_MEMORY;
 
             val_id = vkd3d_dxbc_compiler_emit_load_src(compiler, src, VKD3DSP_WRITEMASK_0);
             condition_id = vkd3d_dxbc_compiler_emit_int_to_bool(compiler, instruction->flags, 1, val_id);
@@ -5149,7 +5149,7 @@ static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_
 
         case VKD3DSIH_LOOP:
             if (!(cf_info = vkd3d_dxbc_compiler_push_control_flow_level(compiler)))
-                return;
+                return VKD3D_ERROR_OUT_OF_MEMORY;
 
             loop_header_block_id = vkd3d_spirv_alloc_id(builder);
             loop_body_block_id = vkd3d_spirv_alloc_id(builder);
@@ -5190,7 +5190,7 @@ static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_
 
         case VKD3DSIH_SWITCH:
             if (!(cf_info = vkd3d_dxbc_compiler_push_control_flow_level(compiler)))
-                return;
+                return VKD3D_ERROR_OUT_OF_MEMORY;
 
             merge_block_id = vkd3d_spirv_alloc_id(builder);
 
@@ -5206,8 +5206,6 @@ static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_
             cf_info->u.switch_.case_blocks = NULL;
             cf_info->u.switch_.case_blocks_size = 0;
             cf_info->u.switch_.case_block_count = 0;
-            vkd3d_array_reserve((void **)&cf_info->u.switch_.case_blocks, &cf_info->u.switch_.case_blocks_size,
-                    10, sizeof(*cf_info->u.switch_.case_blocks));
             cf_info->u.switch_.default_block_id = 0;
             cf_info->inside_block = false;
             cf_info->current_block = VKD3D_BLOCK_SWITCH;
@@ -5215,6 +5213,11 @@ static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_
             vkd3d_spirv_build_op_name(builder, merge_block_id, "switch%u_merge", compiler->switch_id);
 
             ++compiler->switch_id;
+
+            if (!vkd3d_array_reserve((void **)&cf_info->u.switch_.case_blocks, &cf_info->u.switch_.case_blocks_size,
+                    10, sizeof(*cf_info->u.switch_.case_blocks)))
+                return VKD3D_ERROR_OUT_OF_MEMORY;
+
             break;
 
         case VKD3DSIH_ENDSWITCH:
@@ -5252,7 +5255,7 @@ static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_
 
             if (!vkd3d_array_reserve((void **)&cf_info->u.switch_.case_blocks, &cf_info->u.switch_.case_blocks_size,
                     2 * (cf_info->u.switch_.case_block_count + 1), sizeof(*cf_info->u.switch_.case_blocks)))
-                return;
+                return VKD3D_ERROR_OUT_OF_MEMORY;
 
             label_id = vkd3d_spirv_alloc_id(builder);
             if (cf_info->inside_block) /* fall-through */
@@ -5292,7 +5295,7 @@ static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_
             if (!(breakable_cf_info = vkd3d_dxbc_compiler_find_innermost_breakable_cf_construct(compiler)))
             {
                 FIXME("Unhandled break instruction.\n");
-                return;
+                return VKD3D_ERROR_INVALID_SHADER;
             }
 
             if (breakable_cf_info->current_block == VKD3D_BLOCK_LOOP)
@@ -5318,7 +5321,7 @@ static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_
             if (!(loop_cf_info = vkd3d_dxbc_compiler_find_innermost_loop(compiler)))
             {
                 ERR("Invalid 'breakc' instruction outside loop.\n");
-                return;
+                return VKD3D_ERROR_INVALID_SHADER;
             }
 
             merge_block_id = vkd3d_dxbc_compiler_emit_conditional_branch(compiler,
@@ -5336,7 +5339,7 @@ static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_
             if (!(loop_cf_info = vkd3d_dxbc_compiler_find_innermost_loop(compiler)))
             {
                 ERR("Invalid 'continue' instruction outside loop.\n");
-                return;
+                return VKD3D_ERROR_INVALID_SHADER;
             }
 
             vkd3d_spirv_build_op_branch(builder, loop_cf_info->u.loop.continue_block_id);
@@ -5352,7 +5355,7 @@ static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_
             if (!(loop_cf_info = vkd3d_dxbc_compiler_find_innermost_loop(compiler)))
             {
                 ERR("Invalid 'continuec' instruction outside loop.\n");
-                return;
+                return VKD3D_ERROR_INVALID_SHADER;
             }
 
             merge_block_id = vkd3d_dxbc_compiler_emit_conditional_branch(compiler,
@@ -5380,6 +5383,8 @@ static void vkd3d_dxbc_compiler_emit_control_flow_instruction(struct vkd3d_dxbc_
             ERR("Unexpected instruction %#x.\n", instruction->handler_idx);
             break;
     }
+
+    return VKD3D_OK;
 }
 
 static void vkd3d_dxbc_compiler_emit_deriv_instruction(struct vkd3d_dxbc_compiler *compiler,
@@ -6474,9 +6479,11 @@ static bool is_dcl_instruction(enum VKD3D_SHADER_INSTRUCTION_HANDLER handler_idx
     return VKD3DSIH_DCL <= handler_idx && handler_idx <= VKD3DSIH_DCL_VERTICES_OUT;
 }
 
-void vkd3d_dxbc_compiler_handle_instruction(struct vkd3d_dxbc_compiler *compiler,
+int vkd3d_dxbc_compiler_handle_instruction(struct vkd3d_dxbc_compiler *compiler,
         const struct vkd3d_shader_instruction *instruction)
 {
+    int ret = VKD3D_OK;
+
     if (!is_dcl_instruction(instruction->handler_idx) && !compiler->after_declarations_section)
     {
         compiler->after_declarations_section = true;
@@ -6681,7 +6688,7 @@ void vkd3d_dxbc_compiler_handle_instruction(struct vkd3d_dxbc_compiler *compiler
         case VKD3DSIH_RETP:
         case VKD3DSIH_SWITCH:
         case VKD3DSIH_TEXKILL:
-            vkd3d_dxbc_compiler_emit_control_flow_instruction(compiler, instruction);
+            ret = vkd3d_dxbc_compiler_emit_control_flow_instruction(compiler, instruction);
             break;
         case VKD3DSIH_DSX:
         case VKD3DSIH_DSX_COARSE:
@@ -6774,6 +6781,8 @@ void vkd3d_dxbc_compiler_handle_instruction(struct vkd3d_dxbc_compiler *compiler
         default:
             FIXME("Unhandled instruction %#x.\n", instruction->handler_idx);
     }
+
+    return ret;
 }
 
 static void vkd3d_dxbc_compiler_emit_store_shader_output(struct vkd3d_dxbc_compiler *compiler,
diff --git a/libs/vkd3d-shader/vkd3d_shader_main.c b/libs/vkd3d-shader/vkd3d_shader_main.c
index 348fa5d6e7c6..71410f1d10cb 100644
--- a/libs/vkd3d-shader/vkd3d_shader_main.c
+++ b/libs/vkd3d-shader/vkd3d_shader_main.c
@@ -120,10 +120,13 @@ int vkd3d_shader_compile_dxbc(const struct vkd3d_shader_code *dxbc,
             return VKD3D_ERROR_INVALID_ARGUMENT;
         }
 
-        vkd3d_dxbc_compiler_handle_instruction(spirv_compiler, &instruction);
+        if ((ret = vkd3d_dxbc_compiler_handle_instruction(spirv_compiler, &instruction)) < 0)
+            break;
     }
 
-    ret = vkd3d_dxbc_compiler_generate_spirv(spirv_compiler, spirv);
+    if (ret >= 0)
+        ret = vkd3d_dxbc_compiler_generate_spirv(spirv_compiler, spirv);
+
     vkd3d_dxbc_compiler_destroy(spirv_compiler);
     vkd3d_shader_parser_destroy(&parser);
     return ret;
diff --git a/libs/vkd3d-shader/vkd3d_shader_private.h b/libs/vkd3d-shader/vkd3d_shader_private.h
index a2747acd09b2..1d79c91602b8 100644
--- a/libs/vkd3d-shader/vkd3d_shader_private.h
+++ b/libs/vkd3d-shader/vkd3d_shader_private.h
@@ -809,7 +809,7 @@ struct vkd3d_dxbc_compiler *vkd3d_dxbc_compiler_create(const struct vkd3d_shader
         const struct vkd3d_shader_interface *shader_interface,
         const struct vkd3d_shader_compile_arguments *compile_args,
         const struct vkd3d_shader_scan_info *scan_info) DECLSPEC_HIDDEN;
-void vkd3d_dxbc_compiler_handle_instruction(struct vkd3d_dxbc_compiler *compiler,
+int vkd3d_dxbc_compiler_handle_instruction(struct vkd3d_dxbc_compiler *compiler,
         const struct vkd3d_shader_instruction *instruction) DECLSPEC_HIDDEN;
 int vkd3d_dxbc_compiler_generate_spirv(struct vkd3d_dxbc_compiler *compiler,
         struct vkd3d_shader_code *spirv) DECLSPEC_HIDDEN;
-- 
2.18.1




More information about the wine-devel mailing list