X-Git-Url: https://git.xonotic.org/?p=xonotic%2Fgmqcc.git;a=blobdiff_plain;f=parser.cpp;h=518a06da1919a22933031ef15f71652af95f118a;hp=51f7e1ea6c571d20b158953b803b306f52f1c35d;hb=69fa4f8dbd018c092a1e53671f6ce5d4248aac5c;hpb=1a18ff529420930cb4116484991c2dabe3a70654 diff --git a/parser.cpp b/parser.cpp index 51f7e1e..518a06d 100644 --- a/parser.cpp +++ b/parser.cpp @@ -3120,6 +3120,52 @@ static bool parse_switch_go(parser_t *parser, ast_block *block, ast_expression * return false; } swcase.m_value = parse_expression_leave(parser, false, false, false); + + if (!operand->compareType(*swcase.m_value)) { + char ty1[1024]; + char ty2[1024]; + + ast_type_to_string(swcase.m_value, ty1, sizeof ty1); + ast_type_to_string(operand, ty2, sizeof ty2); + + auto fnLiteral = [](ast_expression *expression) -> char* { + if (!ast_istype(expression, ast_value)) + return nullptr; + ast_value *value = (ast_value *)expression; + if (!value->m_hasvalue) + return nullptr; + char *string = nullptr; + basic_value_t *constval = &value->m_constval; + switch (value->m_vtype) + { + case TYPE_FLOAT: + util_asprintf(&string, "%.2f", constval->vfloat); + return string; + case TYPE_VECTOR: + util_asprintf(&string, "'%.2f %.2f %.2f'", + constval->vvec.x, + constval->vvec.y, + constval->vvec.z); + return string; + case TYPE_STRING: + util_asprintf(&string, "\"%s\"", constval->vstring); + return string; + default: + break; + } + return nullptr; + }; + + char *literal = fnLiteral(swcase.m_value); + if (literal) + compile_error(parser_ctx(parser), "incompatible type `%s` for switch case `%s` expected `%s`", ty1, literal, ty2); + else + compile_error(parser_ctx(parser), "incompatible type `%s` for switch case expected `%s`", ty1, ty2); + mem_d(literal); + delete switchnode; + return false; + } + if (!swcase.m_value) { delete switchnode; parseerror(parser, "expected expression for case"); @@ -6226,7 +6272,7 @@ bool parser_finish(parser_t *parser, const char *output) if (!ast_istype(it, ast_value)) continue; asvalue = (ast_value*)it; - if (!asvalue->m_uses && !asvalue->m_hasvalue && asvalue->m_vtype != TYPE_FUNCTION) { + if (!asvalue->m_uses && asvalue->m_cvq != CV_CONST && asvalue->m_vtype != TYPE_FUNCTION) { retval = retval && !compile_warning(asvalue->m_context, WARN_UNUSED_VARIABLE, "unused global: `%s`", asvalue->m_name); } @@ -6324,11 +6370,15 @@ bool parser_finish(parser_t *parser, const char *output) } parser_remove_ast(parser); - if (compile_Werrors) { - con_out("*** there were warnings treated as errors\n"); - compile_show_werrors(); - retval = false; - } + auto fnCheckWErrors = [&retval]() { + if (compile_Werrors) { + con_out("*** there were warnings treated as errors\n"); + compile_show_werrors(); + retval = false; + } + }; + + fnCheckWErrors(); if (retval) { if (OPTS_OPTION_BOOL(OPTION_DUMPFIN)) @@ -6339,6 +6389,9 @@ bool parser_finish(parser_t *parser, const char *output) delete ir; return false; } + + // ir->generate can generate compiler warnings + fnCheckWErrors(); } delete ir; return retval;