Added more instructions for the parser to emit and refactored the code in doing so.
This commit is contained in:
+100
-67
@@ -127,31 +127,92 @@ void HandleAssemblerDirective(void) {
|
||||
}
|
||||
}
|
||||
|
||||
void HandleRegisterBasedOpcode(unsigned char instruction, unsigned char mask) {
|
||||
Memory[ProgramCounter] = mask;
|
||||
|
||||
ProgramCounter++;
|
||||
|
||||
const Token* token = PeekToken();
|
||||
|
||||
if (token->token_class == Reg) {
|
||||
Memory[ProgramCounter - 1] |= (PeekToken()->type - R1) & 0x07;
|
||||
|
||||
AdvanceParser();
|
||||
}
|
||||
else {
|
||||
fprintf(stderr, "[Error] Line %d: Expected register operand.\n", token->line);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
token = PeekToken();
|
||||
|
||||
if (!Expect(1, COMMA)) {
|
||||
fprintf(stderr, "[Error] Expected command one line %d.\n", token->line);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
token = PeekToken();
|
||||
|
||||
if (token->token_class == IDENTIFIER || token->token_class == LABEL) {
|
||||
const Symbol* symbol = GetSymbol(token->lexeme);
|
||||
|
||||
if (!symbol) {
|
||||
fprintf(stderr, "[Error] Line %d: %s is undefined.\n", token->line, token->lexeme);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
Memory[ProgramCounter - 1] |= 0x10;//0b00010000;
|
||||
|
||||
Memory[ProgramCounter] = 2 >> symbol->address & 0xFF;
|
||||
Memory[ProgramCounter + 1] = symbol->address & 0xFF;
|
||||
|
||||
ProgramCounter += 2;
|
||||
|
||||
AdvanceParser();
|
||||
}
|
||||
else if (token->type == NUMBER) {
|
||||
Memory[ProgramCounter - 1] |= 0x08; //0b00001000;
|
||||
|
||||
int* value = PeekToken()->value;
|
||||
|
||||
Memory[ProgramCounter] = 2 >> *value & 0xFF;
|
||||
Memory[ProgramCounter + 1] = *value & 0xFF;
|
||||
|
||||
ProgramCounter += 2;
|
||||
|
||||
AdvanceParser();
|
||||
} else {
|
||||
fprintf(stderr, "[Error] Expected operand, got %s\n", token->lexeme);
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
void HandleOperation(void) {
|
||||
const Instruction* inst = GetOpcodeDetails(PeekToken()->type);
|
||||
const unsigned char registerBasedOpcodeMask = 0xE0;
|
||||
|
||||
if (!inst) return;
|
||||
|
||||
AdvanceParser();
|
||||
|
||||
Memory[ProgramCounter] = GetInstructionMask(inst->op, inst->parameter_one);
|
||||
//Memory[ProgramCounter] = GetInstructionMask(inst->op, inst->parameter_one);
|
||||
unsigned char mask = GetInstructionMask(inst->op, inst->parameter_one);
|
||||
|
||||
ProgramCounter++;
|
||||
|
||||
if (inst->parameter_one == None) {
|
||||
//printf("\n");
|
||||
if (mask & registerBasedOpcodeMask) {
|
||||
HandleRegisterBasedOpcode(Memory[ProgramCounter], mask);
|
||||
return;
|
||||
}
|
||||
|
||||
if (inst->parameter_one && PeekToken()->token_class > 0) {
|
||||
//printf("Matched '%s'\n", PeekToken()->lexeme);
|
||||
switch (mask) {
|
||||
case 0: //NOP
|
||||
Memory[ProgramCounter] = 0x00;
|
||||
ProgramCounter++;
|
||||
return;
|
||||
case 1: //JZ
|
||||
Memory[ProgramCounter] = 0x01;
|
||||
|
||||
ProgramCounter++;
|
||||
|
||||
if (inst->parameter_one & Reg) {
|
||||
//Encode the register number here.
|
||||
Memory[ProgramCounter - 1] |= (PeekToken()->type - R1) & 0x07;
|
||||
//printf("%s ", PeekToken()->lexeme);
|
||||
}
|
||||
else if (inst->parameter_one & Address || inst->parameter_one & Constant) {
|
||||
if (PeekToken()->type == IDENTIFIER || PeekToken()->type == LABEL) {
|
||||
const Symbol* symbol = GetSymbol(PeekToken()->lexeme);
|
||||
|
||||
@@ -160,75 +221,47 @@ void HandleOperation(void) {
|
||||
exit(1);
|
||||
}
|
||||
|
||||
if (inst->op == CMP) Memory[ProgramCounter - 1] |= 0x10;//0b00010000;
|
||||
|
||||
Memory[ProgramCounter] = 2 >> symbol->address & 0xFF;
|
||||
Memory[ProgramCounter + 1] = symbol->address & 0xFF;
|
||||
|
||||
//printf("[%s@%#04X] ", PeekToken()->lexeme, symbol->address);
|
||||
}
|
||||
else if (PeekToken()->type == NUMBER) {
|
||||
Memory[ProgramCounter - 1] |= 0x08; //0b00001000;
|
||||
//printf("%s ", PeekToken()->lexeme);
|
||||
}
|
||||
|
||||
ProgramCounter += 2;
|
||||
}
|
||||
|
||||
AdvanceParser();
|
||||
}
|
||||
|
||||
if (inst->parameter_two == None) {
|
||||
//printf("\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if (PeekToken()->type == COMMA) {
|
||||
AdvanceParser();
|
||||
} else {
|
||||
fprintf(stderr, "Expected comma at line %d\n", PeekToken()->line);
|
||||
exit(666);
|
||||
return;
|
||||
}
|
||||
|
||||
if (inst->parameter_two && PeekToken()->token_class > 0) {
|
||||
//printf("Matched 2 '%s'\n", PeekToken()->lexeme);
|
||||
if (inst->parameter_two & Address || inst->parameter_two & Constant) {
|
||||
if (PeekToken()->type == IDENTIFIER || PeekToken()->type == LABEL) {
|
||||
const Symbol* symbol = GetSymbol(PeekToken()->lexeme);
|
||||
|
||||
if (!symbol) {
|
||||
fprintf(stderr, "[Error] %s is undefined.\n", PeekToken()->lexeme);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
if (inst->op == CMP) Memory[ProgramCounter - 1] |= 0x10;//0b00010000;
|
||||
|
||||
Memory[ProgramCounter] = 2 >> symbol->address & 0xFF;
|
||||
Memory[ProgramCounter + 1] = symbol->address & 0xFF;
|
||||
|
||||
//printf("[%s@%#04X] ", PeekToken()->lexeme, symbol->address);
|
||||
}
|
||||
else if (PeekToken()->type == NUMBER) {
|
||||
Memory[ProgramCounter - 1] |= 0x08; //0b00001000;
|
||||
int* value = PeekToken()->value;
|
||||
|
||||
Memory[ProgramCounter] = 2 >> *value & 0xFF;
|
||||
Memory[ProgramCounter + 1] = *value & 0xFF;
|
||||
|
||||
//printf("%s ", PeekToken()->lexeme);
|
||||
ProgramCounter += 2;
|
||||
}
|
||||
else {
|
||||
fprintf(stderr, "[Error] Line: %d: Expected address after jump if zero (JZ) instruction.\n", ((Token*) TokensList->content[CurrentToken - 1])->line);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
ProgramCounter += 2;
|
||||
}
|
||||
|
||||
AdvanceParser();
|
||||
} else {
|
||||
printf("Failed to match %s (class: %d)\n", PeekToken()->lexeme, PeekToken()->token_class);
|
||||
printf("Inst %s (class: %x)\n", inst->lexeme, inst->parameter_two);
|
||||
return;
|
||||
case 2: //INT
|
||||
Memory[ProgramCounter] = 0x02;
|
||||
|
||||
ProgramCounter++;
|
||||
|
||||
if (PeekToken()->type == NUMBER) {
|
||||
int* value = PeekToken()->value;
|
||||
|
||||
Memory[ProgramCounter] = 2 >> *value & 0xFF;
|
||||
Memory[ProgramCounter + 1] = *value & 0xFF;
|
||||
|
||||
ProgramCounter += 2;
|
||||
}
|
||||
else {
|
||||
fprintf(stderr, "[Error] Line %d: Expected Interrupt vector.\n", PeekToken()->line);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
//printf("\n");
|
||||
return;
|
||||
}
|
||||
|
||||
int ExpectTokenClass(int count, ...) {
|
||||
|
||||
Reference in New Issue
Block a user