Mercurial > repos > blastem
diff blastem.c @ 652:f822d9216968
Merge
author | Michael Pavone <pavone@retrodev.com> |
---|---|
date | Tue, 30 Dec 2014 19:11:34 -0800 |
parents | 649db9397fa1 d77c79cec800 |
children | 759c38bf97f8 |
line wrap: on
line diff
--- a/blastem.c Mon Dec 29 23:08:39 2014 -0800 +++ b/blastem.c Tue Dec 30 19:11:34 2014 -0800 @@ -33,7 +33,7 @@ #define MAX_SOUND_CYCLES 100000 -uint32_t mclks_per_frame = MCLKS_LINE*LINES_NTSC; +uint32_t mclk_target = 0; uint16_t cart[CARTRIDGE_WORDS]; uint16_t ram[RAM_WORDS]; @@ -191,15 +191,19 @@ z80_reset(z_context); need_reset = 0; } - uint32_t vint_cycle = vdp_next_vint_z80(gen->vdp) / MCLKS_PER_Z80; + while (z_context->current_cycle < z_context->sync_cycle) { - if (z_context->iff1 && z_context->current_cycle < (vint_cycle + Z80_VINT_DURATION)) { - z_context->int_cycle = vint_cycle < z_context->int_enable_cycle ? z_context->int_enable_cycle : vint_cycle; + if (z_context->int_pulse_end < z_context->current_cycle || z_context->int_pulse_end == CYCLE_NEVER) { + z_context->int_pulse_start = vdp_next_vint_z80(gen->vdp) / MCLKS_PER_Z80; + z_context->int_pulse_end = z_context->int_pulse_start + Z80_VINT_DURATION; + } + if (z_context->iff1) { + z_context->int_cycle = z_context->int_pulse_start < z_context->int_enable_cycle ? z_context->int_enable_cycle : z_context->int_pulse_start; } else { z_context->int_cycle = CYCLE_NEVER; } z_context->target_cycle = z_context->sync_cycle < z_context->int_cycle ? z_context->sync_cycle : z_context->int_cycle; - dprintf("Running Z80 from cycle %d to cycle %d. Native PC: %p\n", z_context->current_cycle, z_context->sync_cycle, z_context->native_pc); + dprintf("Running Z80 from cycle %d to cycle %d. Int cycle: %d\n", z_context->current_cycle, z_context->sync_cycle, z_context->int_cycle); z_context->run(z_context); dprintf("Z80 ran to cycle %d\n", z_context->current_cycle); } @@ -236,15 +240,15 @@ z80_context * z_context = gen->z80; uint32_t mclks = context->current_cycle * MCLKS_PER_68K; sync_z80(z_context, mclks); - if (mclks >= mclks_per_frame) { + if (mclks >= mclk_target) { sync_sound(gen, mclks); - gen->ym->current_cycle -= mclks_per_frame; - gen->psg->cycles -= mclks_per_frame; + gen->ym->current_cycle -= mclk_target; + gen->psg->cycles -= mclk_target; if (gen->ym->write_cycle != CYCLE_NEVER) { - gen->ym->write_cycle = gen->ym->write_cycle >= mclks_per_frame/MCLKS_PER_68K ? gen->ym->write_cycle - mclks_per_frame/MCLKS_PER_68K : 0; + gen->ym->write_cycle = gen->ym->write_cycle >= mclk_target/MCLKS_PER_68K ? gen->ym->write_cycle - mclk_target/MCLKS_PER_68K : 0; } //printf("reached frame end | 68K Cycles: %d, MCLK Cycles: %d\n", context->current_cycle, mclks); - vdp_run_context(v_context, mclks_per_frame); + vdp_run_context(v_context, mclk_target); if (!headless) { break_on_sync |= wait_render_frame(v_context, frame_limit); @@ -255,28 +259,54 @@ } } frame++; - mclks -= mclks_per_frame; - vdp_adjust_cycles(v_context, mclks_per_frame); - io_adjust_cycles(gen->ports, context->current_cycle, mclks_per_frame/MCLKS_PER_68K); - io_adjust_cycles(gen->ports+1, context->current_cycle, mclks_per_frame/MCLKS_PER_68K); - io_adjust_cycles(gen->ports+2, context->current_cycle, mclks_per_frame/MCLKS_PER_68K); + mclks -= mclk_target; + vdp_adjust_cycles(v_context, mclk_target); + io_adjust_cycles(gen->ports, context->current_cycle, mclk_target/MCLKS_PER_68K); + io_adjust_cycles(gen->ports+1, context->current_cycle, mclk_target/MCLKS_PER_68K); + io_adjust_cycles(gen->ports+2, context->current_cycle, mclk_target/MCLKS_PER_68K); if (busack_cycle != CYCLE_NEVER) { - if (busack_cycle > mclks_per_frame/MCLKS_PER_68K) { - busack_cycle -= mclks_per_frame/MCLKS_PER_68K; + if (busack_cycle > mclk_target/MCLKS_PER_68K) { + busack_cycle -= mclk_target/MCLKS_PER_68K; } else { busack_cycle = CYCLE_NEVER; busack = new_busack; } } - context->current_cycle -= mclks_per_frame/MCLKS_PER_68K; - if (z_context->current_cycle >= mclks_per_frame/MCLKS_PER_Z80) { - z_context->current_cycle -= mclks_per_frame/MCLKS_PER_Z80; + context->current_cycle -= mclk_target/MCLKS_PER_68K; + if (z_context->current_cycle >= mclk_target/MCLKS_PER_Z80) { + z_context->current_cycle -= mclk_target/MCLKS_PER_Z80; } else { z_context->current_cycle = 0; } + if (z_context->int_cycle != CYCLE_NEVER) { + if (z_context->int_cycle >= mclk_target/MCLKS_PER_Z80) { + z_context->int_cycle -= mclk_target/MCLKS_PER_Z80; + } else { + z_context->int_cycle = 0; + } + } + if (z_context->int_pulse_start != CYCLE_NEVER) { + if (z_context->int_pulse_end >= mclk_target/MCLKS_PER_Z80) { + z_context->int_pulse_end -= mclk_target/MCLKS_PER_Z80; + if (z_context->int_pulse_start >= mclk_target/MCLKS_PER_Z80) { + z_context->int_pulse_start -= mclk_target/MCLKS_PER_Z80; + } else { + z_context->int_pulse_start = 0; + } + } + } else { + z_context->int_pulse_start = CYCLE_NEVER; + z_context->int_pulse_end = CYCLE_NEVER; + } + if (z_context->int_enable_cycle >= mclk_target/MCLKS_PER_Z80) { + z_context->int_enable_cycle -= mclk_target/MCLKS_PER_Z80; + } else { + z_context->int_enable_cycle = 0; + } if (mclks) { vdp_run_context(v_context, mclks); } + mclk_target = vdp_cycles_to_frame_end(v_context); } else { //printf("running VDP for %d cycles\n", mclks - v_context->cycles); vdp_run_context(v_context, mclks); @@ -322,10 +352,10 @@ gen->bus_busy = 1; while (vdp_data_port_write(v_context, value) < 0) { while(v_context->flags & FLAG_DMA_RUN) { - vdp_run_dma_done(v_context, mclks_per_frame); - if (v_context->cycles >= mclks_per_frame) { + vdp_run_dma_done(v_context, mclk_target); + if (v_context->cycles >= mclk_target) { context->current_cycle = v_context->cycles / MCLKS_PER_68K; - if (context->current_cycle * MCLKS_PER_68K < mclks_per_frame) { + if (context->current_cycle * MCLKS_PER_68K < mclk_target) { ++context->current_cycle; } sync_components(context, 0); @@ -339,10 +369,10 @@ if (blocked) { while (blocked) { while(v_context->flags & FLAG_DMA_RUN) { - vdp_run_dma_done(v_context, mclks_per_frame); - if (v_context->cycles >= mclks_per_frame) { + vdp_run_dma_done(v_context, mclk_target); + if (v_context->cycles >= mclk_target) { context->current_cycle = v_context->cycles / MCLKS_PER_68K; - if (context->current_cycle * MCLKS_PER_68K < mclks_per_frame) { + if (context->current_cycle * MCLKS_PER_68K < mclk_target) { ++context->current_cycle; } sync_components(context, 0); @@ -1045,7 +1075,7 @@ context.system = gen; //cartridge ROM context.mem_pointers[0] = cart; - context.target_cycle = context.sync_cycle = mclks_per_frame/MCLKS_PER_68K; + context.target_cycle = context.sync_cycle = mclk_target/MCLKS_PER_68K; //work RAM context.mem_pointers[1] = ram; //save RAM/map @@ -1300,7 +1330,6 @@ height = height < 240 ? (width/320) * 240 : height; uint32_t fps = 60; if (version_reg & 0x40) { - mclks_per_frame = MCLKS_LINE * LINES_PAL; fps = 50; } if (!headless) { @@ -1311,7 +1340,8 @@ memset(&gen, 0, sizeof(gen)); gen.master_clock = gen.normal_clock = fps == 60 ? MCLKS_NTSC : MCLKS_PAL; - init_vdp_context(&v_context); + init_vdp_context(&v_context, version_reg & 0x40); + mclk_target = vdp_cycles_to_frame_end(&v_context); ym2612_context y_context; ym_init(&y_context, render_sample_rate(), gen.master_clock, MCLKS_PER_YM, render_audio_buffer(), ym_log ? YM_OPT_WAVE_LOG : 0); @@ -1328,7 +1358,7 @@ z_context.system = &gen; z_context.mem_pointers[0] = z80_ram; - z_context.sync_cycle = z_context.target_cycle = mclks_per_frame/MCLKS_PER_Z80; + z_context.sync_cycle = z_context.target_cycle = mclk_target/MCLKS_PER_Z80; z_context.int_cycle = CYCLE_NEVER; z_context.mem_pointers[1] = z_context.mem_pointers[2] = (uint8_t *)cart; @@ -1351,7 +1381,7 @@ if (i < 0) { strcpy(sram_filename + fname_size, ".sram"); } - set_keybindings(); + set_keybindings(gen.ports); init_run_cpu(&gen, address_log, statefile, debuggerfun); return 0;