Browse Source

implement arithmetic operations asm generation

Arnaud Vergnet 3 years ago
parent
commit
74e97fe963
11 changed files with 152 additions and 69 deletions
  1. 3
    3
      Makefile
  2. 18
    4
      al.lex
  3. 25
    9
      as.y
  4. 16
    1
      asm_instructions.c
  5. 2
    15
      asm_instructions.h
  6. 18
    16
      symbol_table.c
  7. 12
    4
      symbol_table.h
  8. 10
    15
      symbol_table.test.c
  9. 2
    2
      test.c
  10. 30
    0
      yacc_util.c
  11. 16
    0
      yacc_util.h

+ 3
- 3
Makefile View File

5
 all: compilateur test
5
 all: compilateur test
6
 
6
 
7
 test: symbol_table.test.c symbol_table.c symbol_table.h
7
 test: symbol_table.test.c symbol_table.c symbol_table.h
8
-	$(CC) -o test symbol_table.test.c symbol_table.c
8
+	$(CC) -g -o test symbol_table.test.c symbol_table.c
9
 
9
 
10
-compilateur: as.tab.c lex.yy.c symbol_table.c symbol_table.h asm_instructions.c asm_instructions.h
11
-	$(CC) -o compilateur as.tab.c lex.yy.c symbol_table.c asm_instructions.c
10
+compilateur: as.tab.c lex.yy.c symbol_table.c symbol_table.h asm_instructions.c asm_instructions.h yacc_util.c yacc_util.h
11
+	$(CC) -o compilateur as.tab.c lex.yy.c symbol_table.c asm_instructions.c yacc_util.c
12
 
12
 
13
 as.tab.c: as.y
13
 as.tab.c: as.y
14
 	$(YACC) as.y
14
 	$(YACC) as.y

+ 18
- 4
al.lex View File

1
 %{
1
 %{
2
+#include "asm_instructions.h"
3
+#include "symbol_table.h"
2
 #include "as.tab.h"
4
 #include "as.tab.h"
3
 %}
5
 %}
4
 
6
 
11
                 return tNB;
13
                 return tNB;
12
             }
14
             }
13
 
15
 
14
-"+"			{ return tADD; }
15
-"-"			{ return tSUB; }
16
-"*"			{ return tMUL; }
17
-"/"			{ return tDIV; }
16
+"+"			{ 
17
+                yylval.instruction = ADD;
18
+                return tADD; 
19
+            }
20
+"-"			{ 
21
+                yylval.instruction = SOU;
22
+                return tSUB;
23
+            }
24
+"*"			{ 
25
+                yylval.instruction = MUL;
26
+                return tMUL;
27
+            }
28
+"/"			{ 
29
+                yylval.instruction = DIV;
30
+                return tDIV;
31
+            }
18
 "="			{ return tEQ; }
32
 "="			{ return tEQ; }
19
 "("			{ return tPO; }
33
 "("			{ return tPO; }
20
 ")"			{ return tPF; }
34
 ")"			{ return tPF; }

+ 25
- 9
as.y View File

2
 #include "stdio.h"
2
 #include "stdio.h"
3
 #include "stdlib.h"
3
 #include "stdlib.h"
4
 #include "symbol_table.h"
4
 #include "symbol_table.h"
5
+#include "asm_instructions.h"
6
+#include "yacc_util.h"
5
 
7
 
6
 enum Type current_type = TYPE_INT;
8
 enum Type current_type = TYPE_INT;
7
 
9
 
8
 SymbolTable symbol_table;
10
 SymbolTable symbol_table;
11
+InstructionTable instruction_table;
9
 
12
 
10
 %}
13
 %}
11
 
14
 
12
 %union {
15
 %union {
13
     char* symbol_name;
16
     char* symbol_name;
17
+    SymbolItem* symbol;
14
 	int nombre;
18
 	int nombre;
19
+	Instruction instruction;
15
 }
20
 }
16
 
21
 
17
 %token<nombre> tNB
22
 %token<nombre> tNB
