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

CS6612 Compiler Record

The document describes developing a lexical analyzer in C to recognize patterns in a C program. It involves: 1. Reading in a C program file as input and separating it into tokens. 2. Defining keywords and operators in separate files. 3. Matching the tokens to the predefined keywords and operators. 4. Printing the output after recognizing all tokens.

Uploaded by

LOKESH V [34]
Copyright
© © All Rights Reserved
Available Formats
Download as DOC, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
96 views

CS6612 Compiler Record

The document describes developing a lexical analyzer in C to recognize patterns in a C program. It involves: 1. Reading in a C program file as input and separating it into tokens. 2. Defining keywords and operators in separate files. 3. Matching the tokens to the predefined keywords and operators. 4. Printing the output after recognizing all tokens.

Uploaded by

LOKESH V [34]
Copyright
© © All Rights Reserved
Available Formats
Download as DOC, PDF, TXT or read online on Scribd
You are on page 1/ 68

EX.

NO: 1

DATE:

IMPLEMENTATION OF SYMBOL TABLE

AIM:

To write a C program to implement a symbol table.

INTRODUCTION:

A Symbol table is a data structure used by a language translator such as a compiler


or interpreter, where each identifier in a program’s source code is associated with
information

relating to its declaration or appearance in the source

Possible entries in a symbol table:

 Name : a string

 Attribute:

1. Reserved word

2. Variable name

3. Type Name

4. Procedure name

5. Constant name

 Data type

 Scope information: where it can be used.

 Storage allocation
SYMBOL TABLE

ALGORITHM:
1. Start the Program.

2. Get the input from the user with the terminating symbol ‘$’.

3. Allocate memory for the variable by dynamic memory allocation function.

4. If the next character of the symbol is an operator then only the memory is allocated.

5. While reading , the input symbol is inserted into symbol table along with its
memory address.

6. The steps are repeated till”$”is reached.

7. To reach a variable, enter the variable to the searched and symbol table has been
checked for corresponding variable, the variable along its address is displayed as
result.
8. Stop the program.
PROGRAM: ( IMPLEMENTATION OF SYMBOL TABLE)

# include <stdio.h>
# include <conio.h>
# include <alloc.h>
# include <string.h>
# define null 0

int size=0;
void insert();
void del();
int search(char lab[]);
void modify();
void display();

struct symbtab
{
char label[10];
int addr;
struct symtab *next;
};
struct symbtab *first,*last;

void main()
{
int op;
int y;
char la[10];
clrscr();
do
{
printf("\nSYMBOL TABLE IMPLEMENTATION\n");
printf("1. INSERT\n");
printf("2. DISPLAY\n");
printf("3. DELETE\n");
printf("4. SEARCH\n");
printf("5. MODIFY\n");
printf("6. END\n");
printf("Enter your option : ");
scanf("%d",&op);
switch(op)
{
case 1: insert();
display();
break;
case 2: display();
break;
case 3:del();
display();
break;
case 4: printf("Enter the label to be searched : ");
scanf("%s",la);
y=search(la);
if(y==1)
{ printf("The label is already in the symbol Table");
}
else
{ printf("The label is not found in the symbol table");
}
break;
case 5: modify();
display();
break;
case 6:
break;
}
}
while(op<6);
getch();
}

void insert()
{
int n;
char l[10];
printf("Enter the label : ");
scanf("%s",l);
n=search(l);
if(n==1)
{ printf("The label already exists. Duplicate cant be inserted\n");
}
else
{ struct symbtab *p;
p=malloc(sizeof(struct symbtab));
strcpy(p->label,l);
printf("Enter the address : ");
scanf("%d",&p->addr);
p->next=null;
if(size==0)
{ first=p;
last=p;
}
else
{ last->next=p;
last=p;
}
size++;
}}

void display()
{ int i;
struct symbtab *p;
p=first;
printf("LABEL\tADDRESS\n");
for(i=0;i<size;i++)
{ printf("%s\t%d\n",p->label,p->addr);
p=p->next;
}}

int search(char lab[])


{
int i,flag=0;
struct symbtab *p;
p=first;
for(i=0;i<size;i++)
{ if(strcmp(p->label,lab)==0)
{ flag=1;
}
p=p->next;
}
return flag;
}

void modify()
{
char l[10],nl[10];
int add, choice, i, s;
struct symbtab *p;
p=first;
printf("What do you want to modify?\n");
printf("1. Only the label\n");
printf("2. Only the address of a particular label\n");
printf("3. Both the label and address\n");
printf("Enter your choice : ");
scanf("%d",&choice);
switch(choice)
{
case 1: printf("Enter the old label\n");
scanf("%s",l);
printf("Enter the new label\n");
scanf("%s",nl);
s=search(l);
if(s==0)
{ printf("NO such label"); }
else
{ for(i=0;i<size;i++)
{ if(strcmp(p->label,l)==0)
{ strcpy(p->label,nl); }
p=p->next;
}}
break;
case 2: printf("Enter the label whose address is to modified\n");
scanf("%s",l);
printf("Enter the new address\n");
scanf("%d",&add);
s=search(l);
if(s==0)
{ printf("NO such label");
}
else
{ for(i=0;i<size;i++)
{ if(strcmp(p->label,l)==0)
{ p->addr=add; }
p=p->next;
}}
break;
case 3: printf("Enter the old label : ");
scanf("%s",l);
printf("Enter the new label : ");
scanf("%s",nl);
printf("Enter the new address : ");
scanf("%d",&add);
s=search(l);
if(s==0)
{ printf("NO such label");
}
else
{ for(i=0;i<size;i++)
{
if(strcmp(p->label,l)==0)
{ strcpy(p->label,nl);
p->addr=add;
}
p=p->next;
}}
break;
}}

void del()
{
int a;
char l[10];
struct symbtab *p,*q;
p=first;
printf("Enter the label to be deleted\n");
scanf("%s",l);
a=search(l);
if(a==0)
{ printf("Label not found\n");
}
else
{ if(strcmp(first->label,l)==0)
{ first=first->next;
}
else if(strcmp(last->label,l)==0)
{ q=p->next;
while(strcmp(q->label,l)!=0)
{ p=p->next;
q=q->next;
}
p->next=null;
last=p;
}
else
{ q=p->next;
while(strcmp(q->label,l)!=0)
{ p=p->next;
q=q->next;
}
p->next=q->next;
}
size--;
}}
OUTPUT:

SYMBOL TABLE IMPLEMENTATION


1.INSERT
2.DISPLAY
3.DELETE
4.SEARCH
5.MODIFY
6.END

Enter your option:1


Enter the label: A
Enter the address: 10
LABEL ADDRESS
A 10

