From fdb3db52751ca6f9e9ca5e3ec8606f1727d7ea16 Mon Sep 17 00:00:00 2001 From: Zebediah Figura Date: Mon, 8 Jun 2020 16:49:38 -0500 Subject: [PATCH] d3dcompiler: Check for missing return value semantics on the entry point. Signed-off-by: Zebediah Figura Signed-off-by: Matteo Bruni Signed-off-by: Alexandre Julliard --- dlls/d3dcompiler_43/hlsl.y | 50 +++++++++++++++------------ dlls/d3dcompiler_43/tests/hlsl_d3d9.c | 12 +++++++ 2 files changed, 40 insertions(+), 22 deletions(-) diff --git a/dlls/d3dcompiler_43/hlsl.y b/dlls/d3dcompiler_43/hlsl.y index 79becca2578..b5057db8870 100644 --- a/dlls/d3dcompiler_43/hlsl.y +++ b/dlls/d3dcompiler_43/hlsl.y @@ -2971,7 +2971,34 @@ struct bwriter_shader *parse_hlsl(enum shader_type type, DWORD major, DWORD mino hlsl_parse(); - TRACE("Compilation status = %d\n", hlsl_ctx.status); + if (hlsl_ctx.status == PARSE_ERR) + goto out; + + if (!(entry_func = get_func_entry(entrypoint))) + { + hlsl_message("error: entry point %s is not defined\n", debugstr_a(entrypoint)); + goto out; + } + + if (!type_is_void(entry_func->return_type) + && entry_func->return_type->type != HLSL_CLASS_STRUCT && !entry_func->semantic) + { + hlsl_report_message(entry_func->loc, HLSL_LEVEL_ERROR, + "entry point \"%s\" is missing a return value semantic", entry_func->func->name); + } + + /* Index 0 means unused; index 1 means function entry, so start at 2. */ + index_instructions(entry_func->body, 2); + + if (TRACE_ON(hlsl_parser)) + { + TRACE("IR dump.\n"); + wine_rb_for_each_entry(&hlsl_ctx.functions, dump_function, NULL); + } + + compute_liveness(entry_func); + +out: if (messages) { if (hlsl_ctx.messages.size) @@ -2989,27 +3016,6 @@ struct bwriter_shader *parse_hlsl(enum shader_type type, DWORD major, DWORD mino d3dcompiler_free((void *)hlsl_ctx.source_files[i]); d3dcompiler_free(hlsl_ctx.source_files); - if (hlsl_ctx.status == PARSE_ERR) - goto out; - - if (!(entry_func = get_func_entry(entrypoint))) - { - hlsl_message("error: entry point %s is not defined\n", debugstr_a(entrypoint)); - goto out; - } - - /* Index 0 means unused; index 1 means function entry, so start at 2. */ - index_instructions(entry_func->body, 2); - - if (TRACE_ON(hlsl_parser)) - { - TRACE("IR dump.\n"); - wine_rb_for_each_entry(&hlsl_ctx.functions, dump_function, NULL); - } - - compute_liveness(entry_func); - -out: TRACE("Freeing functions IR.\n"); wine_rb_destroy(&hlsl_ctx.functions, free_function_rb, NULL); diff --git a/dlls/d3dcompiler_43/tests/hlsl_d3d9.c b/dlls/d3dcompiler_43/tests/hlsl_d3d9.c index fba8a638b57..e82b466de23 100644 --- a/dlls/d3dcompiler_43/tests/hlsl_d3d9.c +++ b/dlls/d3dcompiler_43/tests/hlsl_d3d9.c @@ -1133,6 +1133,18 @@ static void test_fail(void) "{\n" " return float4(0, 0, 0, 0);\n" "}", + + /* 15 */ + "float4 test()\n" + "{\n" + " return float4(0, 0, 0, 0);\n" + "}", + + "float4 test(out float4 o : SV_TARGET)\n" + "{\n" + " o = float4(1, 1, 1, 1);\n" + " return float4(0, 0, 0, 0);\n" + "}", }; static const char *targets[] = {"ps_2_0", "ps_3_0", "ps_4_0"};