]> git.xonotic.org Git - xonotic/gmqcc.git/blobdiff - parser.c
Cleanups
[xonotic/gmqcc.git] / parser.c
index 6216997879e461e4c759cb17ec2959b9e362f5aa..c9f093fdc2e2e7d2177ff55e743956607c01ba88 100644 (file)
--- a/parser.c
+++ b/parser.c
@@ -49,6 +49,7 @@ typedef struct parser_s {
     size_t         translated;
 
     ht ht_imm_string;
+    ht ht_imm_string_dotranslate;
 
     /* must be deleted first, they reference immediates and values */
     ast_value    **accessors;
@@ -257,17 +258,15 @@ static char *parser_strdup(const char *str)
 
 static ast_value* parser_const_string(parser_t *parser, const char *str, bool dotranslate)
 {
-    size_t hash = util_hthash(parser->ht_imm_string, str);
+    ht ht_string = (dotranslate)
+        ? parser->ht_imm_string_dotranslate
+        : parser->ht_imm_string;
+
     ast_value *out;
-    if ( (out = (ast_value*)util_htgeth(parser->ht_imm_string, str, hash)) ) {
-        if (dotranslate && out->name[0] == '#') {
-            char name[32];
-            util_snprintf(name, sizeof(name), "dotranslate_%lu", (unsigned long)(parser->translated++));
-            ast_value_set_name(out, name);
-            out->expression.flags |= AST_FLAG_INCLUDE_DEF;
-        }
+    size_t     hash = util_hthash(ht_string, str);
+
+    if ((out = (ast_value*)util_htgeth(ht_string, str, hash)))
         return out;
-    }
     /*
     for (i = 0; i < vec_size(parser->imm_string); ++i) {
         if (!strcmp(parser->imm_string[i]->constval.vstring, str))
@@ -281,12 +280,14 @@ static ast_value* parser_const_string(parser_t *parser, const char *str, bool do
         out->expression.flags |= AST_FLAG_INCLUDE_DEF;
     } else
         out = ast_value_new(parser_ctx(parser), "#IMMEDIATE", TYPE_STRING);
+
     out->cvq      = CV_CONST;
     out->hasvalue = true;
     out->isimm    = true;
     out->constval.vstring = parser_strdup(str);
     vec_push(parser->imm_string, out);
-    util_htseth(parser->ht_imm_string, str, hash, out);
+    util_htseth(ht_string, str, hash, out);
+
     return out;
 }
 
@@ -949,7 +950,7 @@ static bool parser_sy_apply_operator(parser_t *parser, shunt *sy)
             if (exprs[1]->vtype != TYPE_FLOAT) {
                 ast_type_to_string(exprs[0], ty1, sizeof(ty1));
                 ast_type_to_string(exprs[1], ty2, sizeof(ty2));
-                compile_error(ctx, "invalid types used in expression: cannot divide tyeps %s and %s", ty1, ty2);
+                compile_error(ctx, "invalid types used in expression: cannot divide types %s and %s", ty1, ty2);
                 return false;
             }
             if (exprs[0]->vtype == TYPE_FLOAT) {
@@ -980,7 +981,7 @@ static bool parser_sy_apply_operator(parser_t *parser, shunt *sy)
             {
                 ast_type_to_string(exprs[0], ty1, sizeof(ty1));
                 ast_type_to_string(exprs[1], ty2, sizeof(ty2));
-                compile_error(ctx, "invalid types used in expression: cannot divide tyeps %s and %s", ty1, ty2);
+                compile_error(ctx, "invalid types used in expression: cannot divide types %s and %s", ty1, ty2);
                 return false;
             }
             break;
@@ -2056,7 +2057,7 @@ static bool parse_sya_operand(parser_t *parser, shunt *sy, bool with_labels)
                         correct = correct_str(&corr, parser->correct_variables[i], parser_tokval(parser));
                         if (strcmp(correct, parser_tokval(parser))) {
                             break;
-                        } else if (correct) {
+                        } else  {
                             mem_d(correct);
                             correct = NULL;
                         }
@@ -2514,7 +2515,8 @@ static ast_expression* process_condition(parser_t *parser, ast_expression *cond,
     }
 
     unary = (ast_unary*)cond;
-    while (ast_istype(cond, ast_unary) && unary->op == INSTR_NOT_F)
+    /* ast_istype dereferences cond, should test here for safety */
+    while (cond && ast_istype(cond, ast_unary) && unary->op == INSTR_NOT_F)
     {
         cond = unary->operand;
         unary->operand = NULL;
@@ -2754,7 +2756,12 @@ static bool parse_dowhile(parser_t *parser, ast_block *block, ast_expression **o
     if (vec_last(parser->breaks) != label || vec_last(parser->continues) != label) {
         parseerror(parser, "internal error: label stack corrupted");
         rv = false;
-        ast_delete(*out);
+        /*
+         * Test for NULL otherwise ast_delete dereferences null pointer
+         * and boom.
+         */
+        if (*out)
+            ast_delete(*out);
         *out = NULL;
     }
     else {
@@ -6299,6 +6306,7 @@ parser_t *parser_create()
     parser->aliases = util_htnew(PARSER_HT_SIZE);
 
     parser->ht_imm_string = util_htnew(512);
+    parser->ht_imm_string_dotranslate = util_htnew(512);
 
     /* corrector */
     vec_push(parser->correct_variables, correct_trie_new());
@@ -6416,6 +6424,7 @@ static void parser_remove_ast(parser_t *parser)
     vec_free(parser->functions);
     vec_free(parser->imm_vector);
     vec_free(parser->imm_string);
+    util_htdel(parser->ht_imm_string_dotranslate);
     util_htdel(parser->ht_imm_string);
     vec_free(parser->imm_float);
     vec_free(parser->globals);