SYMBOL TABLE IMPLEMENTATION


1.INSERT
2.DISPLAY
3.DELETE
4.SEARCH
5.MODIFY
6.END

Enter your option:1


Enter the label: B
Enter the address: 11
LABEL ADDRESS
A 10
B 11

SYMBOL TABLE IMPLEMENTATION


1.INSERT
2.DISPLAY
3.DELETE
4.SEARCH
5.MODIFY
6.END

Enter your option:2


LABEL ADDRESS
A 10
B 11
SYMBOL TABLE IMPLEMENTATION
1.INSERT
2.DISPLAY
3.DELETE
4.SEARCH
5.MODIFY
6.END

Enter your option:3


Enter the label to be deleted: A
LABEL ADDRESS
B 11

SYMBOL TABLE IMPLEMENTATION


1.INSERT
2.DISPLAY
3.DELETE
4.SEARCH
5.MODIFY
6.END

Enter your option:4


Enter the label to be searched: A
The label is not found in the symbol table.

SYMBOL TABLE IMPLEMENTATION


1.INSERT
2.DISPLAY
3.DELETE
4.SEARCH
5.MODIFY
6.END

Enter your option:4


Enter the label to be searched: B
The label is already in the symbol table.

SYMBOL TABLE IMPLEMENTATION


1.INSERT
2.DISPLAY
3.DELETE
4.SEARCH
5.MODIFY
6.END
Enter your option:5
what do you want to modify?
1.only the label
2.only the address of a particular label
3.both the label and address
Enter your choice:1
Enter the old label
B
Enter the new label
A
LABEL ADDRESS
a 11

RESULT:

Thus the C program to implement the symbol table was executed and the output is verified .
EX. NO:2
DATE:

DEVELOP A LEXICAL ANALYZER TO RECOGNIZE

A FEW PATTERNS IN C
AIM:

To Write a C program to develop a lexical analyzer to recognize a few patterns in C.

INTRODUCTION:

Lexical analysis is the process of converting a sequence of characters (such as in a


computer program of web page) into a sequence of tokens (strings with an identified
“meaning”). A program that perform lexical analysis may be called a lexer, tokenize or
scanner.
TOKEN

A token is a structure representing a lexeme that explicitly indicates its categorization

for the Purpose of parsing. A category of token is what in linguistics might be called a part-
of-speech. Examples of token categories may include “identifier” and “integer literal”,
although the set of Token differ in different programming languages.

The process of forming tokens from an input stream of characters is called tokenization.

Consider this expression in the C programming language:

Sum=3 + 2;

Tokenized and represented by the following table:

Lexeme Token category

Sum “identifier”

=
“assignment operator”
3 integer literal

+ addition operator

2 integer literal

; end of the statement

ALGORITHM:

1. Start the program


2. Include the header files.
3. Allocate memory for the variable by dynamic memory allocation function.
4. Use the file accessing functions to read the file.
5. Get the input file from the user.
6. Separate all the file contents as tokens and match it with the functions.
7. Define all the keywords in a separate file and name it as key.c
8. Define all the operators in a separate file and name it as open.c
9. Give the input program in a file and name it as input.c
10. Finally print the output after recognizing all the tokens.
11. Stop the program.

PROGRAM: (DEVELOP A LEXICAL ANALYZER TO RECOGNIZE A FEW PATTERNS IN C)

#include<stdio.h>
#include<conio.h>

void main()
{
int i=0,j=0,k,l,t;
char expr1[190],expr[40][10],num[10];
char keyword[12][10] = {"if", "else", "then", "while", "do", "for", "int", "float", "char",
"long","douoble"};
clrscr();
fflush(stdin);
printf("\nEnter the expression:");
gets(expr1);

while(1)
{ k = 0;
t = expr1[i];

while( (t>96 && t<123) || (t>64 && t<91) || (t>47 && t<58) )
{ expr[j][k] = expr1[i];
i++;
k++;
t = expr1[i];
if(!( (t>96 && t<123) || (t>64 && t<91) || (t>47 && t<58) ))
expr[j++][k] = NULL;
} k=0;

if(t == 42 || t == 43 || t == 45 || t == 47 || t == 61)
{ expr[j][k] = expr1[i];
expr[j++][1] = NULL;
}

if(t == 59)
break;
else if(j > 80 || t == 0)
{ printf("\nStatement Missing.");
exit(0);
getch();
getch();
} i++;
t = expr1[i];
} i = j;
printf("\n\nTotal No. of tokens: %d",j);
printf("\nSigns: ");

for(j=0;j<i;j++)
if(!strcmp(expr[j],"+") || !strcmp(expr[j],"-") || !strcmp(expr[j],"*") || !strcmp(expr[j],"/") ||
!strcmp(expr[j],";"))
{ printf("%s\t",expr[j]);

for(l=j;l<i;l++)
sprintf(expr[l],"%s",expr[l+1]);
i--;
}
printf("\nAssignment operator: ");

for(j=0;j<i;j++)
if(!strcmp(expr[j],"="))
{
printf("%s\t",expr[j]);
for(l=j;l<i;l++)
sprintf(expr[l],"%s",expr[l+1]);
i--;
}
printf("\nNumbers: ");

for(j=0;j<i;j++)
for(k=0;k<32767;k++)
{
sprintf(num,"%d",k);

if(!strcmp(expr[j],num))
{
printf("%d\t",k);
for(l=j;l<i;l++)
sprintf(expr[l],"%s",expr[l+1]);
j--;
i--;
} }
printf("\nKeywords: ");
for(j=0;j<i;j++)
for(k=0;k<11;k++)

if(!strcmp(expr[j],keyword[k]))
{
printf("%s\t",expr[j]);
for(l=j;l<i;l++)
sprintf(expr[l],"%s",expr[l+1]);
i--;
}
printf("\nIdentifiers: ");
for(j=0;j<i;j++)
printf("%s\t",expr[j]);
getch();
}

OUTPUT:

Enter the expression: if a=10 then b=2+a*5;


Total No. of tokens: 12
Signs: + *
Assignment operator: = =
Numbers: 10 2 5
Keywords: if then
Identifiers: a b a

RESULT:

Thus the above program for developing the lexical the lexical analyzer and recognizing the
few pattern s in C is executed successfully and the output is verified.
EX.NO:3
DATE:

IMPLEMENTATION OF LEXICAL ANALYZER USING LEX TOOL

AIM:

To write a program to implement the Lexical Analyzer using lex tool.

INTRODUCTION:

THEORY:

 A language for specifying lexical analyzer.

 There is a wide range of tools for construction of lexical analyzer. The majority
of these tools are based on regular expressions.

 The one of the traditional tools of that kind is lex.

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. Start the program

