Significant progress
This commit is contained in:
parent
66076a7076
commit
6eddacbba2
1 changed files with 125 additions and 16 deletions
117
emulator_shell.c
117
emulator_shell.c
|
@ -464,8 +464,8 @@ int parity(int x, int size)
|
|||
}
|
||||
|
||||
void printState(State8080* state) {
|
||||
printf("\tC=%d,P=%d,S=%d,Z=%d\n", state->cc.cy, state->cc.p,
|
||||
state->cc.s, state->cc.z);
|
||||
printf("\tC=%d,P=%d,S=%d,Z=%d,Enable=%d\n", state->cc.cy, state->cc.p,
|
||||
state->cc.s, state->cc.z, state->int_enable);
|
||||
printf("\tA $%02x B $%02x C $%02x D $%02x E $%02x H $%02x L $%02x SP %04x\n",
|
||||
state->a, state->b, state->c, state->d,
|
||||
state->e, state->h, state->l, state->sp);
|
||||
|
@ -521,6 +521,28 @@ int emulate8080(State8080* state) {
|
|||
state->b = opcode[2];
|
||||
state->pc += 2;
|
||||
break;
|
||||
case 0x02: // STAX B
|
||||
{
|
||||
uint16_t offset = (state->b << 8) | state->c;
|
||||
state->memory[offset] = state->a;
|
||||
}
|
||||
break;
|
||||
case 0x03: // INX B
|
||||
{
|
||||
state->c++;
|
||||
if (state->c == 0) {
|
||||
state->b++;
|
||||
}
|
||||
state->cc.z = (state->b == 0);
|
||||
state->cc.s = (0x80 == (state->b & 0x80));
|
||||
state->cc.p = parity(state->b, 8);
|
||||
}
|
||||
break;
|
||||
case 0x04: // INR B
|
||||
{
|
||||
state->b++;
|
||||
}
|
||||
break;
|
||||
case 0x05: // DCR B
|
||||
{
|
||||
uint8_t res = state->b - 1;
|
||||
|
@ -545,6 +567,13 @@ int emulate8080(State8080* state) {
|
|||
}
|
||||
break;
|
||||
|
||||
case 0x0a: // LDAX B
|
||||
{
|
||||
uint16_t address = (state->b << 8) | state->c;
|
||||
state->a = state->memory[address];
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x0d: // DCR C
|
||||
{
|
||||
uint8_t res = state->c - 1;
|
||||
|
@ -629,6 +658,7 @@ int emulate8080(State8080* state) {
|
|||
state->cc.p = parity((res & 0xff), 8);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 0x29: // DAD H
|
||||
{
|
||||
uint32_t hl = (state->h << 8) | state->l;
|
||||
|
@ -650,6 +680,26 @@ int emulate8080(State8080* state) {
|
|||
}
|
||||
break;
|
||||
|
||||
case 0x34: // ICR M
|
||||
{
|
||||
uint16_t offset = (state->h << 8) | state->l;
|
||||
uint8_t res = state->memory[offset] + 1;
|
||||
state->cc.z = (res == 0);
|
||||
state->cc.s = (0x80 == (res & 0x80));
|
||||
state->cc.p = parity(res, 8);
|
||||
state->memory[offset] = res;
|
||||
}
|
||||
break;
|
||||
case 0x35: // DCR M
|
||||
{
|
||||
uint16_t offset = (state->h << 8) | state->l;
|
||||
uint8_t res = state->memory[offset] - 1;
|
||||
state->cc.z = (res == 0);
|
||||
state->cc.s = (0x80 == (res & 0x80));
|
||||
state->cc.p = parity(res, 8);
|
||||
state->memory[offset] = res;
|
||||
}
|
||||
break;
|
||||
case 0x36: // MVI M, byte
|
||||
{
|
||||
uint16_t adress = (state->h <<8) | (state->l);
|
||||
|
@ -658,6 +708,10 @@ int emulate8080(State8080* state) {
|
|||
}
|
||||
break;
|
||||
|
||||
case 0x37: // STC
|
||||
state->cc.cy = 1;
|
||||
break;
|
||||
|
||||
case 0x3a: // LDA adress
|
||||
{
|
||||
uint16_t adress = (opcode[2]<<8) | (opcode[1]);
|
||||
|
@ -665,6 +719,14 @@ int emulate8080(State8080* state) {
|
|||
state->pc += 2;
|
||||
}
|
||||
break;
|
||||
case 0x3d: // DCR A
|
||||
{
|
||||
state->a--;
|
||||
state->cc.z = (state->a == 0);
|
||||
state->cc.s = (0x80 == (state->a & 0x80));
|
||||
state->cc.p = parity(state->a, 8);
|
||||
}
|
||||
break;
|
||||
case 0x3e: // MVI A, byte
|
||||
state->a = opcode[1];
|
||||
state->pc++;
|
||||
|
@ -766,6 +828,14 @@ int emulate8080(State8080* state) {
|
|||
state->cc.cy = 0;
|
||||
state->cc.ac = 0;
|
||||
break;
|
||||
case 0xc0: // RNZ
|
||||
{
|
||||
if (state->cc.z == 0) {
|
||||
state->pc = state->memory[state->sp] | (state->memory[state->sp+1] << 8);
|
||||
state->sp += 2;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 0xc1: // POP B
|
||||
state->c = state->memory[state->sp];
|
||||
state->b = state->memory[state->sp+1];
|
||||
|
@ -799,10 +869,29 @@ int emulate8080(State8080* state) {
|
|||
state->pc++;
|
||||
}
|
||||
break;
|
||||
|
||||
case 0xc8: // RZ
|
||||
{
|
||||
if (state->cc.z) {
|
||||
state->pc = state->memory[state->sp] | (state->memory[state->sp+1] << 8);
|
||||
state->sp += 2;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 0xc9: // RET
|
||||
state->pc = (state->memory[state->sp+1] << 8) | state->memory[state->sp];
|
||||
state->sp += 2;
|
||||
break;
|
||||
case 0xca: // JZ adress
|
||||
{
|
||||
if (state->cc.z) {
|
||||
state->pc = (opcode[2] << 8) | opcode[1];
|
||||
} else {
|
||||
state->pc +=2;
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case 0xcd: // CALL adress
|
||||
{
|
||||
uint16_t ret = state -> pc+2;
|
||||
|
@ -817,6 +906,15 @@ int emulate8080(State8080* state) {
|
|||
state->d = state->memory[state->sp+1];
|
||||
state->sp += 2;
|
||||
break;
|
||||
case 0xd2: // JNC adress
|
||||
{
|
||||
if (0 == state->cc.cy) {
|
||||
state->pc = (opcode[2] << 8) | opcode[1];
|
||||
} else {
|
||||
state->pc += 2;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 0xd3: // OUT byte
|
||||
{
|
||||
uint8_t port = opcode[1];
|
||||
|
@ -829,6 +927,15 @@ int emulate8080(State8080* state) {
|
|||
state->memory[state->sp-2] = state->e;
|
||||
state->sp -= 2;
|
||||
break;
|
||||
case 0xda: // JC adress
|
||||
{
|
||||
if (state->cc.cy != 0) {
|
||||
state->pc = (opcode[2] << 8) | opcode[1];
|
||||
} else {
|
||||
state->pc += 2;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 0xdb: // IN byte
|
||||
{
|
||||
uint8_t port = opcode[1];
|
||||
|
@ -998,7 +1105,7 @@ typedef struct cpu_data {
|
|||
|
||||
static void draw_callback(GtkWidget *widget, cairo_t *cr, gpointer user_data) {
|
||||
int x, y;
|
||||
int upscaleFactor = 3;
|
||||
int upscaleFactor = 1;
|
||||
uint8_t *video = malloc(sizeof(uint8_t) * 224 * 256 * 4);
|
||||
|
||||
//ROTATION ALGORITHM
|
||||
|
@ -1054,9 +1161,10 @@ void *cpu(void* arg) {
|
|||
while (!done) {
|
||||
counter = emulate8080(cpu->state);
|
||||
cpu->total_cycles_count += counter;
|
||||
printf("Total cycles: %d\n", cpu->total_cycles_count);
|
||||
|
||||
usleep(counter / 2); // EMULATION OF THE PROCESSOR ŠPEED
|
||||
if ((cpu->total_cycles_count > 16000000) && (state->int_enable)) //1/60 second has elapsed
|
||||
if ((cpu->total_cycles_count > 16600) && (state->int_enable)) //1/60 second has elapsed
|
||||
{
|
||||
//redraw screen() will be handeled by the gtk_main() function
|
||||
if (which_interrupt == 2) {
|
||||
|
@ -1083,6 +1191,7 @@ int main (int argc, char *argv[]) {
|
|||
state->cc.p = 1;
|
||||
state->cc.cy = 0;
|
||||
state->cc.ac = 1;
|
||||
state->int_enable = 1;
|
||||
state->pc = 0;
|
||||
state->memory = malloc(0x10000);
|
||||
|
||||
|
|
Loading…
Reference in a new issue