18
-%token tADD
19
-%token tSUB
20
-%token tMUL
21
-%token tDIV
23
+%token<instruction> tADD
24
+%token<instruction> tSUB
25
+%token<instruction> tMUL
26
+%token<instruction> tDIV
22
 %token tPO
27
 %token tPO
23
 %token tPF
28
 %token tPF
24
 %token tPV
29
 %token tPV
50
 %left tSUB
55
 %left tSUB
51
 %left tMUL
56
 %left tMUL
52
 %left tDIV
57
 %left tDIV
53
-// %type<nombre> E
58
+%type<symbol> E
54
 
59
 
55
 %%
60
 %%
56
 
61
 
71
 
76
 
72
 Instruction : Aff | Printf { printf("Instruction\n"); } ;
77
 Instruction : Aff | Printf { printf("Instruction\n"); } ;
73
 
78
 
74
-Aff : tID tEQ E tPV { mark_symbol_initialized(&symbol_table, $1); } ;
79
+Aff : tID tEQ E tPV { write_affectation(&symbol_table, &instruction_table, $1, $3); } ;
75
 
80
 
76
-E : tNB { printf("%d\n", $1); } | tID | E tADD E | E tMUL E | E tSUB E | E tDIV E | tPO E tPF | tSUB E ;
81
+E : tNB { $$ = init_temp_symbol(&symbol_table, &instruction_table, $1); } 
82
+    | tID { $$ = get_symbol_item(&symbol_table, $1); } 
83
+    | E tADD E {$$ = write_op(&symbol_table, &instruction_table, $2, $1, $3); } 
84
+    | E tMUL E { $$ = write_op(&symbol_table, &instruction_table, $2, $1, $3); } 
85
+    | E tSUB E { $$ = write_op(&symbol_table, &instruction_table, $2, $1, $3); } 
86
+    | E tDIV E { $$ = write_op(&symbol_table, &instruction_table, $2, $1, $3); } 
87
+    | tPO E tPF { $$ = $2; } 
88
+    | tSUB E  { $$ = write_negation(&symbol_table, &instruction_table, $2); } ;
77
 
89
 
78
-Declarations : | Declaration Declarations { printf("Declarations\n"); } ;
90
+Declarations : | Declaration Declarations ;
79
 
91
 
80
-Declaration : DeclarationInt | DeclarationConst { printf("Declaration\n"); } ;
92
+Declaration : DeclarationInt | DeclarationConst ;
81
 
93
 
82
 DeclarationInt : tINT { current_type = TYPE_INT; } DeclarationBody tPV ;
94
 DeclarationInt : tINT { current_type = TYPE_INT; } DeclarationBody tPV ;
83
 
95
 
162
 
174
 
163
 void init() {
175
 void init() {
164
     init_table(&symbol_table);
176
     init_table(&symbol_table);
177
+    init_instruction_table(&instruction_table);
165
 }
178
 }
166
 
179
 
167
 void yyerror(char const* err) {
180
 void yyerror(char const* err) {
173
     init();
186
     init();
174
 	yyparse();
187
 	yyparse();
175
 	print_table(&symbol_table);
188
 	print_table(&symbol_table);
189
+    FILE *f = fopen("instruction_table.txt", "w+");
190
+	write_instruction_table(&instruction_table, f);
191
+    fclose(f);
176
 }
192
 }

+ 16
- 1
asm_instructions.c View File

1
 #include "asm_instructions.h"
1
 #include "asm_instructions.h"
2
 
2
 
3
+char* instructions_labels[12] = {
4
+        "ADD",
5
+        "MUL",
6
+        "SOU",
7
+        "DIV",
8
+        "COP",
9
+        "AFC",
10
+        "JMP",
11
+        "JMF",
12
+        "INF",
13
+        "SUP",
14
+        "EQU",
15
+        "PRI"
16
+};
17
+
3
 void init_instruction_table(InstructionTable *table) {
18
 void init_instruction_table(InstructionTable *table) {
4
     table->index = 0;
19
     table->index = 0;
5
 }
20
 }
26
 }
41
 }
27
 
42
 