2. Lex program consists of three parts.

3. Declaration %%

4. Translation rules %%

5. Auxiliary procedure.

6. The declaration section includes declaration of variables, main test, constants


and regular

7. Definitions.

8. Translation rule of lex program are statements of the form

9. P1{action}

10. P2{action}

11. …..

12. …..

13. Pn{action}

14. Write program in the vi editor and save it with .1 extension.

15. Compile the lex program with lex compiler to produce output file as lex.yy.c.

16. Eg. $ lex filename.1

17. $gcc lex.yy.c-11

18. Compile that file with C compiler and verify the output.
PROGRAM: (LEXICAL ANALYZER USING LEX TOOL)

lex.l

digits[0-9]
letters[a-zA-Z]
delimiters[\,\:\;]
relational[\==\!=\<\>\<=\>=]
arithmetic[\+\-\*\/\%]
%{
int line=0;
%}
%%
#.* {printf("\n%s is a preprocessor directive",yytext);}
"/*".*"*/" {printf("\n%s is a comment statement",yytext);}
\".*\" {printf("\n%s is a control string",yytext);}
int|float|char|double|while|for|do|if|break|continue|void|switch|case|long|struct|const|typedef|return|
else|return|goto {printf("\n%s is a keyword",yytext);}
{letters}({letters}|{digits})* {printf("\n %s is a identifier",yytext);}
{digits}+ {printf("\n %s is a number",yytext);}
{delimiters}? {printf("\n %s is a special symbol - delimiters",yytext);}
\{ {printf("\n %s is a opening brace",yytext);}
\} {printf("\n %s is a closing brace",yytext);}
\( {printf("\n %s is a left paranthesis",yytext);}
\) {printf("\n %s is a right paranthesis",yytext);}
{arithmetic}? {printf("\n %s is an arithmetic operators",yytext);}
{relational}? {printf("\n %s is a relational operators",yytext);}
\n {line++;}
%%

int main(int argc,char**argv)


{
yyin=fopen(argv[1],"r");
yylex();
printf("\n\n\n no of lines scanned:%d",line);
fclose(yyin);
return 0;
}
int yywrap()
{
return 0;
}

test.c
main()
{
int a,b,c;
if(a<b)
{
a=a+b;
}
else
{
c=a+b;
}
}

OUTPUT:

C:\GnuWin32\bin> flex lex.l

C:\GnuWin32\bin> gcc lex.yy.c

C:\GnuWin32\bin> a.exe test1.c

main is a identifier
( is a left paranthesis
) is a right paranthesis
{ is a opening brace
int is a keyword
a is a identifier
, is a special symbol - delimiters
b is a identifier
, is a special symbol - delimiters
c is a identifier
; is a special symbol - delimiters

RESULT:
Thus the program for the exercise on lexical analysis using lex has been successfully executed
and output is verified.

EX.NO:4

DATE:
GENERATE YACC SPECIFICATION FOR A FEW SYNTACTIC

CATEGORIES.

AIM :

To write a c program to do exercise on syntax analysis using YACC.

INTRODUCTION :

YACC (yet another compiler) is a program designed to produce designed to compile


a LALR (1) grammar and to produce the source code of the synthetically analyses of
the language produced by the grammar.

ALGORITHM :

1. Start the program.

2. Write the code for parser. l in the declaration port.

3. Write the code for the ‘y’ parser.

4. Also write the code for different arithmetical operations.

5. Write additional code to print the result of computation.

6. Execute and verify it.

7. Stop the program.


PROGRAM TO RECOGNIZE A VALID ARITHMETIC EXPRESSION THAT USES
OPERATOR +, - , * AND /.

4a. Program to recognize a valid arithmetic expression that uses operator +, - , * and /.

prog4.y

%{ #include <stdio.h>
#include <ctype.h>
#include <stdlib.h>
%}
%token num let
%left '+' '-'
%left '*' '/'
%%
Stmt : Stmt '\n' { printf ("\n.. Valid Expression.. \n"); exit(0); }
| expr
| error '\n' { printf ("\n..Invalid ..\n"); exit(0); }
;
expr : num
| let
| expr '+' expr
| expr '-' expr
| expr '*' expr
| expr '/' expr
| '(' expr ')'
;
%%

main ( )
{printf ("Enter an expression to validate : ");
yyparse ( );}
yylex()
{
int ch;
while ( ( ch = getchar() ) == ' ' );
if ( isdigit(ch) )
return num; // return token num
if ( isalpha(ch) )
return let; // return token let
return ch; }

yyerror (char *s)


{
printf ( "%s", s ); }

OUTPUT:

C:\GnuWin32\bin> bison –dy prog4.y

C:\GnuWin32\bin> gcc y.tab.c


C:\GnuWin32\bin> a.exe

Enter an expression to validate: 5+6

. Valid Expression..

C:\GnuWin32\bin> a.exe

Enter an expression to validate: 5++6

syntax error

..Invalid .
Ex.No: 4 a Yacc program to Evaluate an arithmetic expression for operators (+,-,*, / )

eval.y

%{   /* Evaluate simple arithmetic expression */             


        #include <stdio.h>                                  
        #include <ctype.h>                                   
        #include <stdlib.h>                                 
        #define  YYSTYPE  double                             
%}                                                         
%token  num                                                 
%left   '+'   '-'                                              
%left    '*'   '/'                                              
%%                                                         
Stmt    :   Stmt   '\n'        {  printf ( "Value is %f \n", $1);  exit(0); }    
               |     Expr                                           
               |                                                  
               |     error   '\n'          {   printf ("INVALID");  exit(0);  }               
             ;                                                   
Expr    :  num                            {   $$ = $1;  }                                         
               |     Expr    '+'   Expr           {   $$ = $1 + $3;  }                         
               |     Expr    '-'    Expr           {   $$ = $1 - $3;   }                         
               |     Expr    '*'    Expr           {   $$ = $1 * $3;  }                         
               |     Expr    '/'    Expr            {                                   
           if ( $3 == 0 )                          
{   printf ( "division by zero \n");  
     exit (0);
}
else                                             
$$ = $1 / $3;                               
}                                               
               |     '('    Expr    ')'                {  $$  =  $2;  }                                        
            ;                                                                
%% 
main ( )                                                                  
{                                                                        
        printf ( "ENTER AN EXPRESSION TO EVALUATE : \n" );                  
        yyparse ( );                                                      
}
                                                                       
yyerror (char *s)                  
{                                 
        printf ( "%s", s );           
}                                 

yylex ( )                                                                 
{                                                                        
        char ch;                                                         
        while ( (ch = getchar() ) == '  ' ) ;
        if ( isdigit(ch) | ch == '.' )                                         
        {                                                                
                ungetc ( ch, stdin );                                       
                scanf ( "%lf", &yylval );                                   
                return  num;                                              
        }                                                               
        return ch;                
}                 

OUTPUT:

C:\GnuWin32\bin>bison -dy eval.y

C:\GnuWin32\bin>gcc y.tab.c

C:\GnuWin32\bin>a.exe

ENTER AN EXPRESSION TO EVALUATE:

4+8

Value is 12.000000
Ex: No : 4b Yacc program to recognize a valid variable, which starts with a letter followed by
any number of digits and letters.  

pro.y

%{ #include <stdio.h>
#include <ctype.h>
%}
%token let dig
%%
TERM : XTERM '\n' { printf ( "\nAccepted\n" ); exit(0); }
| error { yyerror ("Rejected\n" ); }
;
XTERM : XTERM let
| XTERM dig
| let
;
%%
yylex()
{
char ch;
while ( ( ch = getchar ( ) ) == ' ' ) ;
if ( isalpha (ch) )
return let;
if ( isdigit (ch) )
return dig;
return ch;
}

main()
{
printf ("Enter a variable : ");
yyparse ();
}

yyerror(char *s)
{
printf ("%s", s);
}
OUTPUT:

C:\GnuWin32\bin>bison -dy pro.y

C:\GnuWin32\bin>gcc y.tab.c

C:\GnuWin32\bin>a.exe

Enter a variable: 5hjjkkjd

syntax error Rejected

C:\GnuWin32\bin>a.exe

Enter a variable: number

Accepted
EX. NO: 4 C Implementation of Calculator using LEX and YACC

cal.l

%{
#include<stdio.h>
#include<math.h>
#include "y.tab.h"
%}
%%
[0-9]+ {
yylval.dval=atoi(yytext);
return NUMBER;
}
[t];
n return 0;
. {return yytext[0];}
%%
void yyerror(char *str)
{
printf("\n Invalid Character");
}
int main()
{
printf("Enter Expression => ");
yyparse();
return(0);
}
int yywrap()
{
return 0;
}

cal.y
%{
#include<stdio.h>
int yylex(void);
%}
%union
{
float dval;
}
%token <dval> NUMBER
%left '+' '-'
%left '*' '/'

%nonassoc UMINUS
%type <dval> exp
%%
state : exp {printf("Answer = %f",$1);}
;
exp : NUMBER
| exp '+' exp {$$=$1+$3;}
| exp '-' exp {$$=$1-$3;}
| exp '*' exp {$$=$1*$3;}
| exp '/' exp {$$=$1/$3;}
| '('exp')' {$$=$2;}
| '-' exp %prec UMINUS {$$=-$2;}
;
%%

OUTPUT:

C:\GnuWin32\bin>flex cal.l

C:\GnuWin32\bin>bison -dy cal.y

C:\GnuWin32\bin>gcc lex.yy.c y.tab.c

c:\GnuWin32\bin>a.exe

Enter Expression => 5+6$

Answer = 11.000000
RESULT:

Thus the program for the exercise on the syntax using YACC has been executed successfully and
Output is verified.
EX.NO:5

DATE:

CONVERT THE BNF RULES INTO YACC FORM AND WRITE CODE TO
GENERATE ABSTRACT SYNTAX TREE USING AND YACC.

AIM:

To write a program to convert the BNF rules into YACC

INTRODUCTION:

BNF-Backus Naur form is formal notationfor encoding grammars intended for human

Consumption. Many programming languages, protocol or formats have BNF description in


their Specification.

ALGORITHM:

1. Start the program.

2. Declare the declarations as a header file.


{include<ctype.h>}

3. Token digit

4. Define the translations rule like line,expr,term,factor.

Line:exp”\n”{print”\n%d\n”,$1)}
Expr:expr”+”term($$=$1=$3}
Term:term”+”factor($$=$1*$3}

