* support/Util/SDCCerr.c,
[fw/sdcc] / src / SDCCast.c
index a788e69a85bf4b30c624b902f14c1979b06469e4..3209c0c9eaf80b0633ab362ff092279a8380c81d 100644 (file)
@@ -429,7 +429,8 @@ resolveSymbols (ast * tree)
                               tree->trueLabel->name)))
            tree->trueLabel = csym;
          else
-           werror (E_LABEL_UNDEF, tree->trueLabel->name);
+           werrorfl (tree->filename, tree->lineno, E_LABEL_UNDEF,
+                     tree->trueLabel->name);
        }
 
       if (tree->falseLabel)
@@ -439,7 +440,8 @@ resolveSymbols (ast * tree)
                               tree->falseLabel->name)))
            tree->falseLabel = csym;
          else
-           werror (E_LABEL_UNDEF, tree->falseLabel->name);
+           werrorfl (tree->filename, tree->lineno, E_LABEL_UNDEF,
+                     tree->falseLabel->name);
        }
 
     }
@@ -454,7 +456,8 @@ resolveSymbols (ast * tree)
                              tree->opval.val->sym->name);
 
       if (!csym)
-       werror (E_LABEL_UNDEF, tree->opval.val->sym->name);
+       werrorfl (tree->filename, tree->lineno, E_LABEL_UNDEF,
+                 tree->opval.val->sym->name);
       else
        tree->opval.val->sym = csym;
 
@@ -493,7 +496,9 @@ resolveSymbols (ast * tree)
                tree->opval.val->sym->etype = newIntLink ();
              tree->opval.val->etype = tree->opval.val->etype;
              tree->opval.val->type = tree->opval.val->sym->type;
-             werror (W_IMPLICIT_FUNC, tree->opval.val->sym->name);
+             werrorfl (tree->filename, tree->lineno, W_IMPLICIT_FUNC,
+                       tree->opval.val->sym->name);
+             //tree->opval.val->sym->undefined = 1;
              allocVariables (tree->opval.val->sym);
            }
          else
@@ -670,6 +675,8 @@ processParms (ast * func,
   /* exist and this is not defined as a variable arg   */
   if (!defParm && actParm && !IFFUNC_HASVARARGS(func->ftype))
     {
+      //if (func->type==EX_VALUE && func->opval.val->sym->undefined)
+      //  return 1; /* Already gave them an undefined function error */
       werror (E_TOO_MANY_PARMS);
       return 1;
     }
@@ -857,8 +864,9 @@ createIvalStruct (ast * sym, sym_link * type, initList * ilist)
     }
 
   if (iloop) {
-    werror (W_EXCESS_INITIALIZERS, "struct", 
-           sym->opval.val->sym->name, sym->opval.val->sym->lineDef);
+    werrorfl (filename, sym->opval.val->sym->lineDef,
+             W_EXCESS_INITIALIZERS, "struct", 
+             sym->opval.val->sym->name);
   }
 
   return rast;
@@ -918,7 +926,7 @@ createIvalArray (ast * sym, sym_link * type, initList * ilist)
            char *name=sym->opval.val->sym->name;
            int lineno=sym->opval.val->sym->lineDef;
            
-           werror (W_EXCESS_INITIALIZERS, "array", name, lineno);
+           werrorfl (filename, lineno, W_EXCESS_INITIALIZERS, "array", name);
        }
     }
     else
@@ -943,7 +951,7 @@ createIvalArray (ast * sym, sym_link * type, initList * ilist)
                // there has to be a better way
                char *name=sym->opval.val->sym->name;
                int lineno=sym->opval.val->sym->lineDef;
-               werror (W_EXCESS_INITIALIZERS, "array", name, lineno);
+               werrorfl (filename, lineno, W_EXCESS_INITIALIZERS, "array", name);
                
                break;
            }
@@ -985,8 +993,18 @@ createIvalCharPtr (ast * sym, sym_link * type, ast * iexpr)
       /* to the array element */
       char *s = SPEC_CVAL (iexpr->etype).v_char;
       int i = 0;
+      int size = getSize (iexpr->ftype);
+      int symsize = getSize (type);
+      
+      if (size>symsize)
+        {
+         if (size>(symsize+1))
+           werrorfl (iexpr->filename, iexpr->lineno, W_EXCESS_INITIALIZERS,
+                     "string", sym->opval.val->sym->name);
+         size = symsize;
+       }
 
