0% found this document useful (0 votes)
23 views

Compiler Design Lab Manual

This program implements a parser using lex and yacc tools. It defines rules for token identification and parsing. Lex is used to define patterns for tokens like identifiers, numbers, operators etc. These token definitions are given to yacc to build a parser based on grammar rules. The parser checks for valid syntax and semantics and performs actions based on rules. This allows implementation of a working parser that can understand and interpret a programming language.

Uploaded by

Suba harini
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
23 views

Compiler Design Lab Manual

This program implements a parser using lex and yacc tools. It defines rules for token identification and parsing. Lex is used to define patterns for tokens like identifiers, numbers, operators etc. These token definitions are given to yacc to build a parser based on grammar rules. The parser checks for valid syntax and semantics and performs actions based on rules. This allows implementation of a working parser that can understand and interpret a programming language.

Uploaded by

Suba harini
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 51

SRI KRISHNA COLLEGE OF ENGINEERING AND TECHNOLOGY

COIMBATORE - 641008
(AN AUTONOMOUS INSTITUTION, AFFILIATED TO ANNA UNIVERSITY, CHENNAI)

DEPARTMENT OF COMPUTER SCIENCE AND BUSINESS SYSTEMS

21CB504 – COMPILER DESIGN

RECORD NOTE

Submitted by

Name :

Register No. :

Degree & Branch : B.Tech Computer Science and Business Systems

Class : III B.Tech CSBS


SRI KRISHNA COLLEGE OF ENGINEERING AND
TECHNOLOGY
COIMBATORE – 641008

(AN AUTONOMOUS INSTITUTION, AFFILIATED TO ANNA UNIVERSITY,


CHENNAI)

DEPARTMENT OF COMPUTER SCIENCE AND


BUSINESS SYSTEMS

21CB504 – COMPILER DESIGN

Practical record submitted by

Name: Register No. :

Class : III CSBS Degree & Branch :B.Tech CSBS

BONAFIDE CERTIFICATE

This is to certify that this is a bonafide record of work done by

(Register No.: ) during

the academic year 2023 – 2024.

Faculty In-charge Head of the Department

Submitted for the Autonomous practical examination held on

INTERNAL EXAMINER EXTERNAL EXAMINER


INDEX

Sl. No.: Date Experiment Name Marks Signature


EX.NO: 1
IMPLEMENTATION OF LEXICAL ANALYZER
USING C AND LEX TOOL

AIM:
To write a program for implementing LEXICAL ANALYSIS using C and LEX tool.

PROGRAM: (C-program)
#include <stdbool.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
bool isDelimiter(char ch)
{
if (ch == ' ' || ch == '+' || ch == '-' || ch == '*' || ch == '/' || ch == ',' ||
ch == ';' || ch == '>' || ch == '<' || ch == '=' || ch == '(' || ch == ')' ||
ch == '[' || ch == ']' || ch == '{' || ch == '}')
return (true);
return (false);
}
bool isOperator(char ch)
{
if (ch == '+' || ch == '-' || ch == '*' ||
ch == '/' || ch == '>' || ch == '<' ||
ch == '=')
return (true);
return (false);
}
bool validIdentifier(char* str)
{
if (str[0] == '0' || str[0] == '1' || str[0] == '2' ||
str[0] == '3' || str[0] == '4' || str[0] == '5' ||
str[0] == '6' || str[0] == '7' || str[0] == '8' || str[0] == '9' || isDelimiter(str[0]) == true)
return (false);
return (true);
}
bool isKeyword(char* str)
{
if (!strcmp(str, "if") || !strcmp(str, "else") || !strcmp(str, "while") ||
!strcmp(str, "do") || !strcmp(str, "break") || !strcmp(str, "continue") ||
!strcmp(str, "int") || !strcmp(str, "double") || !strcmp(str, "float")||
!strcmp(str, "return") || !strcmp(str, "char") || !strcmp(str, "case") ||
!strcmp(str, "char") || !strcmp(str, "sizeof") || !strcmp(str, "long") ||
!strcmp(str, "short") || !strcmp(str, "typedef") || !strcmp(str, "switch") ||
!strcmp(str, "unsigned") || !strcmp(str, "void") || !strcmp(str, "static") ||
!strcmp(str, "struct") || !strcmp(str, "goto"))
return (true);
return (false);
}
bool isInteger(char* str)
{
int i, len = strlen(str);
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);
}
bool isRealNumber(char* str)
{
int i, len = strlen(str);
bool hasDecimal = false;
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);
}
char* subString(char* str, int left, int right)
{
int i;
char* subStr = (char*)malloc(
sizeof(char) * (right - left + 2));
for (i = left; i <= right; i++)
subStr[i - left] = str[i];
subStr[right - left + 1] = '\0';
return (subStr);
}
void parse(char* str)
{
int left = 0, right = 0;
int len = strlen(str);
while (right <= len && left <= right) {
if (isDelimiter(str[right]) == false)
right++;
if (isDelimiter(str[right]) == true && left == right) {
if (isOperator(str[right]) == true)
printf("'%c' IS AN OPERATOR\n", str[right]);
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);
else if (isInteger(subStr) == true)
printf("'%s' IS AN INTEGER\n", subStr);
else if (isRealNumber(subStr) == true)
printf("'%s' IS A REAL NUMBER\n", subStr);
else if (validIdentifier(subStr) == true && isDelimiter(str[right - 1]) == false)
printf("'%s' IS A VALID IDENTIFIER\n", subStr);
else if (validIdentifier(subStr) == false && isDelimiter(str[right - 1]) == false)
printf("'%s' IS NOT A VALID IDENTIFIER\n", subStr);
left = right;
}
}
return;
}
int main()
{
char str[100] = "int a = b + 1c; ";
parse(str);
return (0);
}
OUTPUT:

