compilator-2000/as.y
2021-04-06 16:33:49 +02:00

192 lines
4.4 KiB
Text

%{
#include "stdio.h"
#include "stdlib.h"
#include "symbol_table.h"
#include "asm_instructions.h"
#include "yacc_util.h"
enum Type current_type = TYPE_INT;
SymbolTable symbol_table;
InstructionTable instruction_table;
%}
%union {
char* symbol_name;
SymbolItem* symbol;
int nombre;
Instruction instruction;
}
%token<nombre> tNB
%token<instruction> tADD
%token<instruction> tSUB
%token<instruction> tMUL
%token<instruction> tDIV
%token tPO
%token tPF
%token tPV
%token tVIRG
%token tAO
%token tAF
%token tEQ
%token tEQ2
%token tNOTEQ
%token tNOT
%token tINF
%token tINFEQ
%token tSUP
%token tSUPEQ
%token tAND
%token tOR
%token tINT
%token tCONST
%token tMAIN
%token tIF
%token tELSE
%token tELSIF
%token tWHILE
%token tPRINTF
%token<symbol_name> tID
%left tADD
%left tSUB
%left tMUL
%left tDIV
%type<symbol> E
%%
S : Main { printf("S\n"); } ;
Main : tINT tMAIN tPO Params tPF MainBody { printf("Main\n"); } ;
Params : | Param SuiteParams { printf("Params\n"); } ;
Param : tINT tID { printf("Param\n"); } ;
SuiteParams : tVIRG Param SuiteParams { printf("SuiteParam\n"); } ;
MainBody : tAO Declarations Instructions tAF { printf("MainBody\n"); } ;
Body : tAO Instructions tAF { printf("Body\n"); } ;
Instructions : Instruction Instructions | { printf("Instructions\n"); } ;
Instruction : Aff | Printf { printf("Instruction\n"); } ;
Aff : tID tEQ E tPV { write_affectation(&symbol_table, &instruction_table, $1, $3); } ;
E : tNB { $$ = init_temp_symbol(&symbol_table, &instruction_table, $1); }
| tID { $$ = get_symbol_item(&symbol_table, $1); }
| E tADD E {$$ = write_op(&symbol_table, &instruction_table, $2, $1, $3); }
| E tMUL E { $$ = write_op(&symbol_table, &instruction_table, $2, $1, $3); }
| E tSUB E { $$ = write_op(&symbol_table, &instruction_table, $2, $1, $3); }
| E tDIV E { $$ = write_op(&symbol_table, &instruction_table, $2, $1, $3); }
| tPO E tPF { $$ = $2; }
| tSUB E { $$ = write_negation(&symbol_table, &instruction_table, $2); } ;
Declarations : | Declaration Declarations ;
Declaration : DeclarationInt | DeclarationConst ;
DeclarationInt : tINT { current_type = TYPE_INT; } DeclarationBody tPV ;
DeclarationConst : tCONST { current_type = TYPE_CONST; } DeclarationBody tPV ;
DeclarationBody : VariableIdentifier tVIRG DeclarationBody | VariableIdentifier ;
VariableIdentifier: tID { add_symbol(&symbol_table, current_type, $1); }
// While : tWHILE tPO Cond tPF Body { printf("While\n"); } ;
//
// If : IfSimple | IfElse { printf("If\n"); } ;
//
// IfSimple : tIF tPO Cond tPF Body { printf("IfSimple\n"); } ;
//
// IfElse : IfSimple tELSE Body { printf("IfElse\n"); } ;
//
// Cond : tNOT Cond | Cond tAND Cond | Cond tOR Cond | E tEQ2 E | E tINF E | E tINFEQ E | E tSUP E | E tSUPEQ E | E tNOTEQ E | tNOT tPO Cond tPF { printf("Cond\n"); } ;
Printf : tPRINTF tPO E tPF tPV { write_print(&instruction_table, $3); } ;
// If : tIF tPO Cond tPF Body ;
//
// Cond : Cond tAND Cond | Cond tOR Cond | E tEQ2 E | E tINF E | tNOT Cond ;
// Invocation : tID tPO Args tPF ;
// Args : .... cf params
// Return : tRET E tPV ;
%%
#include <string.h>
#define LABEL_SIZE 10
// ADD @ + @ -> @
// SUB @ - @ -> @
// AFC nb -> @
// CPY @ -> @
// Exemple
// y = 1 + 2;
// AFC 1 32
// AFC 2 33
// ADD 32 33 32
// CPY 32 @y
/*
table des symboles (tS) :
sous forme de pile
-> où sera la variable lors de l'exec
|
| nom | type | @ | init |
|-------|--------|-----|--------|
| a | | 0 | |
| b | | 1 | |
| c | | 2 | |
| | | | |
| . | | . | | -> entiers sur 1 octet
| . | | . | |
| . | | . | |
| | | | |
| y | | 26 | |
Donc on remplace @y par 26 dans CPY 32 @y
/!\
E + E + E
| | |
-> -> -> vt variable temporaire (autre expression)
-> -> -> variable -> ADD @E1 @E2 vt
-> -> -> nombre
Donc 9 possibilités (3 par E)
On suppose que E est tout le temps une vt, donc on génère tout le temps le même code
*/
void init() {
init_table(&symbol_table);
init_instruction_table(&instruction_table);
}
void yyerror(char const* err) {
printf("%s\n", err);
exit(1);
}
void main(void) {
init();
yyparse();
print_table(&symbol_table);
FILE *f = fopen("instruction_table.txt", "w+");
write_instruction_table(&instruction_table, f);
fclose(f);
}