-      while (*s)
+      for (i=0;i<size;i++)
        {
          rast = newNode (NULLOP,
                          rast,
@@ -994,15 +1012,8 @@ createIvalCharPtr (ast * sym, sym_link * type, ast * iexpr)
                                   newNode ('[', sym,
                                   newAst_VALUE (valueFromLit ((float) i))),
                                   newAst_VALUE (valueFromLit (*s))));
-         i++;
          s++;
        }
-      rast = newNode (NULLOP,
-                     rast,
-                     newNode ('=',
-                              newNode ('[', sym,
-                                  newAst_VALUE (valueFromLit ((float) i))),
-                              newAst_VALUE (valueFromLit (*s))));
 
       // now WE don't need iexpr's symbol anymore
       freeStringSymbol(AST_SYMBOL(iexpr));
@@ -1114,8 +1125,9 @@ gatherAutoInit (symbol * autoChain)
            work = initAggregates (sym, sym->ival, NULL);
          } else {
            if (getNelements(sym->type, sym->ival)>1) {
-             werror (W_EXCESS_INITIALIZERS, "scalar", 
-                     sym->name, sym->lineDef);
+             werrorfl (filename, sym->lineDef,
+                       W_EXCESS_INITIALIZERS, "scalar", 
+                       sym->name);
            }
            work = newNode ('=', newAst_VALUE (symbolVal (newSym)),
                            list2expr (sym->ival));
@@ -1149,8 +1161,9 @@ gatherAutoInit (symbol * autoChain)
            work = initAggregates (sym, sym->ival, NULL);
          } else {
            if (getNelements(sym->type, sym->ival)>1) {
-             werror (W_EXCESS_INITIALIZERS, "scalar", 
-                     sym->name, sym->lineDef);
+             werrorfl (filename, sym->lineDef,
+                       W_EXCESS_INITIALIZERS, "scalar", 
+                       sym->name);
            }
            work = newNode ('=', newAst_VALUE (symbolVal (sym)),
                            list2expr (sym->ival));
@@ -1194,12 +1207,14 @@ stringToSymbol (value * val)
   static int charLbl = 0;
   symbol *sym;
   set *sp;
+  int size;
 
   // have we heard this before?
   for (sp=statsg->syms; sp; sp=sp->next) {
     sym=sp->item;
-    if (sym->isstrlit && 
-       !strcmp(SPEC_CVAL(sym->etype).v_char, SPEC_CVAL(val->etype).v_char)) {
+    size = getSize (sym->type);
+    if (sym->isstrlit && size == getSize (val->type) &&
+       !memcmp(SPEC_CVAL(sym->etype).v_char, SPEC_CVAL(val->etype).v_char, size)) {
       // yes, this is old news. Don't publish it again.
       sym->isstrlit++; // but raise the usage count
       return symbolVal(sym);
@@ -2093,6 +2108,28 @@ decorateType (ast * tree)
   {
     ast *dtl, *dtr;
 
+    #if 0
+    if (tree->opval.op == NULLOP || tree->opval.op == BLOCK)
+      {
+        if (tree->left && tree->left->type == EX_OPERAND
+           && (tree->left->opval.op == INC_OP
+               || tree->left->opval.op == DEC_OP)
+           && tree->left->left)
+         {
+           tree->left->right = tree->left->left;
+           tree->left->left = NULL;
+         }
+        if (tree->right && tree->right->type == EX_OPERAND
+           && (tree->right->opval.op == INC_OP
+               || tree->right->opval.op == DEC_OP)
+           && tree->right->left)
+         {
+           tree->right->right = tree->right->left;
+           tree->right->left = NULL;
+         }
+      }
+    #endif
+    
     dtl = decorateType (tree->left);
     /* delay right side for '?' operator since conditional macro expansions might
        rely on this */
@@ -2242,6 +2279,10 @@ decorateType (ast * tree)
        break;
       }
       
+      /* This breaks with extern declarations, bitfields, and perhaps other */
+      /* cases (gcse). Let's leave this optimization disabled for now and   */
+      /* ponder if there's a safe way to do this. -- EEP                    */
+      #if 0
       if (IS_ADDRESS_OF_OP (tree->left) && IS_AST_SYM_VALUE(tree->left->left)
           && SPEC_ABSA (AST_SYMBOL (tree->left->left)->etype))
         {
@@ -2274,7 +2315,8 @@ decorateType (ast * tree)
             tree->left = NULL;
             tree->right = NULL;
         }
-
+      #endif
+      
       return tree;
 
       /*------------------------------------------------------------------*/
@@ -2383,7 +2425,7 @@ decorateType (ast * tree)
          goto errorTreeReturn;
        }
 
-      if (SPEC_SCLS (tree->left->etype) == S_REGISTER)
+      if (LETYPE(tree) && SPEC_SCLS (tree->left->etype) == S_REGISTER)
        {
          werror (E_ILLEGAL_ADDR, "address of register variable");
          goto errorTreeReturn;
@@ -2406,7 +2448,9 @@ decorateType (ast * tree)
          werror (E_LVALUE_REQUIRED, "address of");
          goto errorTreeReturn;
        }
-      if (SPEC_SCLS (tree->left->etype) == S_CODE)
+      if (!LETYPE (tree))
+        DCL_TYPE (p) = POINTER;
+      else if (SPEC_SCLS (tree->left->etype) == S_CODE)
        DCL_TYPE (p) = CPOINTER;
       else if (SPEC_SCLS (tree->left->etype) == S_XDATA)
        DCL_TYPE (p) = FPOINTER;
@@ -2773,7 +2817,7 @@ decorateType (ast * tree)
       /* if unary plus */
       if (!tree->right)
        {
-         if (!IS_INTEGRAL (LTYPE (tree)))
+         if (!IS_ARITHMETIC (LTYPE (tree)))
            {
              werror (E_UNARY_OP, '+');
              goto errorTreeReturn;
@@ -3246,7 +3290,7 @@ decorateType (ast * tree)
          tree->opval.val = valCastLiteral (
            LTYPE (tree),
            element->offset
-            + floatFromVal (valFromType (RETYPE (tree->right->left->left)))
+            + floatFromVal (valFromType (RTYPE (tree->right->left->left)))
           );
 
          TTYPE (tree) = tree->opval.val->type;
@@ -3282,7 +3326,7 @@ decorateType (ast * tree)
           sym->cdef = 1;
           sym->isref = 1;
           SPEC_STAT (sym->etype) = 1;
-          SPEC_ADDR(sym->etype) = floatFromVal (valFromType (RETYPE (tree)));
+          SPEC_ADDR(sym->etype) = floatFromVal (valFromType (RTYPE (tree)));
           SPEC_ABSA(sym->etype) = 1;
           addSym (SymbolTab, sym, sym->name, 0, 0, 0);
           allocGlobal (sym);
@@ -3300,7 +3344,7 @@ decorateType (ast * tree)
          tree->type = EX_VALUE;
          tree->opval.val =
          valCastLiteral (LTYPE (tree),
-                         floatFromVal (valFromType (RETYPE (tree))));
+                         floatFromVal (valFromType (RTYPE (tree))));
          TTYPE (tree) = tree->opval.val->type;
          tree->left = NULL;
          tree->right = NULL;
@@ -3345,8 +3389,8 @@ decorateType (ast * tree)
          IS_LITERAL (LTYPE (tree)))
        {
          tree->type = EX_VALUE;
-         tree->opval.val = valLogicAndOr (valFromType (LETYPE (tree)),
-                                          valFromType (RETYPE (tree)),
+         tree->opval.val = valLogicAndOr (valFromType (LTYPE (tree)),
+                                          valFromType (RTYPE (tree)),
                                           tree->opval.op);
          tree->right = tree->left = NULL;
          TETYPE (tree) = getSpec (TTYPE (tree) =
@@ -3387,7 +3431,7 @@ decorateType (ast * tree)
          if (compareType (LTYPE (tree), RTYPE (tree)) == 0)
            {
              werror (E_COMPARE_OP);
-             fprintf (stderr, "comparring type ");
+             fprintf (stderr, "comparing type ");
              printTypeChain (LTYPE (tree), stderr);
              fprintf (stderr, "to type ");
              printTypeChain (RTYPE (tree), stderr);
@@ -3790,7 +3834,7 @@ decorateType (ast * tree)
 
       if (compareType (currFunc->type->next, RTYPE (tree)) == 0)
        {
-         werror (W_RETURN_MISMATCH);
+         werrorfl (tree->filename, tree->lineno, W_RETURN_MISMATCH);
          printFromToType (RTYPE(tree), currFunc->type->next);
          goto errorTreeReturn;
        }
@@ -3799,7 +3843,7 @@ decorateType (ast * tree)
          && tree->right &&
          !IS_VOID (RTYPE (tree)))
        {
-         werror (E_FUNC_VOID);
+         werrorfl (tree->filename, tree->lineno, E_FUNC_VOID);
          goto errorTreeReturn;
        }
 
@@ -3834,7 +3878,7 @@ decorateType (ast * tree)
       /* the switch value must be an integer */
       if (!IS_INTEGRAL (LTYPE (tree)))
        {
-         werror (E_SWITCH_NON_INTEGER);
+         werrorfl (tree->filename, tree->lineno, E_SWITCH_NON_INTEGER);
          goto errorTreeReturn;
        }
       LRVAL (tree) = 1;
@@ -4091,7 +4135,7 @@ createCase (ast * swStat, ast * caseVal, ast * stmnt)
   /* then case is out of context            */
   if (!swStat)
     {
-      werror (E_CASE_CONTEXT);
+      werrorfl (caseVal->filename, caseVal->lineno, E_CASE_CONTEXT);
       return NULL;
     }
 
@@ -4099,14 +4143,14 @@ createCase (ast * swStat, ast * caseVal, ast * stmnt)
   /* if not a constant then error  */
   if (!IS_LITERAL (caseVal->ftype))
     {
-      werror (E_CASE_CONSTANT);
+      werrorfl (caseVal->filename, caseVal->lineno, E_CASE_CONSTANT);
       return NULL;
     }
 
   /* if not a integer than error */
   if (!IS_INTEGRAL (caseVal->ftype))
     {
-      werror (E_CASE_NON_INTEGER);
+      werrorfl (caseVal->filename, caseVal->lineno, E_CASE_NON_INTEGER);
       return NULL;
     }
 
@@ -4129,6 +4173,12 @@ createCase (ast * swStat, ast * caseVal, ast * stmnt)
        {
          pval->next = caseVal->opval.val;
        }
+      else if ((int) floatFromVal (val) == cVal)
+       {
+         werrorfl (caseVal->filename, caseVal->lineno, E_DUPLICATE_LABEL,
+                   "case");
+         return NULL;
+       }
       else
        {
          /* we found a value greater than */
@@ -4161,7 +4211,7 @@ createCase (ast * swStat, ast * caseVal, ast * stmnt)
 /* createDefault - creates the parse tree for the default statement */
 /*-----------------------------------------------------------------*/
 ast *
-createDefault (ast * swStat, ast * stmnt)
+createDefault (ast * swStat, ast * defaultVal, ast * stmnt)
 {
   char defLbl[SDCC_NAME_MAX + 1];
 
@@ -4169,7 +4219,14 @@ createDefault (ast * swStat, ast * stmnt)
   /* then case is out of context            */
   if (!swStat)
     {
-      werror (E_CASE_CONTEXT);
+      werrorfl (defaultVal->filename, defaultVal->lineno, E_CASE_CONTEXT);
+      return NULL;
+    }
+
+  if (swStat->values.switchVals.swDefault)
+    {
+      werrorfl (defaultVal->filename, defaultVal->lineno, E_DUPLICATE_LABEL,
+               "default");
       return NULL;
     }
 
@@ -5694,3 +5751,29 @@ void PA(ast *t)
 {
        ast_print(t,stdout,0);
 }
+
+
+
+/*-----------------------------------------------------------------*/
+/* astErrors : returns non-zero if errors present in tree          */
+/*-----------------------------------------------------------------*/
+int astErrors(ast *t)
+{
+  int errors=0;
+  
+  if (t)
+    {
+      if (t->isError)
+        errors++;
+  
+      if (t->type == EX_VALUE
+          && t->opval.val->sym
+          && t->opval.val->sym->undefined)
+        errors++;
+
+      errors += astErrors(t->left);
+      errors += astErrors(t->right);
+    }
+    
+  return errors;
+}