Factor
Factor”enter”),{$$=$2)

%%

5. Define the supporting C routines.

6. Execute and verify it.

7. Stop the program.

PROGRAM: (CONVERT THE BNF RULES INTO YACC)

%{
#include"y.tab.h"
#include<stdio.h>
#include<string.h>
int LineNo=1;
%}

identifier [a-zA-Z][_a-zA-Z0-9]*
number [0-9]+|([0-9]*\.[0-9]+)
%%
main\(\) return MAIN;
if return IF;
else return ELSE;
while return WHILE;
int |
char |
float return TYPE;
{identifier} {strcpy(yylval.var,yytext);
return VAR;}
{number} {strcpy(yylval.var,yytext);
return NUM;}
\< |
\> |
\>= |
\<= |
== {strcpy(yylval.var,yytext);
return RELOP;}
[ \t] ;
\n LineNo++;
. return yytext[0];
%%
int yywrap()
{
return 1;
}

bnf.y

%{
#include<string.h>
#include<stdio.h>
struct quad
{
char op[5];
char arg1[10];
char arg2[10];
char result[10];
}QUAD[30];
struct stack
{
int items[100];
int top;
}stk;

int Index=0,tIndex=0,StNo,Ind,tInd;
extern int LineNo;
void Addquadruple(char op[5],char arg1[10],char arg2[10],char result[10]);
void puss(int data);
int pop();
%}
%union
{
char var[10];
}

%token <var> NUM VAR RELOP


%token MAIN IF ELSE WHILE TYPE
%type <var> EXPR ASSIGNMENT CONDITION IFST ELSEST WHILELOOP
%left '-' '+'
%left '*' '/'
%%
PROGRAM : MAIN BLOCK
;
BLOCK: '{' CODE '}'
;
CODE: BLOCK
| STATEMENT CODE
| STATEMENT
;

STATEMENT: DESCT ';'


| ASSIGNMENT ';'
| CONDST
| WHILEST
;
DESCT: TYPE VARLIST
;
VARLIST: VAR ',' VARLIST
| VAR
;
ASSIGNMENT: VAR '=' EXPR{
strcpy(QUAD[Index].op,"=");
strcpy(QUAD[Index].arg1,$3);
strcpy(QUAD[Index].arg2,"");
strcpy(QUAD[Index].result,$1);
strcpy($$,QUAD[Index++].result);
}
;

EXPR: EXPR '+' EXPR {Addquadruple("+",$1,$3,$$);}


| EXPR '-' EXPR {Addquadruple("-",$1,$3,$$);}
| EXPR '*' EXPR {Addquadruple("*",$1,$3,$$);}
| EXPR '/' EXPR {Addquadruple("/",$1,$3,$$);}
| '-' EXPR {Addquadruple("UMIN",$2,"",$$);}
| '(' EXPR ')' {strcpy($$,$2);}
| VAR
| NUM
;