28
 void write_instruction(InstructionItem *item, FILE *file) {
43
 void write_instruction(InstructionItem *item, FILE *file) {
29
-    fprintf(file, "%s %d %d %d", instructions_labels[item->instruction], item->arg1, item->arg2, item->arg3);
44
+    fprintf(file, "%s %d %d %d\n", instructions_labels[item->instruction], item->arg1, item->arg2, item->arg3);
30
 }
45
 }

+ 2
- 15
asm_instructions.h View File

8
 typedef enum Instruction {
8
 typedef enum Instruction {
9
         ADD,
9
         ADD,
10
         MUL,
10
         MUL,
11
-        SUO,
11
+        SOU,
12
         DIV,
12
         DIV,
13
         COP,
13
         COP,
14
         AFC,
14
         AFC,
20
         PRI
20
         PRI
21
 } Instruction;
21
 } Instruction;
22
 
22
 
23
-char* instructions_labels[12] = {
24
-        "ADD",
25
-        "MUL",
26
-        "SUO",
27
-        "DIV",
28
-        "COP",
29
-        "AFC",
30
-        "JMP",
31
-        "JMF",
32
-        "INF",
33
-        "SUP",
34
-        "EQU",
35
-        "PRI"
36
-};
23
+char* instructions_labels[12];
37
 
24
 
38
 
25
 
39
 typedef struct InstructionItem {
26
 typedef struct InstructionItem {

+ 18
- 16
symbol_table.c View File

8
     table->temp_index = SYMBOL_TABLE_SIZE - 1;
8
     table->temp_index = SYMBOL_TABLE_SIZE - 1;
9
 }
9
 }
10
 
10
 
11
+void init_symbol_item(SymbolItem *symbol_item, size_t name_size) {
12
+    symbol_item->type = 0;
13
+    symbol_item->name = malloc(name_size);
14
+    symbol_item->address = 0;
15
+    symbol_item->init = 0;
16
+}
17
+
11
 int has_symbol(SymbolTable* table, char *name) {
18
 int has_symbol(SymbolTable* table, char *name) {
12
     for (int i = 0; i < table->index; i++) {
19
     for (int i = 0; i < table->index; i++) {
13
         if (strcmp(table->table[i].name, name) == 0) {
20
         if (strcmp(table->table[i].name, name) == 0) {
30
         return -1;
37
         return -1;
31
     }
38
     }
32
     SymbolItem newItem;
39
     SymbolItem newItem;
40
+    init_symbol_item(&newItem, strlen(name));
33
     newItem.type = type;
41
     newItem.type = type;
34
     newItem.name = name;
42
     newItem.name = name;
35
     newItem.address = table->index;
43
     newItem.address = table->index;
40
     return 0;
48
     return 0;
41
 }
49
 }
42
 
50
 
43
-int add_temp_symbol(SymbolTable* table, enum Type type, char *name) {
51
+const SymbolItem* add_temp_symbol(SymbolTable* table, enum Type type) {
44
     if (table->temp_index < table->index) {
52
     if (table->temp_index < table->index) {
45
-        return -2;
46
-    }
47
-    if (has_symbol(table, name)) {
48
-        return -1;
49
-    }
50
-    if (name[0] != '_') {
51
-        return -3;
53
+        return NULL;
52
     }
54
     }
53
 
55
 
54
-    SymbolItem newItem;
55
-    newItem.type = type;
56
-    newItem.name = name;
57
-    newItem.address = table->temp_index;
58
-    newItem.init = 0;
56
+    SymbolItem *newItem = &table->table[table->temp_index];
57
+    init_symbol_item(newItem, 10);
58
+    newItem->type = type;
59
+    sprintf(newItem->name, "_temp%d", table->temp_index);
60
+    newItem->address = table->temp_index;
61
+    newItem->init = 0;
59
 
62
 
60
-    table->table[table->temp_index] = newItem;
61
     table->temp_index--;
63
     table->temp_index--;
62
-    return 0;
64
+    return newItem;
63
 }
65
 }
64
 
66
 
65
 int mark_symbol_initialized(SymbolTable *table, char *name) {
67
 int mark_symbol_initialized(SymbolTable *table, char *name) {
107
     }
109
     }
108
 }
110
 }
