Compiler Design Lab Manual For R13
Compiler Design Lab Manual For R13
1. Design a lexical analyzer for given language and the lexical analyzer should ignore
redundant spaces, tabs and new lines
1
INTRODUCTION ABOUT LAB
There are 60 systems installed in this Lab. Their configurations are as follows:
RAM : 2GB
Network : LAN
All systems are configured in DUAL BOOT mode i.e., Students can boot from
Windows 8 or Linux as per their lab requirement. This is very useful for
students because they are familiar with different Operating Systems so that
they can execute their programs in different programming environments.
In all the systems TurboC3 and Putty are installed.
Systems are provided for students in the ratio of 1:1.
Systems are assigned numbers and same system is allotted for students when
they do the lab.
2
GUIDELINES TO STUDENTS
The students will write the experiment in the Record as per the following format:
c) Source Program.
d) Results.
3
LIST OF LAB EXERCISES
Convert the BNF rules into YACC form and write code to generate
11
abstract syntax tree.
Transition diagram for recognition of Reserved words and
12
identifiers
4
SOLUTIONS FOR PROGRAMS
1) Lexical Analyzer implimentation by using C program
#include<string.h>
#include<ctype.h>
#include<stdio.h>
void keyword(char[]);
void main()
{
FILE *f1,*f2,*f3;
charc,str[10],st1[10];
intnum[100],lineno=0,tokenvalue=0,i=0,j=0,k=0;
clrscr();
printf("\nEnter the c program\n");
f1=fopen("input.txt","w");
while((c=getchar())!=EOF)
putc(c,f1);
fclose(f1);
f1=fopen("input.txt","r");
f2=fopen("identifier.txt","w");
f3=fopen("specialchar.txt","w");
while((c=getc(f1))!=EOF)
{
if(isdigit(c))
{
tokenvalue=c-48;
c=getc(f1);
while(isdigit(c))
{
tokenvalue=tokenvalue*10+(c-48);
c=getc(f1);
}
num[i++]=tokenvalue;
ungetc(c,f1);
}
else if(isalpha(c))
{
putc(c,f2);
c=getc(f1);
while(isdigit(c)||isalpha(c)||c=='_'||c=='$')
{
putc(c,f2);
c=getc(f1);
}
putc(' ',f2);
ungetc(c,f1);
}
5
else if(c==' '||c=='\t')
printf(" ");
else if(c=='\n')
lineno++;
elseputc(c,f3);
}
fclose(f2);
fclose(f3);
fclose(f1);
printf("\nThe numbers in the program are:");
for(j=0;j<i;j++)
printf(" %d ",num[j]);
printf("\n");
f2=fopen("identifier.txt","r");
k=0;
printf("The keywords and identifiersare:");
while((c=getc(f2))!=EOF)
{
if(c!=' ')
str[k++]=c;
else
{
str[k]='\0';
keyword(str);
k=0;
}
}
fclose(f2);
f3=fopen("specialchar.txt","r");
printf("\nSpecial characters are");
while((c=getc(f3))!=EOF)
printf(" %c ",c);
printf("\n");
fclose(f3);
printf("Total no. of lines are:%d",lineno);
getch();
}
6
OUTPUT
7
2) Simulate First and Follow of a Grammar.
a) FIRST
#include<stdio.h>
#include<ctype.h>
void FIRST(char[],char );
void result(char[],char);
intnop;
char prod[10][10];
void main()
{
int i;
char choice;
char c;
char res1[20];
clrscr();
printf("How many number of productions ? :");
scanf(" %d",&nop);
printf("enter the production string like E=E+T\n");
for(i=0;i<nop;i++)
{
printf("Enter productions Number %d : ",i+1);
scanf(" %s",prod[i]);
}
do
{
printf("\n Find the FIRST of :");
scanf(" %c",&c);
FIRST(res1,c);
printf("\n FIRST(%c)= { ",c);
for(i=0;res1[i]!='\0';i++)
printf(" %c ",res1[i]);
printf("}\n");
printf("press 'y' to continue : ");
scanf(" %c",&choice);
}
while(choice=='y'||choice =='Y');
}
if(!(isupper(c)))
{
8
result(res,c);
return ;
}
for(i=0;i<nop;i++)
{
if(prod[i][0]==c)
{
if(prod[i][2]=='$')
result(res,'$');
else
{
j=2;
while(prod[i][j]!='\0')
{
eps=0;
FIRST(subres,prod[i][j]);
for(k=0;subres[k]!='\0';k++)
result(res,subres[k]);
for(k=0;subres[k]!='\0';k++)
if(subres[k]=='$')
{
eps=1;
break;
}
if(!eps)
break;
j++;
}
}
}
}
return ;
}
void result(char res[],char val)
{
int k;
for(k=0 ;res[k]!='\0';k++)
if(res[k]==val)
return;
res[k]=val;
res[k+1]='\0';
}
OUTPUT
How many number of productions ?:8
enter the production string like E=E+T
Enter productions Number 1 : E=TX
Enter productions Number 2 : X=+TX
Enter productions Number 3 : X=$
Enter productions Number 4 : T=FY
9
Enter productions Number 5 : Y=*FY
Enter productions Number 6 : Y=$
Enter productions Number 7 : F=(E)
Enter productions Number 8 : F=i
FIRST(X)= { + $ }
press 'y' to continue : Y
FIRST(F)= { ( i }
press 'y' to continue : Y
FIRST(Y)= { * $ }
press 'y' to continue : Y
FIRST(E)= { ( i }
press 'y' to continue : Y
FIRST(T)= { ( i }
press 'y' to continue : N
b) FOLLOW
#include<stdio.h>
#include<string.h>
intnop,m=0,p,i=0,j=0;
char prod[10][10],res[10];
void main()
{
int i;
int choice;
charc,ch;
printf("Enter the no.of productions: ");
scanf("%d", &nop);
printf("enter the production string like E=E+T\n");
10
for(i=0;i<nop;i++)
{
printf("Enter productions Number %d : ",i+1);
scanf(" %s",prod[i]);
}
do
{
m=0;
printf("Find FOLLOW of -->");
scanf(" %c",&c);
FOLLOW(c);
printf("FOLLOW(%c) = { ",c);
for(i=0;i<m;i++)
printf("%c ",res[i]);
printf(" }\n");
printf("Do you want to continue(Press 1 to continue....)?");
scanf("%d%c",&choice,&ch);
}
while(choice==1);
}
void FOLLOW(char c)
{
if(prod[0][0]==c)
result('$');
for(i=0;i<nop;i++)
{
for(j=2;j<strlen(prod[i]);j++)
{
if(prod[i][j]==c)
{
if(prod[i][j+1]!='\0')
first(prod[i][j+1]);
if(prod[i][j+1]=='\0'&&c!=prod[i][0])
FOLLOW(prod[i][0]);
}
}
}
}
void first(char c)
{
int k;
if(!(isupper(c)))
result(c);
for(k=0;k<nop;k++)
{
if(prod[k][0]==c)
{
if(prod[k][2]=='$')
11
FOLLOW(prod[i][0]);
else if(islower(prod[k][2]))
result(prod[k][2]);
else
first(prod[k][2]);
}
}
}
void result(char c)
{
int i;
for( i=0;i<=m;i++)
if(res[i]==c)
return;
res[m++]=c;
}
OUTPUT
Enter the no.of productions: 8
enter the production string like E=E+T
Enter productions Number 1 : E=TX
Enter productions Number 2 : X=+TX
Enter productions Number 3 : X=$
Enter productions Number 4 : T=FY
Enter productions Number 5 : Y=*FY
Enter productions Number 6 : Y=$
Enter productions Number 7 : F=(E)
Enter productions Number 8 : F=i
Find FOLLOW of -->X
FOLLOW(X) = { $ ) }
Do you want to continue(Press 1 to continue....)?1
Find FOLLOW of -->E
FOLLOW(E) = {$ ) }
Do you want to continue(Press 1 to continue....)?1
Find FOLLOW of -->Y
FOLLOW(Y) = { + $ ) }
Do you want to continue(Press 1 to continue....)?1
Find FOLLOW of -->T
FOLLOW(T) = { +$ ) }
Do you want to continue(Press 1 to continue....)?1
Find FOLLOW of -->F
FOLLOW(F) = { * + $ ) }
Do you want to continue(Press 1 to continue....)?2
12
3) Develop an operator precedence parser for a given language.
#include<stdio.h>
#include<conio.h>
void main()
{
char stack[20],ip[20],opt[10][10][1],ter[10];
inti,j,k,n,top=0,row,col;
clrscr();
for(i=0;i<10;i++)
{
stack[i]=NULL;
ip[i]=NULL;
for(j=0;j<10;j++)
{
opt[i][j][1]=NULL;
}
}
printf("Enter the no.of terminals:");
scanf("%d",&n);
printf("\nEnter the terminals:");
scanf("%s",ter);
printf("\nEnter the table values:\n");
for(i=0;i<n;i++)
{
for(j=0;j<n;j++)
{
printf("Enter the value for %c %c:",ter[i],ter[j]);
scanf("%s",opt[i][j]);
}
}
printf("\nOPERATOR PRECEDENCE TABLE:\n");
for(i=0;i<n;i++)
{
printf("\t%c",ter[i]);
}
printf("\n_________________________________________");
printf("\n");
for(i=0;i<n;i++)
{
printf("\n%c |",ter[i]);
for(j=0;j<n;j++)
{
printf("\t%c",opt[i][j][0]);
}
}
stack[top]='$';
printf("\n\nEnter the input string(append with $):");
scanf("%s",ip);
i=0;
13
printf("\nSTACK\t\t\tINPUT STRING\t\t\tACTION\n");
printf("\n%s\t\t\t%s\t\t\t",stack,ip);
while(i<=strlen(ip))
{
for(k=0;k<n;k++)
{
if(stack[top]==ter[k])
row=k;
if(ip[i]==ter[k])
col=k;
}
if((stack[top]=='$')&&(ip[i]=='$'))
{
printf("String is ACCEPTED");
break;
}
else if((opt[row][col][0]=='<') ||(opt[row][col][0]=='='))
{
stack[++top]=opt[row][col][0];
stack[++top]=ip[i];
ip[i]=' ';
printf("Shift %c",ip[i]);
i++;
}
else
{
if(opt[row][col][0]=='>')
{
while(stack[top]!='<')
{
--top;
}
top=top-1;
printf("Reduce");
}
else
{
printf("\nString is not accepted");
break;
}
}
printf("\n");
printf("%s\t\t\t%s\t\t\t",stack,ip);
}
getch();
}
14
OUTPUT
Enter the no.of terminals:4
i| - >>>
+ | <><>
* | <>>>
$ | <<< -
$ i+i*i$ Shift
$<i +i*i$ Reduce
$<i +i*i$ Shift
$<+ i*i$ Shift
$<+<i *i$ Reduce
$<+<i *i$ Shift
$<+<* i$ Shift
$<+<*<i $ Reduce
$<+<*<i $ Reduce
$<+<*<i $ Reduce
$<+<*<i $ String is ACCEPTED
15
4) Construct a recursive descent parser for an expression.
#include<stdio.h>
#include<string.h>
char input[10];
int i=0,error=0;
void E();
void T();
voidEprime();
voidTprime();
void F();
void main()
{
clrscr();
printf("Enter an arithmetic expression :\n");
gets(input);
E();
if(strlen(input)==i&&error==0)
printf("\nAccepted..!!!");
else
printf("\nRejected..!!!");
getch();
}
void E()
{
T();
Eprime();
}
voidEprime()
{
if(input[i]=='+')
{
i++;
T();
Eprime();
}
}
void T()
{
F();
Tprime();
}
voidTprime()
{
if(input[i]=='*')
{
i++;
16
F();
Tprime();
}
}
void F()
{
if(input[i]=='(')
{
i++;
E();
if(input[i]==')')
i++;
}
else if(isalpha(input[i]))
{
i++;
while(isalnum(input[i])||input[i]=='_')
i++;
}
else
error=1;
}
OUTPUT
1)
Enter an arithmetic expression :
sum+month*interest
Accepted..!!!
2)
Enter an arithmetic expression :
sum+avg*+interest
Rejected..!!!
17
5) Construct a LL(1) parser for an expression
#include<string.h>
#include<conio.h>
char a[10];
int top=-1,i;
void error()
{
printf("Syntax Error");
}
char TOS()
{
return a[top];
}
void pop()
{
if(top>=0)
a[top--]='\0';
}
void display()
{
for(i=0;i<=top;i++)
printf("%c",a[i]);
}
char* stack()
{
return a;
}
18
void main()
{
charip[20],r[20],nt,cin;
intir,ic,j=0,k;
char t[5][6][10]={"$","$","TH","$","TH","$",
"+TH","$","$","e","$","e",
"$","$","FU","$","FU","$",
"e","*FU","$","e","$","e",
"$","$","(E)","$","i","$"};
clrscr();
printf("\nEnter any String(Append with $)");
gets(ip);
printf("Stack\tInput\tOutput\n\n");
push("$E");
display();
printf("\t%s\n",ip);
for(j=0;ip[j]!='\0';)
{
if(TOS()==cin)
{
pop();
display();
display1(ip,j+1);
printf("\tPOP\n");
j++;
}
cin=ip[j];
nt=TOS();
if(nt=='E')ir=0;
else if(nt=='H')ir=1;
else if(nt=='T')ir=2;
else if(nt=='U')ir=3;
else if(nt=='F')ir=4;
else {
error();
break;
}
if(cin=='+')ic=0;
else if(cin=='*')ic=1;
else if(cin=='(')ic=2;
else if(cin==')')ic=3;
else if(isalpha(cin)){ic=4;cin='i';}
else if(cin=='$')ic=5;
strcpy(r,strrev(t[ir][ic]));
strrev(t[ir][ic]);
pop();
push(r);
if(TOS()=='e')
{
19
pop();
display();
display1(ip,j);
printf("\t%c->%c\n",nt,238);
}
else{
display();
display1(ip,j);
printf("\t%c->%s\n",nt,t[ir][ic]);
}
if(TOS()=='$'&&cin=='$')
break;
if(TOS()=='$'){
error();
break;
}
}
k=strcmp(stack(),"$");
if(k==0)
printf("\n Given String is accepted");
else
printf("\n Given String is not accepted");
getch();
}
OUTPUT
1)
Enter any String(Append with $)i+i*i$
Stack Input Output
$E i+i*i$
$HT i+i*i$ E->TH
$HUF i+i*i$ T->FU
$HUii+i*i$ F->i
$HU +i*i$ POP
$H +i*i$ U->ε
$HT+ +i*i$ H->+TH
$HT i*i$ POP
$HUF i*i$ T->FU
$HUi i*i$ F->i
$HU *i$ POP
$HUF* *i$ U->*FU
$HUF i$ POP
$HUi i$ F->i
$HU $ POP
$H $ U->ε
$ $ H->ε
20
2)
$E i+i**i$
$HT i+i**i$ E->TH
$HUF i+i**i$ T->FU
$HUii+i**i$ F->i
$HU +i**i$ POP
$H +i**i$ U->ε
$HT+ +i**i$ H->+TH
$HT i**i$ POP
$HUF i**i$ T->FU
$HUi i**i$ F->i
$HU **i$ POP
$HUF* **i$ U->*FU
$HUF *i$ POP
$HU$ *i$ F->$
Syntax Error
Given String is not accepted
21
6) Design predictive parser for the given language
#include<stdio.h>
#include<string.h>
# define SIZE 30
charst[100];
int top=-1;
int s1(char),ip(char);
int n1,n2;
charnt[SIZE],t[SIZE];
/*Function to return variable index*/
int s1(char c)
{
int i;
for(i=0;i<n1;i++)
{
if(c==nt[i])
return i;
}
}
/*Function to return terminal index*/
intip(char c)
{
int i;
for(i=0;i<n2;i++)
{
if(c==t[i])
return i;
}
}
void push(char c)
{
top++;
st[top]=c;
return;
}
void pop()
{
top--;
return;
}
main()
{
char table[SIZE][SIZE][10],input[SIZE];
intx,f,s,i,j,u;
printf("Enter the number of variables:");
scanf("%d",&n1);
printf("\nUse single capital letters for variables\n");
for(i=0;i<n1;i++)
{
22
printf("Enter the %d nonterminal:",i+1);
scanf("%c",&nt[i]);
}
printf("Enter the number of terminals:");
scanf("%d",&n2);
printf("\nUse single small letters for terminals\n");
for(i=0;i<n2;i++)
{
printf("Enter the %d terminal:",i+1);
scanf("%c",&t[i]);
}
/*Reading the parsing table*/
printf("Please enter only right sides of productions\n");
printf("Use symbol n to denote no entry and e to epsilon\n");
for(i=0;i<n1;i++)
{
for(j=0;j<n2;j++)
{
printf("\nEnter the entry for %c under %c:",nt[i],t[j]);
scanf("%s",table[i][j]);
}
}
/*Printing the parsing taable*/
for(i=0;i<n2;i++)
printf("\t%c",t[i]);
printf("\n---------------------------------------------------------\n");
for(i=0;i<n1;i++)
{
printf("\n%c|\t",nt[i]);
for(j=0;j<n2;j++)
{
if(!strcmp(table[i][j],"n"))
printf("\t");
else
printf("%s\t",Table[i][j]);
}
printf("\n");
}
printf("Enter the input:");
scanf("%s",input);
/*Initialising the stack*/
top++;
st[top]='$';
top++;
st[top]=nt[0];
printf("STACK content INPUT content PRODUCTION used\n");
printf("--------------------------------------------------------------\n");
i=0;
printf("$%c\t\t\t%s\n\n",st[top],input);
while(st[top]!='$')
23
{
x=0;
f=s1(st[top]);
s=ip(input[i]);
if(!strcmp(table[f][s],"n"))
{
printf("'String not accepted");
}
else
if(!strcmp(table[f][s],"e"))
{
pop();
}
else
if(st[top]==input[i])
{
x=1;
pop();
i++;
}
else
{
pop();
for(j=strlen(table[f][s])-1;j>0;j--)
{
{
push(table[f][s][j]);
}
}
for(u=0;u<=top;u++)
printf("%c",st[u]);
printf("\t\t\t");
for(u=i;input[u]!='\0';u++)
printf("%c",input[u]);
printf("\t\t\t");
if(x==0)
printf("%c->%s\n\n",nt[f],table[f][s]);
printf("'\n\n");
}
printf("\n\nThus string is accepted");
}
}
OUTPUT:
Enter the number of variables:5
Use single capital letters for the variables
Enter the 1 non terminal:E
Enter the 2 non terminal:A
Enter the 3 non terminal:T
Enter the 4 non terminal:B
Enter the 5 non terminal:F
24
Enter the number of terminals:6
Use only single small letter for the terminals
Enter the 1 terminal:+
Enter the 2 terminal:*
Enter the 3 terminal:(
Enter the 4 terminal:)
Enter the 5 terminal:i
Enter the 6 terminal:$
Please enter only the right sides of productions.
Use symbol n to denote noentry and e to epsilon
Enter the entry for E under $: n
Enter the entry for E under +: n
Enter the entry for E under *: n
Enter the entry for E under (: TA
Enter the entry for E under ): n
Enter the entry for E under i: TA
Enter the entry for A under +: +TA
Enter the entry for A under *: n
Enter the entry for A under (: n
Enter the entry for A under ): e
Enter the entry for A under i: n
Enter the entry for A under $: e
Enter the entry for T under +: n
Enter the entry for T under *: n
Enter the entry for T under (: FB
Enter the entry for T under ): n
Enter the entry for T under i: FB
Enter the entry for T under $: n
Enter the entry for B under +: e
Enter the entry for B under *: *FB
Enter the entry for B under (: n
Enter the entry for B under ): e
Enter the entry for B under i: n
Enter the entry for B under $: e
Enter the entry for F under +: n
Enter the entry for F under *: n
Enter the entry for F under (: (E)
Enter the entry for F under ): n
Enter the entry for F under i: i
Enter the entry for F under $: n
+*()i$
-----------------------------------------------------------------------------
E| TA TA
A| +TA e e
T| FB FB
B| e *FB e e
F| (E) i
Enter the input: i+i*i$
25
-----------------------------------------------------------------------------------
$E i+i*i$
$A i+i*i$ E->TA
$AB i+i*i$ T->FB
$AB i+i*i$ F->i
$A +i*i$
$ +i*i$ B->e
$AT +i*i$ A->+TA
$A i*i$
$AB i*i$ T->FB
$AB i*i$ F->i
$A *i$
$ABF *i$ B->*FB
$AB i$
$AB i$ F->i
$A $
$ $ B->e
$ A->e
Thus string is accepted
26
7) Implementation of shift reduce parsing algorithm.
#include"stdio.h"
#include"conio.h"
#include"string.h"
charip_sym[15],stack[15];
intip_ptr=0,st_ptr=0,len,i;
char temp[2],temp2[2];
char act[15];
void check();
void main()
{
clrscr();
printf("\n\t\t SHIFT REDUCE PARSER\n");
printf("\n GRAMMER\n");
printf("\n E->E+E\n E->E/E");
printf("\n E->E*E\n E->E-E\n E->id");
printf("\n enter the input symbol:\t");
gets(ip_sym);
printf("\n\t stack implementation table");
printf("\n stack\t\t input symbol\t\t action");
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();
}
void check()
{
int flag=0;
temp2[0]=stack[st_ptr];
27
temp2[1]='\0';
if(islower(temp2[0]))
{
stack[st_ptr]='E';
flag=1;
}
if((!strcmp(temp2,"+"))||(!strcmp(temp2,"*"))
||(!strcmp(temp2,"/"))||(!strcmp(temp2,"-")))
{
flag=1;
}
if((!strcmp(stack,"E+E"))||(!strcmp(stack,"E/E"))
||(!strcmp(stack,"E*E"))||(!strcmp(stack,"E-E")))
{
if(!strcmp(stack,"E+E"))
{
strcpy(stack,"E");
printf("\n $%s\t\t%s$\t\t\tE->E+E",stack,ip_sym);
}
else
if(!strcmp(stack,"E/E"))
{
strcpy(stack,"E");
printf("\n $%s\t\t %s$\t\t\tE->E/E",stack,ip_sym);
}
else
if(!strcmp(stack,"E-E"))
{
strcpy(stack,"E");
printf("\n $%s\t\t %s$\t\t\tE->E-E",stack,ip_sym);
}
else
{
strcpy(stack,"E");
printf("\n $%s\t\t%s$\t\t\tE->E*E",stack,ip_sym);
}
flag=1;
st_ptr=0;
}
if(!strcmp(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);
28
}
return;
}
OUTPUT:
1)SHIFT REDUCE PARSER GRAMMER
E->E+E
E->E/E
E->E*E
E->E-E
E->id
enter the input symbol: a+b*c
$ a+b*c$ --
$a +b*c$ shift a
$E +b*c$ E->a
$E+ b*c$ shift +
$E+b *c$ shift b
$E+E *c$ E->b
$E *c$ E->E+E
$E* c$ shift *
$E*c $ shift c
$E*E $ E->c
$E $ E->E*E
$E $ ACCEPT
E->E+E
E->E/E
E->E*E
E->E-E
E->id
enter the input symbol: a+b*+c
$ a+b*+c$ --
$a +b*+c$ shift a
$E +b*+c$ E->a
$E+ b*+c$ shift +
$E+b *+c$ shift b
$E+E *+c$ E->b
29
$E *+c$ E->E+E
$E* +c$ shift *
$E*+ c$ shift +
$E*+c $ shift c
$E*+E $ E->c
$E*+E reject
30
8) Design a LALR bottom up parser for the given language.
{%
#nclude<stdio.h>
#include<conio.h>
intyylex(void);
%}
%token ID
%start line
%%
line:expr '\n', {printf("%d",S1);}
expr:expr'+'term {SS=S1+S3;}
|term
term:term'*'factor {SS=S1+S3;}
|factor
factor:'('expr')' {SS=S2;}
|ID
%%
yylex()
{
char c[10],i;
gets(c);
if(isdigit(c))
{
yylval=c;
return ID;
}
return c;
}
Output:
$vi lalr.y
$yacc –v lalr.y
$vi y.output
y.output contains the ouput
31
exprgoto 4
term goto 5
state 1
factor : ID . (7)
. reduce 7
state 2
factor : '(' . expr ')' (6)
ID shift 1
'(' shift 2
. error
exprgoto 7
term goto 5
factor goto 6
state 3
$accept : line . $end (0)
$end accept
state 4
line :expr . '\n' (1)
expr :expr . '+' term (2)
'\n' shift 8
'+' shift 9
. error
state 5
expr : term . (3)
term : term . '*' factor (4)
'*' shift 10
'\n' reduce 3
'+' reduce 3
')' reduce 3
state 6
term : factor . (5)
. reduce 5
state 7
expr :expr . '+' term (2)
factor : '(' expr . ')' (6)
'+' shift 9
')' shift 11
. error
state 8
line :expr '\n' . (1)
. reduce 1
state 9
expr :expr '+' . term (2)
ID shift 1
'(' shift 2
. error
term goto 12
factor goto 6
state 10
term : term '*' . factor (4)
32
ID shift 1
'(' shift 2
. error
factor goto 13
state 11
factor : '(' expr ')' . (6)
. reduce 6
state 12
expr :expr '+' term . (2)
term : term . '*' factor (4)
'*' shift 10
'\n' reduce 2
'+' reduce 2
')' reduce 2
state 13
term : term '*' factor . (4)
. reduce 4
8 terminals, 5 nonterminals
8 grammar rules, 14 states
33
9) Implement the lexical analyzer using JLex, flex or lex or other lexical analyzer
generating tools
delim [\t]
ws {delim}+
letter [A-Za-z]
digit [0-9]
id {letter}({letter}|{digit})*
num {digit}+(\.{digit}+)?(E[+/-]?{digit}+)?
%%
ws {printf("no action");}
if|else|then {{printf("%s is a keyword",yytext);} // TYPE 32 KEYWORDS
{id} {printf("%s is a identifier",yytext);}
{num} {printf(" it is a number");}
"<" {printf("it is a relational operator less than");}
"<=" {printf("it is a relational operator less than or equal");}
">" {printf("it is a relational operator greater than");}
">=" {printf("it is a relational operator greater than");}
"==" {printf("it is a relational operator equal");}
"<>" {printf("it is a relational operator not equal");}
%%
main()
{
yylex();
}
OUTPUT
lexlexicalfile.l
cc lex.yy.c -ll
if
if is a keyword
number
number is a identifier
254
It is a number
<>
it is a relational operator not equal
^Z
34
10) Write a program to perform loop unrolling.
#include<stdio.h>
int main()
{
int i;
for(i=0;i<5;i++)
{
printf("fun(%d)\n",i+1);
}
}
OUTPUT
fun(1)
fun(2)
fun(3)
fun(4)
fun(5)
35
11) Convert the BNF rules into YACC form and write code to generate abstract syntax
tree.
%token T_ocbT_ccbT_com id
%token T_oaT_caT_scT_cpT_op
%token aop mop rop cons T_eq
%token INT WHILE DO IF THEN ENDIF ELSE
%token ENDDO print
%%
program : block {printf("\n\n***parsed successfully***\n");return;}
;
block :T_ocbvdslT_ccb
| T_ocbslT_ccb
;
vd : INT vdef
;
vdef :vde
| vdeT_comvdef
;
vde : id
| idT_oa cons T_ca
;
sl :st
| stT_scsl
;
st : ass
| ifst
| whilest
| block
| printst
|
;
ass : id T_eqexpr
| idT_oaexprT_caT_eqexpr
;
ifst : IF bexpr THEN sl ELSE sl ENDIF
| IF bexpr THEN sl ENDIF
;
whilest : WHILE bexpr DO sl ENDDO
;
printst : print T_opexprT_cp
;
expr :expraop term
| term
| aop term
;
bexpr :exprropexpr
;
term : term mop fact
| fact
;
36
fact : cons
| id
| idT_oaexprT_ca
| T_opexprT_cp
;
%%
main()
{
returnyyparse();
}
OUTPUT:
[root@localhost ~]# gcc -o p lex.y.oy.tab.ob.o -ll
[root@localhost ~]# ./p
{
int
char
}
***parsed successfully***
37
12) Write a program for constant propagation.
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
voidsubstr(char s[], char sub[], int p, int l) {
int c = 0;
while (c < l) {
sub[c] = s[p+c-1];c++;
}sub[c] = '\0';
}
inteval(inta,int b, int op)
{
switch(op)
{
case 2: return a*b;
case 3: return a/b;
case 4: return a-b;
case 5: return a+b;
}return -1;
}
void main()
{
inti,j=0,j1,cnt,k;
char str[30],sub[10];int a[30],c[10],op[10],oc=0,cc=0;
printf("Enter String:");gets(str);
for(i=0;i<strlen(str);i++)
{
a[i]=0;
if(isdigit(str[i]))a[i]=1;
else if(str[i]=='*') a[i]=2;
else if(str[i]=='/') a[i]=3;
else if(str[i]=='-') a[i]=4;
else if(str[i]=='+') a[i]=5;
}
while(j<=strlen(str))
{
if(a[j]>1) { op[oc++]=a[j++]; }
else if(a[j]==1){
cnt=0;k=j;while(a[k++]==1) cnt++;
substr(str,sub,j+1,cnt);printf("\n%s",sub);
j+=cnt;c[cc++]=atoi(sub);//printf("\n %d",c[cc-1]);
if(cc==1) { j1 = k-1; }
if(cc==2) { c[0] = eval(c[0],c[1],a[j1]);cc=1;//printf("\n%d",c[0]);
}
}else j++;
}
j=0;
itoa(c[0],sub,10);oc=0;
while(j<strlen(str))
{
38
if(a[j]!=0) { while(oc<strlen(sub)) str[j++]=sub[oc++];
j+=oc-1;
k=0; if(strlen(sub)==1)j1=j; else j1=j-1;
while(a[j++]!=0) k++;
for(i=j1;i<strlen(str);i++)
str[i]=str[i+k+1];
str[i]='\0';
}
else j++;
}
printf("\n%s",str);
getch();
}
OUTPUT
Enter String: 2*3+4
2
3
4
10
39
VIVA QUESTIONS
1. What is a compiler?
2. What are the two parts of a compilation?
3. List the subparts or phases of analysis part.
4. Depict diagrammatically how a language is processed?
5. What is linear analysis?
6. Explain the various phases of a compiler?
7. What are the classifications of a compiler?
8. What is a symbol table?
9. Mention some of the cousins of a compiler?
10. List the phases that constitute the front end of a compiler.
11. Mention the back-end phases of a compiler.
12. Define compiler-compiler.
13. List the various compiler construction tools.
14. Differentiate tokens, patterns, and lexeme.
15. List the operations on languages.
16. Write a regular expression for an identifier
17. Mention the various notational short hands for representing regular expressions.
18. What is the function of a hierarchical analysis?
19. What does a semantic analysis do?
20. List the various error recovery strategies for a lexical analysis.
21. Define parser.
22. Mention the basic issues in parsing.
23. Why lexical and syntax analyzers are separated out?
24. Define a context free grammar.
25. Define ambiguous grammar.
26. What is a operator precedence parser?
27. List the properties of LR parser.
28. Mention the types of LR parser.
29. What are the problems with top down parsing?
30. Write the algorithm for FIRST and FOLLOW.
31. List the advantages and disadvantages of operator precedence parsing.
32. What is dangling else problem?
33. What is YACC?
34. What is meant by handle pruning?
35. Define LR(0) items.
36. What is meant by viable prefixes?
37. Define handle.
38. What are kernel & non-kernel items?
39. What is phrase level error recovery?
40. What are the benefits of intermediate code generation?
41. What are the various types of intermediate code representation?
42. Define backpatching.
43. What are the various methods of implementing three address statements?
44. What is Basic block?
45. What is a flow graph?
46. What is a DAG? What are its applications?
47. Define peephole optimization.
48. List the characteristics of peephole optimization.
40
49. How do you calculate the cost of an instruction?
50. Define symbol table.
51. What do you mean by machine dependent and machine independent optimization?
52. List the different storage allocation strategies.
53. What is dynamic scoping?
54. What is code motion?
55. What are the contents of activation record?
41
REFERENCES
1. Compilers, Principles Techniques and Tools- Alfred V Aho, Monica S Lam, Ravi
Sethi, Jeffrey D. Ullman,2nd ed, Pearson,2007
2. Compiler Design, K. Muneeswaran, Oxford..
42