CONDST: IFST{
Ind=pop();
sprintf(QUAD[Ind].result,"%d",Index);
Ind=pop();
sprintf(QUAD[Ind].result,"%d",Index);
}
| IFST ELSEST
;

IFST: IF '(' CONDITION ')' {


strcpy(QUAD[Index].op,"==");
strcpy(QUAD[Index].arg1,$3);
strcpy(QUAD[Index].arg2,"FALSE");
strcpy(QUAD[Index].result,"-1");
puss(Index);
Index++;
}

BLOCK {
strcpy(QUAD[Index].op,"GOTO");
strcpy(QUAD[Index].arg1,"");
strcpy(QUAD[Index].arg2,"");
strcpy(QUAD[Index].result,"-1");
puss(Index);
Index++;
};

ELSEST: ELSE{
tInd=pop();
Ind=pop();
puss(tInd);
sprintf(QUAD[Ind].result,"%d",Index);
}

BLOCK{
Ind=pop();
sprintf(QUAD[Ind].result,"%d",Index);
};

CONDITION: VAR RELOP VAR {Addquadruple($2,$1,$3,$$);


StNo=Index-1;
}
| VAR
| NUM
;

WHILEST: WHILELOOP{
Ind=pop();
sprintf(QUAD[Ind].result,"%d",StNo);
Ind=pop();
sprintf(QUAD[Ind].result,"%d",Index);
}
;

WHILELOOP: WHILE '(' CONDITION ')' {


strcpy(QUAD[Index].op,"==");
strcpy(QUAD[Index].arg1,$3);
strcpy(QUAD[Index].arg2,"FALSE");
strcpy(QUAD[Index].result,"-1");
puss(Index);
Index++;
}
BLOCK {
strcpy(QUAD[Index].op,"GOTO");
strcpy(QUAD[Index].arg1,"");
strcpy(QUAD[Index].arg2,"");
strcpy(QUAD[Index].result,"-1");
puss(Index);
Index++;
}
;
%%
extern FILE *yyin;
int main(int argc,char *argv[])
{
FILE *fp;
int i;
if(argc>1)
{
fp=fopen(argv[1],"r");
if(!fp)
{
printf("\n File not found");
exit(0);
}
yyin=fp;
}
yyparse();
printf("\n\n\t\t ----------------------------\n\t\t Pos Operator Arg1 Arg2 Result\n\t\t--------------------");
for(i=0;i<Index;i++)
{
printf("\n\t\t %d\t %s\t %s\t %s\t%s",i,QUAD[i].op,QUAD[i].arg1,QUAD[i].arg2,QUAD[i].result);
}
printf("\n\t\t -----------------------");
printf("\n\n");
return 0;
}
void puss(int data)
{
stk.top++;
if(stk.top==100)
{
printf("\n Stack overflow\n");
exit(0);
}
stk.items[stk.top]=data;
}

int pop()
{
int data;
if(stk.top==-1)
{
printf("\n Stack underflow\n");
exit(0);
}
data=stk.items[stk.top--];
return data; }
void Addquadruple(char op[5],char arg1[10],char arg2[10],char result[10])
{
strcpy(QUAD[Index].op,op);
strcpy(QUAD[Index].arg1,arg1);
strcpy(QUAD[Index].arg2,arg2);
sprintf(QUAD[Index].result,"t%d",tIndex++);
strcpy(result,QUAD[Index++].result);
}

yyerror()
{
printf("\n Error on line no:%d",LineNo);
}

main()
{
int a,b,c;
if(a<b)
{ a=a+b; }
while(a<b)
{ a=a+b; }
if(a<=b)
{
c=a-b;
}
else
{
c=a+b;
}
}
OUTPUT:

C:\GnuWin32\bin>flex bnf.l

C:\GnuWin32\bin>bison -dy bnf.y

C:\GnuWin32\bin>gcc lex.yy.c y.tab.c

C:\GnuWin32\bin>a.exe test.c

Pos Operator Arg1 Arg2 Result

0 < a b t0
1 == t0 FALSE 5
2 + a b t1
3 = t1 a
4 GOTO 5
5 < a b t2
6 == t2 FALSE 10
7 + a b t3
8 = t3 a
9 GOTO 5
10 <= a b t4
11 == t4 FALSE 15
12 - a b t5
13 = t5 c
14 GOTO 17
15 + a b t6
16 = t6 c

RESULT:

Thus the program for the exercise on the syntax using YACC has been executed successfully
and output is verified.
EX.NO:6

DATE:

IMPLEMENTATION OF TYPE CHECKING


AIM:

To write a C program for implementing type checking for given expression.

INTRODUCTION:

The type analysis and type checking is an important activity done in the semantic
analysis phase. The need for type checking is

1. To detect the errors arising in the expression due to incompatible operand.

2. To generate intermediate code for expressions due to incompatible operand

Role of type checker

Source parse tree Type checker parse tree Intermediate

program parser
code
ALGORITHM:

1. Start a program.

2. Include all the header files.

3. Initialize all the functions and variables.

4. Get the expression from the user and separate into the tokens.

5. After separation, specify the identifiers, operators and number.

6. Print the output.

7. Stop the program.

PROGRAM: ( TYPE CHECKING)

Type.c

#include<stdio.h>
#include<conio.h>
#include<string.h>
struct symbol{
char name[10],type[10];
}s[10];

void main(){
int i=0,k=0,l=0,m=0,flag=0;
char temp[50],temp1[50],t1[50],b[10],c[10],str[50],buf[50];
char *a[10]={"int","float","char","double"};
char *op[10]={"+","-","*","/","<",">"};
FILE *fp;
clrscr();
fp=fopen("sample.c","r");
while(!feof(fp))
{ fscanf(fp,"%s",str);
//printf("%s\n",str);
for(i=0;i<4;i++)
{
if(strcmp(str,a[i])==0)
{
strcpy(s[k].type,str);
fscanf(fp,"%s",buf);
strcpy(s[k].name,buf);
k++;
/*if(buf!=","||buf!=";")
{
strcpy(s[k].name,buf);
k++;
} */
}
}
}
printf("symbol table\n");
for(k=0;k<10;k++)
{ printf("%s\t%s\t\n",s[k].type,s[k].name);
}
fclose(fp);
fp=fopen("sample.c","r");

while(!feof(fp))
{ fscanf(fp,"%s",temp);
//printf("%s\n",temp);
strcpy(t1,temp);
fscanf(fp,"%s",temp);
//printf("%s\n",temp);
//getch();
for(l=0;l<10;l++)
{ if(strcmp(temp,op[l])==0)
{ //printf("\n%s\n",t1);
//printf("%s\n",temp);
fscanf(fp,"%s",temp1);
//printf("%s\n",temp1);
for(m=0;m<10;m++)
{
if(strcmp(t1,s[m].name)==0)
strcpy(b,s[m].type);
if(strcmp(temp1,s[m].name)==0)
strcpy(c,s[m].type);
flag=1;
} }
//printf("\nFlag=%d",flag);
if(flag==1)
{
if(strcmp(b,c)==0)
printf("valid");
else
printf("invalid");
flag=0;
} } }
getch();
}

