new #pragma LESS_PEDANTIC
[fw/sdcc] / src / SDCC.lex
index b9aafd72112dabe0b186328ee83d92d0a9d5b1af..d844195103eb346ea77685273834fc42976be36e 100644 (file)
@@ -35,13 +35,13 @@ IS       (u|U|l|L)*
 #include <ctype.h>
 #include "common.h"
 #include "newalloc.h"
-    
+#include "dbuf.h"
+
 char *stringLiteral();
 char *currFname;
 
 extern int lineno, column;
 extern char *filename ;
-extern char *fullSrcFileName ;
 int   yylineno = 1               ;
 void count()                     ;
 int process_pragma(char *);
@@ -73,10 +73,14 @@ struct options  save_options  ;
      P_STACKAUTO ,
      P_NOJTBOUND ,
      P_NOOVERLAY ,
+     P_LESSPEDANTIC,
      P_NOGCSE    ,
      P_CALLEE_SAVES,
      P_EXCLUDE   ,
-     P_LOOPREV
+     P_NOIV      ,
+     P_LOOPREV   ,
+     P_OVERLAY_             /* I had a strange conflict with P_OVERLAY while */
+                    /* cross-compiling for MINGW32 with gcc 3.2 */
  };
 
 %}
@@ -91,8 +95,7 @@ struct options  save_options  ;
 <asm>"_endasm" { 
   count();
   *asmp = '\0';
-  yylval.yyinline = malloc (strlen(asmbuff)+1);
-  strcpy(yylval.yyinline,asmbuff);
+  yylval.yyinline = strdup (asmbuff);
   BEGIN(INITIAL);
   return (INLINEASM);
 }
@@ -172,6 +175,8 @@ struct options  save_options  ;
 "xdata"        { count(); TKEYWORD(XDATA); }
 "..."         { count(); return(VAR_ARGS);}
 "__typeof"     { count(); return TYPEOF;}
+"_JavaNative"  { count(); TKEYWORD(JAVANATIVE);}
+"_overlay"     { count(); TKEYWORD(OVERLAY);}
 {L}({L}|{D})*  { count(); return(check_type()); }
 0[xX]{H}+{IS}? { count(); yylval.val = constVal(yytext); return(CONSTANT); }
 0{D}+{IS}?     { count(); yylval.val = constVal(yytext); return(CONSTANT); }
@@ -281,7 +286,9 @@ int checkCurrFile ( char *s)
     /* get the currentfile name info    */
     s++ ;
 
