From 833c897aac2ea2eb006be6aa206058d991976cde Mon Sep 17 00:00:00 2001 From: Zebediah Figura Date: Mon, 16 Aug 2021 21:01:51 -0500 Subject: [PATCH] vkd3d-shader/hlsl: Parse register space reservations. --- libs/vkd3d-shader/hlsl.h | 2 +- libs/vkd3d-shader/hlsl.y | 62 +++++++++++++++++++++++++++++++--------- 2 files changed, 50 insertions(+), 14 deletions(-) diff --git a/libs/vkd3d-shader/hlsl.h b/libs/vkd3d-shader/hlsl.h index aff3c59f..ba8b09d2 100644 --- a/libs/vkd3d-shader/hlsl.h +++ b/libs/vkd3d-shader/hlsl.h @@ -392,7 +392,7 @@ struct hlsl_attribute struct hlsl_reg_reservation { char reg_type; - unsigned int reg_index; + unsigned int reg_space, reg_index; char offset_type; unsigned int offset_index; diff --git a/libs/vkd3d-shader/hlsl.y b/libs/vkd3d-shader/hlsl.y index ea108a52..f99f322d 100644 --- a/libs/vkd3d-shader/hlsl.y +++ b/libs/vkd3d-shader/hlsl.y @@ -1197,17 +1197,18 @@ static bool add_effect_group(struct hlsl_ctx *ctx, const char *name, struct hlsl return true; } -static struct hlsl_reg_reservation parse_reg_reservation(const char *reg_string) +static bool parse_reservation_index(const char *string, char *type, uint32_t *index) { - struct hlsl_reg_reservation reservation = {0}; + if (!sscanf(string + 1, "%u", index)) + return false; - if (!sscanf(reg_string + 1, "%u", &reservation.reg_index)) - { - FIXME("Unsupported register reservation syntax.\n"); - return reservation; - } - reservation.reg_type = ascii_tolower(reg_string[0]); - return reservation; + *type = ascii_tolower(string[0]); + return true; +} + +static bool parse_reservation_space(const char *string, uint32_t *space) +{ + return !ascii_strncasecmp(string, "space", 5) && sscanf(string + 5, "%u", space); } static struct hlsl_reg_reservation parse_packoffset(struct hlsl_ctx *ctx, const char *reg_string, @@ -6330,17 +6331,52 @@ semantic: register_reservation: ':' KW_REGISTER '(' any_identifier ')' { - $$ = parse_reg_reservation($4); + memset(&$$, 0, sizeof($$)); + if (!parse_reservation_index($4, &$$.reg_type, &$$.reg_index)) + hlsl_error(ctx, &@4, VKD3D_SHADER_ERROR_HLSL_INVALID_RESERVATION, + "Invalid register reservation '%s'.", $4); + vkd3d_free($4); } | ':' KW_REGISTER '(' any_identifier ',' any_identifier ')' { - FIXME("Ignoring shader target %s in a register reservation.\n", debugstr_a($4)); - vkd3d_free($4); + memset(&$$, 0, sizeof($$)); + if (parse_reservation_index($6, &$$.reg_type, &$$.reg_index)) + { + hlsl_fixme(ctx, &@4, "Reservation shader target %s.", $4); + } + else if (parse_reservation_space($6, &$$.reg_space)) + { + if (!parse_reservation_index($4, &$$.reg_type, &$$.reg_index)) + hlsl_error(ctx, &@4, VKD3D_SHADER_ERROR_HLSL_INVALID_RESERVATION, + "Invalid register reservation '%s'.", $4); + } + else + { + hlsl_error(ctx, &@6, VKD3D_SHADER_ERROR_HLSL_INVALID_RESERVATION, + "Invalid register or space reservation '%s'.", $6); + } - $$ = parse_reg_reservation($6); + vkd3d_free($4); vkd3d_free($6); } + | ':' KW_REGISTER '(' any_identifier ',' any_identifier ',' any_identifier ')' + { + hlsl_fixme(ctx, &@4, "Reservation shader target %s.", $4); + + memset(&$$, 0, sizeof($$)); + if (!parse_reservation_index($6, &$$.reg_type, &$$.reg_index)) + hlsl_error(ctx, &@6, VKD3D_SHADER_ERROR_HLSL_INVALID_RESERVATION, + "Invalid register reservation '%s'.", $6); + + if (!parse_reservation_space($8, &$$.reg_space)) + hlsl_error(ctx, &@8, VKD3D_SHADER_ERROR_HLSL_INVALID_RESERVATION, + "Invalid register space reservation '%s'.", $8); + + vkd3d_free($4); + vkd3d_free($6); + vkd3d_free($8); + } packoffset_reservation: ':' KW_PACKOFFSET '(' any_identifier ')'