INPUT:

Sample.c

main ()

int a ;

float b ;

if ( a < b )

OUTPUT:

invalid

RESULT:

Thus the program has been executed successfully and Output is verified.
EX.NO:7A
DATE:

IMPLEMENT CONTROL FLOW ANALYSIS

AIM:

To Writs a C program to implement control flow analysis.

INTRODUCTION:

 Control flow analysis can be represent by basic blocks. It depicts how th program
control is being passed among the blocks.

ALGORITHM:

1. Start the program

2. Declare the necessary variables

3. Get the choice to insert, delete and display the values in stack

4. Perform PUSH() operation

a. t = newnode()

b. Enter info to be inserted

c. Read n

d. t ->info= n

e. t ->next=top
f. top = t

g. Return

5. Perform POP() operation

a. If (top=NULL)

b. Print”underflow”

c. Return

d. X=top

e. Top=top->next

f. Delnode(x)

g. Return

6. Display the values

7. Stop the program.

PROGRAM: (CONTROL FLOW ANALYSIS)

Controlflow.c

#include<stdio.h>
#include<conio.h>
#include<string.h>

void main()
{
int i,flag,count=0;
char *a[2]={"for","while"}; /* loop keywords */
char c,str[10],temp[10],index[10];
FILE *fp;
clrscr();
fp=fopen("file2.c","r");
do
{
fscanf(fp,"%s",str);
for(i=0;i<2;i++)
{
if(strcmp(str,a[i])==0)
{ fscanf(fp,"%s",temp);
fscanf(fp,"%s",temp);
strcpy(index,temp);
}
}
}while(strcmp(str,"{")!=0);
printf("%s",str);
printf("%s",index);
while(!feof(fp))
{
flag=0;
fscanf(fp,"%s",str);
if(strcmp(str,"}")==0) break;
count++;
do
{
if(strcmp(str,index)==0)
flag++;
fscanf(fp,"%s",str);
}while(strcmp(str,";")!=0);
if(flag!=0)
printf("%d has a variant variable\n",count);
else
printf("%d has a invariant variable\n",count);
}
getch();
}
Input

file2.c
While ( i < 3 )
{ j = i ++ ;
k = 10 ;
}

Output
1 has a variant variable
2 has a invariant variable

RESULT:
Thus the C program to implement control flow analysis was executed successfully.
EX.NO:7B
DATE:

IMPLEMENT DATA FLOW ANALYSIS

AIM:

To Writs a C program to implement data flow analysis.

INTRODUCTION:

 Data flow analysis is a technique for gathering information about the possible set
of value calculated at various points in a computer program.

ALGORITHM:

1. Start the program

2. Declare the necessary variables

3. Get the choice to insert, delete and display the values in stack

4. Perform PUSH() operation

a. t = newnode()

b. Enter info to be inserted

c. Read n

d. t ->info= n

e. t ->next=top
f. top = t

g. Return

5. Perform POP() operation

a. If (top=NULL)

b. Print”underflow”

c. Return

d. X=top

e. Top=top->next

f. Delnode(x)

g. Return

6. Display the values

7. Stop the program.

PROGRAM: (DATA FLOW ANALYSIS)

Dataflow.c

#include<stdio.h>
#include<conio.h>

void main()
{
FILE *fp;
int count,k;
char c,ch;
clrscr();
count=1;
fp = fopen("file.c","r");
for(c=getc(fp);c!=EOF;c=getc(fp))
{
if(c=='\n')
{
count=count+1;
printf("\nline: %d\t",count);
}
else
{
printf("%c",c);
}
}
fclose(fp);
fp=fopen("fileee.c","r");
printf("\n enter the variable to check for Liveness:\n");
scanf("%c",&ch);
count=1;
for(c=getc(fp);c!=EOF;c=getc(fp))
{
if(c=='\n'&&c!=ch)
{
count=count+1;
}
else if(strcmp(c,ch)==0)
{
printf("%d\t",count);
}
}
fclose(fp);
getch();
}
Input

file.c
{
int a , b ;
a=0;
b=a+1;
a=3;
a=a+b;
}

Output
enter the variable to check for Liveness: b
246

RESULT:
Thus the C program to implement data flow analysis was executed successfully.
EX.NO:8

DATE:

IMPLEMENT ANY ONE STORAGE ALLOCATION STRATEGIES


(HEAP,STACK,STATIC)
AIM:

To write a C program for Stack to use dynamic storage allocation.

INTRODUCTION:

Storage Allocation

Runtime environment manages runtime memory requirements for the following entities:

 Code: It is known as the part of a program that does not change at runtime. Its
memory requirements are at the compile time

 Procedures: Their text part is static but they are called in a random manner. That is
why, stack storage is used to manage procedure calls and activations.

 Variables: Variables are known at the runtime only, unless they are global or
constant. Heap memory allocation scheme is used for managing allocation and de-
allocation of memory for variables in runtime.

ALGORITHM:

1. Start the program

2. Enter the expression for which intermediate code is to be generated

3. If the length of the string is greater than 3, than call the procedure to return
the precedence
4. Among the operands.

5. Assign the operand to exp array and operators to the array.

6. Create the three address code using quadruples structure.

7. Reduce the no of temporary variables.

8. Continue this process until we get an output.

9. Stop the program.

Heap.c