-    if ( strncmp(s,fullSrcFileName,strlen(fullSrcFileName)) == 0) {
+    /* in c1mode fullSrcFileName is NULL */
+    if ( fullSrcFileName &&
+         strncmp(s,fullSrcFileName,strlen(fullSrcFileName)) == 0) {
       lineno = yylineno = lNum;                                        
       currFname = fullSrcFileName ;
     }  else {
@@ -289,8 +296,7 @@ int checkCurrFile ( char *s)
        /* mark the end of the filename */
        while (*s != '"') s++;
        *s = '\0';
-       currFname = malloc (strlen(sb)+1);
-       strcpy(currFname,sb);
+       currFname = strdup (sb);
        lineno = yylineno = lNum;
     }
     filename = currFname ;
@@ -321,93 +327,102 @@ int check_type()
 {
        /* check if it is in the typedef table */
        if (findSym(TypedefTab,NULL,yytext)) {
-               strcpy(yylval.yychar,yytext);
+               strncpyz(yylval.yychar,yytext, SDCC_NAME_MAX);
                return (TYPE_NAME) ;
        }
        else   {
-               strcpy (yylval.yychar,yytext);
+               strncpyz (yylval.yychar,yytext, SDCC_NAME_MAX);
                return(IDENTIFIER);
        }
 }
 
-char strLitBuff[2048]; // TODO: this is asking for the next bug :)
-
 /*
  * Change by JTV 2001-05-19 to not concantenate strings
  * to support ANSI hex and octal escape sequences in string liteals 
  */
 
-char *stringLiteral () {
+char *stringLiteral()
+{
+#define STR_BUF_CHUNCK_LEN  1024
   int ch;
-  char *str = strLitBuff;
-  
-  *str++ = '\"';
+  static struct dbuf_s dbuf;
+  char buf[2];
+
+  if (dbuf.alloc == 0)
+    dbuf_init(&dbuf, STR_BUF_CHUNCK_LEN);
+  else
+    dbuf_set_size(&dbuf, 0);
+
+
+  dbuf_append(&dbuf, "\"", 1);
   /* put into the buffer till we hit the first \" */
-  
-  while (1) {
-    ch = input();
-    
-    if (!ch)
-      break; /* end of input */
-    
-    /* if it is a \ then escape char's are allowed */
-    if (ch == '\\') {
-      ch=input();
-      if (ch=='\n') {
-       /* \<newline> is a continuator */
-       lineno=++yylineno;
-       column=0;
-       continue;
+
+  while ((ch = input()) != 0) {
+    switch (ch) {
+    case '\\':
+      /* if it is a \ then escape char's are allowed */
+      ch = input();
+      if (ch == '\n') {
+        /* \<newline> is a continuator */
+        lineno = ++yylineno;
+        column = 0;
       }
-      *str++ = '\\'; /* backslash in place */
-      *str++ = ch; /* get the escape char, no further check */
-      continue; /* carry on */
-    }
-    
-    /* if new line we have a new line break, which is illegal */
-    if (ch == '\n') {
-      werror (W_NEWLINE_IN_STRING);
-      *str++ = '\n';
-      lineno=++yylineno;
-      column=0;
-      continue;
-    }
-    
-    /* if this is a quote then we have work to do */
-    /* find the next non whitespace character     */
-    /* if that is a double quote then carry on    */
-    if (ch == '\"') {
-      *str++  = ch ; /* Pass end of this string or substring to evaluator */
+      else {
+        buf[0] = '\\';
+        buf[1] = ch;
+        dbuf_append(&dbuf, buf, 2); /* get the escape char, no further check */
+      }
+      break; /* carry on */
+
+    case '\n':
+      /* if new line we have a new line break, which is illegal */
+      werror(W_NEWLINE_IN_STRING);
+      dbuf_append(&dbuf, "\n", 1);
+      lineno = ++yylineno;
+      column = 0;
+      break;
+
+    case '"':
+      /* if this is a quote then we have work to do */
+      /* find the next non whitespace character     */
+      /* if that is a double quote then carry on    */
+      dbuf_append(&dbuf, "\"", 1);  /* Pass end of this string or substring to evaluator */
       while ((ch = input()) && (isspace(ch) || ch=='\\')) {
-       switch (ch) {
-       case '\\':
-         if ((ch=input())!='\n') {
-           werror (W_STRAY_BACKSLASH, column);
-           unput(ch);
-         } else {
-           lineno=++yylineno;
-           column=0;
-         }
-         break;
-       case '\n':
-         yylineno++;
-         break;
-       }
+        switch (ch) {
+        case '\\':
+          if ((ch = input()) != '\n') {
+            werror(W_STRAY_BACKSLASH, column);
+            unput(ch);
+          }
+          else {
+            lineno = ++yylineno;
+            column = 0;
+          }
+          break;
+
+        case '\n':
+          yylineno++;
+          break;
+        }
       }
 
       if (!ch) 
-       break; 
+        goto out;
 
       if (ch != '\"') {
-       unput(ch) ;
-       break ;
+        unput(ch) ;
+        goto out;
       }
+      break;
+
+    default:
+      buf[0] = ch;
+      dbuf_append(&dbuf, buf, 1);  /* Put next substring introducer into output string */
     }
-    *str++  = ch; /* Put next substring introducer into output string */
-  }  
-  *str = '\0';
-  
-  return strLitBuff;
+  }
+
+out:
+  return (char *)dbuf_c_str(&dbuf);
 }
 
 void doPragma (int op, char *cp)
@@ -442,6 +457,9 @@ void doPragma (int op, char *cp)
     case P_NOOVERLAY:
        options.noOverlay = 1;
        break;
+    case P_LESSPEDANTIC:
+        options.lessPedantic = 1;
+       break;
     case P_CALLEE_SAVES:
        {
            int i=0;
@@ -454,9 +472,14 @@ void doPragma (int op, char *cp)
     case P_EXCLUDE:
        parseWithComma(options.excludeRegs, Safe_strdup(cp));
        break;
+    case P_NOIV:
+       options.noiv = 1;
+       break;
     case P_LOOPREV:
        optimize.noLoopReverse = 1;
        break;
+    case P_OVERLAY_:
+       break; /* notyet */
     }
 }
 
@@ -527,6 +550,11 @@ int process_pragma(char *s)
        return 0;
     }
     
+    if (strncmp(cp,PRAGMA_LESSPEDANTIC,strlen(PRAGMA_LESSPEDANTIC)) == 0) {
+       doPragma(P_LESSPEDANTIC,cp+strlen(PRAGMA_LESSPEDANTIC));
+       return 0;
+    }
+    
     if (strncmp(cp,PRAGMA_CALLEESAVES,strlen(PRAGMA_CALLEESAVES)) == 0) {
        doPragma(P_CALLEE_SAVES,cp+strlen(PRAGMA_CALLEESAVES));
        return 0;
@@ -537,6 +565,11 @@ int process_pragma(char *s)
        return 0;
     }
 
+    if (strncmp(cp,PRAGMA_NOIV,strlen(PRAGMA_NOIV)) == 0) {
+       doPragma(P_NOIV,cp+strlen(PRAGMA_NOIV));
+       return 0;
+    }
+
     if (strncmp(cp,PRAGMA_NOLOOPREV,strlen(PRAGMA_NOLOOPREV)) == 0) {
        doPragma(P_LOOPREV,NULL);
        return 0;
@@ -568,10 +601,13 @@ int yyerror(char *s)
 {
    fflush(stdout);
 
-   if (yylineno && filename)
-       fprintf(stdout,"\n%s:%d: %s: token -> '%s' ; column %d\n",
-               filename,yylineno,
-               s,yytext,column);
-   fatalError++;
+   if (yylineno && filename) {
+     fprintf(stdout,"\n%s:%d: %s: token -> '%s' ; column %d\n",
+            filename,yylineno,
+            s,yytext,column);
+     fatalError++;
+   } else {
+     // this comes from an empy file, no problem
+   }
    return 0;
 }