]> andersk Git - splint.git/blobdiff - src/llerror.c
*** empty log message ***
[splint.git] / src / llerror.c
index 2585be81613b75d7bc817dbe2f60e00fa9aa780b..c1ab4b6a3e3fd8c203a6b438ee5ca3bd011db60c 100644 (file)
@@ -1,6 +1,6 @@
 /*
 ** LCLint - annotation-assisted static program checker
-** Copyright (C) 1994-2000 University of Virginia,
+** Copyright (C) 1994-2001 University of Virginia,
 **         Massachusetts Institute of Technology
 **
 ** This program is free software; you can redistribute it and/or modify it
 # include "llmain.h"
 # include "version.h"
 
+/* Don't allow possibly-recursive assertion failures. */
+# undef llassert
+# define llassert llassertprotect
+
 static void printIndentMessage (FILE *p_stream, /*@only@*/ cstring p_sc, int p_indent)
    /*@modifies *p_stream@*/ ;
 
@@ -47,16 +51,31 @@ static int mcount = 0;
 static /*@only@*/ cstring saveOneMessage = cstring_undefined;
 static /*@only@*/ fileloc lastparseerror = fileloc_undefined;
 static /*@only@*/ fileloc lastbug = fileloc_undefined;
-static bool llgenerrorreal (/*@only@*/ cstring p_s, fileloc p_fl, bool p_iserror, bool p_indent)
+static bool llgenerrorreal (char *p_srcFile, int p_srcLine, 
+                           /*@only@*/ cstring p_s, fileloc p_fl, bool p_iserror, bool p_indent)
                  /*@modifies g_msgstream@*/ ;
-static bool llgenerroraux (/*@only@*/ cstring p_s, fileloc p_fl, bool p_iserror, bool p_indent)
+static bool llgenerroraux (char *p_srcFile, int p_srcLine, 
+                          /*@only@*/ cstring p_s, fileloc p_fl, bool p_iserror, bool p_indent)
                  /*@modifies g_msgstream@*/ ;
+
 static void printError (FILE *p_stream, /*@only@*/ cstring p_sc)
    /*@globals lastfileloclen @*/
    /*@modifies *p_stream@*/ ;
 static void printMessage (FILE *p_stream, /*@only@*/ cstring p_s)
    /*@modifies *p_stream@*/ ;
 
+static void llgenhint (/*@only@*/ cstring p_s) /*@modifies g_msgstream@*/ ;
+
+static void showSourceLoc (char *srcFile, int srcLine)
+     /*@modifies g_msgstream@*/
+{
+  if (context_getFlag (FLG_SHOWSOURCELOC)) {
+    llgenhint (message ("%s:%d: Source code error generation point.",
+                       cstring_fromChars (srcFile), srcLine));
+  }
+  
+}
+
 static /*@null@*/ char *
 maxcp (/*@null@*/ /*@returned@*/ char *a, /*@null@*/ /*@returned@*/ char *b)
 {
@@ -77,7 +96,9 @@ static bool s_needsPrepare = TRUE;
 
 void prepareMessage (void)
 {
-  if (context_isPreprocessing ()
+  DPRINTF (("Prepare message: %s", bool_unparse (context_loadingLibrary ())));
+
+  if ((context_isPreprocessing () || context_loadingLibrary ())
       && s_needsPrepare
       && context_getDebug (FLG_SHOWSCAN))
     {
@@ -97,7 +118,7 @@ void closeMessage (void)
       llflush ();
       fprintf (stderr, "< more preprocessing .");
 
-      llassert (!s_needsPrepare);
+      llassertprotect (!s_needsPrepare);
       s_needsPrepare = TRUE;
     }
   else
@@ -133,7 +154,7 @@ llmsgplain (/*@only@*/ cstring s)
   closeMessage ();
 }
 
-void flagWarning (cstring s)
+void llerror_flagWarning (cstring s)
 {
   if (context_getFlag (FLG_WARNFLAGS))
     {
@@ -141,20 +162,28 @@ void flagWarning (cstring s)
 
       if (fileloc_isBuiltin (g_currentloc))
        {
-         llmsg (message ("Warning: %s", s));
+         llmsg (message ("Warning: %q", s));
        }
       else
        {
-         llgenmsg (message ("Warning: %s", s), g_currentloc);
+         llgenmsg (message ("Warning: %q", s), g_currentloc);
        }
     }
+  else
+    {
+      cstring_free (s);
+    }
 }
 
 static void
 llgenhint (/*@only@*/ cstring s) /*@modifies g_msgstream@*/
 {
+  int indent = context_getIndentSpaces () - 1;
+
+  if (indent < 0) indent = 0;
+
   context_setNeednl ();
-  printIndentMessage (g_msgstream, s, 2);
+  printIndentMessage (g_msgstream, s, indent);
 }
 
 void
@@ -188,11 +217,73 @@ llshowhint (flagcode f)
     }
 }
 
