CD Manual
CD Manual
Course Objectives: To enlighten the student with knowledge base in compiler design and its
applications
List of Experiments:
4. Write a C program to implement the Brute force technique of Top down Parsing.
6. Write C program to compute the First and Follow Sets for the given Grammar.
7. Write a C program for eliminating the left recursion and left factoring of a given grammar
8. Write a C program to check the validity of input string using Predictive Parser.
9. Write a C program for implementation of LR parsing algorithm to accept a given input string.
10. Write a C program for implementation of a Shift Reduce Parser using Stack Data Structure to
accept a given input string of a given grammar.
13. Write a C program for generating the three address code of a given expression/statement.
Page 1
COMPILER DESIGN LAB III YEAR II SEM
CONTENTS
Page 2
COMPILER DESIGN LAB III YEAR II SEM
Page 3
COMPILER DESIGN LAB III YEAR II SEM
if (len == 0)
return (false);
for (i = 0; i <len; i++) {
if (str[i] != '0' &&str[i] != '1' &&str[i] != '2'
&&str[i] != '3' &&str[i] != '4' &&str[i] != '5'
&&str[i] != '6' &&str[i] != '7' &&str[i] != '8'
&&str[i] != '9' || (str[i] == '-' && i > 0))
return (false);
}
return (true);
}
if (len == 0)
return (false);
for (i = 0; i <len; i++) {
if (str[i] != '0' &&str[i] != '1' &&str[i] != '2'
&&str[i] != '3' &&str[i] != '4' &&str[i] != '5'
&&str[i] != '6' &&str[i] != '7' &&str[i] != '8'
&&str[i] != '9' &&str[i] != '.' ||
(str[i] == '-' && i > 0))
return (false);
if (str[i] == '.')
hasDecimal = true;
}
return (hasDecimal);
}
Page 4
COMPILER DESIGN LAB III YEAR II SEM
right++;
left = right;
} else if (isDelimiter(str[right]) == true && left != right
|| (right == len&&left != right)) {
char* subStr = subString(str, left, right - 1);
if (isKeyword(subStr) == true)
printf("'%s' IS A KEYWORD\n", subStr);
// DRIVER FUNCTION
int main()
Page 5
COMPILER DESIGN LAB III YEAR II SEM
{
// maximum length of string is 100 here
charstr[100] = "int a = b + 1c; ";
return (0);
}
Output
'int' IS A KEYWORD
'a' IS A VALID IDENTIFIER
'=' IS AN OPERATOR
'b' IS A VALID IDENTIFIER
'+' IS AN OPERATOR
'1c' IS NOT A VALID IDENTIFIER
Page 6
COMPILER DESIGN LAB III YEAR II SEM
Lex:-
The lex is used in the manner depicted. A specification of the lexical analyzer is
preferred by creating a program lex.1 in the lex language.
Then lex.1 is run through the lex compiler to produce a ‘c’ program lex.yy.c.
The program lex.yy.c consists of a tabular representation of a transition diagram
constructed from the regular expression of lex.1 together with a standard routine that
uses table of recognize leximes.
Lex.yy.c is run through the ‘C’ compiler to produce as object program a.out, which is the
lexical analyzer that transform as input stream into sequence of tokens.
Algorithm:
1. First, a specification of a lexical analyzer is prepared by creating a program lexp.l in the LEX
language.
2. The Lexp.l program is run through the LEX compiler to produce an equivalent code in C
language named Lex.yy.c
3. The program lex.yy.c consists of a table constructed from the Regular Expressions of Lexp.l,
together with standard routines that uses the table to recognize lexemes.
4. Finally, lex.yy.c program is run through the C Compiler to produce an object program a.out,
which is the lexical analyzer that transforms an input stream into a sequence of tokens.
Program: lexp.l
%{
int COMMENT=0;
%}
identifier [a-zA-Z][a-zA-Z0-9]*
%%
#.* {printf ("\n %s is a Preprocessor Directive",yytext);}
int |
Page 7
COMPILER DESIGN LAB III YEAR II SEM
float |
main |
if |
else |
printf |
scanf |
for |
char |
getch |
while {printf("\n %s is a Keyword",yytext);}
"/*" {COMMENT=1;}
"*/" {COMMENT=0;}
{identifier}\( {if(!COMMENT) printf("\n Function:\t %s",yytext);}
\{ {if(!COMMENT) printf("\n Block Begins");
\} {if(!COMMENT) printf("\n Block Ends");}
{identifier}(\[[0-9]*\])? {if(!COMMENT) printf("\n %s is an Identifier",yytext);}
\".*\" {if(!COMMENT) printf("\n %s is a String",yytext);}
[0-9]+ {if(!COMMENT) printf("\n %s is a Number",yytext);}
\)(\;)? {if(!COMMENT) printf("\t");ECHO;printf("\n");}
\( ECHO;
= {if(!COMMENT) printf("\n%s is an Assmt oprtr",yytext);}
\<= |
\>= |
\< |
== {if(!COMMENT) printf("\n %s is a Rel. Operator",yytext);}
.|\n
%%
int main(int argc, char **argv)
{
if(argc>1)
{
FILE *file;
file=fopen(argv[1],"r");
if(!file)
{
printf("\n Could not open the file: %s",argv[1]);
exit(0);
}
yyin=file;
}
yylex(); printf("\n\n");
return 0;
}
int yywrap()
{
return 0;
}
Output:
test.c
Page 8
COMPILER DESIGN LAB III YEAR II SEM
#include<stdio.h>
main()
{
int fact=1,n;
for(int i=1;i<=n;i++)
{
fact=fact*i;
} printf("Factorial Value of N is", fact);
getch();
}
$ lex lexp.l
$ cc lex.yy.c
$ ./a.out test.c
#include<stdio.h>is a Preprocessor Directive
Function: main( )
Block Begins
int is a Keyword
fact is an Identifier
= is an Assignment Operator
1 is a Number
n is an Identifier
Function: for(
int is a Keyword
i is an Identifier
= is an Assignment Operator
1 is a Number
i is an Identifier
<= is a Relational Operator
n is an Identifier
i is an Identifier
);
Block Begins
fact is an Identifier
= is an Assignment Operator
fact is an Identifier
i is an Identifier
Block Ends
Function: printf(
"Factorial Value of N is" is a String
fact is an Identifier );
Function: getch( );
Block Ends
Page 9
COMPILER DESIGN LAB III YEAR II SEM
#include<stdio.h>
void main()
{
char s[5];
//clrscr();
printf("\n Enter any operator:");
gets(s);
switch(s[0])
{
case'>': if(s[1]=='=')
printf("\n Greater than or equal");
else
printf("\n Greater than");
break;
case'<': if(s[1]=='=')
printf("\n Less than or equal");
else
printf("\nLess than");
break;
case'=': if(s[1]=='=')
printf("\nEqual to");
else
printf("\nAssignment");
break;
case'!': if(s[1]=='=')
printf("\nNot Equal");
else
printf("\n Bit Not");
break;
case'&': if(s[1]=='&')
printf("\nLogical AND");
else
printf("\n Bitwise AND");
break;
case'|': if(s[1]=='|')
printf("\nLogical OR");
else
printf("\nBitwise OR");
break;
case'+': printf("\n Addition");
break;
case'-': printf("\nSubstraction");
break;
case'*': printf("\nMultiplication");
break;
case'/': printf("\nDivision");
Page 10
COMPILER DESIGN LAB III YEAR II SEM
break;
case'%': printf("Modulus");
break;
default: printf("\n Not a operator");
}
//getch();
}
Output
Enter any operator:*
Multiplication
Page 11
COMPILER DESIGN LAB III YEAR II SEM
Output
Page 12
COMPILER DESIGN LAB III YEAR II SEM
if(E() &&ip=="\0"){
printf("\n--------------------------------\n");
printf("\n String is successfully parsed\n");
}
else{
printf("\n--------------------------------\n");
printf("Error in parsing String\n");
}
}
int E()
{
printf("%s\tE->TE' \n",ip);
if(T())
{
if(Edash())
{
return 1;
}
else
return 0;
}
else
return 0;
}
intEdash()
{
if(*ip=='+')
{
printf("%s\tE'->+TE' \n",ip);
ip++;
if(T())
{
if(Edash())
{
return 1;
}
else
Page 13
COMPILER DESIGN LAB III YEAR II SEM
return 0;
}
else
return 0;
}
else
{
printf("%s\tE'->^ \n",ip);
return 1;
}
}
int T()
{
printf("%s\tT->FT' \n",ip);
if(F())
{
if(Tdash())
{
return 1;
}
else
return 0;
}
else
return 0;
}
intTdash()
{
if(*ip=='*')
{
printf("%s\tT'->*FT' \n",ip);
ip++;
if(F())
{
if(Tdash())
{
return 1;
}
else
return 0;
}
else
return 0;
}
else
{
printf("%s\tT'->^ \n",ip);
return 1;
}
}
Page 14
COMPILER DESIGN LAB III YEAR II SEM
int F()
{
if(*ip=='(')
{
printf("%s\tF->(E) \n",ip);
ip++;
if(E())
{
if(*ip==')')
{
ip++;
return 0;
}
else
return 0;
}
else
return 0;
}
else if(*ip=='i')
{
ip++;
printf("%s\tF->id \n",ip);
return 1;
}
else
return 0;
}
Output
Enter the string
compilerdesign
Input Action
--------------------------------
compilerdesign E->TE'
compilerdesign T->FT'
--------------------------------
Error in parsing String
Page 15
COMPILER DESIGN LAB III YEAR II SEM
6.write a c program to compute the first and follow sets for the given
grammar
#include<stdio.h>
#include<ctype.h>
#include<string.h>
int count, n = 0;
intkay;
Page 16
COMPILER DESIGN LAB III YEAR II SEM
char done[count];
intptr = -1;
if (xxx == 1)
continue;
// Function call
findfirst(c, 0, 0);
ptr += 1;
if (first[i] == calc_first[point1][lark])
{
chk = 1;
break;
}
}
if(chk == 0)
{
printf("%c, ", first[i]);
calc_first[point1][point2++] = first[i];
Page 17
COMPILER DESIGN LAB III YEAR II SEM
}
}
printf("}\n");
jm = n;
point1++;
}
printf("\n");
printf("-----------------------------------------------\n\n");
chardonee[count];
ptr = -1;
// Checking if Follow of ck
// has already been calculated
for(kay = 0; kay<= ptr; kay++)
if(ck == donee[kay])
xxx = 1;
if (xxx == 1)
continue;
land += 1;
// Function call
follow(ck);
ptr += 1;
Page 18
COMPILER DESIGN LAB III YEAR II SEM
chk = 1;
break;
}
}
if(chk == 0)
{
printf("%c, ", f[i]);
calc_follow[point1][point2++] = f[i];
}
}
printf(" }\n\n");
km = m;
point1++;
}
}
void follow(char c)
{
int i, j;
Page 19
COMPILER DESIGN LAB III YEAR II SEM
int j;
Page 20
COMPILER DESIGN LAB III YEAR II SEM
Output
First(E) = { (, i, }
First(R) = { +, #, }
First(T) = { (, i, }
First(Y) = { *, #, }
First(F) = { (, i, }
-----------------------------------------------
Follow(E) = { $, ), }
Follow(R) = { $, ), }
Page 21
COMPILER DESIGN LAB III YEAR II SEM
Follow(T) = { +, $, ), }
Follow(Y) = { +, $, ), }
Follow(F) = { *, +, $, ), }
Page 22
COMPILER DESIGN LAB III YEAR II SEM
7.write a c program for eliminating the left recursion and left factoring of a
given grammar
#include<iostream.h>
#include<stdio.h>
#include<conio.h>
#include<string.h>
//Structure Declaration
struct production
{
char lf;
charrt[10];
intprod_rear;
intfl;
};
struct production prodn[20],prodn_new[20]; //Creation of object
//Variables Declaration
int b=-1,d,f,q,n,m=0,c=0;
char terminal[20],nonterm[20],alpha[10],extra[10];
char epsilon='^';
void main()
{
clrscr();
//Input of Productions
Page 23
COMPILER DESIGN LAB III YEAR II SEM
cin>>prodn[cnt].lf;
cout<<"->";
cin>>prodn[cnt].rt;
prodn[cnt].prod_rear=strlen(prodn[cnt].rt);
prodn[cnt].fl=0;
}
for(int cnt1=0;cnt1<n;cnt1++)
{
for(int cnt2=cnt1+1;cnt2<n;cnt2++)
{
if(prodn[cnt1].lf==prodn[cnt2].lf)
{
cnt=0;
int p=-1;
while((prodn[cnt1].rt[cnt]!='\0')&&(prodn[cnt2].rt[cnt]!='\0'))
{
if(prodn[cnt1].rt[cnt]==prodn[cnt2].rt[cnt])
{
extra[++p]=prodn[cnt1].rt[cnt];
prodn[cnt1].fl=1;
prodn[cnt2].fl=1;
}
else
{
if(p==-1)
break;
else
{
int h=0,u=0;
prodn_new[++b].lf=prodn[cnt1].lf;
strcpy(prodn_new[b].rt,extra);
prodn_new[b].rt[p+1]=alpha[c];
prodn_new[++b].lf=alpha[c];
for(int g=cnt;g<prodn[cnt2].prod_rear;g++)
prodn_new[b].rt[h++]=prodn[cnt2].rt[g];
prodn_new[++b].lf=alpha[c];
for(g=cnt;g<=prodn[cnt1].prod_rear;g++)
prodn_new[b].rt[u++]=prodn[cnt1].rt[g];
m=1;
break;
}
}
cnt++;
}
if((prodn[cnt1].rt[cnt]==0)&&(m==0))
{
int h=0;
prodn_new[++b].lf=prodn[cnt1].lf;
Page 24
COMPILER DESIGN LAB III YEAR II SEM
strcpy(prodn_new[b].rt,extra);
prodn_new[b].rt[p+1]=alpha[c];
prodn_new[++b].lf=alpha[c];
prodn_new[b].rt[0]=epsilon;
prodn_new[++b].lf=alpha[c];
for(int g=cnt;g<prodn[cnt2].prod_rear;g++)
prodn_new[b].rt[h++]=prodn[cnt2].rt[g];
}
if((prodn[cnt2].rt[cnt]==0)&&(m==0))
{
int h=0;
prodn_new[++b].lf=prodn[cnt1].lf;
strcpy(prodn_new[b].rt,extra);
prodn_new[b].rt[p+1]=alpha[c];
prodn_new[++b].lf=alpha[c];
prodn_new[b].rt[0]=epsilon;
prodn_new[++b].lf=alpha[c];
for(int g=cnt;g<prodn[cnt1].prod_rear;g++)
prodn_new[b].rt[h++]=prodn[cnt1].rt[g];
}
c++;
m=0;
}
}
}
//Display of Output
cout<<"\n\n********************************";
cout<<"\n AFTER LEFT FACTORING ";
cout<<"\n********************************";
cout<<endl;
for(int cnt3=0;cnt3<=b;cnt3++)
{
cout<<"Production "<<cnt3+1<<" is: ";
cout<<prodn_new[cnt3].lf;
cout<<"->";
cout<<prodn_new[cnt3].rt;
cout<<endl<<endl;
}
for(int cnt4=0;cnt4<n;cnt4++)
{
if(prodn[cnt4].fl==0)
{
cout<<"Production "<<cnt3++<<" is: ";
cout<<prodn[cnt4].lf;
cout<<"->";
cout<<prodn[cnt4].rt;
cout<<endl<<endl;
}
Page 25
COMPILER DESIGN LAB III YEAR II SEM
}
getche();
} //end of main program
Output
Left recursion
#include<stdio.h>
#include<string.h>
void main()
{
char input[100],l[50],r[50],temp[10],tempprod[20],productions[25][50];
int i=0,j=0,flag=0,consumed=0;
printf("Enter the productions: ");
scanf("%1s->%s",l,r);
printf("%s",r);
while(sscanf(r+consumed,"%[^|]s",temp) == 1 && consumed <= strlen(r))
{
if(temp[0] == l[0])
{
flag = 1;
sprintf(productions[i++],"%s->%s%s'\0",l,temp+1,l);
}
else
sprintf(productions[i++],"%s'->%s%s'\0",l,temp,l);
consumed += strlen(temp)+1;
}
if(flag == 1)
Page 26
COMPILER DESIGN LAB III YEAR II SEM
{
sprintf(productions[i++],"%s->ε\0",l);
printf("The productions after eliminating Left Recursion are:\n");
for(j=0;j<i;j++)
printf("%s\n",productions[j]);
}
else
printf("The Given Grammar has no Left Recursion");
}
Output
Enter the productions: E->E+E|T
E+E|TThe productions after eliminating Left Recursion are:
E->+EE'
E'->TE'
E->ε
Page 27
COMPILER DESIGN LAB III YEAR II SEM
#include<stdio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>
#define SIZE 128
#define NONE -1
#define EOS '\0'
#define NUM 257
#define KEYWORD 258
#define ID 259
#define DONE 260
#define MAX 999
char lexemes[MAX];
char buffer[SIZE];
int lastchar=-1;
int lastentry=0;
int tokenval=DONE;
int lineno=1;
int lookahead;
struct entry
{
char *lexptr;
int token;
}
symtable[100];
struct entry
keywords[]= {"if",KEYWORD,"else",KEYWORD,"for",KEYWORD,"int",KEYWORD,"float",KEYWORD,
"double",KEYWORD,"char",KEYWORD,"struct",KEYWORD,"return",KEYWORD,0,0
};
void Error_Message(char *m)
{
fprintf(stderr,"line %d, %s \n",lineno,m);
exit(1);
}
int look_up(char s[ ])
{
int k;
for(k=lastentry; k>0; k--)
if(strcmp(symtable[k].lexptr,s)==0)
return k;
return 0;
}
int insert(char s[ ],int tok)
{
int len;
len=strlen(s);
if(lastentry+1>=MAX)
Error_Message("Symbpl table is full");
if(lastchar+len+1>=MAX)
Error_Message("Lexemes array is full");
lastentry=lastentry+1;
symtable[lastentry].token=tok;
Page 28
COMPILER DESIGN LAB III YEAR II SEM
symtable[lastentry].lexptr=&lexemes[lastchar+1];
lastchar=lastchar+len+1;
strcpy(symtable[lastentry].lexptr,s);
return lastentry;
}
/*void Initialize()
{
struct entry *ptr;
for(ptr=keywords;ptr->token;ptr+1)
insert(ptr->lexptr,ptr->token);
}*/
int lexer()
{
int t;
int val,i=0;
while(1)
{
t=getchar();
if(t==' '||t=='\t');
else if(t=='\n')
lineno=lineno+1;
else if(isdigit(t))
{
ungetc(t,stdin);
scanf("%d",&tokenval);
return NUM;
}
else if(isalpha(t))
{
while(isalnum(t))
{
buffer[i]=t;
t=getchar();
i=i+1;
if(i>=SIZE)
Error_Message("Compiler error");
}
buffer[i]=EOS;
if(t!=EOF)
ungetc(t,stdin);
val=look_up(buffer);
if(val==0)
val=insert(buffer,ID);
tokenval=val;
return symtable[val].token;
}
else if(t==EOF)
return DONE;
else
{
tokenval=NONE;
return t;
}
}
}
void Match(int t)
{
Page 29
COMPILER DESIGN LAB III YEAR II SEM
if(lookahead==t)
lookahead=lexer();
else
Error_Message("Syntax error");
}
void display(int t,int tval)
{
if(t=='+'||t=='-'||t=='*'||t=='/')
printf("\nArithmetic Operator: %c",t);
else if(t==NUM)
printf("\n Number: %d",tval);
else if(t==ID)
printf("\n Identifier: %s",symtable[tval].lexptr);
else
printf("\n Token %d tokenval %d",t,tokenval);
}
void F()
{
//void E();
switch(lookahead)
{
case '(' :
Match('(');
E();
Match(')');
break;
case NUM :
display(NUM,tokenval);
Match(NUM);
break;
case ID :
display(ID,tokenval);
Match(ID);
break;
default :
Error_Message("Syntax error");
}
}
void T()
{
int t;
F();
while(1)
{
switch(lookahead)
{
case '*' :
t=lookahead;
Match(lookahead);
F();
display(t,NONE);
continue;
case '/' :
t=lookahead;
Match(lookahead);
display(t,NONE);
continue;
Page 30
COMPILER DESIGN LAB III YEAR II SEM
default :
return;
}
}
}
void E()
{
int t;
T();
while(1)
{
switch(lookahead)
{
case '+' :
t=lookahead;
Match(lookahead);
T();
display(t,NONE);
continue;
case '-' :
t=lookahead;
Match(lookahead);
T();
display(t,NONE);
continue;
default :
return;
}
}
}
void parser()
{
lookahead=lexer();
while(lookahead!=DONE)
{
E();
Match(';');
}
}
int main()
{
char ans[10];
printf("\n Program for recursive descent parsing ");
printf("\n Enter the expression ");
printf("And place ; at the end\n");
printf("Press Ctrl-Z to terminate\n");
parser();
return 0;
}
Output
Program for recursive descent parsing
Enter the expression And place ; at the end
Press Ctrl-Z to terminate
a*b+c;
Identifier: a
Page 31
COMPILER DESIGN LAB III YEAR II SEM
Identifier: b
Arithmetic Operator: *
Identifier: c
Arithmetic Operator: +
5*7;
Number: 5
Number: 7
Arithmetic Operator: *
*2;
line 5, Syntax error
Page 32
COMPILER DESIGN LAB III YEAR II SEM
PROGRAM:
#include
#include
char stack[30];
int top=-1;
void push(char c)
top++;
stack[top]=c;
char pop()
char c;
if(top!=-1)
c=stack[top];
top--;
return c;
Page 33
COMPILER DESIGN LAB III YEAR II SEM
return'x';
void printstat()
int i;
printf("\n\t\t\t $");
for(i=0;i<=top;i++)
printf("%c",stack[i]);
void main()
int i,j,k,l;
char s1[20],s2[20],ch1,ch2,ch3;
clrscr();
printf("\n\n\t\t LR PARSING");
scanf("%s",s1);
l=strlen(s1);
j=0;
printf("\n\t\t $");
s1[i]=' ';
Page 34
COMPILER DESIGN LAB III YEAR II SEM
s1[i+1]='E';
printstat(); printf("id");
push('E');
printstat();
push(s1[i]);
printstat();
printstat();
l=strlen(s2);
while(l)
ch1=pop();
if(ch1=='x')
printf("\n\t\t\t $");
break;
if(ch1=='+'||ch1=='/'||ch1=='*'||ch1=='-')
ch3=pop();
if(ch3!='E')
Page 35
COMPILER DESIGN LAB III YEAR II SEM
printf("errror");
exit();
else
push('E');
printstat();
ch2=ch1;
getch();
} </l;i++)<>
OUTPUT:
LR PARSING
id+id*id-id
$id
$E
$E+
$E+id
$E+E
Page 36
COMPILER DESIGN LAB III YEAR II SEM
$E+E*
$E+E*id
$E+E*E
$E+E*E-
$E+E*E-id
$E+E*E-E
$E+E*E-E
$E+E*E
$E
10.Write a C program for implementation of a Shift Reduce Parser using Stack Data
Structure to accept a given input string of a given grammar.
Page 37
COMPILER DESIGN LAB III YEAR II SEM
ALGORITHM:
1. Get the input expression and store it in the input buffer.
2. Read the data from the input buffer one at the time.
3. Using stack and push & pop operation shift and reduce symbols with respect to
production rules available.
4. Continue the process till symbol shift and production rule reduce reaches the start
symbol.
5. Display the Stack Implementation table with corresponding Stack actions with input
symbols.
PROGRAM:
#include
#include
#include
#include
char ip_sym[15],stack[15];
int ip_ptr=0,st_ptr=0,len,i;
char temp[2],temp2[2];
char act[15];
void check();
void main()
clrscr();
printf("\n GRAMMER\n");
gets(ip_sym);
Page 38
COMPILER DESIGN LAB III YEAR II SEM
printf("\n________\t\t____________\t\t____________\n");
printf("\n $\t\t%s$\t\t\t--",ip_sym);
strcpy(act,"shift");
temp[0]=ip_sym[ip_ptr];
temp[1]='\0';
strcat(act,temp);
len=strlen(ip_sym);
for(i=0;i<=len-1;i++)
stack[st_ptr]=ip_sym[ip_ptr];
stack[st_ptr+1]='\0';
ip_sym[ip_ptr]=' ';
ip_ptr++;
printf("\n $%s\t\t%s$\t\t\t%s",stack,ip_sym,act);
strcpy(act,"shift");
temp[0]=ip_sym[ip_ptr];
temp[1]='\0';
strcat(act,temp);
check();
st_ptr++;
st_ptr++;
check();
Page 39
COMPILER DESIGN LAB III YEAR II SEM
void check()
int flag=0;
temp2[0]=stack[st_ptr];
temp2[1]='\0';
if((!strcmpi(temp2,"a"))||(!strcmpi(temp2,"b")))
stack[st_ptr]='E';
if(!strcmpi(temp2,"a"))
printf("\n $%s\t\t%s$\t\t\tE->a",stack,ip_sym);
else
printf("\n $%s\t\t%s$\t\t\tE->b",stack,ip_sym);
flag=1;
if((!strcmpi(temp2,"+"))||(strcmpi(temp2,"*"))||(!strcmpi(temp2,"/")))
flag=1;
if((!strcmpi(stack,"E+E"))||(!strcmpi(stack,"E\E"))||(!strcmpi(stack,"E*E")))
strcpy(stack,"E");
st_ptr=0;
if(!strcmpi(stack,"E+E"))
printf("\n $%s\t\t%s$\t\t\tE->E+E",stack,ip_sym);
Page 40
COMPILER DESIGN LAB III YEAR II SEM
else
if(!strcmpi(stack,"E\E"))
printf("\n $%s\t\t%s$\t\t\tE->E\E",stack,ip_sym);
else
if(!strcmpi(stack,"E*E"))
printf("\n $%s\t\t%s$\t\t\tE->E*E",stack,ip_sym);
else
printf("\n $%s\t\t%s$\t\t\tE->E+E",stack,ip_sym);
flag=1;
if(!strcmpi(stack,"E")&&ip_ptr==len)
printf("\n $%s\t\t%s$\t\t\tACCEPT",stack,ip_sym);
getch();
exit(0);
if(flag==0)
printf("\n%s\t\t\t%s\t\t reject",stack,ip_sym);
exit(0);
return;
OUTPUT:
Page 41
COMPILER DESIGN LAB III YEAR II SEM
GRAMMER
E->E+E
E->E/E
E->E*E
E->a/b
Page 42
COMPILER DESIGN LAB III YEAR II SEM
Aim: Study the LEX and YACC tool and Evaluate an arithmetic expression with parentheses, unary
and binary operators using Flex and Yacc. [Need to write yylex() function and to be used with Lex
and yacc.].
Description: LEX-A Lexical analyzer generator: Lex is a computer program that generates lexical
analyzers ("scanners" or "lexers").Lex is commonly used with the yacc parser generator. Lex reads an
input stream specifying the lexical analyzer and outputs source code implementing the lexer in the C
programming language 1. A lexer or scanner is used to perform lexical analysis, or the breaking up of
an input stream into meaningful units, or tokens. 2. For example, consider breaking a text file up into
individual words. 3. Lex: a tool for automatically generating a lexer or scanner given a lex
specification (.l file).
Structure
The structure of a Lex file is intentionally similar to that of a yacc file; files are divided up into
three sections, separated by lines that contain only two percent signs, as follows:
Definition section:
%%
Rules section: %%
C code section:
➢ The definition section is the place to define macros and to import header files written in
C. It is also possible to write any C code here, which will be copied verbatim into the
generated source file.
➢ The rules section is the most important section; it associates patterns with C statements.
Patterns are simply regular expressions. When the lexer sees some text in the input
matching a given pattern, it executes the associated C code. This is the basis of how Lex
operates. 14 Prepared by-Ramesh Chotiya GCEK, BHAWANIPATNA CSE Department
➢ The C code section contains C statements and functions that are copied verbatim to the
generated source file. These statements presumably contain code called by the rules in
the rules section. In large programs it is more convenient to place this code in a separate
file and link it in at compile time.
Algorithm:
1) Get the input from the user and Parse it token by token.
2) First identify the valid inputs that can be given for a program.
3) The Inputs include numbers, functions like LOG, COS, SIN, TAN, etc. and operators.
4) Define the precedence and the associativity of various operators like +,-,/,* etc.
5) Write codes for saving the answer into memory and displaying the result on the screen.
6) Write codes for performing various arithmetic operations.
7) Display the possible Error message that can be associated with this calculation.
Page 43
COMPILER DESIGN LAB III YEAR II SEM
8) Display the output on the screen else display the error message on the screen.
Program:
CALC.L
%{
#include<stdio.h>
#include<stdlib.h>
void yyerror(char *);
#include "y.tab.h"
int yylval;
%}
%%
[a-z] {yylval=*yytext='&'; return VARIABLE;}
[0-9]+ {yylval=atoi(yytext); return INTEGER;}
CALC.Y
[\t] ;
%%
int yywrap(void)
{
return 1;
}
%token INTEGER VARIABLE
%left '+' '-'
%left '*' '/'
%{
int yylex(void);
void yyerror(char *);
int sym[26];
%}
%%
PROG:
PROG STMT '\n'
;
STMT: EXPR {printf("\n %d",$1);}
| VARIABLE '=' EXPR {sym[$1] = $3;}
Page 44
COMPILER DESIGN LAB III YEAR II SEM
;
EXPR: INTEGER
| VARIABLE {$$ = sym[$1];}
| EXPR '+' EXPR {$$ = $1 + $3;}
| '(' EXPR ')' {$$ = $2;}
%%
void yyerror(char *s)
{
printf("\n %s",s);
return;
}
int main(void)
{
printf("\n Enter the Expression:");
yyparse();
return 0;
}
Output:
$ lex calc.l
$ yacc -d calc.y
$ cc y.tab.c lex.yy.c -ll -ly -lm
$ . / a . out
Enter the Expression: ( 5 + 4 ) * 3
Answer: 27
Page 45
COMPILER DESIGN LAB III YEAR II SEM
%{
/* Definition section */
#include<stdio.h>
#include "y.tab.h"
extern int yylval;
%}
/* Rule Section */
%%
[0-9]+ {
yylval=atoi(yytext);
return NUMBER;
}
[\t] ;
[\n] return 0;
. return yytext[0];
%%
int yywrap()
{
return 1;
}
Parser Source Code :
%{
/* Definition section */
#include<stdio.h>
int flag=0;
%}
%token NUMBER
Page 46
COMPILER DESIGN LAB III YEAR II SEM
/* Rule Section */
%%
ArithmeticExpression: E{
printf("\nResult=%d\n", $$);
return 0;
};
E:E'+'E {$$=$1+$3;}
|E'-'E {$$=$1-$3;}
|E'*'E {$$=$1*$3;}
|E'/'E {$$=$1/$3;}
|E'%'E {$$=$1%$3;}
|'('E')' {$$=$2;}
| NUMBER {$$=$1;}
%%
//driver code
void main()
{
printf("\nEnter Any Arithmetic Expression which
can have operations Addition,
Subtraction, Multiplication, Division,
Modulus and Round brackets:\n");
yyparse();
if(flag==0)
printf("\nEntered arithmetic expression is Valid\n\n");
}
Page 47
COMPILER DESIGN LAB III YEAR II SEM
void yyerror()
{
printf("\nEntered arithmetic expression is Invalid\n\n");
flag=1;
}
Output:
Page 48
COMPILER DESIGN LAB III YEAR II SEM
13. Write a C program for generating the three address code of a given
expression/statement.
In source code I use the Three function pm(),plus(),div(), I use the keyword strlen and I
include the string.h header package.
Example Source Code Programming | Generation Three address code Project
#include<stdio.h>
#include<string.h>
void pm();
void plus();
void div();
int i,ch,j,l,addr=100;
char ex[10], exp[10] ,exp1[10],exp2[10],id1[5],op[5],id2[5];
void main()
{
clrscr();
while(1)
{
printf("\n1.assignment\n2.arithmetic\n3.relational\n4.Exit\nEnter the choice:");
scanf("%d",&ch);
switch(ch)
{
case 1:
printf("\nEnter the expression with assignment operator:");
scanf("%s",exp);
l=strlen(exp);
exp2[0]='\0';
i=0;
while(exp[i]!='=')
{
i++;
}
strncat(exp2,exp,i);
strrev(exp);
exp1[0]='\0';
strncat(exp1,exp,l-(i+1));
strrev(exp1);
printf("Three address code:\ntemp=%s\n%s=temp\n",exp1,exp2);
break;
case 2:
printf("\nEnter the expression with arithmetic operator:");
scanf("%s",ex);
strcpy(exp,ex);
l=strlen(exp);
exp1[0]='\0';
for(i=0;i<l;i++)
{
if(exp[i]=='+'||exp[i]=='-')
Page 49
COMPILER DESIGN LAB III YEAR II SEM
{
if(exp[i+2]=='/'||exp[i+2]=='*')
{
pm();
break;
}
else
{
plus();
break;
}
}
else if(exp[i]=='/'||exp[i]=='*')
{
div();
break;
}
}
break;
case 3:
printf("Enter the expression with relational operator");
scanf("%s%s%s",&id1,&op,&id2);
if(((strcmp(op,"<")==0)||(strcmp(op,">")==0)||(strcmp(op,"<=")==0)||(strcmp(op,">=")==0)||
(strcmp(op,"==")==0)||(strcmp(op,"!=")==0))==0)
printf("Expression is error");
else
{
printf("\n%d\tif %s%s%s goto %d",addr,id1,op,id2,addr+3);
addr++;
printf("\n%d\t T:=0",addr);
addr++;
printf("\n%d\t goto %d",addr,addr+2);
addr++;
printf("\n%d\t T:=1",addr);
}
break;
case 4:
exit(0);
}
}
}
void pm()
{
strrev(exp);
j=l-i-1;
strncat(exp1,exp,j);
strrev(exp1);
printf("Three address code:\ntemp=%s\ntemp1=%c%ctemp\n",exp1,exp[j+1],exp[j]);
}
Page 50
COMPILER DESIGN LAB III YEAR II SEM
void div()
{
strncat(exp1,exp,i+2);
printf("Three address code:\ntemp=%s\ntemp1=temp%c%c\n",exp1,exp[i+2],exp[i+3]);
}
void plus()
{
strncat(exp1,exp,i+2);
printf("Three address code:\ntemp=%s\ntemp1=temp%c%c\n",exp1,exp[i+2],exp[i+3]);
}
1. assignment
2. arithmetic
3. relational
4. Exit
Enter the choice:1
Enter the expression with assignment operator:
a=b
Three address code:
temp=b
a=temp
1.assignment
2.arithmetic
3.relational
4.Exit
Enter the choice:2
Enter the expression with arithmetic operator:
a+b-c
Three address code:
temp=a+b
temp1=temp-c
1.assignment
2.arithmetic
3.relational
4.Exit
Enter the choice:2
Enter the expression with arithmetic operator:
a-b/c
Three address code:
temp=b/c
temp1=a-temp
1.assignment
2.arithmetic
3.relational
4.Exit
Page 51
COMPILER DESIGN LAB III YEAR II SEM
1.assignment
2.arithmetic
3.relational
4.Exit
Enter the choice:2
Enter the expression with arithmetic operator:a/b*c
Three address code:
temp=a/b
temp1=temp*c
1.assignment
2.arithmetic
3.relational
4.Exit
Enter the choice:3
Enter the expression with relational operator
a
<=
b
1.assignment
2.arithmetic
3.relational
4.Exit
Enter the choice:4
Page 52
COMPILER DESIGN LAB III YEAR II SEM
Program
#include<stdio.h>
#include<conio.h>
#include<string.h>
int i=1,j=0,no=0,tmpch=90;
char str[100],left[15],right[15];
void findopr();
void explore();
void fleft(int);
void fright(int);
struct exp
int pos;
char op;
}k[15];
void main()
scanf("%s",str);
findopr();
Page 53
COMPILER DESIGN LAB III YEAR II SEM
explore();
void findopr()
for(i=0;str[i]!='\0';i++)
if(str[i]==':')
k[j].pos=i;
k[j++].op=':';
for(i=0;str[i]!='\0';i++)
if(str[i]=='/')
k[j].pos=i;
k[j++].op='/';
for(i=0;str[i]!='\0';i++)
if(str[i]=='*')
k[j].pos=i;
k[j++].op='*';
for(i=0;str[i]!='\0';i++)
if(str[i]=='+')
Page 54
COMPILER DESIGN LAB III YEAR II SEM
k[j].pos=i;
k[j++].op='+';
for(i=0;str[i]!='\0';i++)
if(str[i]=='-')
k[j].pos=i;
k[j++].op='-';
void explore()
i=1;
while(k[i].op!='\0')
fleft(k[i].pos);
fright(k[i].pos);
str[k[i].pos]=tmpch--;
printf("\t%c := %s%c%s\t\t",str[k[i].pos],left,k[i].op,right);
printf("\n");
i++;
fright(-1);
if(no==0)
Page 55
COMPILER DESIGN LAB III YEAR II SEM
fleft(strlen(str));
printf("\t%s := %s",right,left);
getch();
exit(0);
printf("\t%s := %c",right,str[k[--i].pos]);
getch();
void fleft(int x)
int w=0,flag=0;
x--;
if(str[x]!='$'&& flag==0)
left[w++]=str[x];
left[w]='\0';
str[x]='$';
flag=1;
x--;
void fright(int x)
Page 56
COMPILER DESIGN LAB III YEAR II SEM
int w=0,flag=0;
x++;
if(str[x]!='$'&& flag==0)
right[w++]=str[x];
right[w]='\0';
str[x]='$';
flag=1;
x++;
Page 57
COMPILER DESIGN LAB III YEAR II SEM
Page 58