Advertisement
alexarcan

Incercare lab5, lexical analiser, CT

Mar 24th, 2016
322
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 4.32 KB | None | 0 0
  1. #include<stdio.h>
  2. #include<stdlib.h>
  3. #include<errno.h>
  4. #include<ctype.h>
  5. #include<stdarg.h>
  6. #include<string.h>
  7. #define SAFEALLOC(var,Type) if((var=(Type*)malloc(sizeof(Type)))==NULL) err("not enough memory");
  8. int line;
  9. const char *pCrtCh;
  10.  
  11. enum{
  12.     ID, END,
  13.     //constants
  14.     CT_INT, CT_REAL, CT_CHAR, CT_STRING,
  15.     //keywords
  16.     BREAK, CHAR, DOUBLE, ELSE, FOR, IF, INT, RETURN, STRUCT, VOID, WHILE,
  17.     //delimiters
  18.     COMMA, SEMICOLON, LPAR, RPAR, LBRACKET, RBRACKET, LACC, RACC,
  19.     //operators
  20.     ADD, SUB, MUL, DIV, DOT, AND, OR, NOT, ASSIGN, EQUAL, NOTEQ, LESS, LESSEQ, GREATER, GREATEREQ,
  21.     SPACE, LINECOMMENT, COMMENT
  22. }; //tokens codes
  23.  
  24. typedef struct _Token{
  25.   int code; // code (name)
  26.   union{
  27.     char *text; //  used for ID, CT_STRING(dynamically allocated )
  28.     long  int  i;  //  used   for CT_INT, CT_CHAR
  29.     double r;//  used for   CT_REAL
  30.   };
  31.   int line; // the input file line
  32.   struct _Token *next; // link to the next token
  33. }Token;
  34.  
  35. void err(const char *fmt,...)
  36. {
  37.   va_list va;
  38.   va_start(va,fmt);
  39.   fprintf(stderr,"error: ");
  40.   vfprintf(stderr,fmt,va);
  41.   fputc('\n',stderr);
  42.   va_end(va);
  43.   exit(-1);
  44. }
  45.  
  46. Token *lastToken, *tokens;
  47.  
  48. Token *addTk(int code)
  49. {
  50.   Token *tk;
  51.   SAFEALLOC(tk,Token);
  52.   tk->code=code;
  53.   tk->line=line;
  54.   tk->next=NULL;
  55.   if(lastToken){
  56.     lastToken->next=tk;    
  57.   }else{
  58.       tokens=tk;
  59.   }
  60.   lastToken=tk;
  61.   return tk;  
  62. }
  63.  
  64.  
  65. void tkerr (const Token *tk, const char *fmt,...)
  66. {
  67.   va_list va;
  68.   va_start(va,fmt);
  69.   fprintf(stderr,"error in line %d:", tk->line);
  70.   vfprintf(stderr,fmt,va);
  71.   fputc('\n', stderr);
  72.   va_end(va);
  73.   exit(-1);
  74. }
  75.  
  76. char* createString(const char *s1, const char *s2)
  77. {
  78.   char *result = malloc(strlen(s1)+strlen(s2)+1);//+1 for the zero-terminator
  79.   strcpy(result, s1);
  80.   strcat(result, s2);
  81.   return result;
  82. }
  83.  
  84. int getNextToken()
  85. {
  86.   int state=0, nCh;
  87.   char ch;
  88.   const char *pStartCh;
  89.   Token *tk;
  90.  
  91.   while(1)
  92.   {
  93.    ch=*pCrtCh;
  94.    printf("state: %d, character:%c\n",state,ch);
  95.    switch(state)
  96.    {
  97.      case 0:
  98.        if(ch==' '||ch=='\r'||ch=='\t')
  99.        {
  100.      pCrtCh++; // consume the characterand remains in state 0
  101.        }
  102.        else if(ch=='\n')//handled separately in order to update the current line
  103.        {
  104.      line++;
  105.      pCrtCh++;
  106.        }
  107.        else if(ch>='1' || ch<='9')
  108.        {
  109.      pCrtCh++;
  110.      state=1;    
  111.        }
  112.        else if(ch=='0')
  113.        {
  114.      pCrtCh++;
  115.      state=2;
  116.        }
  117.        else if(ch==0) //the end of the input string
  118.        {
  119.      addTk(END);
  120.      return END;
  121.        }
  122.        else tkerr(addTk(END),"invalid character");
  123.        break;
  124.        
  125.      case 1:
  126.        while(ch>='0'&&ch<='9') pCrtCh++;
  127.        state=3;//CT INT
  128.        break;
  129.        
  130.      case 2:
  131.        pStart=pCrtCh;
  132.        pCrtCh++;
  133.        state=3;
  134.        break;
  135.      
  136.      case 3:
  137.        while(ch>='0'&&ch<='7') pCrtCh++;
  138.        state=4;
  139.      /*case 2:
  140.        nCh=pCrtCh-pStartCh;//the id length
  141.        //keywords tests
  142.        if(nCh==5&&!memcmp(pStartCh,"break",5))tk=addTk(BREAK);
  143.        else if(nCh==4&&!memcmp(pStartCh,"char",4))tk=addTk(CHAR);
  144.        //...all keywords...
  145.        else //if no keyword, then it is an ID
  146.        {
  147.      tk=addTk(ID);
  148.      tk->text=createString(pStartCh,pCrtCh);
  149.        }
  150.        return tk->code;
  151.      */
  152.      case 48:
  153.     if(ch=='=')
  154.     {  
  155.       pCrtCh++;
  156.       state=49;
  157.     }
  158.     else state = 50;
  159.     break;
  160.    
  161.      case 49:
  162.        addTk(ASSIGN);
  163.        return ASSIGN;
  164.    
  165.      case 50:
  166.        addTk(EQUAL);
  167.        return EQUAL;
  168.        
  169.      
  170.        
  171.    }  
  172.    
  173.   }
  174. }
  175.  
  176. void printTokens()
  177. {
  178.     Token *current=tokens;
  179.     while(current!=NULL)
  180.     {
  181.         printf("%i", current->code);
  182.         switch(current->code)
  183.         {
  184.             case ID:
  185.             case CT_STRING:
  186.                 printf(":%s",current->text);
  187.                 break;
  188.             case CT_CHAR:
  189.                 printf(":%c",(int)current->i);
  190.                 break;
  191.             case CT_INT:
  192.                 printf(":%li",current->i);
  193.                 break;
  194.             case CT_REAL:
  195.                 printf(":%lf",current->r);
  196.                 break;
  197.         }
  198.         printf(" ");
  199.         current=current->next;
  200.     }
  201.     printf("\n");
  202. }
  203.  
  204. void getTokens()
  205. {
  206.     do
  207.     {
  208.         getNextToken();
  209.     }while(*pCrtCh);
  210. }
  211.  
  212. int main(void)
  213. {
  214.   getTokens();
  215.   printTokens();
  216.    
  217.   return 0;
  218. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement