130 lines
3.3 KiB
C
130 lines
3.3 KiB
C
#include "../includes/opcodes.h"
|
|
#include <stdlib.h>
|
|
#include <string.h>
|
|
|
|
Instruction instructions[OPCODECOUNT] = {
|
|
{ "copy", COPY, Reg | Address, Reg | Constant | Address },
|
|
{ "add", ADD, Reg, Reg | Constant },
|
|
{ "sub", SUB, Reg, Reg | Constant },
|
|
{ "jz", JZ, Address, None },
|
|
{ "int", INT, Constant, None },
|
|
{ "yld", YLD, None, None },
|
|
{ "ret", RET, None, None },
|
|
{ "cmp", CMP, Reg, Reg | Constant },
|
|
{ "in", IN, Constant | Reg, None},
|
|
{ "out", OUT, None, None},
|
|
{ "nop", NOP, None, None},
|
|
{ "jmp", JMP, Address, None},
|
|
{ "call", CALL, Address, None}
|
|
};
|
|
|
|
unsigned char GetInstructionMask(TokenType type, TokenClass parameterOneType) {
|
|
switch (type) {
|
|
case COPY:
|
|
if (parameterOneType & Reg) return 0x20; //0b00100000;
|
|
|
|
return 0xA0;//0b10100000;
|
|
case ADD:
|
|
return 0x40;//0b01000000;
|
|
case SUB:
|
|
return 0x60;//0b01100000;
|
|
case CMP:
|
|
return 0x80;//0b10000000;
|
|
case JZ:
|
|
return 0x01;//0b00000001;
|
|
case INT:
|
|
return 0x02; //0b00000010;
|
|
case YLD:
|
|
return 0x03;
|
|
case RET:
|
|
return 0x04;
|
|
case CALL:
|
|
return 0x05;
|
|
case JMP:
|
|
return 0x06;//0b00000110;
|
|
case IN:
|
|
return 0x07;//0b00000111;
|
|
case OUT:
|
|
return 0x08;//0b00001000;
|
|
default:
|
|
return 0x00;
|
|
}
|
|
}
|
|
|
|
/*
|
|
NOP - 0000 0000 NOP
|
|
JZ - 0000 0001 JZ Address
|
|
INT - 0000 0010 INT Constant
|
|
YLD - 0000 0011 YLD
|
|
RET - 0000 0100 RET
|
|
CALL - 0000 0101 CALL Address
|
|
JMP - 0000 0110 JMP Address
|
|
IN - 0000 0111 IN Constant
|
|
OUT - 0000 1000 OUT Constant
|
|
COPY - 0010 0XXX COPY REG, REG
|
|
- 0010 1XXX COPY REG, Constant
|
|
- 0011 0XXX COPY REG, Address
|
|
- 1010 0XXX COPY Address, REG
|
|
- 1010 1XXX COPY Address, Constant
|
|
- 1011 0XXX COPY Address, Address
|
|
ADD - 0100 0XXX ADD REG, REG
|
|
- 0100 1XXX ADD REG, Constant
|
|
SUB - 0110 0XXX SUB REG, REG
|
|
- 0110 1XXX SUB REG, Constant
|
|
CMP - 1000 0XXX CMP REG, REG
|
|
- 1000 1XXX CMP REG, Constant
|
|
- 1001 0XXX CMP REG, Address
|
|
*/
|
|
//COPY X01X XXXX
|
|
//ADD 010X XXXX
|
|
//SUB 011X XXXX
|
|
//CMP 100X XXXX
|
|
//REG XXX0 0XXX
|
|
//Constant XXX0 1XXX
|
|
//Address XXX1 0XXX
|
|
//R1 XXXX X000 -> XXXX X111 (R1 to R8)
|
|
|
|
Register registers[REGISTERCOUNT] = {
|
|
{ "r1", R1 },
|
|
{ "r2", R2 },
|
|
{ "r3", R3 },
|
|
{ "r4", R4 },
|
|
{ "r5", R5 },
|
|
{ "r6", R6 },
|
|
{ "r7", R7 },
|
|
{ "r8", R8 }
|
|
};
|
|
|
|
const Instruction* GetOpcodeDetails(TokenType type) {
|
|
for(int i = 0; i < OPCODECOUNT; i++) {
|
|
if (instructions[i].op == type) return &instructions[i];
|
|
}
|
|
|
|
return NULL;
|
|
}
|
|
|
|
int IsOpcode(const char* text, TokenType* opcode) {
|
|
if (!text) return 0;
|
|
|
|
for(int i = 0; i < OPCODECOUNT; i++) {
|
|
if (strcmp(instructions[i].lexeme, text) == 0) {
|
|
if (opcode) *opcode = instructions[i].op;
|
|
return 1;
|
|
}
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
int IsRegister(const char* text, TokenType* reg) {
|
|
if (!text) return 0;
|
|
|
|
for(int i = 0; i < REGISTERCOUNT; i++) {
|
|
if (strcmp(registers[i].lexeme, text) == 0) {
|
|
*reg = registers[i].type;
|
|
return 1;
|
|
}
|
|
}
|
|
|
|
return 0;
|
|
} |