109
 
111
 
110
-SymbolItem *get_symbol_item(SymbolTable *table, char *name) {
112
+SymbolItem *get_symbol_item(SymbolTable *table, const char *name) {
111
     for (int i = 0; i < table->index; i++) {
113
     for (int i = 0; i < table->index; i++) {
112
         if (strcmp(table->table[i].name, name) == 0) {
114
         if (strcmp(table->table[i].name, name) == 0) {
113
             return &table->table[i];
115
             return &table->table[i];

+ 12
- 4
symbol_table.h View File

1
 #ifndef SYMBOL_TABLE_H_INCLUDED
1
 #ifndef SYMBOL_TABLE_H_INCLUDED
2
 #define SYMBOL_TABLE_H_INCLUDED
2
 #define SYMBOL_TABLE_H_INCLUDED
3
 
3
 
4
+#include <stddef.h>
5
+
4
 #define SYMBOL_TABLE_SIZE 100
6
 #define SYMBOL_TABLE_SIZE 100
5
 
7
 
6
 enum Type {
8
 enum Type {
32
 void init_table(SymbolTable *table);
34
 void init_table(SymbolTable *table);
33
 
35
 
34
 /**
36
 /**
37
+ * Initializes the symbol
38
+ *
39
+ * @param table
40
+ */
41
+void init_symbol_item(SymbolItem *symbol_item, size_t name_size);
42
+
43
+/**
35
  * Checks if the given symbol is in the table
44
  * Checks if the given symbol is in the table
36
  *
45
  *
37
  * @param table
46
  * @param table
57
  * @param table
66
  * @param table
58
  * @param type
67
  * @param type
59
  * @param name
68
  * @param name
60
- * @return 0 on success, -1 if the symbol already exists, -2 if the table is full
61
- *          -3 if the name doesn't start by _
69
+ * @return 0 on success, -1 if the table is full
62
  */
70
  */
63
-int add_temp_symbol(SymbolTable* table, enum Type type, char *name);
71
+const SymbolItem* add_temp_symbol(SymbolTable* table, enum Type type);
64
 
72
 
65
 /**
73
 /**
66
  * Marks the given symbol as initialized
74
  * Marks the given symbol as initialized
100
  * @param name
108
  * @param name
101
  * @return the item if found, NULL otherwise
109
  * @return the item if found, NULL otherwise
102
  */
110
  */
103
-SymbolItem *get_symbol_item(SymbolTable* table, char *name);
111
+SymbolItem *get_symbol_item(SymbolTable* table, const char *name);
104
 
112
 
105
 #endif /* !SYMBOL_TABLE_H_INCLUDED  */
113
 #endif /* !SYMBOL_TABLE_H_INCLUDED  */

+ 10
- 15
symbol_table.test.c View File

1
 #include "symbol_table.h"
1
 #include "symbol_table.h"
2
 #include <stdio.h>
2
 #include <stdio.h>
3
 #include <assert.h>
3
 #include <assert.h>
4
+#include <string.h>
4
 
5
 
5
 int main() {
6
 int main() {
6
     int err;
7
     int err;
33
     printf("Mark b initialized\n");
34
     printf("Mark b initialized\n");
34
     assert(err == -1);
35
     assert(err == -1);
35
 
36
 
36
-    err = add_temp_symbol(&table, TYPE_INT, "_temp1");
37
-    printf("Add _temp1 temporary variable\n");
38
-    assert(err == 0);
39
-    err = add_temp_symbol(&table, TYPE_INT, "_temp2");
40
-    printf("Add _temp2 temporary variable\n");
41
-    assert(err == 0);
42
-    err = add_temp_symbol(&table, TYPE_INT, "_temp1");
43
-    printf("Add _temp1 temporary variable\n");
44
-    assert(err == -1);
45
-    err = add_temp_symbol(&table, TYPE_INT, "temp1");
46
-    printf("Add temp1 temporary variable\n");
47
-    assert(err == -3);
37
+    const SymbolItem* var1 = add_temp_symbol(&table, TYPE_INT);
38
+    printf("Add _temp99 temporary variable\n");
39
+    assert(strcmp(var1->name, "_temp99") == 0);
40
+    const SymbolItem* var2 = add_temp_symbol(&table, TYPE_INT);
41
+    printf("Add _temp98 temporary variable\n");
42
+    assert(strcmp(var2->name, "_temp98") == 0);
48
 
43
 
49
-    item = get_symbol_item(&table, "_temp1");
50
-    printf("_temp1:\n");
44
+    item = get_symbol_item(&table, "_temp98");
45
+    printf("_temp98:\n");
51
     print_item(item);
46
     print_item(item);
52
-    item = get_symbol_item(&table, "_temp5");
47
+    item = get_symbol_item(&table, "_temp0");
53
     printf("_temp5:\n");
48
     printf("_temp5:\n");
54
     print_item(item);
49
     print_item(item);
55
 
50
 

+ 2
- 2
test.c View File

2
     int x, y, z;
2
     int x, y, z;
3
     const PL5_op, b, c;
3
     const PL5_op, b, c;
4
     printf(x);
4
     printf(x);
5
-    x = 3 + 2;
6
-    y = 3;
5
+    x = 2;
6
+    y = 3 + 3 + x;
7
 }
7
 }

+ 30
- 0
yacc_util.c View File

1
+#include "yacc_util.h"
2
+
3
+void write_affectation(SymbolTable* symbol_table, InstructionTable *instruction_table, char* symbol_dest, SymbolItem* src) {
4
+    mark_symbol_initialized(symbol_table, symbol_dest);
5
+    SymbolItem *dest = get_symbol_item(symbol_table, symbol_dest);
6
+    add_instruction(instruction_table, COP, src->address, dest->address, 0);
7
+}
8
+
9
+const SymbolItem* write_op(SymbolTable* symbol_table, InstructionTable *instruction_table, Instruction instruction, SymbolItem *op1, SymbolItem *op2) {
10
+    const SymbolItem* dest = add_temp_symbol(symbol_table, TYPE_INT);
11
+    add_instruction(instruction_table, instruction, dest->address, op1->address, op2->address);
12
+    return dest;
13
+}
14
+
15
+const SymbolItem* write_negation(SymbolTable* symbol_table, InstructionTable *instruction_table, SymbolItem *op2) {
16
+//    Create temp variable with 0
17
+    const SymbolItem* op1 = init_temp_symbol(symbol_table, instruction_table, 0);
18
+    const SymbolItem* dest = add_temp_symbol(symbol_table, TYPE_INT);
19
+//    Make the 0 - variable operation
20
+    add_instruction(instruction_table, SOU, dest->address, op1->address, op2->address);
21
+    return dest;
22
+}
23
+
24
+
25
+const SymbolItem* init_temp_symbol(SymbolTable* symbol_table, InstructionTable *instruction_table, int constant) {
26
+    const SymbolItem* dest = add_temp_symbol(symbol_table, TYPE_INT);
27
+    add_instruction(instruction_table, AFC, dest->address, constant, 0);
28
+    return dest;
29
+}
30
+

+ 16
- 0
yacc_util.h View File

1
+#include "symbol_table.h"
2
+#include "asm_instructions.h"
3
+
4
+#ifndef COMPILATOR_2000_YACC_UTIL_H
5
+#define COMPILATOR_2000_YACC_UTIL_H
6
+
7
+
8
+void write_affectation(SymbolTable* symbolTable, InstructionTable *instructionTable, char* symbol_dest, SymbolItem* src);
9
+
10
+const SymbolItem* write_op(SymbolTable* symbol_table, InstructionTable *instruction_table, Instruction instruction, SymbolItem *op1, SymbolItem *op2);
11
+
12
+const SymbolItem* write_negation(SymbolTable* symbol_table, InstructionTable *instruction_table, SymbolItem *op2);
13
+
14
+const SymbolItem* init_temp_symbol(SymbolTable* symbol_table, InstructionTable *instruction_table, int constant);
15
+
16
+#endif //COMPILATOR_2000_YACC_UTIL_H

Loading…
Cancel
Save