+static void
+llsuppresshint2 (char c, flagcode f1, flagcode f2)
+{
+
+  if (context_getFlag (FLG_HINTS))
+    {
+      if ((flagcode_numReported (f1) == 0
+          || flagcode_numReported (f2) == 0)
+         || context_getFlag (FLG_FORCEHINTS))
+       {
+         cstring desc = flagcodeHint (f1);
+         context_setNeednl ();
+         lastfileloclen = 8;
+
+         if (cstring_isUndefined (desc))
+           {
+             desc = flagcodeHint (f2);
+           }
+
+         if (flagcode_isNamePrefixFlag (f1))
+           {
+             f1 = FLG_NAMECHECKS;
+           }
+
+         if (flagcode_isNamePrefixFlag (f2))
+           {
+             f2 = FLG_NAMECHECKS;
+           }
+
+         if (f1 == f2)
+           {
+             if (cstring_isDefined (desc))
+               {
+                 llgenhint (message ("%s (Setting %h%s will suppress message)", desc,
+                                     c,
+                                     flagcode_unparse (f1)));
+               }
+             else
+               {
+                 llgenhint (message ("(Setting %h%s will suppress message)", 
+                                     c, flagcode_unparse (f1)));
+               }
+           }
+         else
+           {
+             if (cstring_isDefined (desc))
+               {
+                 llgenhint (message ("%s (Setting either %h%s or %h%s will suppress message)", desc, 
+                                     c,
+                                     flagcode_unparse (f1),
+                                     c,
+                                     flagcode_unparse (f2)));
+               }
+             else
+               {
+                 llgenhint (message ("(Setting either %h%s or %h%s will suppress message)", c,
+                                     flagcode_unparse (f1),
+                                     c, flagcode_unparse (f2)));
+               }
+           }
+       }
+    }
+}
 
 static void
 llsuppresshint (char c, flagcode f)
 {
-
   if (context_getFlag (FLG_HINTS))
     {
       if ((flagcode_numReported (f) == 0) || context_getFlag (FLG_FORCEHINTS))
@@ -209,12 +300,12 @@ llsuppresshint (char c, flagcode f)
          if (cstring_isDefined (desc))
            {
              llgenhint (message ("%s (%h%s will suppress message)", desc, c,
-                                 flagcode_name (f)));
+                                 flagcode_unparse (f)));
            }
          else
            {
              llgenhint (message ("(%h%s will suppress message)", c,
-                                 flagcode_name (f)));
+                                 flagcode_unparse (f)));
            }
        }
     }
