From b46f03748fcad3852ac4077f33f7010e5d5b0056 Mon Sep 17 00:00:00 2001 From: Toni Wilen Date: Sun, 13 Jun 2021 16:19:31 +0300 Subject: [PATCH] Custom emulation update WIP. --- custom.cpp | 66 +++++++++++++++++++++++++++++------------------ drawing.cpp | 17 ++++++------ include/custom.h | 8 ++++-- include/drawing.h | 1 - 4 files changed, 56 insertions(+), 36 deletions(-) diff --git a/custom.cpp b/custom.cpp index 23d25dba..b8bf270e 100644 --- a/custom.cpp +++ b/custom.cpp @@ -528,7 +528,7 @@ static int bprun; static int bprun_cycle; static int bprun_pipeline_flush_delay; static bool plane0; -static bool harddis; +static bool harddis_v, harddis_h; static uae_u16 dmal_alloc_mask; #define RGA_PIPELINE_OFFSET_BPL_WRITE 3 @@ -742,7 +742,8 @@ static void remember_ctable_for_border(void) remember_ctable(); } -STATIC_INLINE int get_equ_vblank_endline(void) +// This does not need start line check because only OCS Denise modes use this. +static int get_equ_vblank_endline(void) { return equ_vblank_endline + (equ_vblank_toggle ? (lof_current ? 1 : 0) : 0); } @@ -1116,7 +1117,7 @@ static void estimate_last_fetch_cycle(int hpos) end_estimate_last_fetch_cycle(hpos); } else { - int hard_ddf_stop = harddis ? 0x100 : HARD_DDF_STOP; + int hard_ddf_stop = harddis_h ? 0x100 : HARD_DDF_STOP; int start = bpl_hstart; int adjusted_plfstop = plfstop; int estimated_cycle_count; @@ -1208,7 +1209,7 @@ static void end_estimate_last_fetch_cycle(int hpos) static void estimate_last_fetch_cycle(int hpos) { - int hard_ddf_stop = harddis ? 0x100 : HARD_DDF_STOP; + int hard_ddf_stop = harddis_h ? 0x100 : HARD_DDF_STOP; int start = bpl_hstart; int adjusted_plfstop = plfstop; int estimated_cycle_count; @@ -3216,7 +3217,7 @@ static void update_fetch(int until, int fm) #endif && toscr_nr_planes == toscr_nr_planes_agnus) { - int hard_ddf_stop = harddis ? 0x100 : HARD_DDF_STOP; + int hard_ddf_stop = harddis_h ? 0x100 : HARD_DDF_STOP; int adjusted_plfstop = plfstop; int ddfstop_to_test_ddf = hard_ddf_stop; if (adjusted_plfstop >= last_fetch_hpos && adjusted_plfstop < ddfstop_to_test_ddf) { @@ -3323,14 +3324,14 @@ static void decide_vline(void) /* Take care of the vertical DIW. */ if (vpos == plffirstline) { // Following line after VB start has bitplane DMA start inhibited (if HARDDIS=0) - if (vb_start_line != 2 || harddis) { + if (vb_start_line != 2 || harddis_v) { diwstate = DIW_waiting_stop; diwstate_vpos = vpos; SET_LINE_CYCLEBASED; } } // VB start line forces vertical display window off (if HARDDIS=0) - if (vpos == plflastline || (vb_start_line == 1 && !harddis)) { + if (vpos == plflastline || (vb_start_line == 1 && !harddis_v)) { diwstate = DIW_waiting_start; diwstate_vpos = vpos; SET_LINE_CYCLEBASED; @@ -4326,6 +4327,7 @@ static void reset_decisions_hsync_start(void) thisline_decision.bordersprite_seen = issprbrd(-1, bplcon0, bplcon3); thisline_decision.xor_seen = (bplcon4 & 0xff00) != 0; + // handle bitplane data wrap around bool toshift = false; for (int i = 0; i < thisline_decision.nr_planes; i++) { if (todisplay2_aga[i] || todisplay2[i]) { @@ -4333,10 +4335,10 @@ static void reset_decisions_hsync_start(void) } } if (bprun > 0 || todisplay_fetched[0] || toshift) { + SET_LINE_CYCLEBASED; int hpos = current_hpos(); - thisline_decision.plfleft = hpos; + thisline_decision.plfleft = hpos; if (hpos_hsync_extra) { - //delay_cycles -= ((hpos_hsync_extra) * 2 - DDF_OFFSET) << (toscr_res + toscr_res_mult); delay_cycles = ((hpos) * 2 - DDF_OFFSET) << (toscr_res + toscr_res_mult); hpos_hsync_extra = 0; } @@ -4930,22 +4932,33 @@ static void init_hz(bool checkvposw) } if (currprefs.gfx_extraheight > 0) { - int mfl = minfirstline; - maxvpos_display_vsync += currprefs.gfx_extraheight / 2; - minfirstline -= currprefs.gfx_extraheight / 2; - if (minfirstline < maxvpos_display_vsync + 1) { - minfirstline = maxvpos_display_vsync + 1; - } - if (firstblankedline <= mfl && firstblankedline >= minfirstline) { - firstblankedline -= currprefs.gfx_extraheight / 2; + if (beamcon0 & (0x0200 | 0x0010)) { + maxvpos_display_vsync += currprefs.gfx_extraheight / 2; + minfirstline -= currprefs.gfx_extraheight / 2; + if (maxvpos_display_vsync >= vsstop) { + maxvpos_display_vsync = vsstop - 1; + } + if (minfirstline <= vsstop) { + minfirstline = vsstop + 1; + } + } else { + maxvpos_display_vsync = 3; + minfirstline -= currprefs.gfx_extraheight / 2; + if (minfirstline < 8) { + minfirstline = 8; + } } } - if (minfirstline < 2) { - minfirstline = 2; + if (maxvpos_display_vsync < 1) { + maxvpos_display_vsync = 1; } - if (!(beamcon0 & 0x80) && minfirstline < 10) { - minfirstline = 10; + + if (minfirstline < 1) { + minfirstline = 1; + } + if (!(beamcon0 & 0x80) && minfirstline < 8 && !currprefs.gfx_extraheight) { + minfirstline = 8; } if (minfirstline >= maxvpos) { @@ -5899,7 +5912,9 @@ static void ADKCON(int hpos, uae_u16 v) static void check_harddis(void) { // VARBEAMEN, HARDDIS, SHRES, UHRES - harddis = ecs_agnus && ((new_beamcon0 & 0x80) || (new_beamcon0 & 0x4000) || (bplcon0 & 0x40) || (bplcon0 & 0x80)); + harddis_h = ecs_agnus && ((new_beamcon0 & 0x80) || (new_beamcon0 & 0x4000) || (bplcon0 & 0x40) || (bplcon0 & 0x80)); + // VARBEAMEN, VARVBEN, HARDDIS + harddis_v = ecs_agnus && (new_beamcon0 & 0x80) || (new_beamcon0 & 0x1000) || (new_beamcon0 & 0x4000); } static void BEAMCON0(int hpos, uae_u16 v) @@ -7191,7 +7206,7 @@ static void decide_line(int endhpos) // Triggers DDFSTOP condition if hard limits are not disabled. ddf_limit = true; if (bprun && !ddf_stopping) { - if (!harddis) { + if (!harddis_h) { decide_line_decision_fetches(hpos); ddf_stopping = 1; } @@ -7216,7 +7231,7 @@ static void decide_line(int endhpos) } // BPRUN can only start if DMA, DIW or DDF state has changed since last time - bool hwi = dma && diw && ddf_enable_on && (!ddf_limit || harddis); + bool hwi = dma && diw && ddf_enable_on && (!ddf_limit || harddis_h); if (!bprun && dma && diw && hwi && !hwi_old) { decide_line_decision_fetches(hpos); @@ -8272,7 +8287,7 @@ static void init_sprites(void) static void init_hardware_frame(void) { first_bpl_vpos = -1; - if (!harddis) { + if (!harddis_v) { diwstate = DIW_waiting_start; } @@ -10752,6 +10767,7 @@ void custom_reset(bool hardreset, bool keyboardreset) cop_state.strobe = 0; cop_state.ignore_next = 0; diwstate = DIW_waiting_start; + check_harddis(); dmal = 0; init_hz_normal(); diff --git a/drawing.cpp b/drawing.cpp index 05c9fc6e..21e1f041 100644 --- a/drawing.cpp +++ b/drawing.cpp @@ -680,7 +680,7 @@ int get_custom_limits (int *pw, int *ph, int *pdx, int *pdy, int *prealh) ddffirstword_total = min; if (ddflastword_total > max) ddflastword_total = max; - if (0 && !(currprefs.chipset_mask & CSMASK_AGA)) { + if (0 && !aga_mode) { if (ddffirstword_total > diwfirstword_total) diwfirstword_total = ddffirstword_total; if (ddflastword_total < diwlastword_total) @@ -1323,14 +1323,15 @@ static void fill_line_border(int lineno) { struct vidbuf_description *vidinfo = &adisplays[0].gfxvidinfo; int lastpos = visible_left_border; - int endpos = visible_left_border + vidinfo->drawbuffer.inwidth; + int endpos = visible_right_border; + int w = endpos - lastpos; if (lineno < visible_top_start || lineno >= visible_bottom_stop) { int b = hposblank; hposblank = 3; - fill_line2(lastpos, vidinfo->drawbuffer.inwidth); + fill_line2(lastpos, w); if (need_genlock_data) { - memset(xlinebuffer_genlock + lastpos, 0, vidinfo->drawbuffer.inwidth); + memset(xlinebuffer_genlock + lastpos, 0, w); } hposblank = b; return; @@ -1339,17 +1340,17 @@ static void fill_line_border(int lineno) // full hblank if (hposblank) { hposblank = 3; - fill_line2(lastpos, vidinfo->drawbuffer.inwidth); + fill_line2(lastpos, w); if (need_genlock_data) { - memset(xlinebuffer_genlock + lastpos, 0, vidinfo->drawbuffer.inwidth); + memset(xlinebuffer_genlock + lastpos, 0, w); } return; } // hblank not visible if (hblank_left_start <= lastpos && hblank_right_stop >= endpos) { - fill_line2(lastpos, vidinfo->drawbuffer.inwidth); + fill_line2(lastpos, w); if (need_genlock_data) { - memset(xlinebuffer_genlock + lastpos, 0, vidinfo->drawbuffer.inwidth); + memset(xlinebuffer_genlock + lastpos, 0, w); } return; } diff --git a/include/custom.h b/include/custom.h index 374c2fef..764b1507 100644 --- a/include/custom.h +++ b/include/custom.h @@ -12,6 +12,8 @@ #include "uae/types.h" #include "machdep/rpt.h" +extern bool aga_mode, ecs_agnus, ecs_denise, direct_rgb; + /* These are the masks that are ORed together in the chipset_mask option. * If CSMASK_AGA is set, the ECS bits are guaranteed to be set as well. */ #define CSMASK_ECS_AGNUS 1 @@ -198,14 +200,16 @@ extern int xbluecolor_s, xbluecolor_b, xbluecolor_m; /* get resolution from bplcon0 */ STATIC_INLINE int GET_RES_DENISE(uae_u16 con0) { - if (!(currprefs.chipset_mask & CSMASK_ECS_DENISE)) + if (!ecs_denise) { con0 &= ~0x40; // SUPERHIRES + } return ((con0) & 0x40) ? RES_SUPERHIRES : ((con0) & 0x8000) ? RES_HIRES : RES_LORES; } STATIC_INLINE int GET_RES_AGNUS(uae_u16 con0) { - if (!(currprefs.chipset_mask & CSMASK_ECS_AGNUS)) + if (!ecs_agnus) { con0 &= ~0x40; // SUPERHIRES + } return ((con0) & 0x40) ? RES_SUPERHIRES : ((con0) & 0x8000) ? RES_HIRES : RES_LORES; } /* get sprite width from FMODE */ diff --git a/include/drawing.h b/include/drawing.h index 09f4d9e5..836bf5ec 100644 --- a/include/drawing.h +++ b/include/drawing.h @@ -23,7 +23,6 @@ #endif extern int lores_shift, shres_shift, interlace_seen; -extern bool aga_mode, ecs_agnus, ecs_denise, direct_rgb; extern int visible_left_border, visible_right_border; extern int detected_screen_resolution; extern int hsync_end_left_border, hsynctotal; -- 2.47.3