From a38e75db00c701123251567648d37f7b1f0f89ba Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 16 Dec 2018 09:56:53 +0100 Subject: [PATCH] - improved error reporting for badly defined translations. This needs to be handled by the caller for all use cases because the translation parser lacks the context to do a proper error report. --- src/r_data/r_translate.cpp | 261 +++++++++++---------- src/sc_man.cpp | 2 +- src/scripting/thingdef_properties.cpp | 14 +- src/textures/formats/multipatchtexture.cpp | 11 +- 4 files changed, 150 insertions(+), 138 deletions(-) diff --git a/src/r_data/r_translate.cpp b/src/r_data/r_translate.cpp index c11f9be94..5264095e7 100644 --- a/src/r_data/r_translate.cpp +++ b/src/r_data/r_translate.cpp @@ -633,148 +633,140 @@ bool FRemapTable::AddToTranslation(const char *range) sc.OpenMem("translation", range, int(strlen(range))); sc.SetCMode(true); - try + sc.MustGetToken(TK_IntConst); + start = sc.Number; + sc.MustGetToken(':'); + sc.MustGetToken(TK_IntConst); + end = sc.Number; + sc.MustGetToken('='); + if (start < 0 || start > 255 || end < 0 || end > 255) { + sc.ScriptError("Palette index out of range"); + return false; + } + + sc.MustGetAnyToken(); + + if (sc.TokenType == '[') + { + // translation using RGB values + int r1,g1,b1,r2,g2,b2; + sc.MustGetToken(TK_IntConst); - start = sc.Number; + r1 = sc.Number; + sc.MustGetToken(','); + + sc.MustGetToken(TK_IntConst); + g1 = sc.Number; + sc.MustGetToken(','); + + sc.MustGetToken(TK_IntConst); + b1 = sc.Number; + sc.MustGetToken(']'); sc.MustGetToken(':'); + sc.MustGetToken('['); + sc.MustGetToken(TK_IntConst); - end = sc.Number; - sc.MustGetToken('='); - if (start < 0 || start > 255 || end < 0 || end > 255) - { - sc.ScriptError("Palette index out of range"); - return false; - } + r2 = sc.Number; + sc.MustGetToken(','); + + sc.MustGetToken(TK_IntConst); + g2 = sc.Number; + sc.MustGetToken(','); + + sc.MustGetToken(TK_IntConst); + b2 = sc.Number; + sc.MustGetToken(']'); + + return AddColorRange(start, end, r1, g1, b1, r2, g2, b2); + } + else if (sc.TokenType == '%') + { + // translation using RGB values + double r1,g1,b1,r2,g2,b2; + + sc.MustGetToken('['); + sc.MustGetAnyToken(); + if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); + r1 = sc.Float; + sc.MustGetToken(','); sc.MustGetAnyToken(); + if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); + g1 = sc.Float; + sc.MustGetToken(','); - if (sc.TokenType == '[') - { - // translation using RGB values - int r1,g1,b1,r2,g2,b2; + sc.MustGetAnyToken(); + if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); + b1 = sc.Float; + sc.MustGetToken(']'); + sc.MustGetToken(':'); + sc.MustGetToken('['); - sc.MustGetToken(TK_IntConst); - r1 = sc.Number; - sc.MustGetToken(','); + sc.MustGetAnyToken(); + if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); + r2 = sc.Float; + sc.MustGetToken(','); - sc.MustGetToken(TK_IntConst); - g1 = sc.Number; - sc.MustGetToken(','); + sc.MustGetAnyToken(); + if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); + g2 = sc.Float; + sc.MustGetToken(','); - sc.MustGetToken(TK_IntConst); - b1 = sc.Number; - sc.MustGetToken(']'); - sc.MustGetToken(':'); - sc.MustGetToken('['); + sc.MustGetAnyToken(); + if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); + b2 = sc.Float; + sc.MustGetToken(']'); - sc.MustGetToken(TK_IntConst); - r2 = sc.Number; - sc.MustGetToken(','); - - sc.MustGetToken(TK_IntConst); - g2 = sc.Number; - sc.MustGetToken(','); - - sc.MustGetToken(TK_IntConst); - b2 = sc.Number; - sc.MustGetToken(']'); - - return AddColorRange(start, end, r1, g1, b1, r2, g2, b2); - } - else if (sc.TokenType == '%') - { - // translation using RGB values - double r1,g1,b1,r2,g2,b2; - - sc.MustGetToken('['); - sc.MustGetAnyToken(); - if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); - r1 = sc.Float; - sc.MustGetToken(','); - - sc.MustGetAnyToken(); - if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); - g1 = sc.Float; - sc.MustGetToken(','); - - sc.MustGetAnyToken(); - if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); - b1 = sc.Float; - sc.MustGetToken(']'); - sc.MustGetToken(':'); - sc.MustGetToken('['); - - sc.MustGetAnyToken(); - if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); - r2 = sc.Float; - sc.MustGetToken(','); - - sc.MustGetAnyToken(); - if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); - g2 = sc.Float; - sc.MustGetToken(','); - - sc.MustGetAnyToken(); - if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst); - b2 = sc.Float; - sc.MustGetToken(']'); - - return AddDesaturation(start, end, r1, g1, b1, r2, g2, b2); - } - else if (sc.TokenType == '#') - { - // Colourise translation - int r, g, b; - sc.MustGetToken('['); - sc.MustGetToken(TK_IntConst); - r = sc.Number; - sc.MustGetToken(','); - sc.MustGetToken(TK_IntConst); - g = sc.Number; - sc.MustGetToken(','); - sc.MustGetToken(TK_IntConst); - b = sc.Number; - sc.MustGetToken(']'); - - return AddColourisation(start, end, r, g, b); - } - else if (sc.TokenType == '@') - { - // Tint translation - int a, r, g, b; - - sc.MustGetToken(TK_IntConst); - a = sc.Number; - sc.MustGetToken('['); - sc.MustGetToken(TK_IntConst); - r = sc.Number; - sc.MustGetToken(','); - sc.MustGetToken(TK_IntConst); - g = sc.Number; - sc.MustGetToken(','); - sc.MustGetToken(TK_IntConst); - b = sc.Number; - sc.MustGetToken(']'); - - return AddTint(start, end, r, g, b, a); - } - else - { - int pal1, pal2; - - sc.TokenMustBe(TK_IntConst); - pal1 = sc.Number; - sc.MustGetToken(':'); - sc.MustGetToken(TK_IntConst); - pal2 = sc.Number; - return AddIndexRange(start, end, pal1, pal2); - } + return AddDesaturation(start, end, r1, g1, b1, r2, g2, b2); } - catch (CRecoverableError &err) + else if (sc.TokenType == '#') { - Printf("Error in translation '%s':\n%s\n", range, err.GetMessage()); - return false; + // Colourise translation + int r, g, b; + sc.MustGetToken('['); + sc.MustGetToken(TK_IntConst); + r = sc.Number; + sc.MustGetToken(','); + sc.MustGetToken(TK_IntConst); + g = sc.Number; + sc.MustGetToken(','); + sc.MustGetToken(TK_IntConst); + b = sc.Number; + sc.MustGetToken(']'); + + return AddColourisation(start, end, r, g, b); + } + else if (sc.TokenType == '@') + { + // Tint translation + int a, r, g, b; + + sc.MustGetToken(TK_IntConst); + a = sc.Number; + sc.MustGetToken('['); + sc.MustGetToken(TK_IntConst); + r = sc.Number; + sc.MustGetToken(','); + sc.MustGetToken(TK_IntConst); + g = sc.Number; + sc.MustGetToken(','); + sc.MustGetToken(TK_IntConst); + b = sc.Number; + sc.MustGetToken(']'); + + return AddTint(start, end, r, g, b, a); + } + else + { + int pal1, pal2; + + sc.TokenMustBe(TK_IntConst); + pal1 = sc.Number; + sc.MustGetToken(':'); + sc.MustGetToken(TK_IntConst); + pal2 = sc.Number; + return AddIndexRange(start, end, pal1, pal2); } } @@ -1529,7 +1521,16 @@ void R_ParseTrnslate() do { sc.MustGetToken(TK_StringConst); - NewTranslation.AddToTranslation(sc.String); + + try + { + NewTranslation.AddToTranslation(sc.String); + } + catch (CRecoverableError &err) + { + sc.ScriptMessage("Error in translation '%s':\n" TEXTCOLOR_YELLOW "%s\n", sc.String, err.GetMessage()); + } + } while (sc.CheckToken(',')); int trans = NewTranslation.StoreTranslation(TRANSLATION_Custom); diff --git a/src/sc_man.cpp b/src/sc_man.cpp index 7eb6b3c3a..f1b9b9267 100644 --- a/src/sc_man.cpp +++ b/src/sc_man.cpp @@ -1120,7 +1120,7 @@ void FScanner::ScriptMessage (const char *message, ...) va_end (arglist); } - Printf (TEXTCOLOR_RED "Script error, \"%s\" line %d:\n" TEXTCOLOR_RED "%s\n", ScriptName.GetChars(), + Printf (TEXTCOLOR_RED "Script error, \"%s\"" TEXTCOLOR_RED "line %d:\n" TEXTCOLOR_RED "%s\n", ScriptName.GetChars(), AlreadyGot? AlreadyGotLine : Line, composed.GetChars()); } diff --git a/src/scripting/thingdef_properties.cpp b/src/scripting/thingdef_properties.cpp index f62ad91b7..d54684a48 100644 --- a/src/scripting/thingdef_properties.cpp +++ b/src/scripting/thingdef_properties.cpp @@ -729,7 +729,6 @@ DEFINE_PROPERTY(translation, L, Actor) else { FRemapTable CurrentTranslation; - bool success = true; CurrentTranslation.MakeIdentity(); for(int i = 1; i < PROP_PARM_COUNT; i++) @@ -744,14 +743,17 @@ DEFINE_PROPERTY(translation, L, Actor) else { // parse all ranges to get a complete list of errors, if more than one range fails. - success |= CurrentTranslation.AddToTranslation(str); + try + { + CurrentTranslation.AddToTranslation(str); + } + catch (CRecoverableError &err) + { + bag.ScriptPosition.Message(MSG_WARNING, "Error in translation '%s':\n" TEXTCOLOR_CYAN "%s\n", str, err.GetMessage()); + } } } defaults->Translation = CurrentTranslation.StoreTranslation (TRANSLATION_Decorate); - if (!success) - { - bag.ScriptPosition.Message(MSG_WARNING, "Failed to parse translation"); - } } } diff --git a/src/textures/formats/multipatchtexture.cpp b/src/textures/formats/multipatchtexture.cpp index fb9381808..78fcca56b 100644 --- a/src/textures/formats/multipatchtexture.cpp +++ b/src/textures/formats/multipatchtexture.cpp @@ -49,6 +49,7 @@ #include "v_video.h" #include "v_text.h" #include "cmdlib.h" +#include "doomerrors.h" // On the Alpha, accessing the shorts directly if they aren't aligned on a // 4-byte boundary causes unaligned access warnings. Why it does this at @@ -954,7 +955,15 @@ void FMultiPatchTexture::ParsePatch(FScanner &sc, TexPart & part, TexInit &init) do { sc.MustGetString(); - part.Translation->AddToTranslation(sc.String); + + try + { + part.Translation->AddToTranslation(sc.String); + } + catch (CRecoverableError &err) + { + sc.ScriptMessage("Error in translation '%s':\n" TEXTCOLOR_YELLOW "%s\n", sc.String, err.GetMessage()); + } } while (sc.CheckString(",")); }