@@ -223,7 +314,6 @@ llsuppresshint (char c, flagcode f)
 static void
 llnosuppresshint (flagcode f)
 {
-
   if (context_getFlag (FLG_FORCEHINTS))
     {
       cstring desc = flagcodeHint (f);
@@ -253,9 +343,12 @@ mstring_split (/*@returned@*/ char **sp,
   char *nl;
   char *t;
   char *s = *sp;
+  char *osp = *sp;
 
   *tp = NULL;
 
+  DPRINTF (("Split: %s / %d", *sp, maxline));
+
   if (maxline < MINLINELEN)
     {
       maxline = MINLINELEN;
@@ -264,6 +357,7 @@ mstring_split (/*@returned@*/ char **sp,
   if (*indentchars > 0)
     {
       s = *sp = mstring_concatFree1 (mstring_spaces (*indentchars), s);
+      osp = s;
     }
 
   nl = strchr (s, '\n');
@@ -291,6 +385,7 @@ mstring_split (/*@returned@*/ char **sp,
 
       if (*t == '\0')
        {
+         llassertprotect (*tp == NULL || (*tp > osp));
          return;
        }
 
@@ -298,13 +393,14 @@ mstring_split (/*@returned@*/ char **sp,
        {
          *indentchars += (int) (*t - '\1') + 1;
          t++;
-               }
-
+       }
+      
       *tp = t;
       return;
     }
   else if (size_toInt (strlen (s)) < maxline)
     {
+      llassertprotect (*tp == NULL || (*tp > osp));
       return;
     }
   else
@@ -326,11 +422,14 @@ mstring_split (/*@returned@*/ char **sp,
       splitat = maxcp (lcolon, lsemi);
 
       if (splitat != NULL && ((int)(splitat - s) > MINLINE)
-         && *(splitat + 1) == ' ' && *(splitat + 2) != '}')
+         && *(splitat) != '\0'
+         && *(splitat + 1) == ' ' 
+         && (*(splitat + 2) != '}' && (*(splitat + 2) != '\0'))) 
        {
          *(splitat + 1) = '\0';
          t = splitat + 2;
          *tp = t;
+         llassertprotect (*tp == NULL || (*tp > osp));
          return;
        }
 
@@ -342,24 +441,28 @@ mstring_split (/*@returned@*/ char **sp,
 
       if (*t != ' ' && *t != '\t')
        {
+         llassertprotect (maxline > 0);
          t = mstring_copy (s + maxline);
          *(s + maxline) = '\0';
 
          if (*t == '\0')
            {
              sfree (t);
+             llassertprotect (*tp == NULL || (*tp > osp));
              return;
            }
 
          mstring_markFree (t);
          *tp = t;
+         /* Won't be true since t is a copy: llassertprotect (*tp == NULL || (*tp > osp)); */
          return;
        }
       else
        {
+
          *t = '\0';
          t++;
-
+         
          if (*t == '\0') return;
 
          /*
@@ -367,9 +470,22 @@ mstring_split (/*@returned@*/ char **sp,
          */
 
          *tp = t;
+
+# if 0
+         /* Hack to prevent error case for wierd strings. */
+         if (t <= osp)
+           {
+             *tp = NULL;
+             return;
+           }
+         llassertprotect (*tp == NULL || (*tp > osp));
+# endif          
+
          return;
        }
     }
+
+  BADBRANCH;
 }
 
 static
@@ -447,7 +563,7 @@ llgenindentmsg (/*@only@*/ cstring s, fileloc fl)
   cstring flstring = fileloc_unparse (fl);
 
   prepareMessage ();
-  (void) printIndentMessage (g_msgstream, message ("%q: %q", flstring, s), 3);
+  (void) printIndentMessage (g_msgstream, message ("%q: %q", flstring, s), context_getIndentSpaces ());
   closeMessage ();
 }
 
@@ -455,13 +571,14 @@ void
 llgenindentmsgnoloc (/*@only@*/ cstring s)
 {
   prepareMessage ();
-  (void) printIndentMessage (g_msgstream, s, 3);
+  (void) printIndentMessage (g_msgstream, s, context_getIndentSpaces ());
   closeMessage ();
 }
 
 static bool
-  llgentypeerroraux (flagcode ocode, ctype t1, exprNode e1, ctype t2, exprNode e2,
-                    /*@only@*/ cstring s, fileloc fl)
+llgentypeerroraux (char *srcFile, int srcLine,
+                  flagcode ocode, ctype t1, exprNode e1, ctype t2, exprNode e2,
+                  /*@only@*/ cstring s, fileloc fl)
 {
   cstring hint = cstring_undefined;
   flagcode code = ocode;
@@ -469,6 +586,15 @@ static bool
   ctype ut1 = t1;
   ctype ut2 = t2;
 
+  DPRINTF (("Type error [%s]: %s / %s : %s / %s",
+           flagcode_unparse (ocode),
+           exprNode_unparse (e1), exprNode_unparse (e2),
+           ctype_unparse (t1), ctype_unparse (t2)));
+  
+  DPRINTF (("Bool: %s / %s",
+           bool_unparse (ctype_isBool (t1)),
+           bool_unparse (ctype_isBool (t2))));
+
   /* 
   ** Set the flag using the underlying types that didn't match.
   */
@@ -493,8 +619,9 @@ static bool
     {
       hcode = FLG_NUMLITERAL;
     }
-  else if ((ctype_isDirectBool (ut1) && ctype_isInt (ut2))
-          || (ctype_isInt (ut1) && ctype_isDirectBool (ut2)))
+  else if ((ctype_isManifestBool (ut1) && ctype_isInt (ut2))
+          || (ctype_isInt (ut1) && ctype_isManifestBool (ut2)))
+    /* evs 2000-07-24: was ctype_isDirectBool */
     {
       hcode = FLG_BOOLINT;
     }
@@ -586,56 +713,80 @@ static bool
          ;
        }
     }
-  else if (ctype_isAbstract (ut1) && !ctype_isAbstract (ut2))
+  else
     {
-      uentry ue1 = usymtab_getTypeEntry (ctype_typeId (ut1));
-      ctype ct = uentry_getType (ue1);
+      ;
+    }
 
-      if (ctype_match (ct, ut2))
+  if (hcode == INVALID_FLAG)
+    {
+      DPRINTF (("[%s] %s - %s / %s",
+               ctype_unparse (ut1),
+               bool_unparse (ctype_isEnum (ut1)),
+               bool_unparse (ctype_isEnum (ctype_realType (ut1))),
+               bool_unparse (ctype_isInt (ut2))));
+
+      if (ctype_isAbstract (ut1) && !ctype_isAbstract (ut2))
        {
-         code = FLG_ABSTRACT;
-         hint = message ("Underlying types match, but %s is an "
-                         "abstract type that is not accessible here.",
-                         ctype_unparse (t1));
+         uentry ue1 = usymtab_getTypeEntry (ctype_typeId (ut1));
+         ctype ct = uentry_getType (ue1);
+         
+         if (ctype_match (ct, ut2))
+           {
+             code = FLG_ABSTRACT;
+             hint = message ("Underlying types match, but %s is an "
+                             "abstract type that is not accessible here.",
+                             ctype_unparse (t1));
+           }
        }
-    }
-  else if (ctype_isAbstract (ut2) && !ctype_isAbstract (ut1))
-    {
-      uentry ue = usymtab_getTypeEntry (ctype_typeId (ut2));
-      ctype ct = uentry_getType (ue);
+      else if (ctype_isAbstract (ut2) && !ctype_isAbstract (ut1))
+       {
+         uentry ue = usymtab_getTypeEntry (ctype_typeId (ut2));
+         ctype ct = uentry_getType (ue);
+         
+         if (ctype_match (ct, ut1))
+           {
+             code = FLG_ABSTRACT;
+             hint = message ("Underlying types match, but %s is an "
+                             "abstract type that is not accessible here.",
+                             ctype_unparse (t2));
+           }
+       }
+      else
+       {
+         ; /* Not an abstract mismatch. */
+       }
+                                      
 
-      if (ctype_match (ct, ut1))
+      if (hcode == INVALID_FLAG)
        {
-         code = FLG_ABSTRACT;
-         hint = message ("Underlying types match, but %s is an "
-                         "abstract type that is not accessible here.",
-                         ctype_unparse (t2));
+         if ((ctype_isEnum (ut1) && ctype_isInt (ut2))
+             || (ctype_isEnum (ut2) && ctype_isInt (ut1))) 
+           {
+             hcode = FLG_ENUMINT;
+           }
+         else if ((ctype_isEnum (ut1) && ctype_isInt (ut2))
+                  || (ctype_isEnum (ut2) && ctype_isInt (ut1))) 
+           {
+             hcode = FLG_ENUMINT;
+           }
+         else if ((ctype_isSignedChar (ut1) && ctype_isUnsignedChar (ut2))
+                  || (ctype_isUnsignedChar (ut1) && ctype_isSignedChar (ut2)))
+           {
+             hcode = FLG_CHARUNSIGNEDCHAR;
+           }
+         else if (ctype_isNumeric (ut1) && ctype_isNumeric (ut2)) 
+           {
+             hcode = FLG_RELAXTYPES;
+             DPRINTF (("Setting relax types!"));
+           }
+         else
+           {
+             DPRINTF (("No special type rule: %s / %s", ctype_unparse (ut1),
+                       ctype_unparse (ut2)));
+           }
        }
     }
-  else if ((ctype_isEnum (ut1) && ctype_isArbitraryIntegral (ut2))
-          || (ctype_isEnum (ut2) && ctype_isArbitraryIntegral (ut1))) 
-    {
-      code = FLG_ENUMINT;
-    }
-  else if ((ctype_isEnum (ut1) && ctype_isArbitraryIntegral (ut2))
-          || (ctype_isEnum (ut2) && ctype_isArbitraryIntegral (ut1))) 
-    {
-      code = FLG_ENUMINT;
-    }
-  else if ((ctype_isSignedChar (ut1) && ctype_isUnsignedChar (ut2))
-          || (ctype_isUnsignedChar (ut1) && ctype_isSignedChar (ut2)))
-    {
-      code = FLG_CHARUNSIGNEDCHAR;
-    }
-  else if (ctype_isNumeric (ut1) && ctype_isNumeric (ut2)) 
-    {
-      code = FLG_RELAXTYPES;
-    }
-  else
-    {
-      DPRINTF (("No special type rule: %s / %s", ctype_unparse (ut1),
-               ctype_unparse (ut2)));
-    }
 
   if (cstring_isDefined (hint))
     {
@@ -652,7 +803,7 @@ static bool
     }
   else
     {
-      if (llgenerroraux (s, fl, TRUE, FALSE))
+      if (llgenerroraux (srcFile, srcLine, s, fl, TRUE, FALSE))
        {
          if (hcode != INVALID_FLAG && hcode != ocode)
            {
@@ -674,23 +825,25 @@ static bool
 }
 
 bool
-llgentypeerror (ctype t1, exprNode e1, ctype t2, exprNode e2,
-               /*@only@*/ cstring s, fileloc fl)
+xllgentypeerror (char *srcFile, int srcLine,
+                ctype t1, exprNode e1, ctype t2, exprNode e2,
+                /*@only@*/ cstring s, fileloc fl)
 {
-  return llgentypeerroraux (FLG_TYPE, t1, e1, t2, e2, s, fl);
+  return llgentypeerroraux (srcFile, srcLine, FLG_TYPE, t1, e1, t2, e2, s, fl);
 }
 
 bool
-llgenformattypeerror (ctype t1, exprNode e1, ctype t2, exprNode e2,
-                     /*@only@*/ cstring s, fileloc fl)
+xllgenformattypeerror (char *srcFile, int srcLine,
+                      ctype t1, exprNode e1, ctype t2, exprNode e2,
+                      /*@only@*/ cstring s, fileloc fl)
 {
-  return llgentypeerroraux (FLG_FORMATTYPE, t1, e1, t2, e2, s, fl);
+  return llgentypeerroraux (srcFile, srcLine, FLG_FORMATTYPE, t1, e1, t2, e2, s, fl);
 }
 
 bool
-llgenerror (flagcode o, /*@only@*/ cstring s, fileloc fl)
+xllgenerror (char *srcFile, int srcLine, flagcode o, /*@only@*/ cstring s, fileloc fl)
 {
-  if (llgenerroraux (s, fl, TRUE, FALSE))
+  if (llgenerroraux (srcFile, srcLine, s, fl, TRUE, FALSE))
     {
       llnosuppresshint (o);
       flagcode_recordError (o);
@@ -705,12 +858,13 @@ llgenerror (flagcode o, /*@only@*/ cstring s, fileloc fl)
 }
 
 bool
-llgenhinterror (flagcode o, /*@only@*/ cstring s, /*@only@*/ cstring hint,
-               fileloc fl)
+xllgenhinterror (char *srcFile, int srcLine,
+                flagcode o, /*@only@*/ cstring s, /*@only@*/ cstring hint,
+                fileloc fl)
 {
   if (!context_suppressFlagMsg (o, fl))
     {
-      if (llgenerroraux (s, fl, TRUE, FALSE))
+      if (llgenerroraux (srcFile, srcLine, s, fl, TRUE, FALSE))
        {
          flagcode_recordError (o);
 
@@ -740,15 +894,15 @@ llgenhinterror (flagcode o, /*@only@*/ cstring s, /*@only@*/ cstring hint,
 }
 
 static bool
-llrealerror (/*@only@*/ cstring s, fileloc fl)
+llrealerror (char *srcFile, int srcLine, /*@only@*/ cstring s, fileloc fl)
 {
-  return (llgenerrorreal (s, fl, TRUE, FALSE));
+  return (llgenerrorreal (srcFile, srcLine, s, fl, TRUE, FALSE));
 }
 
 static bool
-llgenerroraux (/*@only@*/ cstring s, fileloc fl, bool iserror, bool indent)
+llgenerroraux (char *srcFile, int srcLine,
+              /*@only@*/ cstring s, fileloc fl, bool iserror, bool indent)
 {
-
   if (context_inSuppressZone (fl))
     {
       cstring_free (s);
@@ -759,19 +913,30 @@ llgenerroraux (/*@only@*/ cstring s, fileloc fl, bool iserror, bool indent)
       ;
     }
 
-  return (llgenerrorreal (s, fl, iserror, indent));
+  if (llgenerrorreal (srcFile, srcLine, s, fl, iserror, indent)) {
+    return TRUE;
+  } else {
+    return FALSE;
+  }
 }
 
-void
-llforceerror (flagcode code, /*@only@*/ cstring s, fileloc fl)
+bool
+xllforceerror (char *srcFile, int srcLine, 
+              flagcode code, /*@only@*/ cstring s, fileloc fl)
 {
   flagcode_recordError (code);
-  (void) llgenerrorreal (s, fl, TRUE, FALSE);
-  closeMessage ();
+
+  if (llgenerrorreal (srcFile, srcLine, s, fl, TRUE, FALSE)) {
+    closeMessage ();
+    return TRUE;
+  } else {
+    return FALSE;
+  }
 }
 
 static bool
-llgenerrorreal (/*@only@*/ cstring s, fileloc fl, bool iserror, bool indent)
+llgenerrorreal (char *srcFile, int srcLine, 
+               /*@only@*/ cstring s, fileloc fl, bool iserror, bool indent)
 {
   cstring flstring;
 
@@ -779,6 +944,8 @@ llgenerrorreal (/*@only@*/ cstring s, fileloc fl, bool iserror, bool indent)
 
   if (!messageLog_add (context_messageLog (), fl, s))
     {
+      DPRINTF (("Duplicate message suppressed! %s / %s",
+               fileloc_unparse (fl), s));
       cstring_free (s);
       return FALSE;
     }
@@ -836,6 +1003,8 @@ llgenerrorreal (/*@only@*/ cstring s, fileloc fl, bool iserror, bool indent)
        }
     }
 
+  DPRINTF (("Here..."));
+
   if (context_hasAliasAnnote ())
     {
       char *sc = cstring_toCharsSafe (s);
@@ -919,7 +1088,6 @@ llgenerrorreal (/*@only@*/ cstring s, fileloc fl, bool iserror, bool indent)
     }
 
   flstring = fileloc_unparse (fl);
-
   lastfileloclen = cstring_length (flstring);
 
   if (indent)
@@ -931,6 +1099,7 @@ llgenerrorreal (/*@only@*/ cstring s, fileloc fl, bool iserror, bool indent)
       printError (g_msgstream, message ("%q: %q", flstring, s));
     }
 
+  showSourceLoc (srcFile, srcLine);
   return TRUE;
 }
 
@@ -953,22 +1122,29 @@ void printMessage (FILE *stream, /*@only@*/ cstring s)
 static
 void printIndentMessage (FILE *stream, /*@only@*/ cstring sc, int indent)
 {
+  static bool inbody = FALSE;
   int maxlen = context_getLineLen ();
   char *s = cstring_toCharsSafe (sc);
+  char *olds = NULL;
 
+  llassertprotect (!inbody);
+  inbody = TRUE;
 
   do
     {
       char *t = NULL;
       char *st = s;
 
+      llassertprotect (st != olds);
+      olds = st;
       mstring_split (&st, &t, maxlen, &indent);
       fprintf (stream, "%s\n", st);
-      llassert (t != s);
+      llassertprotect (t != s);
       s = t;
     } while (s != NULL) ;
 
   cstring_free (sc);
+  inbody = FALSE;
 }
 
 static
@@ -983,6 +1159,8 @@ void printError (FILE *stream, /*@only@*/ cstring sc)
   char *os = s;
   char *t = NULL;
 
+  DPRINTF (("Print error: [%s]", sc));
+
   if (len < (maxlen + nextlen) && (strchr (s, '\n') == NULL))
     {
       mstring_split (&s, &t, maxlen, &indent);
@@ -1023,6 +1201,8 @@ void printError (FILE *stream, /*@only@*/ cstring sc)
     }
   else
     {
+      DPRINTF (("Here 1: [%s]", sc));
+
       if (len < (maxlen + maxlen - 1) && (strchr (s, '\n') != NULL))
        {
          nspaces = ((maxlen + maxlen - 1) - len) / 2;
@@ -1063,7 +1243,9 @@ void printError (FILE *stream, /*@only@*/ cstring sc)
          nspaces = 4;
          nextlen = maxlen - nspaces;
 
+         DPRINTF (("Here 2: [%s]", s));
          mstring_split (&s, &t, maxlen, &indent);
+         DPRINTF (("Here 3: [%s] [%s]", s, t));
 
          fprintf (stream, "%s\n", s);
 
@@ -1082,8 +1264,11 @@ void printError (FILE *stream, /*@only@*/ cstring sc)
              while (t != NULL)
                {
                  char *st = t;
+                 DPRINTF (("Loop: [%s]", t));
                  mstring_split (&st, &t, nextlen, &indent);
+                 DPRINTF (("Split: [%s] [%s]", st, t));
                  fprintf (stream, "%s%s\n", spaces, st);
+                 DPRINTF (("Next..."));
                }
 
              sfree (spaces);
@@ -1091,15 +1276,17 @@ void printError (FILE *stream, /*@only@*/ cstring sc)
        }
     }
 
+  DPRINTF (("Done"));
   sfree (os);
 }
 
 void
-llfatalbug (/*@only@*/ cstring s)
+xllfatalbug (char *srcFile, int srcLine, /*@only@*/ cstring s)
 {
   prepareMessage ();
   printError (stderr, message ("%q: *** Fatal bug: %q",
                               fileloc_unparse (g_currentloc), s));
+  showSourceLoc (srcFile, srcLine);
   printCodePoint ();
   printBugReport ();
   llexit (LLFAILURE);
@@ -1150,12 +1337,17 @@ void llbugaux (cstring file, int line, /*@only@*/ cstring s)
 
   prepareMessage ();
 
+  /*@i3232@*/
+  /*
   if (fileloc_isRealLib (g_currentloc))
     {
-      llfatalerror (message ("%q: Library file appears to be corrupted.  Error: %q:%s",
-                            fileloc_unparse (g_currentloc), 
-                            fileloc_unparseRaw (file, line), s));
+      DPRINTF (("Here we are!"));
+      llfatalerror (message ("%q: Library file appears to be corrupted.  Error: %q: %s",
+                       fileloc_unparse (g_currentloc), 
+                       fileloc_unparseRaw (file, line), 
+                       s));
     }
+  */
 
   if (fileloc_withinLines (lastparseerror, g_currentloc, 7))
     {
@@ -1178,12 +1370,12 @@ void llbugaux (cstring file, int line, /*@only@*/ cstring s)
 
   numbugs++;
 
-  if (numbugs > 5 && fileloc_withinLines (lastbug, g_currentloc, 2))
+  if (numbugs > context_getBugsLimit () && fileloc_withinLines (lastbug, g_currentloc, 2))
     {
-      llfatalerror (message ("%q: Cannot recover from last bug.",
+      llfatalerror (message ("%q: Cannot recover from last bug. (If you really want LCLint to try to continue, use -bugslimit <n>.)",
                             fileloc_unparse (g_currentloc)));
     }
-
+  
   fprintf (stderr, "       (attempting to continue, results may be incorrect)\n");
   fileloc_free (lastbug);
   lastbug = fileloc_copy (g_currentloc);
@@ -1222,15 +1414,12 @@ llfatalerrorLoc (/*@only@*/ cstring s)
   (void) fflush (g_msgstream);
   printError (stderr, message ("%q: %q", fileloc_unparse (g_currentloc), s));
   printError (stderr, cstring_makeLiteral ("*** Cannot continue."));
+  (void) fflush (g_msgstream);
   llexit (LLFAILURE);
 }
 
-/*
-** free's s!
-*/
-
 void
-llgloberror (/*@only@*/ cstring s)
+xllgloberror (char *srcFile, int srcLine, /*@only@*/ cstring s)
 {
   if (context_inSuppressRegion ())
     {
@@ -1243,6 +1432,7 @@ llgloberror (/*@only@*/ cstring s)
       context_hasError ();
       flagcode_recordError (FLG_SPECIAL);
       printError (g_msgstream, s);
+      showSourceLoc (srcFile, srcLine);
       closeMessage ();
     }
 }
@@ -1277,7 +1467,7 @@ lclNumberErrors (void)
 }
 
 void
-lclerror (ltoken t, /*@only@*/ cstring msg)
+xlclerror (char *srcFile, int srcLine, ltoken t, /*@only@*/ cstring msg)
 {
   lclerrors++;
 
@@ -1288,10 +1478,12 @@ lclerror (ltoken t, /*@only@*/ cstring msg)
       lastfileloclen = cstring_length (loc);
 
       printError (g_msgstream, message ("%q: %q", loc, msg));
+      showSourceLoc (srcFile, srcLine);
     }
   else
     {
       printError (g_msgstream, msg);
+      showSourceLoc (srcFile, srcLine);
     }
 }
 
@@ -1451,21 +1643,29 @@ static void llreportparseerror (/*@only@*/ cstring s)
     }
 }
 
-bool lloptgenerror (flagcode o, /*@only@*/ cstring s, fileloc loc)
+bool xlloptgenerror (char *srcFile, int srcLine, 
+                    flagcode o, /*@only@*/ cstring s, fileloc loc)
 {
-  if (llrealerror (s, loc))
+  DPRINTF (("xllopt: %s", s));
+
+  if (llrealerror (srcFile, srcLine, s, loc))
     {
+      DPRINTF (("Here we are!"));
       llsuppresshint ('-', o);
       closeMessage ();
       flagcode_recordError (o);
       return TRUE;
     }
-
-  flagcode_recordSuppressed (o);
-  return FALSE;
+  else
+    {
+      DPRINTF (("Suppressed!"));
+      flagcode_recordSuppressed (o);
+      return FALSE;
+    }
 }
 
-bool optgenerror2 (flagcode f1, flagcode f2, /*@only@*/ cstring s, fileloc loc)
+bool xoptgenerror2 (char *srcFile, int srcLine,
+                   flagcode f1, flagcode f2, /*@only@*/ cstring s, fileloc loc)
 {
   if (context_suppressFlagMsg (f1, loc))
     {
@@ -1481,21 +1681,25 @@ bool optgenerror2 (flagcode f1, flagcode f2, /*@only@*/ cstring s, fileloc loc)
        }
       else
        {
-         if (llrealerror (s, loc))
+         if (llrealerror (srcFile, srcLine, s, loc))
            {
-             llsuppresshint ('-', f2);
+             llsuppresshint2 ('-', f1, f2);
              flagcode_recordError (f2);
              closeMessage ();
              return TRUE;
            }
-
-         flagcode_recordSuppressed (f2);
+         else
+           {
+             flagcode_recordSuppressed (f2);
+           }
        }
     }
+
   return FALSE;
 }
 
-bool optgenerror2n (flagcode f1, flagcode f2, /*@only@*/ cstring s, fileloc loc)
+bool xoptgenerror2n (char *srcFile, int srcLine,
+                    flagcode f1, flagcode f2, /*@only@*/ cstring s, fileloc loc)
 {
 
   if (context_suppressFlagMsg (f1, loc))
@@ -1512,7 +1716,7 @@ bool optgenerror2n (flagcode f1, flagcode f2, /*@only@*/ cstring s, fileloc loc)
        }
       else
        {
-         if (llrealerror (s, loc))
+         if (llrealerror (srcFile, srcLine, s, loc))
            {
              llsuppresshint ('+', f2);
              flagcode_recordError (f2);
@@ -1526,9 +1730,10 @@ bool optgenerror2n (flagcode f1, flagcode f2, /*@only@*/ cstring s, fileloc loc)
   return FALSE;
 }
 
-bool llnoptgenerror (flagcode o, /*@only@*/ cstring s, fileloc loc)
+bool xllnoptgenerror (char *srcFile, int srcLine,
+                     flagcode o, /*@only@*/ cstring s, fileloc loc)
 {
-  if (llrealerror (s, loc))
+  if (llrealerror (srcFile, srcLine, s, loc))
     {
       llsuppresshint ('+', o);
       flagcode_recordError (o);
@@ -1540,7 +1745,6 @@ bool llnoptgenerror (flagcode o, /*@only@*/ cstring s, fileloc loc)
   return FALSE;
 }
 
-
 void llparseerror (cstring s)
 {
   if (context_getFlag (FLG_TRYTORECOVER))
@@ -1594,6 +1798,31 @@ void llparseerror (cstring s)
     }
 }
 
+bool xfsgenerror (char *srcFile, int srcLine,
+                  flagSpec fs, /*@only@*/ cstring s, fileloc fl) 
+{
+  if (flagSpec_isOn (fs, fl))
+    {
+      if (llgenerroraux (srcFile, srcLine, s, fl, TRUE, FALSE))
+       {
+         llsuppresshint ('-', flagSpec_getFirstOn (fs, fl));
+         flagcode_recordError (flagSpec_getFirstOn (fs, fl));
+         return TRUE;
+       }
+      else
+       {
+         flagcode_recordSuppressed (flagSpec_getFirstOn (fs, fl));
+         return FALSE;
+       }
+    }
+  else
+    {
+      flagcode_recordSuppressed (flagSpec_getDominant (fs));
+      cstring_free (s);
+      return FALSE;
+    }
+}
+
 bool doCheck (bool x, cstring pred, cstring file, int line)
 {
   if (!x) {
This page took 0.161081 seconds and 4 git commands to generate.