CALL and RET instructions.
Changed PSHP and POPP into CALL and RET, streamlining their use for subroutine calls. Updated Assembler and Emulator. New demonstration programs.
This commit is contained in:
@@ -71,11 +71,14 @@ void assemblerCleanup(intermediateElement *intermediateArray, int arraySize, cha
|
||||
}
|
||||
// Free the intermediateArray itself.
|
||||
free(intermediateArray);
|
||||
|
||||
// Free the list of included files.
|
||||
freeIncludeList();
|
||||
|
||||
// Free the list of labels.
|
||||
freeLabelList();
|
||||
// Free the output file name.
|
||||
|
||||
// Free the output file name
|
||||
free(outputFileName);
|
||||
}
|
||||
|
||||
|
||||
@@ -27,6 +27,8 @@ Instruction instruction_set[] = {
|
||||
{0x11, "BRQ"},
|
||||
{0x12, "BRA"},
|
||||
{0x13, "BRB"},
|
||||
{0x14, "CALL"},
|
||||
{0x15, "RET"},
|
||||
// Register Operations:
|
||||
{0x20, "RSTA"},
|
||||
{0x21, "RSTB"},
|
||||
@@ -42,12 +44,10 @@ Instruction instruction_set[] = {
|
||||
{0x30, "PSHQ"},
|
||||
{0x31, "PSHA"},
|
||||
{0x32, "PSHB"},
|
||||
{0x33, "PSHP"},
|
||||
{0x34, "PSHD"},
|
||||
{0x35, "POPA"},
|
||||
{0x36, "POPB"},
|
||||
{0x37, "POPP"},
|
||||
{0x38, "POPD"},
|
||||
{0x33, "PSHD"},
|
||||
{0x34, "POPA"},
|
||||
{0x35, "POPB"},
|
||||
{0x36, "POPD"},
|
||||
// Data Operations:
|
||||
{0x40, "INCD"},
|
||||
{0x41, "DECD"},
|
||||
|
||||
@@ -112,9 +112,9 @@ void populateOutputBuffers(intermediateElement *intermediateArray, int arraySize
|
||||
Program[(*programCount)++] = intermediateArray[i].byteValue;
|
||||
|
||||
// Check if it's a branch instruction.
|
||||
if ((intermediateArray[i].byteValue & 0xF0) == 0x10) {
|
||||
if (((intermediateArray[i].byteValue & 0xF0) == 0x10) && (intermediateArray[i].byteValue != 0x15)){
|
||||
if (intermediateArray[i + 1].type != LABEL) {
|
||||
fprintf(stderr, "Error: Branch without label.\n");
|
||||
fprintf(stderr, RED "Error: Branch without label.\n" RESET);
|
||||
printf("File: %s at line %d.\n", intermediateArray[i].fileName, intermediateArray[i].lineNumber);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
+22
-19
@@ -114,6 +114,24 @@ uint8_t executeOperation(uint8_t Instruction, CPURegisters *cpu) {
|
||||
cpu->ProgramCounter+=2;
|
||||
}
|
||||
break;
|
||||
case 0x14:
|
||||
// CALL - Push the Program Counter to the Stack, and perform an immediate branch.
|
||||
// Order, low byte, high byte
|
||||
cpu->Data[cpu->StackPointer] = cpu->ProgramCounter & 0xFF;
|
||||
cpu->StackPointer--;
|
||||
cpu->Data[cpu->StackPointer] = (cpu->ProgramCounter >> 8) & 0xFF;
|
||||
cpu->StackPointer--;
|
||||
genericBranch(cpu);
|
||||
break;
|
||||
case 0x15:
|
||||
// RET - Return from subroutine, restore the Program Counter from the Stack.
|
||||
// POPP - Pop Data to the Program Counter
|
||||
cpu->StackPointer++;
|
||||
cpu->ProgramCounter = (uint16_t)cpu->Data[cpu->StackPointer] << 8;
|
||||
cpu->StackPointer++;
|
||||
cpu->ProgramCounter = cpu->ProgramCounter | (uint16_t)cpu->Data[cpu->StackPointer];
|
||||
cpu->ProgramCounter += 2; // Because it needs to skip over the address when it returns.
|
||||
break;
|
||||
//
|
||||
// 2x - Register Operations:
|
||||
//
|
||||
@@ -177,15 +195,8 @@ uint8_t executeOperation(uint8_t Instruction, CPURegisters *cpu) {
|
||||
cpu->Data[cpu->StackPointer] = cpu->B;
|
||||
cpu->StackPointer--;
|
||||
break;
|
||||
case 0x33:
|
||||
// PSHP - Push the Program Counter to the Stack.
|
||||
// Order, low byte, high byte
|
||||
cpu->Data[cpu->StackPointer] = cpu->ProgramCounter & 0xFF;
|
||||
cpu->StackPointer--;
|
||||
cpu->Data[cpu->StackPointer] = (cpu->ProgramCounter >> 8) & 0xFF;
|
||||
cpu->StackPointer--;
|
||||
break;
|
||||
case 0x34:
|
||||
case 0x33:
|
||||
// PSHD - Push the Data Pointer to the Stack.
|
||||
// Order, low byte, high byte
|
||||
cpu->Data[cpu->StackPointer] = cpu->DataPointer & 0xFF;
|
||||
@@ -193,26 +204,18 @@ uint8_t executeOperation(uint8_t Instruction, CPURegisters *cpu) {
|
||||
cpu->Data[cpu->StackPointer] = (cpu->DataPointer >> 8) & 0xFF;
|
||||
cpu->StackPointer--;
|
||||
break;
|
||||
case 0x35:
|
||||
case 0x34:
|
||||
// POPA - Pop Data to A.
|
||||
cpu->StackPointer++;
|
||||
cpu->A = cpu->Data[cpu->StackPointer];
|
||||
|
||||
break;
|
||||
case 0x36:
|
||||
case 0x35:
|
||||
// POPB - Pop Data to B.
|
||||
cpu->StackPointer++;
|
||||
cpu->B = cpu->Data[cpu->StackPointer];
|
||||
break;
|
||||
case 0x37:
|
||||
// POPP - Pop Data to the Program Counter
|
||||
cpu->StackPointer++;
|
||||
cpu->ProgramCounter = (uint16_t)cpu->Data[cpu->StackPointer] << 8;
|
||||
cpu->StackPointer++;
|
||||
cpu->ProgramCounter = cpu->ProgramCounter | (uint16_t)cpu->Data[cpu->StackPointer];
|
||||
cpu->ProgramCounter += 3; // Because it needs to skip over the subsequent branch instruction on return.
|
||||
break;
|
||||
case 0x38:
|
||||
case 0x36:
|
||||
// POPD - Pop Data to the Data Pointer
|
||||
cpu->StackPointer++;
|
||||
cpu->DataPointer = (uint16_t)cpu->Data[cpu->StackPointer] << 8;
|
||||
|
||||
Reference in New Issue
Block a user