본문 바로가기
대학교/4.컴파일러

[03] lex.l

by Jcoder 2019. 4. 14.

 

lex.h
0.00MB
lex.l
0.00MB
main.c
0.00MB

main.c

main.c

#include <stdio.h>

#include <stdlib.h>

#include "lex.h"

 

extern FILE *yyin;       /* input stream */

 

extern int yylval,       /* integer value of TK_NUM */

           yylen;        /* length of TK_ID string */

 

extern char *yytext;    /* point to TK_ID string */

 

main(argc, argv)

   register int argc;

   register char *argv[];

{

   int n, i;

   char *c;

 

   if (argc != 2) {

      fprintf(stderr, "usage: scan <input>\n");

      exit(1) ;

   }

 

   if ((yyin = fopen(argv[1], "r")) == NULL) {

      fprintf(stderr, "can't open %s\n", argv[1]);

      exit(1) ;

   }

 

   n = yylex();

   while (n) {

      switch(n) {

         case TK_ID: printf("%s""TK_ID: ");

            c = yytext;

            for (i=0; i<yylen; i++)

               printf("%c"*c++);

            printf("\n");

            break;

         case TK_NUM:  printf("%s""TK_NUM: ");

            printf("%d\n", yylval);

            break;

         case TK_IF:     printf("%s\n""TK_IF"); break;

         case TK_ELSE:   printf("%s\n""TK_ELSE"); break;

         case TK_ASSIGN: printf("%s\n""TK_ASSIGN"); break;

         case TK_EQ:     printf("%s\n""TK_EQ"); break;

         case TK_NE:     printf("%s\n""TK_NE"); break;

         case TK_GT:     printf("%s\n""TK_GT"); break;

         case TK_GE:     printf("%s\n""TK_GE"); break;

         case TK_LT:     printf("%s\n""TK_LT"); break;

         case TK_LE:     printf("%s\n""TK_LE"); break;

         case TK_LPAR:   printf("%s\n""TK_LPAR"); break;

         case TK_RPAR:   printf("%s\n""TK_RPAR"); break;

         case TK_SCOLON: printf("%s\n""TK_SCOLON"); break;

      }

      n = yylex();

   }

   printf("%s\n""TK_EOF");

 

   fclose(yyin);

}

Colored by Color Scripter

lex.h

lex.h

#define TK_ID           256

#define TK_NUM          257

#define TK_IF           258

#define TK_ELSE         259

#define TK_ASSIGN       260

#define TK_EQ           261

#define TK_NE           262

#define TK_GT           263

#define TK_GE           264

#define TK_LT           265

#define TK_LE           266

#define TK_LPAR         267

#define TK_RPAR         268

#define TK_SCOLON       269

#define TK_EOF          270

lex.l

lex.l

%{

#include <stdio.h>

#include <string.h>

#include "lex.h"

 

static int linenumber = 1, columnnumber = 0;

static int count();

static int comment();

static int invalid_char();

 

char err_msg[30];      /* error message buffer */

int yylval, yylen;

char *yytext;

//static unsigned char *forwward=yytext;

%}

 

delim [ \t\n]

ws {delim}+

letter [A-Za-z]

digit [0-9]

id {letter}({letter}|{digit})*

number {digit}+(\.{digit}+)?(E[+\-]?{digit}+)?

 

%%

 

{ws}       {count();}

if            {count(); return (TK_IF);}

else        {count(); return (TK_ELSE);}

{id}         {yylen = strlen(yytext); count(); return (TK_ID);}

{number} {yylval = atoi(yytext); count(); return (TK_NUM);}

"<"         {count(); return (TK_GT);}

"<="        {count(); return (TK_GE);}

">"        {count(); return (TK_LT);}

">="        {count(); return (TK_LE);}

"="        {count(); return (TK_ASSIGN);}

"!="        {count(); return (TK_NE);}

"=="        {count(); return (TK_EQ);}

"("        {count(); return (TK_LPAR);}

")"        {count(); return (TK_RPAR);}

";"         {count(); return (TK_SCOLON);}

"/*"         {count(); comment();}

.         {count(); invalid_char();}

 

%%

 

yywrap()

{

   return(1);

}

 

/* prints the current line, column error message */

void yyerror(msg)

   char *msg;

{

   fprintf(stderr, "line:%3d, column:%3d %s\n", linenumber, columnnumber, msg); 

}

 

/* keep column numbers correct */

static int count()

{

   int i;

 

   for(i = 0; yytext[i] != '\0'; i++)

      if(yytext[i] == '\n') {

         linenumber++;

         columnnumber = 0;

      }

      else if(yytext[i] == '\t')

         columnnumber += 8 - (columnnumber%8);

      else columnnumber++;

}

 

/* read remainder of comments */

static int comment()

{

   char c;

 

   c = input();

   do {

      unput(c);

      while((c=input()) != '*')

         if (c =='\n'){

            linenumber++;

            columnnumber = 0;

         }

         else if (c =='\t')

            columnnumber += 8 - (columnnumber%8);

         else columnnumber++;

      columnnumber++;    /* count the closing '*' */

   } while((c=input()) != '/');

   columnnumber++;       /* count the closing '/' */

}

 

static int invalid_char()

{

   sprintf(err_msg, "invalid character: 0x%x", yytext[0]);

   yyerror(err_msg);

}

 

Colored by Color Scripter

'대학교 > 4.컴파일러' 카테고리의 다른 글

[02] lex.c  (0) 2019.04.14
[01] wc  (0) 2019.03.20