#include "tables.h" #include #include #define TAILLE_BUFFER_INSTRUCTIONS (1024) #define TAILLE_MEMOIRE (64) #define TAILLE_PILE_APPELS (16) #define SECURED (1) /**************************************************/ /**************************************************/ /************ Variables et structures *************/ /**************************************************/ /**************************************************/ // Structure coding an instruction struct str_instruction { enum instruction_t instruction; int param1; int param2; int param3; }; // Buffer stockant le programme struct str_instruction programme[TAILLE_BUFFER_INSTRUCTIONS * sizeof(struct str_instruction)]; // Pointeur d'instruction int eip = 0; // Memoire du programme int mem[TAILLE_MEMOIRE]; // Pointeur de base dans la mémoire int ebp = 0; // Memoire du programme int pile[TAILLE_PILE_APPELS]; // Pointeur de sommet dans la pile d'appel int esp = 0; /**************************************************/ /**************************************************/ /******* Fonctions internes de verification *******/ /**************************************************/ /**************************************************/ // Verifie qu'une adresse est bien en mémoire (renvoi l'adresse si oui, leve une exception si non) int check_adresse(int adresse) { if (adresse >= TAILLE_MEMOIRE || adresse < 0) { printf("\033[31;01m ERROR : \033[00m Segmentation fault\n"); exit(2); } return adresse; } // Verifie que les limites de la mémoire d'appels ne sont pas franchies int check_adresse_pile(int adresse) { if (adresse >= TAILLE_PILE_APPELS || adresse < 0) { printf("\033[31;01m ERROR : \033[00m Stack error\n"); exit(2); } return adresse; } // Verifie que eip ne depasse pas la taille du buffer int check_eip(int eip) { if (eip >= TAILLE_BUFFER_INSTRUCTIONS) { printf("\033[31;01m ERROR : \033[00m Taille du buffer insuffisante pour charger le programme\n"); exit(2); } else if (eip < 0) { printf("\033[31;01m ERROR : \033[00m EIP < 0\n"); exit(2); } return eip; } /**************************************************/ /**************************************************/ /********** Fonction interne d'affichage **********/ /**************************************************/ /**************************************************/ // Affiche la mémoire void print() { int i; printf("EBP : %d\n", ebp); for (i=0; i mem[check_adresse(ebp + programme[eip].param3)]; } else if (programme[eip].instruction == EQU) { mem[check_adresse(ebp + programme[eip].param1)] = mem[check_adresse(ebp + programme[eip].param2)] == mem[check_adresse(ebp + programme[eip].param3)]; } else if (programme[eip].instruction == AFC) { mem[check_adresse(ebp + programme[eip].param1)] = programme[eip].param2; } else if (programme[eip].instruction == CPY) { mem[check_adresse(ebp + programme[eip].param1)] = mem[check_adresse(ebp + programme[eip].param2)]; } else if (programme[eip].instruction == AFCA) { mem[check_adresse(ebp + programme[eip].param1)] = ebp + programme[eip].param2; } else if (programme[eip].instruction == READ) { mem[check_adresse(ebp + programme[eip].param1)] = mem[check_adresse(mem[check_adresse(ebp + programme[eip].param2)])]; } else if (programme[eip].instruction == WRITE) { mem[check_adresse(mem[check_adresse(ebp + programme[eip].param1)])] = mem[check_adresse(ebp + programme[eip].param2)]; } else if (programme[eip].instruction == JMP) { eip = programme[eip].param1 - 1; } else if (programme[eip].instruction == JMF) { if (!mem[check_adresse(ebp + programme[eip].param1)]) { eip = programme[eip].param2 - 1; } } else if (programme[eip].instruction == GET) { scanf("%d", &(mem[check_adresse(ebp + programme[eip].param1)])); } else if (programme[eip].instruction == PRI) { printf("%d", mem[check_adresse(ebp + programme[eip].param1)]); } else if (programme[eip].instruction == PRIC) { printf("%c", mem[check_adresse(ebp + programme[eip].param1)]); } else if (programme[eip].instruction == CALL) { if (SECURED) { pile[check_adresse_pile(esp)] = ebp; esp++; pile[check_adresse_pile(esp)] = eip + 1; esp++; ebp = ebp + programme[eip].param2; eip = programme[eip].param1 - 1; } else { mem[check_adresse(ebp + programme[eip].param2)] = ebp; mem[check_adresse(ebp + programme[eip].param2 + 1)] = eip + 1; ebp = ebp + programme[eip].param2 + 2; eip = programme[eip].param1 - 1; } } else if (programme[eip].instruction == RET) { if (SECURED) { esp--; eip = pile[check_adresse_pile(esp)] - 1; esp--; ebp = pile[check_adresse_pile(esp)]; } else { int lastebp = ebp; eip = mem[check_adresse(ebp - 1)] - 1; ebp = mem[check_adresse(ebp - 2)]; mem[check_adresse(lastebp - 2)] = mem[check_adresse(lastebp)]; } } else if (programme[eip].instruction == STOP) { if (programme[eip].param1 == 0) { continuer = 0; } } eip = (eip + 1) % TAILLE_BUFFER_INSTRUCTIONS; //printf("EIP : %d \n", eip); } }