PROGRAM:(lex tool)
//Implementation of Lexical Analyzer using Lex tool
%{
int COMMENT=0;
%}
identifier [a-zA-Z][a-zA-Z0-9]*
%%
#.* {printf("\n%s is a preprocessor directive",yytext);}
int |
float |
char |
double |
while |
for |
struct |
typedef |
do |
if |
break |
continue |
void |
switch |
return |
else |
goto {printf("\n\t%s is a keyword",yytext);}
"/*" {COMMENT=1;}{printf("\n\t %s is a COMMENT",yytext);}
{identifier}\( {if(!COMMENT)printf("\nFUNCTION \n\t%s",yytext);}
\{ {if(!COMMENT)printf("\n BLOCK BEGINS");}
\} {if(!COMMENT)printf("BLOCK ENDS ");}
{identifier}(\[[0-9]*\])? {if(!COMMENT) printf("\n %s IDENTIFIER",yytext);}
\".*\" {if(!COMMENT)printf("\n\t %s is a STRING",yytext);}
[0-9]+ {if(!COMMENT) printf("\n %s is a NUMBER ",yytext);}
\)(\:)? {if(!COMMENT)printf("\n\t");ECHO;printf("\n");}
\( ECHO;
= {if(!COMMENT)printf("\n\t %s is an ASSIGNMENT OPERATOR",yytext);}
\<= |
\>= |
\< |
== |
\> {if(!COMMENT) printf("\n\t%s is a RELATIONAL OPERATOR",yytext);}
%%
int main(int argc, char **argv)
{
FILE *file;
file=fopen("var.c","r");
if(!file)
{
printf("could not open the file");
exit(0);
}
yyin=file;
yylex();
printf("\n");
return(0);
}
int yywrap()
{
return(1);
}

INPUT:
#include<stdio.h>
#include<conio.h>
void main()
{
int a,b,c;
a=1;
b=2;
c=a+b;
printf("Sum:%d",c);
}
OUTPUT:

RESULT:
Thus, a program for implementing a Lexical analyser using C and LEX tool has been
executed successfully.
EX.NO: 2

IMPLEMENTATION OF A CALCULATOR THAT TAKES


AN EXPRESSION (WITH DIGITS, + AND *), COMPUTES
AND PRINTS ITS VALUE, USING YACC.

AIM:
To implement a calculator that takes expression within circular brackets

PROGRAM:
Source code(lex.l):
%{
#include<stdio.h>
#include "y.tab.h"
extern int yylval;
%}
%%
[0-9]+ {
yylval=atoi(yytext);
return NUMBER;
}
[\t] ;
[\n] return 0;
. return yytext[0];
%%
int yywrap()
{
return 1;
}
Yacc.y:
%{
#include<stdio.h>
int flag=0;
%}
%token NUMBER
%left '+' '-'
%left '*' '/' '%'
%left '(' ')'
%%
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;}
;
%%
void main()
{
printf("\nEnter Any Arithmetic Expression which can have operations Addition, Subtraction,
Multiplication, Divison, Modulus and Round brackets:\n");
yyparse();
if(flag==0)
printf("\nEntered arithmetic expression is Valid\n\n");
}
void yyerror()
{
printf("\nEntered arithmetic expression is Invalid\n\n");
flag=1;
}

OUTPUT:

RESULT:
Hence the program has been successfully executed and the token has been identified.
EX.NO: 3

IMPLEMENTATION OF PARSER USING LEX AND YACC TOOL

AIM:
To write a program for implementing parser using lex and yacc.

PROGRAM:
%{
#include <stdio.h>
#include <string.h>
#include "y.tab.h"
void yyerror(char *);
char identifier[50][50];
int total_id = 0;
int lineNum = 0;
%}
digit [0-9]
letter [a-zA-Z]
mulop [*/%]
addop [+-]
%%{
"if" {yyerror("No rules for if");}
"else" {yyerror("No rules for else");}
"while" {yyerror("No rules for while");}
"for" {yyerror("No rules for 'for'");}
"repeat" {yyerror("No rules for repeat");}
"until" {yyerror("No rules for until");}
"return" {yyerror("No rules for return");}
"main" {yyerror("No rules for main");}
{letter}({letter}|{digit}|"_")({letter}|{digit}|"_")({letter}|{digit}|"_")({letter}|{digit}|"_")({let
ter}|{digit}|"_
")+ {
{yyerror("Identifier greater than 5 characters");}
}
{letter}({letter}|{digit}|"_")?({letter}|{digit}|"_")?({letter}|{digit}|"_")?({letter}|{digit}|"_")?
{
int i;
int flag=0;
for (i = 0; i<total_id; i++) {
if (strcmp(identifier[i], yytext)==0)
{
flag=1;
break;
}
}
if(flag==0)
{
if(total_id==0) puts("");
printf("\r%s\n", yytext);
strcpy(identifier[total_id++],yytext);
}
return ID;
}
{digit}+|({digit}+("."){digit}+) {return NUM;}
"=="|">="|"<="|">"|"<"|"!=" {return RELOP;}
{addop}|("||") {return ADDOP;}
{mulop}|("&&") {return MULOP;}
"=" {return ASSIGN;}
";" {return END;}
"!" {return NOT;}
"[" {return SQRBO;}
"]" {return SQRBC;}
"(" {return STRBO;}
")" {return STRBC;}
"\n" {lineNum++;}
[._]+ {yyerror("Invalid character");}
[ \t]+;
%%

%{
#include <stdio.h>
#include <string.h>
extern FILE *yyin;
extern int lineNum;
int ErrorRecovered = 0;
char message[100];
%}
%start Start
%token ID NUM RELOP ADDOP MULOP ASSIGN NOT SQRBO SQRBC STRBO STRBC
END NEWLINE
%%
Start : Stmt_list;
Stmt_list : Stmt {strcpy(message, "Missing expression!");}
| Stmt_list END Stmt {strcpy(message,"It's not the last line of the file!");};
Stmt : Variable ASSIGN Expression {strcpy(message,"Variable or expression missing. Cannot
assign anything!");};
Variable : ID {strcpy(message,"Expecting something else!");}
| ID SQRBO Expression SQRBC {strcpy(message,"'[' or ']' missing OR expression not
found!");};
Expression : Simple_expression {strcpy(message,"Missing expression!");}
| Simple_expression RELOP Simple_expression {strcpy(message,"Conditional operation
cannot be
done");};
Simple_expression : Term {}
| Simple_expression ADDOP Term {strcpy(message,"Additive operation cannot be done");};
Term : Factor {}
| Term MULOP Factor {strcpy(message,"Multiplicative operation cannot be done!");};
Factor : ID {strcpy(message,"Expecting something else!");}
| NUM {strcpy(message,"Unrecognized number format!");}
| STRBO Expression STRBC {strcpy(message,"'(' or ')' missing OR expression not found!");}
| ID SQRBO Expression SQRBC {strcpy(message,"'[' or ']' missing OR ID not found!");}
| NOT Factor;
%%
int yywrap()
{
return 1;
}
int main()
{
yyin=fopen("input.txt","r");
yyparse();
fclose(yyin);
if(ErrorRecovered==0) printf("Success!\n");
return 0;
}
int yyerror(char *str)
{
if(ErrorRecovered==0){
{
printf("Error Found @ line #%d: ", lineNum+1);
if(strcmp(str,"Invalid character")==0 || strcmp(str,"Identifier greater than 5 characters")==0)
printf("%s!", str);
else if(strlen(message))
printf("%s\n",message);
else printf("%s\n", str);
}
printf("\n");
ErrorRecovered = 1;
}
}
Input(input.txt):
a=a*b;
ab = 15

OUTPUT:

RESULT:
Thus, a program for implementing parser using lex and yacc has been executed
successfully
EX.NO:4
IMPLEMENTATION OF SYMBOL TABLE USING C

AIM:
To write a program for implementing Symbol Table using C.

PROGRAM:
#include<stdio.h>
#include<ctype.h>
#include<stdlib.h>
#include<string.h>
#include<math.h>
void main()
{
int i=0,j=0,x=0,n;
void *p,*add[5];
char ch,srch,b[15],d[15],c;
printf("Expression terminated by $:");
while((c=getchar())!='$')
{
b[i]=c;
i++;
}
n=i-1;
printf("Given Expression:");
i=0;
while(i<=n)
{
printf("%c",b[i]);
i++;
}
printf("\n Symbol Table\n");
printf("Symbol \t\t addr \t\t type");
while(j<=n)
{
c=b[j];
if(isalpha(toascii(c)))
{
p=malloc(c);
add[x]=p;
d[x]=c;
printf("\n%c \t %d \t identifier\n",c,p);
x++;
j++;
}
else
{
ch=c;
if(ch=='+'||ch=='-'||ch=='*'||ch=='=')
{
p=malloc(ch);
add[x]=p;
d[x]=ch;
printf("\n %c \t %d \t operator\n",ch,p);
x++;
j++;
}
}
}
}

OUTPUT:

RESULT:
Thus, program for implementing Symbol Table using C has been executed successfully.
EX.NO: 5

IMPLEMENTATION OF PREDICTIVE PARSING

AIM:
To write a program for implementing a Predictive parsing.

PROGRAM:
#include<stdio.h>
#include<conio.h>
#include<string.h>
char prol[7][10]={"S","A","A","B","B","C","C"};
char pror[7][10]={"A","Bb","Cd","aB","@","Cc","@"};
char prod[7][10]={"S->A","A->Bb","A->Cd","B->aB","B->@","C->Cc","C->@"};
char first[7][10]={"abcd","ab","cd","a@","@","c@","@"};
char follow[7][10]={"$","$","$","a$","b$","c$","d$"};
char table[5][6][10];
numr(char c)
{
switch(c){
case 'S':
return 0;
case 'A':
return 1;
case 'B':
return 2;
case 'C':
return 3;
case 'a':
return 0;
case 'b':
return 1;
case 'c':
return 2;
case 'd':
return 3;
case '$':
return 4;
}
return(2);
}
void main(){
int i,j,k;
for(i=0;i<5;i++)
for(j=0;j<6;j++)
strcpy(table[i][j]," ");
printf("\nThe following is the predictive parsing table for the following grammar:\n");
for(i=0;i<7;i++)
printf("%s\n",prod[i]);
printf("\nPredictive parsing table is\n");
fflush(stdin);
for(i=0;i<7;i++){
k=strlen(first[i]);
for(j=0;j<10;j++)
if(first[i][j]!='@')
strcpy(table[numr(prol[i][0])+1][numr(first[i][j])+1],prod[i]);
}
for(i=0;i<7;i++){
if(strlen(pror[i])==1){
if(pror[i][0]=='@'){
k=strlen(follow[i]);
for(j=0;j<k;j++)
strcpy(table[numr(prol[i][0])+1][numr(follow[i][j])+1],prod[i]);
}
}
}
strcpy(table[0][0]," ");
strcpy(table[0][1],"a");
strcpy(table[0][2],"b");
strcpy(table[0][3],"c");
strcpy(table[0][4],"d");
strcpy(table[0][5],"$");
strcpy(table[1][0],"S");
strcpy(table[2][0],"A");
strcpy(table[3][0],"B");
strcpy(table[4][0],"C");
printf("\n--------------------------------------------------------\n");
for(i=0;i<5;i++)
for(j=0;j<6;j++){
printf("%-10s",table[i][j]);
if(j==5)
printf("\n--------------------------------------------------------\n");
}
getch();
}
OUTPUT:

RESULT:
Thus, a program for implementing a Predictive parsing has been executed successfully.
EX.NO: 6

IMPLEMENTATION OF SHIFT REDUCE PARSING ALGORITHM

AIM:
To write a program for implementing a Shift Reduce Parsing Algorithm.

PROGRAM:
#include<stdio.h>
#include<string.h>
int k=0,z=0,i=0,j=0,c=0;
char a[16],ac[20],stk[15],act[10];
void check();
int main()
{
puts("GRAMMAR is E->E+E \n E->E*E \n E->(E) \n E->id");
puts("enter input string ");
gets(a);
c=strlen(a);
strcpy(act,"SHIFT->");
puts("stack \t input \t action");
for(k=0,i=0; j<c; k++,i++,j++)
{
if(a[j]=='i' && a[j+1]=='d') {
stk[i]=a[j];
stk[i+1]=a[j+1];
stk[i+2]='\0';
a[j]=' ';
a[j+1]=' ';
printf("\n$%s\t%s$\t%sid",stk,a,act);
check();
}
else{
stk[i]=a[j];
stk[i+1]='\0';
a[j]=' ';
printf("\n$%s\t%s$\t%ssymbols",stk,a,act);
check();
}
}
}
void check(){
strcpy(ac,"REDUCE TO E");
for(z=0; z<c; z++)
if(stk[z]=='i' && stk[z+1]=='d'){
stk[z]='E';
stk[z+1]='\0';
printf("\n$%s\t%s$\t%s",stk,a,ac);
j++;
}
for(z=0; z<c; z++)
if(stk[z]=='E' && stk[z+1]=='+' && stk[z+2]=='E'){
stk[z]='E';
stk[z+1]='\0';
stk[z+2]='\0';
printf("\n$%s\t%s$\t%s",stk,a,ac);
i=i-2;
}
for(z=0; z<c; z++)
if(stk[z]=='E' && stk[z+1]=='*' && stk[z+2]=='E'){
stk[z]='E';
stk[z+1]='\0';
stk[z+1]='\0';
printf("\n$%s\t%s$\t%s",stk,a,ac);
i=i-2;
}
for(z=0; z<c; z++)
if(stk[z]=='(' && stk[z+1]=='E' && stk[z+2]==')'){
stk[z]='E';
stk[z+1]='\0';
stk[z+1]='\0';
printf("\n$%s\t%s$\t%s",stk,a,ac);
i=i-2;
}
}
OUTPUT:

RESULT:
Thus, a program for implementing a Shift Reduce Parsing Algorithm has been executed
successfully.
EX.NO: 7

IMPLEMENTATION OF LR PARSING
AIM:
To write a program for implementing a LR Parsing.

PROGRAM:
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
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;
}
return'x';
}
void printstat(){
int i;
printf("\n$");
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;
printf("LR PARSING");
printf("\nENTER THE EXPRESSION");
scanf("%s",s1);
l=strlen(s1);
j=0;
printf("\n$");
for(i=0;i<l;i++){
if(s1[i]=='i' && s1[i+1]=='d'){
s1[i]=' ';
s1[i+1]='E';
printstat(); printf("id");
push('E');
printstat();
}
else if(s1[i]=='+'||s1[i]=='-'||s1[i]=='*' ||s1[i]=='/' ||s1[i]=='d'){
push(s1[i]);
printstat();
}
}
printstat();
l=strlen(s2);
while(l){
ch1=pop();
if(ch1=='x'){
printf("\n$");
break;
}
if(ch1=='+'||ch1=='/'||ch1=='*'||ch1=='-'){
ch3=pop();
if(ch3!='E'){
printf("errror");
}
else{
push('E');
printstat();
}
}
ch2=ch1;
}
}
OUTPUT:

RESULT:
Thus, a program for implementing a LR Parsing has been executed successfully.
EX.NO: 8

IMPLEMENTATIONS OF FRONT END OF COMPILER

AIM:
To write a program for implementing the front end of a compiler that generates the three
address code for a simple language with: One data type integer, arithmetic operators, relational
operators, variable declaration statement, one conditional construct, one iterative construct and
assignment statement.

PROGRAM:
%{
#include<stdio.h>
#include<stdlib.h>
#include "y.tab.h"
#include<string.h>
int countn=0;
%}

%option yylineno
alpha [a-zA-Z]
digit [0-9]
%%

printf {strcpy(yylval.nam.name,(yytext));return printff;}


scanf {strcpy(yylval.nam.name,(yytext));return scanff;}
int {strcpy(yylval.nam.name,(yytext));return INT;}
float {strcpy(yylval.nam.name,(yytext));return FLOAT;}
char {strcpy(yylval.nam.name,(yytext));return CHAR;}

void return VOID;


return return RETURN;
if return IF;
else return ELSE;
while return WHILE;

^"#include"[ ]*<.+\.h> return INCLUDE;


"true" return TR;
"false" return FL;

{digit}+ { strcpy(yylval.nam.name,(yytext)); return NUM;}


{alpha}({alpha}|{digit})* {strcpy(yylval.nam.name,yytext); return ID;}

"<=" {strcpy(yylval.nam.name,yytext); return LE;}


">=" {strcpy(yylval.nam.name,yytext); return GE;}
"==" {strcpy(yylval.nam.name,yytext); return EQ;}
"!=" {strcpy(yylval.nam.name,yytext); return NE;}
">" {strcpy(yylval.nam.name,yytext);return GT;}
"<" {strcpy(yylval.nam.name,yytext);return LT;}
"&&" {strcpy(yylval.nam.name,yytext); return AND;}
"||" {strcpy(yylval.nam.name,yytext);return OR;}
\/\/.* ;
\/\*(.*\n)*.*\*\/ ;
[ \t]* ;
[\n] countn++;
. return yytext[0];
["].*["] {strcpy(yylval.nam.name,yytext);return STRLT;}

%%
int yywrap (){return 1;}

Yacc Code(ex9.y):
%{
#include<stdio.h>
#include<stdlib.h>
#include<ctype.h>
#include<string.h>
#include "lex.yy.c"
char nL[3];
void yyerror(const char*);
int yylex();
int yywrap();
void insert_type();
void add(char);
int sym_search(char *);
int search(char *);
void addTo(char i,char *n);
void FOO();
void add_ptr();
void pop();
void insert_type_table();
char temptype(char *,char*);
void type_check(char *,char*);
void printtree(struct node1*);
void optimized();
struct node{ int val;} x;
struct dataType{
char * id_name;
char * data_type;
char * type;
int line_no;
}symbolTable[100];
int ifd=0;//Label
int eld=20;
char typeStack[10][100];
int typeStack_top = 0;
char type[10];
char count=0;
int nxt=1;//printed next once
int c=0;//Temp var count
int q;
extern int countn;
struct intermediate
{
char op[2];
char op1[5];
char op2[5];
char res[5];
}intermediate_code[20];
int code=0;
struct node1{ struct node1*left;struct node1*right;char* token;};
struct node1* mknode(struct node1 *left,struct node1 *right, char *token);

%}
%union { struct var_name {char name[100];struct node1* nd;} nam ;
struct gen_code{char tr[10];char fal[10];struct node1* nd;} gen;
}
%token <nam> IF ELSE INT FLOAT CHAR WHILE
%token VOID INCLUDE RETURN
%token <nam> LE GE LT GT EQ NE NUM AND OR TR FL STRLT ID printff scanff
%type <gen> B C
%type <nam> relop Q T F E assign Arg P I M R TER N G U S EL S1 S2
%start P
%left '+' '-' '*' '/'
%right '=' '^'
%%
P : I M ID {insert_type_table();} '('{add('t');} R ')'{add('t');} '{'{add('t');} S { printf("Label
next:\n");} U '}'{$$.nd = mknode(NULL,$12.nd,"start");printf("\n\n------------------------------
---------------------------------------------\n");
printf("\n\t\t\tSyntax Tree in Inorder traversal\n--------------------------------------------------------
-------------------\n");
printtree($$.nd);
printf("\n\n");
add('t');
optimized();};
I : I I | INCLUDE {add('H');} ;
M : INT{insert_type();} | FLOAT{insert_type();}| CHAR{insert_type();} |
VOID{insert_type();} ;
R : R ','{add('t');} R | M N TER | N TER;
TER : ';'{add('t');} | ;
N : ID{insert_type_table();} G | '*'{add_ptr();} N ;
G : '['{add('t');} NUM {add('n');}']' G | '['ID ']' G | '['{add('t');} ']' G | ;
U : RETURN NUM {add('n');} ';'{add('t');printf("Return\t%s\n",$2.name);} | RETURN ID ';'
{add('t');printf("Return\t%s\n",$2.name);}| ;
S: S1
|S2
|assign {$$.nd=$1.nd;}
|M ID TER {$$.nd=mknode(NULL,NULL,"definition"); int
i=sym_search($2.name);if(i!=-1)
{if(strcmp($1.name,"int")==0){addTo('i',$2.name);}
else if(strcmp($1.name,"float")==0)addTo('f',$2.name);
else addTo('c',$2.name);}
else{printf("Variable already defined, error at line no: %d\n",yylineno);exit(0);}}
|S S {$$.nd=mknode($1.nd,$2.nd,"statement");strcpy($$.name,"STATEMENT");}
|printff {add('f');} '(' STRLT ')'';' {$$.nd = mknode(NULL,NULL,"printf");}
|scanff {add('f');}'('STRLT ',''&'ID')' ';'{$$.nd = mknode(NULL,NULL,"scanf");}
|{$$.nd=mknode(NULL,NULL,"EPSILON");};
S1 : IF{add('k');} '(' C ')'{printf("\n Label\t%s:\n",$4.tr);}'{'{addTo('{',"Punctuations");} S
'}'{addTo('}',"Punctuations");
pop();
printf("goto next\n");
printf("\nLabel\t%s:\n",$4.fal);} EL {$$.nd=mknode($4.nd,$9.nd,"IF");
strcpy($$.name,"IF");}
|assign {$$.nd=$1.nd;}
|M ID TER {$$.nd=mknode(NULL,NULL,"definition"); int
i=sym_search($2.name);if(i!=-1)
{if(strcmp($1.name,"int")==0){addTo('i',$2.name);}
else if(strcmp($1.name,"float")==0)addTo('f',$2.name);
else addTo('c',$2.name);}
else{printf("Variable already defined, error at line no: %d\n",yylineno);exit(0);}}
|S S {$$.nd=mknode($1.nd,$2.nd,"statement");strcpy($$.name,"STATEMENT");}
|printff {add('f');} '(' STRLT ')'';' {$$.nd = mknode(NULL,NULL,"printf");}
|scanff {add('f');}'('STRLT ',''&'ID')' ';'{$$.nd = mknode(NULL,NULL,"scanf");}
|{$$.nd=mknode(NULL,NULL,"EPSILON");};
S2:
WHILE{add('k'); sprintf(nL,"L%d",ifd);ifd++;printf("\n Label \t %s : \n",nL);} '(' C
')'{printf("\n Label\t%s:\n",$4.tr);}'{'{addTo('{',"Punctuations");} S
'}'{addTo('}',"Punctuations");
pop();
printf("goto %s\n",nL);
printf("\nLabel\t%s:\n",$4.fal);} EL {$$.nd=mknode($4.nd,$9.nd,"WHILE");
strcpy($$.name,"WHILE");}
|assign {$$.nd=$1.nd;}
|M ID TER {$$.nd=mknode(NULL,NULL,"definition"); int
i=sym_search($2.name);if(i!=-1)
{if(strcmp($1.name,"int")==0){addTo('i',$2.name);}
else if(strcmp($1.name,"float")==0)addTo('f',$2.name);
else addTo('c',$2.name);}
else{printf("Variable already defined, error at line no: %d\n",yylineno);exit(0);}}
|S S {$$.nd=mknode($1.nd,$2.nd,"statement");strcpy($$.name,"STATEMENT");}
|printff {add('f');} '(' STRLT ')'';' {$$.nd = mknode(NULL,NULL,"printf");}
|scanff {add('f');}'('STRLT ',''&'ID')' ';'{$$.nd = mknode(NULL,NULL,"scanf");}
|{$$.nd=mknode(NULL,NULL,"EPSILON");};
EL: ELSE{add('k');} '{'{addTo('{',"Punctuations");} S '}' {$$=$5;addTo('}',"Punctuations");
pop();
printf("goto next\n");
printf("\n");}| {printf("goto next\n");
printf("\n");};
Arg : STRLT ;
C : C AND B | C OR B | NE B | B{$$.nd=$1.nd;};
B: E relop E {$$.nd=mknode($1.nd,$3.nd,$2.name);
int i=search($1.name);
int j=search($3.name);
if(i!=0&&j!=0){
printf("if %s %s %s goto L%d else goto L%d\n",$1.name,$2.name,$3.name,ifd,eld);
sprintf($$.tr,"L%d",ifd);
sprintf($$.fal,"L%d",eld);ifd++;eld++;}
else{printf(" Variable not declared at line no: %d\n", yylineno);exit(0);}}
| ID '=' {add('o');} E{int i=search($1.name);
int j=search($4.name);
if(i!=0&&j!=0)
{
printf("if %s!=0 goto L%d else goto L%d\n",$1.name,ifd,eld);
sprintf($$.tr,"L%d",ifd);
sprintf($$.fal,"L%d",eld);ifd++;eld++;}
else{printf(" Variable not declared at line no: %d\n", yylineno);
exit(0);}}
| FL{printf("if False goto L%d\n",eld);
sprintf($$.tr,"L%d",ifd);
sprintf($$.fal,"L%d",eld);ifd++;eld++;}
| TR {printf("if True goto L%d\n",ifd);
sprintf($$.tr,"L%d",ifd);
sprintf($$.fal,"L%d",eld);ifd++;eld++;}
| ID {int i=search($1.name);
if(i!=0)
{
printf("if %s!=0 goto L%d else goto L%d\n",$1.name,ifd,eld);
sprintf($$.tr,"L%d",ifd);
sprintf($$.fal,"L%d",eld);ifd++;eld++;}
else {printf(" Variable not declared at line no: %d\n", yylineno);
exit(0);} }
| NUM {add('n');
printf("if %s!=0 goto L%d else goto L%d\n",$1.name,ifd,eld);
sprintf($$.tr,"L%d",ifd);
sprintf($$.fal,"L%d",eld);ifd++;eld++;} ;
assign : ID '='{add('o');} E ';'{$1.nd = mknode(NULL,NULL,$1.name);
$$.nd=mknode($1.nd,$4.nd,"=");
strcpy($$.name,"=");add('t');
int i=search($1.name);
int j=search($4.name);
if(i!=0&&j!=0)
{
type_check($1.name,$4.name);
printf("= \t %s\t %s \n",$4.name,$1.name);
strcpy(intermediate_code[code].op,"=");
strcpy(intermediate_code[code].res,$1.name);
strcpy(intermediate_code[code].op1,$4.name);
code++;
}
else {printf("Variable not declared at line no: %d\n", yylineno);
exit(0);}} |ID '(' Arg ')' ';'{add('t');};
E: E '+'{add('o');} E {$$.nd=mknode($1.nd,$4.nd,"+");strcpy($$.name,"+");
int i=search($1.name);
int j=search($4.name);
sprintf($$.name,"t%d",c);c++;
addTo(temptype($1.name,$4.name),$$.name);
if(i!=0 && j!=0)
{printf("%s\t%s\t%s\t%s\n","+",$1.name,$4.name,$$.name);strcpy(intermediate_code[code].
op,"+");
strcpy(intermediate_code[code].res,$$.name);
strcpy(intermediate_code[code].op1,$1.name);
strcpy(intermediate_code[code].op2,$4.name);
code++;}
else {printf(" Variable not declared at line no: %d\n", yylineno);exit(0);}}
| E '-' {add('o');}E { $$.nd=mknode($1.nd,$4.nd,"-");
strcpy($$.name,"-");
int i=search($1.name);
int j=search($4.name);
sprintf($$.name,"t%d",c);c++;
addTo(temptype($1.name,$4.name),$$.name);
if(i!=0 && j!=0) {printf("%s\t%s\t%s\t%s\n","-",$1.name,$4.name,$$.name);
strcpy(intermediate_code[code].op,"-");
strcpy(intermediate_code[code].res,$$.name);
strcpy(intermediate_code[code].op1,$1.name);
strcpy(intermediate_code[code].op2,$4.name);
code++;}
else {printf(" Variable not declared at line no: %d\n", yylineno);exit(0);}}
| F{$$.nd=$1.nd;};
F: F '*'{add('o');} F {$$.nd=mknode($1.nd,$4.nd,"*");
strcpy($$.name,"*");
int i=search($1.name);
int j=search($4.name);
sprintf($$.name,"t%d",c);c++;
addTo(temptype($1.name,$4.name),$$.name);
if(i!=0 && j!=0)
{printf("%s\t%s\t%s\t%s\n","*",$1.name,$4.name,$$.name);strcpy(intermediate_code[code].
op,"*");
strcpy(intermediate_code[code].res,$$.name);
strcpy(intermediate_code[code].op1,$1.name);
strcpy(intermediate_code[code].op2,$4.name);
code++;}
else {printf(" Variable not declared at line no: %d\n", yylineno);exit(0);}}
| F '/' {add('o');}F {$$.nd=mknode($1.nd,$4.nd,"/");strcpy($$.name,"/");
int i=search($1.name);
int j=search($4.name);
sprintf($$.name,"%d",c);
strcat($$.name,"t");c++;
addTo(temptype($1.name,$4.name),$$.name);
if(i!=0 && j!=0)
{
printf("%s\t%s\t%s\t%s\n","/",$1.name,$4.name,$$.name);strcpy(intermediate_code[c
ode].op,"/");
strcpy(intermediate_code[code].res,$$.name);
strcpy(intermediate_code[code].op1,$1.name);
strcpy(intermediate_code[code].op2,$4.name);
code++;
}
else {printf(" Variable not declared at line no: %d\n", yylineno);
exit(0);}}
| T {$$.nd=$1.nd;};
T: T '^'{add('o');} T {$$.nd=mknode($1.nd,$4.nd,"^");
strcpy($$.name,"^");
int i=search($1.name);
int j=search($4.name);
sprintf($$.name,"%d",c);
strcat($$.name,"t");c++;
addTo(temptype($1.name,$4.name),$$.name);
if(i!=0 && j!=0) {
printf("%s\t%s\t%s\t%s\n","^",$1.name,$4.name,$$.name);strcpy(intermediate_code[
code].op,"^");
strcpy(intermediate_code[code].res,$$.name);
strcpy(intermediate_code[code].op1,$1.name);
strcpy(intermediate_code[code].op2,$4.name);
code++;}
else {printf(" Variable not declared at line no: %d\n", yylineno);exit(0);}}
| Q {$$.nd=$1.nd;};
Q : '('{add('t');} E ')'{add('t'); $$=$3;} | ID {insert_type_table();} G
{$$.nd=mknode(NULL,NULL,$1.name);strcpy($$.name,$1.name);}|
NUM{add('n');}{$$.nd=mknode(NULL,NULL,$1.name);
strcpy($$.name,$1.name);} ;
relop : LE {add('r');} | GE {add('r');}| LT {add('r');} | GT {add('r');}| EQ {add('r');};
%%
int main()
{
extern int yylineno;
x.val=10;
printf("\n\n############################################################
###################\n");
printf("\t\t\tIntermediate code\n");
printf("###############################################################
################\n");
yyparse();
printf("\nParsing is Successful\n");
printf("\n\n############################################################
###################\n");
printf("\t\t\tSymbol table\n");
printf("###############################################################
################\n");
printf("\nsymbol \t type \t identify \t line number\n");
printf("_______________________________________________________________
________________\n");
int i=0;
for(i=0;i<100;i++){
if(symbolTable[i].id_name!=NULL)

printf("%s\t%s\t%s\t%d\t\n",symbolTable[i].id_name,symbolTable[i].data_type,symb
olTable[i].type,symbolTable[i].line_no);
}
for(i=0;i<count;i++){
free(symbolTable[i].id_name);
free(symbolTable[i].type);
}
return 0;
}
void yyerror(const char* s)
{
printf("Not accepted\n");
exit(0);
}
//insert the type into symboltable
void insert_type(){
strcpy(type,yytext);
//printf("hey");
q=search(type);
//printf("qval=%d",q);
if(q==0){
symbolTable[count].id_name=strdup(yytext);
symbolTable[count].data_type=strdup("N/A");
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("KEYWORD\t");
count++;
}
}
struct node1* mknode(struct node1 *left, struct node1 *right, char *token)
{
struct node1 *newnode = (struct node1 *)malloc(sizeof(struct node1));
char *newstr = (char *)malloc(strlen(token)+1);
strcpy(newstr, token);
newnode->left = left;
newnode->right = right;
newnode->token = newstr;
return(newnode);
}
void pop()
{
int i;
//printf("count %d\n",count);
int temp=count-1;
for(i=temp;i>=0;i--)
{
if(strcmp(symbolTable[i].id_name,"{")!=0)
{
//printf("$$\n");
count=count-1;;
}
else
{
count=count-1;
break;
}
}
}
//add declaration of data to symboltable
void addTo(char i,char *n)
{
if(i=='i')
{
symbolTable[count].id_name=strdup(n);
symbolTable[count].data_type="int";
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("variable");
count++;
}
else if(i=='f')
{
symbolTable[count].id_name=strdup(n);
symbolTable[count].data_type="float";
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("variable");
count++;
}
else if(i=='c')
{
symbolTable[count].id_name=strdup(n);
symbolTable[count].data_type="char";
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("variable");
count++;
}
else if(i=='{')
{
symbolTable[count].id_name=strdup("{");;
symbolTable[count].data_type="N/A";
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("punctuation");
count++;
}
else if(i=='}')
{
symbolTable[count].id_name=strdup("}");;
symbolTable[count].data_type="N/A";
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("punctuation");
count++;
}
}
char temptype(char* one,char* two)
{
int y;
char* onetype;
char* twotype;
for(y = 0;y<count;y++)
{
if(strcmp(symbolTable[y].id_name,one)==0)
onetype=symbolTable[y].data_type;
if(strcmp(symbolTable[y].id_name,two)==0)
twotype=symbolTable[y].data_type;
}
if((strcmp(onetype,"float")==0) || (strcmp(twotype,"float")==0))
return 'f';
else
return 'i';
}
void insert_type_table(){
q=search(yytext);
if(q==0){
symbolTable[count].id_name=strdup(yytext);
symbolTable[count].data_type=strdup(type);
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("IDENTIFIER");
count++;
}
}
void type_check(char* one, char* two)
{
int y;
char* onetype;
char* twotype;
for(y = 0;y<count;y++)
{
if(strcmp(symbolTable[y].id_name,one)==0)
onetype=symbolTable[y].data_type;
if(strcmp(symbolTable[y].id_name,two)==0)
twotype=symbolTable[y].data_type;
}
if(strcmp(onetype,twotype)>0){ printf("type error at lineno %d\n",yylineno);exit(0);}
}
//ADD the recent parsed string into symboltable
void add(char c)
{
q=search(yytext);
if(q==0){
if(c=='H')
{
symbolTable[count].id_name=strdup(yytext);
symbolTable[count].data_type=strdup(type);
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("Header");
count++;
}
else if(c=='t')
{
symbolTable[count].id_name=strdup(yytext);
symbolTable[count].data_type=strdup("N/A");
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("Punctuation");
count++;
}
else if(c=='o')
{
symbolTable[count].id_name=strdup(yytext);
symbolTable[count].data_type=strdup("N/A");
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("Operator");
count++;
}
else if(c=='r')
{
symbolTable[count].id_name=strdup(yytext);
symbolTable[count].data_type=strdup("N/A");
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("Rel Op\t");
count++;
}
else if(c=='k')
{

symbolTable[count].id_name=strdup(yytext);
symbolTable[count].data_type=strdup("N/A");
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("KEYWORD\t");
//printf("ADDDDDDDDD%s\n",symbolTable[count].id_name);
count++;
}
else if(c=='n')
{
symbolTable[count].id_name=strdup(yytext);
symbolTable[count].data_type=strdup("int");
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("NUMBER\t");
count++;
}
else if(c=='f')
{
symbolTable[count].id_name=strdup(yytext);
symbolTable[count].data_type=strdup("N/A");
symbolTable[count].line_no = countn;
symbolTable[count].type=strdup("FUNCTION\t");
count++;
}
}
}
int sym_search(char *type)
{
int i;
for(i=count -1 ;i>=0&&(strcmp(symbolTable[i].id_name,"{")!=0);i--)
{
if(strcmp(symbolTable[i].id_name,type)==0)
{
return -1;
break;
}

}
return 0;
}
//Search in the Symbol table whether the parsed String is present in Symbol table already
int search(char *type)
{
int i;
for(i=count -1 ;i>=0;i--)
{
if(strcmp(symbolTable[i].id_name,type)==0)
{
return -1;
break;
}
}
return 0;
}
void add_ptr(){
strcat(type,"*");
}
//print the abstract syntax tree
void printtree(struct node1* tree)
{
int i;
if (tree->left)
{
printtree(tree->left);
}
printf(" %s , ", tree->token);
if (tree->right)
{
printtree(tree->right);
}
}
void optimized()
{
int i;
int j;
int n,m;
int k;
char yay[10];
int len;
int rem;
for (i=0;i<code;i++)// Common Subexpression Elimination
for(j=i+1;j<code;j++)
if(strcmp(intermediate_code[i].op,intermediate_code[j].op)==0)
{
if(strcmp(intermediate_code[i].op1,intermediate_code[j].op1)==0)
if(strcmp(intermediate_code[i].op2,intermediate_code[j].op2)==0 &&
strcmp(intermediate_code[i].op1,intermediate_code[i].res)!=0 &&
strcmp(intermediate_code[i].op2,intermediate_code[i].res)!=0 )
{
for(k=i+1;k<j;k++)
if(strcmp(intermediate_code[j].op1,intermediate_code[k].res)==0
||strcmp(intermediate_code[j].op2,intermediate_code[k].res)==0)
break;
if(k==j)
{
strcpy(intermediate_code[j].op,"=");
strcpy(intermediate_code[j].op1,intermediate_code[i].res);
strcpy(intermediate_code[j].op2,"");
}
}
if(strcmp(intermediate_code[i].op1,intermediate_code[j].op2)==0 &&
strcmp(intermediate_code[i].op2,intermediate_code[j].op1)==0
&&(strcmp(intermediate_code[i].op,"+")==0 || strcmp(intermediate_code[i].op,"*")==0))
{
for(k=i+1;k<j;k++)
if(strcmp(intermediate_code[j].op1,intermediate_code[k].res)==0
||strcmp(intermediate_code[j].op2,intermediate_code[k].res)==0)
break;
if(k==j)
{
strcpy(intermediate_code[j].op,"=");
strcpy(intermediate_code[j].op1,intermediate_code[i].res);
strcpy(intermediate_code[j].op2,"");
}
}
}
//constant Folding
for(i=0;i<code;i++)
{
n=strlen(intermediate_code[i].op1);
m=strlen(intermediate_code[i].op2);
for(k=0;k<n;k++)
if(isdigit(intermediate_code[i].op1[k])==0)
break;
for(j=0;j<m;j++)
if(isdigit(intermediate_code[i].op1[j])==0)
break;
if(j==m && k==n)
{
j=atoi(intermediate_code[i].op1);
k=atoi(intermediate_code[i].op2);
if(strcmp(intermediate_code[i].op,"*")==0)
{
m=j*k;
}
else if(strcmp(intermediate_code[i].op,"+")==0)
{
m=j+k;
}
else if(strcmp(intermediate_code[i].op,"-")==0)
{
m=j-k;
}
else if(strcmp(intermediate_code[i].op,"/")==0)
{
m=j/k;
}
/* j = m;
while (j != 0)
{
len++;
j /= 10;
}
for (i = 0; i < len; i++){
rem = j % 10;
j = j / 10;
yay[len - (i + 1)] = rem + '0';
}
yay[len] = '\0';*/
strcpy(intermediate_code[i].op,"=");
sprintf(intermediate_code[i].op1,"%d",m);
//strcpy(intermediate_code[i].op1,yay);
strcpy(intermediate_code[i].op2,"");

}
}
printf("\n\n__________________________________________________________________
_____________\n");
printf("Optimized code\n");
printf("_____________________________________________________________________
__________\n");
for (i=0;i<code;i++)
printf("%s\t%s\t%s\t%s\n",intermediate_code[i].op,intermediate_code[i].op1,intermediate_co
de[i].op2,intermediate_code[i].res);
}

Input.txt:
#include<stdio.h>
#include<stdlib.h>
int main(int argv,char *argc[]){
int a;
int b;
int c;
int i;
int j;
int k;
int z;
a=6;
z=5;
i=3;
k=6;
if(a<10){
printf("HELL0");
i=i+1;
k=k*10;
if(i){
printf("YYYYYY");
}
else{
a=a+1;
}
}
else{
z=z+1;
}
}

OUTPUT:
RESULT:
Thus, a program for implementing a Front End of Compiler has been executed
successfully.
EX.NO: 9

IMPLEMENTATIONS OF BACK END OF COMPILER

AIM:
To write a program for implementing a back end of the compiler which takes the three
address code as input and produces assembly language instructions that can be assembled and
run using an 8086 assembler. The target assembly instructions can be simple move, add, sub,
and jump.

PROGRAM:
#include<stdio.h>
#include<stdio.h>
#include<string.h>
void main()
{
char icode[10][30],str[20],opr[10];
int i=0;
printf("\n Enter the set of intermediate code (terminated by exit):\n");
do
{
scanf("%s",icode[i]);
} while(strcmp(icode[i++],"exit")!=0);
printf("\n target code generation");
printf("\n************************");
i=0;
do
{
strcpy(str,icode[i]);
switch(str[3])
{
case '+':
strcpy(opr,"ADD");
break;
case '-':
strcpy(opr,"SUB");
break;
case '*':
strcpy(opr,"MUL");
break;
case '/':
strcpy(opr,"DIV");
break;
}
printf("\n\tMov %c,R%d",str[2],i);
printf("\n\t%s%c,R%d",opr,str[4],i);
printf("\n\tMov R%d,%c",i,str[0]);
}while(strcmp(icode[++i],"exit")!=0);
}

OUTPUT:

RESULT:
Thus, a program for implementing a back End of Compiler has been executed
successfully
EX.NO: 10
IMPLEMENTATION OF CODE OPTIMIZER
AIM:
To write a program for implementing Code optimizer using C phase of a compiler that
eliminates dead code and common sub-expressions.

PROGRAM:
#include<stdio.h>
#include<string.h>
struct op
{
char l;
char r[20];
}
op[10],pr[10];
int main()
{
int a,i,k,j,n,z=0,m,q;
char *p,*l;
char temp,t;
char *tem;
printf("Enter the Number of Values:");
scanf("%d",&n);
for(i=0;i<n;i++)
{
printf("left: ");
scanf(" %c",&op[i].l);
printf("right: ");
scanf(" %s",op[i].r);
}
printf("Intermediate Code\n") ;
for(i=0;i<n;i++)
{
printf("%c=",op[i].l);
printf("%s\n",op[i].r);
}
for(i=0;i<n-1;i++)
{
temp=op[i].l;
for(j=0;j<n;j++)
{
p=strchr(op[j].r,temp);
if(p)
{
pr[z].l=op[i].l;
strcpy(pr[z].r,op[i].
r);
z++;
}
}
}
pr[z].l=op[n-1].l;
strcpy(pr[z].r,op[n-1].r);
z++;
printf("\nAfter Dead Code Elimination\n");
for(k=0;k<z;k++)
{
printf("%c\t=",pr[k].l);
printf("%s\n",pr[k].r);
}
for(m=0;m<z;m++)
{
tem=pr[m].r;
for(j=m+1;j<z;j++)
{
p=strstr(tem,pr[j].r);
if(p)
{
t=pr[j].l;
pr[j].l=pr[m].l;
for(i=0;i<z;i++)
{
l=strchr(pr[i].r,t) ;
if(l)
{
a=l-pr[i].r;
printf("pos: %d\n",a);
pr[i].r[a]=pr[m].l;
}}}}}
printf("Eliminate Common Expression\n");
for(i=0;i<z;i++)
{
printf("%c\t=",pr[i].l);
printf("%s\n",pr[i].r);
}
for(i=0;i<z;i++)
{
for(j=i+1;j<z;j++)
{
q=strcmp(pr[i].r,pr[j].r);
if((pr[i].l==pr[j].l)&&!q)
{
pr[i].l='\0';
}
}
}
printf("Optimized Code\n");
for(i=0;i<z;i++)
{
if(pr[i].l!='\0')
{
printf("%c=",pr[i].l);
printf("%s\n",pr[i].r);
}
}
}

OUTPUT:
RESULT:
Thus, a program for implementing Code Optimization using C has been executed
successfully.

You might also like