mirror of
https://github.com/holub/mame
synced 2025-05-31 01:51:46 +03:00
Amiga: Emulate DIWHIGH register for ECS machines, reduce some code
duplication.
This commit is contained in:
parent
8eeb461935
commit
f6005251d8
@ -361,6 +361,8 @@ public:
|
||||
m_centronics_perror(0),
|
||||
m_centronics_select(0),
|
||||
m_gayle_reset(false),
|
||||
m_diw(),
|
||||
m_diwhigh_valid(false),
|
||||
m_previous_lof(true),
|
||||
m_rx_shift(0),
|
||||
m_tx_shift(0),
|
||||
@ -620,6 +622,11 @@ private:
|
||||
|
||||
bool m_gayle_reset;
|
||||
|
||||
// display window
|
||||
rectangle m_diw;
|
||||
bool m_diwhigh_valid;
|
||||
void update_display_window();
|
||||
|
||||
bool m_previous_lof;
|
||||
bitmap_ind16 m_flickerfixer;
|
||||
bitmap_ind32 m_flickerfixer32;
|
||||
@ -667,6 +674,5 @@ MACHINE_CONFIG_EXTERN( ntsc_video );
|
||||
/*----------- defined in video/amigaaga.c -----------*/
|
||||
|
||||
void amiga_aga_palette_write(running_machine &machine, int color_reg, UINT16 data);
|
||||
void amiga_aga_diwhigh_written(running_machine &machine, int written);
|
||||
|
||||
#endif /* __AMIGA_H__ */
|
||||
|
@ -1553,14 +1553,20 @@ WRITE16_MEMBER( amiga_state::custom_chip_w )
|
||||
CUSTOM_REG(offset + 32) = (data >> 1) & 0x777;
|
||||
}
|
||||
break;
|
||||
|
||||
// display window start/stop
|
||||
case REG_DIWSTRT:
|
||||
case REG_DIWSTOP:
|
||||
if (IS_AGA(state))
|
||||
amiga_aga_diwhigh_written(space.machine(), 0);
|
||||
m_diwhigh_valid = false;
|
||||
break;
|
||||
|
||||
// display window high
|
||||
case REG_DIWHIGH:
|
||||
if (IS_AGA(state))
|
||||
amiga_aga_diwhigh_written(space.machine(), 1);
|
||||
if (IS_ECS(state) || IS_AGA(state))
|
||||
{
|
||||
m_diwhigh_valid = true;
|
||||
CUSTOM_REG(REG_DIWHIGH) = data;
|
||||
}
|
||||
break;
|
||||
|
||||
case REG_BEAMCON0:
|
||||
|
@ -197,6 +197,7 @@ void amiga_copper_setpc(running_machine &machine, UINT32 pc)
|
||||
int amiga_copper_execute_next(running_machine &machine, int xpos)
|
||||
{
|
||||
amiga_state *state = machine.driver_data<amiga_state>();
|
||||
UINT8 ypos = state->m_last_scanline & 0xff;
|
||||
int word0, word1;
|
||||
|
||||
/* bail if not enabled */
|
||||
@ -215,7 +216,7 @@ int amiga_copper_execute_next(running_machine &machine, int xpos)
|
||||
/* if we're waiting, check for a breakthrough */
|
||||
if (state->m_copper_waiting)
|
||||
{
|
||||
int curpos = (state->m_last_scanline << 8) | (xpos >> 1);
|
||||
int curpos = (ypos << 8) | (xpos >> 1);
|
||||
|
||||
/* if we're past the wait time, stop it and hold up 2 cycles */
|
||||
if ((curpos & state->m_copper_waitmask) >= (state->m_copper_waitval & state->m_copper_waitmask) &&
|
||||
@ -283,6 +284,7 @@ int amiga_copper_execute_next(running_machine &machine, int xpos)
|
||||
state->m_copper_waitmask = 0xffff;
|
||||
state->m_copper_waitblit = FALSE;
|
||||
state->m_copper_waiting = TRUE;
|
||||
|
||||
return 511;
|
||||
}
|
||||
}
|
||||
@ -290,6 +292,12 @@ int amiga_copper_execute_next(running_machine &machine, int xpos)
|
||||
{
|
||||
/* extract common wait/skip values */
|
||||
state->m_copper_waitval = word0 & 0xfffe;
|
||||
|
||||
#if 0
|
||||
if (state->m_copper_waitval != 0xfffe)
|
||||
state->m_copper_waitval = (word0 & 0x00fe) | ((((word0 >> 8) & 0xff) + 1) << 8);
|
||||
#endif
|
||||
|
||||
state->m_copper_waitmask = word1 | 0x8001;
|
||||
state->m_copper_waitblit = (~word1 >> 15) & 1;
|
||||
|
||||
@ -305,7 +313,7 @@ int amiga_copper_execute_next(running_machine &machine, int xpos)
|
||||
/* handle a skip */
|
||||
else
|
||||
{
|
||||
int curpos = (state->m_last_scanline << 8) | (xpos >> 1);
|
||||
int curpos = (ypos << 8) | (xpos >> 1);
|
||||
|
||||
if (LOG_COPPER)
|
||||
logerror(" Skipping if %04x & %04x (currently %04x)\n", state->m_copper_waitval, state->m_copper_waitmask, (state->m_last_scanline << 8) | (xpos >> 1));
|
||||
@ -613,6 +621,41 @@ INLINE int update_ham(amiga_state *state, int newpix)
|
||||
}
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// DISPLAY WINDOW
|
||||
//**************************************************************************
|
||||
|
||||
void amiga_state::update_display_window()
|
||||
{
|
||||
amiga_state *state = this;
|
||||
|
||||
int vstart = CUSTOM_REG(REG_DIWSTRT) >> 8;
|
||||
int vstop = CUSTOM_REG(REG_DIWSTOP) >> 8;
|
||||
int hstart = CUSTOM_REG(REG_DIWSTRT) & 0xff;
|
||||
int hstop = CUSTOM_REG(REG_DIWSTOP) & 0xff;
|
||||
|
||||
if (m_diwhigh_valid)
|
||||
{
|
||||
vstart |= (CUSTOM_REG(REG_DIWHIGH) & 7) << 8;
|
||||
vstop |= ((CUSTOM_REG(REG_DIWHIGH) >> 8) & 7) << 8;
|
||||
hstart |= ((CUSTOM_REG(REG_DIWHIGH) >> 5) & 1) << 8;
|
||||
hstop |= ((CUSTOM_REG(REG_DIWHIGH) >> 13) & 1) << 8;
|
||||
}
|
||||
else
|
||||
{
|
||||
vstop |= ((~CUSTOM_REG(REG_DIWSTOP) >> 7) & 0x100);
|
||||
hstop |= 0x100;
|
||||
}
|
||||
|
||||
if (hstop < hstart)
|
||||
{
|
||||
hstart = 0x00;
|
||||
hstop = 0x1ff;
|
||||
}
|
||||
|
||||
m_diw.set(hstart, hstop, vstart, vstop);
|
||||
}
|
||||
|
||||
|
||||
/*************************************
|
||||
*
|
||||
@ -626,8 +669,6 @@ void amiga_state::render_scanline(bitmap_ind16 &bitmap, int scanline)
|
||||
UINT16 save_color0 = CUSTOM_REG(REG_COLOR00);
|
||||
int ddf_start_pixel = 0, ddf_stop_pixel = 0;
|
||||
int hires = 0, dualpf = 0, ham = 0;
|
||||
int hstart = 0, hstop = 0;
|
||||
int vstart = 0, vstop = 0;
|
||||
int pf1pri = 0, pf2pri = 0;
|
||||
int planes = 0;
|
||||
|
||||
@ -723,15 +764,8 @@ void amiga_state::render_scanline(bitmap_ind16 &bitmap, int scanline)
|
||||
if ( ( CUSTOM_REG(REG_DDFSTRT) ^ CUSTOM_REG(REG_DDFSTOP) ) & 0x04 )
|
||||
ddf_stop_pixel += 8;
|
||||
|
||||
/* compute the horizontal start/stop */
|
||||
hstart = CUSTOM_REG(REG_DIWSTRT) & 0xff;
|
||||
hstop = (CUSTOM_REG(REG_DIWSTOP) & 0xff);
|
||||
hstop |= 0x100;
|
||||
|
||||
/* compute the vertical start/stop */
|
||||
vstart = CUSTOM_REG(REG_DIWSTRT) >> 8;
|
||||
vstop = (CUSTOM_REG(REG_DIWSTOP) >> 8);
|
||||
vstop |= ((~CUSTOM_REG(REG_DIWSTOP) >> 7) & 0x100);
|
||||
// display window
|
||||
update_display_window();
|
||||
|
||||
/* extract playfield priorities */
|
||||
pf1pri = CUSTOM_REG(REG_BPLCON2) & 7;
|
||||
@ -780,7 +814,7 @@ void amiga_state::render_scanline(bitmap_ind16 &bitmap, int scanline)
|
||||
/* to render, we must have bitplane DMA enabled, at least 1 plane, and be within the */
|
||||
/* vertical display window */
|
||||
if ((CUSTOM_REG(REG_DMACON) & (DMACON_BPLEN | DMACON_DMAEN)) == (DMACON_BPLEN | DMACON_DMAEN) &&
|
||||
planes > 0 && scanline >= vstart && scanline < vstop)
|
||||
planes > 0 && scanline >= m_diw.min_y && scanline < m_diw.max_y)
|
||||
{
|
||||
int pfpix0 = 0, pfpix1 = 0, collide;
|
||||
|
||||
@ -885,7 +919,7 @@ void amiga_state::render_scanline(bitmap_ind16 &bitmap, int scanline)
|
||||
CUSTOM_REG(REG_CLXDAT) |= 0x001;
|
||||
|
||||
/* if we are within the display region, render */
|
||||
if (dst != NULL && x >= hstart && x < hstop)
|
||||
if (dst != NULL && x >= m_diw.min_x && x < m_diw.max_x)
|
||||
{
|
||||
int pix, pri;
|
||||
|
||||
@ -975,7 +1009,7 @@ void amiga_state::render_scanline(bitmap_ind16 &bitmap, int scanline)
|
||||
}
|
||||
|
||||
// end of the line: time to add the modulos
|
||||
if (scanline >= vstart && scanline < vstop)
|
||||
if (scanline >= m_diw.min_y && scanline < m_diw.max_y)
|
||||
{
|
||||
// update odd planes
|
||||
for (pl = 0; pl < planes; pl += 2)
|
||||
|
@ -399,12 +399,7 @@ INLINE void fetch_bitplane_data(amiga_state *state, int plane)
|
||||
}
|
||||
}
|
||||
|
||||
void amiga_aga_diwhigh_written(running_machine &machine, int written)
|
||||
{
|
||||
amiga_state *state = machine.driver_data<amiga_state>();
|
||||
|
||||
state->m_aga_diwhigh_written = written;
|
||||
}
|
||||
|
||||
/*************************************
|
||||
*
|
||||
@ -449,8 +444,6 @@ void amiga_state::aga_render_scanline(bitmap_rgb32 &bitmap, int scanline)
|
||||
UINT16 save_color0 = CUSTOM_REG(REG_COLOR00);
|
||||
int ddf_start_pixel = 0, ddf_stop_pixel = 0;
|
||||
int hires = 0, dualpf = 0, ham = 0;
|
||||
int hstart = 0, hstop = 0;
|
||||
int vstart = 0, vstop = 0;
|
||||
int pf1pri = 0, pf2pri = 0;
|
||||
int planes = 0;
|
||||
|
||||
@ -539,7 +532,6 @@ void amiga_state::aga_render_scanline(bitmap_rgb32 &bitmap, int scanline)
|
||||
hires = CUSTOM_REG(REG_BPLCON0) & BPLCON0_HIRES;
|
||||
ham = CUSTOM_REG(REG_BPLCON0) & BPLCON0_HOMOD;
|
||||
dualpf = CUSTOM_REG(REG_BPLCON0) & BPLCON0_DBLPF;
|
||||
// lace = CUSTOM_REG(REG_BPLCON0) & BPLCON0_LACE;
|
||||
|
||||
/* get default bitoffset */
|
||||
switch(CUSTOM_REG(REG_FMODE) & 0x3)
|
||||
@ -557,37 +549,8 @@ void amiga_state::aga_render_scanline(bitmap_rgb32 &bitmap, int scanline)
|
||||
if ( ( CUSTOM_REG(REG_DDFSTRT) ^ CUSTOM_REG(REG_DDFSTOP) ) & 0x04 )
|
||||
ddf_stop_pixel += 8;
|
||||
|
||||
/* compute the horizontal start/stop */
|
||||
hstart = CUSTOM_REG(REG_DIWSTRT) & 0xff;
|
||||
hstop = (CUSTOM_REG(REG_DIWSTOP) & 0xff);
|
||||
|
||||
if (m_aga_diwhigh_written)
|
||||
{
|
||||
hstart |= ((CUSTOM_REG(REG_DIWHIGH) >> 5) & 1) << 8;
|
||||
hstop |= ((CUSTOM_REG(REG_DIWHIGH) >> 13) & 1) << 8;
|
||||
}
|
||||
else
|
||||
{
|
||||
hstop |= 0x100;
|
||||
}
|
||||
if ( hstop < hstart )
|
||||
{
|
||||
hstart = 0x00;
|
||||
hstop = 0x1ff;
|
||||
}
|
||||
|
||||
/* compute the vertical start/stop */
|
||||
vstart = CUSTOM_REG(REG_DIWSTRT) >> 8;
|
||||
vstop = (CUSTOM_REG(REG_DIWSTOP) >> 8);
|
||||
if (m_aga_diwhigh_written)
|
||||
{
|
||||
vstart |= (CUSTOM_REG(REG_DIWHIGH) & 7) << 8;
|
||||
vstop |= ((CUSTOM_REG(REG_DIWHIGH) >> 8) & 7) << 8;
|
||||
}
|
||||
else
|
||||
{
|
||||
vstop |= ((~CUSTOM_REG(REG_DIWSTOP) >> 7) & 0x100);
|
||||
}
|
||||
// display window
|
||||
update_display_window();
|
||||
|
||||
/* extract playfield priorities */
|
||||
pf1pri = CUSTOM_REG(REG_BPLCON2) & 7;
|
||||
@ -636,7 +599,7 @@ void amiga_state::aga_render_scanline(bitmap_rgb32 &bitmap, int scanline)
|
||||
/* to render, we must have bitplane DMA enabled, at least 1 plane, and be within the */
|
||||
/* vertical display window */
|
||||
if ((CUSTOM_REG(REG_DMACON) & (DMACON_BPLEN | DMACON_DMAEN)) == (DMACON_BPLEN | DMACON_DMAEN) &&
|
||||
planes > 0 && scanline >= vstart && scanline < vstop)
|
||||
planes > 0 && scanline >= m_diw.min_y && scanline < m_diw.max_y)
|
||||
{
|
||||
int pfpix0 = 0, pfpix1 = 0, collide;
|
||||
|
||||
@ -741,7 +704,7 @@ void amiga_state::aga_render_scanline(bitmap_rgb32 &bitmap, int scanline)
|
||||
CUSTOM_REG(REG_CLXDAT) |= 0x001;
|
||||
|
||||
/* if we are within the display region, render */
|
||||
if (dst != NULL && x >= hstart && x < hstop)
|
||||
if (dst != NULL && x >= m_diw.min_x && x < m_diw.max_x)
|
||||
{
|
||||
int pix, pri;
|
||||
|
||||
@ -854,7 +817,7 @@ void amiga_state::aga_render_scanline(bitmap_rgb32 &bitmap, int scanline)
|
||||
#endif
|
||||
|
||||
/* end of the line: time to add the modulos */
|
||||
if (scanline >= vstart && scanline < vstop)
|
||||
if (scanline >= m_diw.min_y && scanline < m_diw.max_y)
|
||||
{
|
||||
/* update odd planes */
|
||||
for (pl = 0; pl < planes; pl += 2)
|
||||
|
Loading…
Reference in New Issue
Block a user