#include<stdio.h>
#include<conio.h>
#include<stdlib.h>
#define TRUE 1
#define FALSE 0
typedef struct Heap
{ int data;
struct Heap *next;
}node;
node *create();
void main()
{
/*local declarations*/
int choice,val;
char ans;
node *head;
void display(node *);
node *search(node *,int);
node *insert(node *);
void dele(node **);
head=NULL;
do
{
clrscr();
printf("\n Program to perform various operations on heapusing dynamic memory
management");
printf("\n1.Create");
printf("\n2.Display");
printf("\n3.Insert an element in a list");
printf("\n4.Delete an element from list");
printf("\n5.Quit");
printf("\n Enter Your Choice(1-5)");
scanf("%d",&choice);
switch(choice)
{ case 1:head=create();break;
case 2:display(head);break;
case 3:head=insert(head);break;
case 4:dele(&head);break;
case 5:exit(0);default:clrscr();
printf("Invalid Choice,Try again");
getch();
}}
while(choice!=5);}
node *create()
{ node *temp,*new1,*head;
int val,flag;
char ans='y';
node *get_node();
temp=NULL;
flag=TRUE;
/*flag to indicate whether a new node is created for the first time or not*/
do
{ printf("\n Enter the Element");
scanf("%d",&val);
/*allocate new node*/
new1=get_node();
if(new1==NULL)
printf("\n Memory is not allocated");
new1-> data=val;
if (flag==TRUE)/* Executed only for the first time*/
{ head=new1;
temp=head; /*head is the first node in the heap*/
flag=FALSE;
}
else
{ /*temp keeps track of the most recently created node*/
temp->next=new1;
temp=new1;
}
printf("\nDo you want to enter more elements?(y/n)");
ans=getch();
}while(ans=='y');
printf("\nThe list is created");
getch();
clrscr();
return head;
}
node *get_node()
{
node *temp;
temp=(node*)malloc(sizeof(node));
//using the mem. Allocation function
temp->next=NULL;
return temp;
}
void display(node*head)
{ node *temp;
temp=head;
if(temp==NULL)
{ printf("\n The list is empty\n");
getch();
clrscr();
return; }
while(temp!= NULL)
{ printf("%d->",temp-> data);
temp=temp->next; }
printf("NULL");
getch();clrscr(); }
node *search(node *head,int key)
{ node *temp;
int found;
temp=head;
if (temp==NULL)
{ printf("The linked list is empty\n");
getch();clrscr();
return NULL; }
found=FALSE;
while((temp!=NULL)&&(found==FALSE))
{ if(temp->data != key)
temp = temp->next;
else
found = TRUE; }
if(found == TRUE)
{ printf("\n The Elements is present in the list\n");
getch();
return temp; }
else
printf("\n The Element is not present in the list\n");
getch();
return NULL; }
node *insert(node *head)
{ int choice;
node *insert_head(node*);
void insert_after(node*);
void insert_last(node*);
printf("\nInsert a node as a head node");
printf("\nInsert a node as a last node");
printf("\nInsert a node as at the intermediate position in the list ");
printf("\nEnter your choice for insertion of node ");
scanf("%d",&choice);
switch(choice)
{ case 1:head = insert_head(head);break;
case 2:insert_last(head);break;
case 3:insert_after (head);break;
} return head; }
/*Insertion of node at first position*/
node *insert_head(node*head)
{ node *New,*temp;
New = get_node();
printf ("\n Enter the element which you want to insert ");
scanf("%d",&New->data);
if(head == NULL)
head = New;
else
{ temp=head;
New->next = temp;
head= New;
}
return head; }
/*Insertion of node at last position*/
void insert_last(node *head)
{ node *New,*temp;
New = get_node();
printf ("\n Enter the element which you want to insert ");
scanf("%d",&New->data);
if(head == NULL)
{ head = New;
}
else
{ temp=head;
while(temp->next!=NULL)
temp=temp->next;
temp->next=New;
New->next=NULL;
}}
/*Insertion of node at intermediate position*/
void insert_after(node *head)
{ int key;
node *New,*temp;
New = get_node();
printf("Enter the element after which you want to insert ");
scanf("%d",&key);
temp=head;
do
{ if(temp->data==key)
{ printf ("Enter element which you want to insert ");
scanf("%d",&New->data);
New->next=temp->next;
temp->next=New;
return;}
else
temp=temp->next;
}while(temp!=NULL); }
node *get_prev(node *head,int val)
{ node *temp,*prev;
int flag;
temp = head;
if(temp == NULL)
return NULL;
flag = FALSE;
prev = NULL;
while(temp!=NULL && !flag)
{ if(temp->data!=val)
{ prev = temp;
temp = temp->next; }
else
flag = TRUE; }
if(flag) /*if Flag is true*/
return prev;
else
return NULL; }
void dele(node **head)
{ int key;
node *New,*temp, *prev;
temp=*head;
if (temp== NULL)
{ printf ("\n The list is empty\n ");
getch();
clrscr();
return; }
clrscr();
printf("\nENTER the Element you want to delete:");
scanf("%d",&key);
temp= search(*head,key);
if(temp !=NULL)
{ prev = get_prev(*head,key);
if(prev != NULL)
{ prev ->next = temp-> next;
free(temp); }
else
{ *head = temp->next;
free(temp); // using the mem. Dellocation function
}
printf("\nThe Element is deleted\n");
getch();
clrscr();
}}
OUTPUT:

Program to perform various operations on heap using Dynamic memory management.


1.Create
2.Display
3.Insert an element in a list
4. Delete an element from list
5. Quit
Enter your choice(1-5) 1
Enter the element: 10
Do you want to enter more elements? (y/n) y
Enter the element:20
Do you want to enter more elements?(y/n)y
Enter the element:30
Do you want to enter more elements?(y/n)n
The List is created
Program to perform various operations on Heap using Dynamic memory management.
1. Create
2. Display
3. Insert an element in a list
4. Delete an element from list
5. Quit 
Enter your choice(1-5) 4
Enter the element you want to delete: 20
The element is present in the list
The element is deleted
Program to perform various operations on Heap using Dynamic memory management.
1. Create
2. Display
3. Insert an element in a list
4. Delete an element from list
5. Quit
Enter your choice(1-5) 2
10-> 30-> NULL
Ex.No: 9 Program to generate DAG

Dag.c

#include<stdio.h>
#include<conio.h>
#include<alloc.h>
int node_gen_number=0;
struct node
{ int node_no;
char label; /* id : i, num : n */
int l_child; /* 0 : No entry */
int r_child; /* 0 : No entry */
char entry;
int disp;
struct node *next;
};
struct node* mkleafnode(char type,char entry)
{ struct node *n;
n=malloc(sizeof(struct node));
n->label=type;
n->entry=entry;
n->l_child=0;
n->r_child=0;
n->next=NULL;
n->disp=0;
return(n); }
struct node* mknode(char type,int l,int r)
{ struct node *n;
n=malloc(sizeof(struct node));
n->label=type;
n->l_child=l;
n->r_child=r;
n->entry='!';
n->next=NULL;
n->disp=0;
return(n); }
struct node* comparenode(struct node *first,struct node *second)
{ while(first!=NULL)
{ if(first->label==second->label&&first->l_child==second->l_child&&first-r_child==
second->r_child&&first->entry=='!'&&second->entry=='!')
{ free(second);
return(first); }
else
if(first->l_child==0&&second->l_child==0&&first->label==second->label&&first-
>entry==second->entry)
{ free(second);
return(first); }
first=first->next; }
second->node_no=++node_gen_number;
return(second); }
struct node* findnode(struct node *first,char check)
{ while(first!=NULL)
if(first->entry==check)
return(first);
else
first=first->next;
return(NULL); }
struct node* find_node(struct node *first,int no)
{ while(first!=NULL)
if(first->node_no==no)
return(first);
else
first=first->next;
return(NULL); }
void display(struct node *tree,struct node *curr)
{ struct node *temp;
if(curr->entry=='!')
printf("\t\t%d\t%c\t%d\t\t%d\n",curr->node_no,curr->label,curr->l_child,curr->r_child);
else
printf("\t\t%d\t%c\t%c\t\t-\n",curr->node_no,curr->label,curr->entry);
if(curr->l_child!=0&&curr->r_child!=0)
{ temp=find_node(tree,curr->l_child);
if(temp->disp!=1)
{ temp->disp=1;
display(tree,temp); }
temp=find_node(tree,curr->r_child);
if(temp->disp!=1)
{ temp->disp=1;
display(tree,temp); } } }
void main()
{
int i,j,ip=0;
char input[30];
struct node *head=NULL,*temp,*check,*tail;
struct node *tree=NULL;
clrscr();
printf("\t\tConstruction of Directed Acyclic Graph.\n\n");
printf("Enter the Input String: ");
scanf("%s",input);
while(input[ip]!='\0')
{
if(input[ip]!='+'&&input[ip]!='-'&&input[ip]!='*'&&input[ip]!='/')
{ if(isalpha(input[ip]))
temp=mkleafnode('i',input[ip]);
else
temp=mkleafnode('n',input[ip]);
check=comparenode(head,temp);
if(head==NULL)
{ head=temp;
tail=temp; }
else
if(temp==check)
{ tail->next=temp;
tail=temp; } }
ip++;
} ip=0;
while(input[ip]!='\0')
{ if(input[ip]=='+'||input[ip]=='-'||input[ip]=='*'||input[ip]=='/')
{
if(tree==NULL)
{ temp=findnode(head,input[ip-1]);
check=findnode(head,input[ip+1]);
temp=mknode(input[ip],temp->node_no,check- >node_no); }
else {
temp=findnode(head,input[ip+1]);
temp=mknode(input[ip],tail->node_no,temp->node_no); }
check=comparenode(tree,temp);
if(tree==NULL)
{ tree=temp;
tail=temp; }
else
if(temp==check)
{ tail->next=temp;
tail=temp; }
} ip++; }
temp=head;
while(temp!=NULL)
{ check=temp;
temp=temp->next; }
check->next=tree;
printf("\n\n\t\tNode\tLabel\tl_Child|Entry\tR_child\n\n");
display(head,tail);
getch(); }
OUTPUT:

Construction of Directed Acyclic Graph.

Enter the Input String: a+b*a+b

Node
1_Child|Entry R_child
Label
5 + 4 2
4 * 3 1
3 + 1 2
1 i a -
2 i b -
Ex. No: 10 Implement the back end of the compiler (Or) Implementation of Code Generator

Code.c

#include<stdio.h>
#include<conio.h>
#include<string.h>
#include<ctype.h>
#include<graphics.h>
typedef struct
{ char var[10];
int alive; }
regist;
regist preg[10];
void substring(char exp[],int st,int end)
{ int i,j=0;
char dup[10]="";
for(i=st;i<end;i++)
dup[j++]=exp[i];
dup[j]='0';
strcpy(exp,dup); }
int getregister(char var[])
{ int i;
for(i=0;i<10;i++)
{ if(preg[i].alive==0)
{ strcpy(preg[i].var,var);
break; } }
return(i); }
void getvar(char exp[],char v[])
{ int i,j=0;
char var[10]="";
for(i=0;exp[i]!='\0';i++)
if(isalpha(exp[i]))
var[j++]=exp[i];
else
break;
strcpy(v,var);}
void main()
{ char basic[10][10],var[10][10],fstr[10],op;
int i,j,k,reg,vc,flag=0;
clrscr();
printf("\nEnter the Three Address Code:\n");
for(i=0;;i++)
{ gets(basic[i]);
if(strcmp(basic[i],"exit")==0)
break; }
printf("\nThe Equivalent Assembly Code is:\n");
for(j=0;j<i;j++)
{ getvar(basic[j],var[vc++]);
strcpy(fstr,var[vc-1]);
substring(basic[j],strlen(var[vc-1])+1,strlen(basic[j]));
getvar(basic[j],var[vc++]);
reg=getregister(var[vc-1]);
if(preg[reg].alive==0)
{ printf("\nMov R%d,%s",reg,var[vc-1]);
preg[reg].alive=1;
}
op=basic[j][strlen(var[vc-1])];
substring(basic[j],strlen(var[vc-1])+1,strlen(basic[j]));
getvar(basic[j],var[vc++]);
switch(op)
{ case '+': printf("\nAdd"); break;
case '-': printf("\nSub"); break;
case '*': printf("\nMul"); break;
case '/': printf("\nDiv"); break; }
flag=1;
for(k=0;k<=reg;k++)
{ if(strcmp(preg[k].var,var[vc-1])==0)
{ printf("R%d, R%d",k,reg);
preg[k].alive=0;
flag=0;
break; } }
if(flag)
{ printf(" %s,R%d",var[vc-1],reg);
printf("\nMov %s,R%d",fstr,reg); }
strcpy(preg[reg].var,var[vc-3]);
getch();
}
}
OUTPUT:

Enter the Three Address Code:


a=b+c
c=a*c
exit
The Equivalent Assembly Code is:
Mov R0,b
Add c,R0
Mov a,R0
Mov R1,a
Mul c,R1
Mov c,R1
Ex. No 11: Implementation of Simple Code Optimization Techniques

#include<stdio.h>
#include<conio.h>
#include<string.h>
struct op
{ char l;
char r[20]; }
op[10],pr[10];
void main()
{ int a,i,k,j,n,z=0,m,q;
char *p,*l;
char temp,t;
char *tem;
clrscr();
printf("Enter the Number of Values:");
scanf("%d",&n);
for(i=0;i<n;i++)
{ printf("left: ");
op[i].l=getche();
printf("\tright: ");
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");
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",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';
strcpy(pr[i].r,'\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); } }
getch(); }
OUTPUT:

Enter the Number of Values:5


left: a right: 9
left: b right: c+d
left: e right: c+d
left: f right: b+e
left: r right: f
Intermediate Code
a=9
b=c+d
e=c+d
f=b+e
r=f
After Dead Code Elimination
b=c+d
e=c+d
f=b+e
r=f
pos: 2
Eliminate Common Expression
b =c+d
b =c+d
f =b+b
r =f
Optimized Code
b=c+d
f=b+b
r=f

You might also like