diff --git a/src/apps/gbdb.c b/src/apps/gbdb.c index 256fe90..f1bd0b1 100644 --- a/src/apps/gbdb.c +++ b/src/apps/gbdb.c @@ -164,8 +164,10 @@ static void init(void) static void cycle() { - lr35902_cycle(&cpu); - gb_video_cycle(&video); + int cycles; + + cycles = lr35902_cycle(&cpu); + gb_video_cycle(&video, cycles); } static void show_prompt() diff --git a/src/gbemu/cpu.c b/src/gbemu/cpu.c index 5098ec1..65731c8 100644 --- a/src/gbemu/cpu.c +++ b/src/gbemu/cpu.c @@ -315,23 +315,17 @@ static const unsigned int cb_extra_cycles[256] = { 0 }; (cpu)->zf = (tmp) == 0; \ } while (0) -void lr35902_cycle(struct lr35902_state *cpu) +int lr35902_cycle(struct lr35902_state *cpu) { uint8_t inst; uint8_t val; uint16_t val_16; uint8_t *reg = NULL; - - cpu->metrics.cycles++; - - if (cpu->stall_cycles > 0) { - cpu->stall_cycles--; - return; - } + int cycles; cpu->metrics.retired_instrs++; inst = cpu->mem_read(cpu, cpu->pc++); - cpu->stall_cycles = op_extra_cycles[inst]; + cycles = op_extra_cycles[inst]; switch (inst) { case 0x00: /* NOP */ @@ -995,7 +989,7 @@ void lr35902_cycle(struct lr35902_state *cpu) case 0xca: case 0xcb: inst = cpu->mem_read(cpu, cpu->pc++); - cpu->stall_cycles = cb_extra_cycles[inst]; + cycles = cb_extra_cycles[inst]; switch (inst) { case 0x00: case 0x01: @@ -1475,4 +1469,7 @@ void lr35902_cycle(struct lr35902_state *cpu) RST(cpu, 0x38); break; } + + cpu->metrics.cycles += cycles + 1; + return cycles + 1; } diff --git a/src/gbemu/cpu.h b/src/gbemu/cpu.h index e4ab46d..55f73b0 100644 --- a/src/gbemu/cpu.h +++ b/src/gbemu/cpu.h @@ -135,6 +135,6 @@ void lr35902_set_reg_8(struct lr35902_state *cpu, lr35902_regs_8 reg, uint8_t val); -void lr35902_cycle(struct lr35902_state *cpu); +int lr35902_cycle(struct lr35902_state *cpu); #endif diff --git a/src/gbemu/video.c b/src/gbemu/video.c index d5e00f4..f9d141f 100644 --- a/src/gbemu/video.c +++ b/src/gbemu/video.c @@ -12,12 +12,11 @@ void gb_video_init(struct gb_video *video) memset(video, 0, sizeof(*video)); } -void gb_video_cycle(struct gb_video *video) +void gb_video_cycle(struct gb_video *video, int cycles) { - if (video->line_counter < CYCLES_PER_LINE - 1) { - video->line_counter++; - } else { - video->line_counter = 0; + video->line_counter += cycles; + if (video->line_counter >= CYCLES_PER_LINE) { + video->line_counter -= CYCLES_PER_LINE; video->curline += 1; if (video->curline > LCD_Y_MAX) { video->curline = 0; diff --git a/src/gbemu/video.h b/src/gbemu/video.h index 4d78803..4facce5 100644 --- a/src/gbemu/video.h +++ b/src/gbemu/video.h @@ -93,7 +93,7 @@ struct gb_video { }; void gb_video_init(struct gb_video *video); -void gb_video_cycle(struct gb_video *video); +void gb_video_cycle(struct gb_video *video, int cycles); uint8_t gb_video_mem_read(struct gb_video *video, uint16_t addr); void gb_video_mem_write(struct gb_video *video, uint16_t addr, uint8_t val);