upd7220: better output for the compis and dmv [Carl]

This commit is contained in:
cracyc 2014-10-20 13:24:17 -05:00
parent ddbeb7b0e4
commit 681142c125
4 changed files with 70 additions and 55 deletions

View File

@ -33,6 +33,7 @@
- honor visible area - honor visible area
- wide mode (32-bit access) - wide mode (32-bit access)
- light pen - light pen
- dad and mask are the same, in figd dad is shifted every step and when msb or lsb are 1 ead is advanced in x dir
*/ */
@ -120,15 +121,19 @@ enum
#define UPD7220_SR_HBLANK_ACTIVE 0x40 #define UPD7220_SR_HBLANK_ACTIVE 0x40
#define UPD7220_SR_LIGHT_PEN_DETECT 0x80 #define UPD7220_SR_LIGHT_PEN_DETECT 0x80
#define UPD7220_MODE_S 0x01
#define UPD7220_MODE_REFRESH_RAM 0x04 #define UPD7220_MODE_REFRESH_RAM 0x04
#define UPD7220_MODE_I 0x08
#define UPD7220_MODE_DRAW_ON_RETRACE 0x10 #define UPD7220_MODE_DRAW_ON_RETRACE 0x10
#define UPD7220_MODE_DISPLAY_MASK 0x22 #define UPD7220_MODE_DISPLAY_MASK 0x22
#define UPD7220_MODE_DISPLAY_MIXED 0x00 #define UPD7220_MODE_DISPLAY_MIXED 0x00
#define UPD7220_MODE_DISPLAY_GRAPHICS 0x02 #define UPD7220_MODE_DISPLAY_GRAPHICS 0x02
#define UPD7220_MODE_DISPLAY_CHARACTER 0x20 #define UPD7220_MODE_DISPLAY_CHARACTER 0x20
#define UPD7220_MODE_DISPLAY_INVALID 0x22 #define UPD7220_MODE_DISPLAY_INVALID 0x22
#define UPD7220_MODE_INTERLACE_MASK 0x09
#define UPD7220_MODE_INTERLACE_NONE 0x00
#define UPD7220_MODE_INTERLACE_INVALID 0x01
#define UPD7220_MODE_INTERLACE_REPEAT 0x08
#define UPD7220_MODE_INTERLACE_ON 0x09
static const int x_dir[8] = { 0, 1, 1, 1, 0,-1,-1,-1}; static const int x_dir[8] = { 0, 1, 1, 1, 0,-1,-1,-1};
static const int y_dir[8] = { 1, 1, 0,-1,-1,-1, 0, 1}; static const int y_dir[8] = { 1, 1, 0,-1,-1,-1, 0, 1};
@ -366,9 +371,16 @@ inline void upd7220_device::update_blank_timer(int state)
inline void upd7220_device::recompute_parameters() inline void upd7220_device::recompute_parameters()
{ {
int horiz_mult;
/* TODO: assume that the pitch also controls number of horizontal pixels in a single cell */ /* TODO: assume that the pitch also controls number of horizontal pixels in a single cell */
int horiz_mult = ((m_pitch == 40) ? 16 : 8); // horiz_mult = 4 if both mixed and interlace?
int horiz_pix_total = (m_hs + m_hbp + m_aw + m_hfp) * horiz_mult; if(((m_mode & UPD7220_MODE_DISPLAY_MASK) == UPD7220_MODE_DISPLAY_MIXED) ||
((m_mode & UPD7220_MODE_INTERLACE_MASK) == UPD7220_MODE_INTERLACE_ON))
horiz_mult = 8;
else
horiz_mult = 16;
int horiz_pix_total = (m_hs + m_hbp + m_hfp + m_aw) * horiz_mult;
int vert_pix_total = m_vs + m_vbp + m_al + m_vfp; int vert_pix_total = m_vs + m_vbp + m_al + m_vfp;
//printf("%d %d %d %d\n",m_hs,m_hbp,m_aw,m_hfp); //printf("%d %d %d %d\n",m_hs,m_hbp,m_aw,m_hfp);
@ -377,7 +389,7 @@ inline void upd7220_device::recompute_parameters()
if (horiz_pix_total == 0 || vert_pix_total == 0) //bail out if screen params aren't valid if (horiz_pix_total == 0 || vert_pix_total == 0) //bail out if screen params aren't valid
return; return;
attoseconds_t refresh = HZ_TO_ATTOSECONDS(clock() * horiz_mult) * horiz_pix_total * vert_pix_total; attoseconds_t refresh = HZ_TO_ATTOSECONDS(clock() * 8) * horiz_pix_total * vert_pix_total;
rectangle visarea; rectangle visarea;
@ -419,6 +431,7 @@ inline void upd7220_device::reset_figs_param()
m_figs.m_d1 = 0x0008; m_figs.m_d1 = 0x0008;
m_figs.m_d2 = 0x0000; m_figs.m_d2 = 0x0000;
m_figs.m_dm = 0x0000; m_figs.m_dm = 0x0000;
m_figs.m_gd = 0;
} }
@ -479,19 +492,21 @@ inline void upd7220_device::write_vram(UINT8 type, UINT8 mod)
result = 0; result = 0;
if(((m_mode & UPD7220_MODE_DISPLAY_MASK) == UPD7220_MODE_DISPLAY_GRAPHICS) || m_figs.m_gd)
result = BITSWAP8(m_pr[1],0,1,2,3,4,5,6,7) | (BITSWAP8(m_pr[2],0,1,2,3,4,5,6,7) << 8);
else
result = m_pr[1] | (m_pr[2] << 8);
switch(type) switch(type)
{ {
case 0: case 0:
result = (m_pr[1] & 0xff);
result |= (m_pr[2] << 8);
result &= m_mask; result &= m_mask;
break; break;
case 2: case 2:
result = (m_pr[1] & 0xff);
result &= (m_mask & 0xff); result &= (m_mask & 0xff);
break; break;
case 3: case 3:
result = (m_pr[1] << 8); result <<= 8;
result &= (m_mask & 0xff00); result &= (m_mask & 0xff00);
break; break;
} }
@ -760,7 +775,7 @@ void upd7220_device::device_timer(emu_timer &timer, device_timer_id id, int para
void upd7220_device::draw_pixel(int x, int y, int xi, UINT16 tile_data) void upd7220_device::draw_pixel(int x, int y, int xi, UINT16 tile_data)
{ {
UINT32 addr = (y * m_pitch * 2 + (x >> 3)) & 0x3ffff; UINT32 addr = ((y * m_pitch * 2) + (x >> 3)) & 0x3ffff;
UINT8 data = readbyte(addr); UINT8 data = readbyte(addr);
UINT8 new_pixel = (xi & 8 ? tile_data >> 8 : tile_data & 0xff) & (0x80 >> (xi & 7)); UINT8 new_pixel = (xi & 8 ? tile_data >> 8 : tile_data & 0xff) & (0x80 >> (xi & 7));
new_pixel = new_pixel ? (0xff & (0x80 >> (x & 7))) : 0; new_pixel = new_pixel ? (0xff & (0x80 >> (x & 7))) : 0;
@ -797,7 +812,7 @@ void upd7220_device::draw_line(int x, int y)
UINT16 pattern = (m_ra[8]) | (m_ra[9]<<8); UINT16 pattern = (m_ra[8]) | (m_ra[9]<<8);
int line_step = 0; int line_step = 0;
LOG(("uPD7220 line check: %d %d %02x %08x %d %d\n",x,y,m_figs.m_dir,m_ead,m_figs.m_d1,m_figs.m_dc)); LOG(("uPD7220 line check: %d %d %02x %08x %d %d %d\n",x,y,m_figs.m_dir,m_ead,m_figs.m_d1,m_figs.m_dc,m_bitmap_mod));
line_size = m_figs.m_dc; line_size = m_figs.m_dc;
@ -815,7 +830,7 @@ void upd7220_device::draw_line(int x, int y)
x += (line_step*line_x_step[m_figs.m_dir]); x += (line_step*line_x_step[m_figs.m_dir]);
y += (line_step*line_y_step[m_figs.m_dir]); y += (line_step*line_y_step[m_figs.m_dir]);
m_ead = (x >> 4) + (y * m_pitch); m_ead = (x >> 4) + (y * (m_pitch >> m_figs.m_gd));
m_dad = x & 0x0f; m_dad = x & 0x0f;
} }
@ -880,7 +895,7 @@ void upd7220_device::draw_arc(int x, int y)
break; break;
} }
m_ead = (x >> 4) + (y * m_pitch); m_ead = (x >> 4) + (y * (m_pitch >> m_figs.m_gd));
m_dad = x & 0x0f; m_dad = x & 0x0f;
} }
@ -935,7 +950,7 @@ void upd7220_device::draw_rectangle(int x, int y)
y+=rect_y_dir[rect_dir]; y+=rect_y_dir[rect_dir];
} }
m_ead = (x >> 4) + (y * m_pitch); m_ead = (x >> 4) + (y * (m_pitch >> m_figs.m_gd));
m_dad = x & 0x0f; m_dad = x & 0x0f;
} }
@ -975,7 +990,7 @@ void upd7220_device::draw_char(int x, int y)
} }
} }
m_ead = (x >> 4) + (y * m_pitch); m_ead = (x >> 4) + (y * (m_pitch >> m_figs.m_gd));
m_dad = (x & 0xf); m_dad = (x & 0xf);
} }
@ -1037,6 +1052,7 @@ void upd7220_device::process_fifo()
{ {
UINT8 data; UINT8 data;
int flag; int flag;
UINT16 eff_pitch = m_pitch >> m_figs.m_gd;
dequeue(&data, &flag); dequeue(&data, &flag);
@ -1203,12 +1219,12 @@ void upd7220_device::process_fifo()
m_ead = (upper_addr << 16) | (m_pr[2] << 8) | m_pr[1]; m_ead = (upper_addr << 16) | (m_pr[2] << 8) | m_pr[1];
//LOG(("uPD7220 '%s' EAD: %06x\n", tag(), m_ead)); LOG(("uPD7220 '%s' EAD: %06x\n", tag(), m_ead));
if(m_param_ptr == 4) if(m_param_ptr == 4)
{ {
m_dad = m_pr[3] >> 4; m_dad = m_pr[3] >> 4;
//LOG(("uPD7220 '%s' DAD: %01x\n", tag(), m_dad)); LOG(("uPD7220 '%s' DAD: %01x\n", tag(), m_dad));
} }
} }
break; break;
@ -1246,7 +1262,7 @@ void upd7220_device::process_fifo()
if (m_param_ptr == 3 || (m_param_ptr == 2 && m_cr & 0x10)) if (m_param_ptr == 3 || (m_param_ptr == 2 && m_cr & 0x10))
{ {
//printf("%02x = %02x %02x (%c) %04x\n",m_cr,m_pr[2],m_pr[1],m_pr[1],EAD); LOG(("%02x = %02x %02x (%c) %06x %04x\n",m_cr,m_pr[2],m_pr[1],m_pr[1]?m_pr[1]:' ',m_ead,m_figs.m_dc));
fifo_set_direction(FIFO_WRITE); fifo_set_direction(FIFO_WRITE);
write_vram((m_cr & 0x18) >> 3,m_cr & 3); write_vram((m_cr & 0x18) >> 3,m_cr & 3);
@ -1280,7 +1296,10 @@ void upd7220_device::process_fifo()
m_figs.m_dc = (m_pr[2]) | (m_figs.m_dc & 0x3f00); m_figs.m_dc = (m_pr[2]) | (m_figs.m_dc & 0x3f00);
if (m_param_ptr == 4) if (m_param_ptr == 4)
{
m_figs.m_dc = (m_pr[2]) | ((m_pr[3] & 0x3f) << 8); m_figs.m_dc = (m_pr[2]) | ((m_pr[3] & 0x3f) << 8);
m_figs.m_gd = (m_pr[3] & 0x40) && ((m_mode & UPD7220_MODE_DISPLAY_MASK) == UPD7220_MODE_DISPLAY_MIXED);
}
if (m_param_ptr == 6) if (m_param_ptr == 6)
m_figs.m_d = (m_pr[4]) | ((m_pr[5] & 0x3f) << 8); m_figs.m_d = (m_pr[4]) | ((m_pr[5] & 0x3f) << 8);
@ -1298,13 +1317,13 @@ void upd7220_device::process_fifo()
case COMMAND_FIGD: /* figure draw start */ case COMMAND_FIGD: /* figure draw start */
if(m_figs.m_figure_type == 0) if(m_figs.m_figure_type == 0)
draw_pixel(((m_ead % m_pitch) << 4) | (m_dad & 0xf),(m_ead / m_pitch),m_dad,(m_ra[8]) | (m_ra[9]<<8)); draw_pixel(((m_ead % eff_pitch) << 4) | (m_dad & 0xf),(m_ead / eff_pitch),m_dad,(m_ra[8]) | (m_ra[9]<<8));
else if(m_figs.m_figure_type == 1) else if(m_figs.m_figure_type == 1)
draw_line(((m_ead % m_pitch) << 4) | (m_dad & 0xf),(m_ead / m_pitch)); draw_line(((m_ead % eff_pitch) << 4) | (m_dad & 0xf),(m_ead / eff_pitch));
else if(m_figs.m_figure_type == 4) else if(m_figs.m_figure_type == 4)
draw_arc(((m_ead % m_pitch) << 4) | (m_dad & 0xf),(m_ead / m_pitch)); draw_arc(((m_ead % eff_pitch) << 4) | (m_dad & 0xf),(m_ead / eff_pitch));
else if(m_figs.m_figure_type == 8) else if(m_figs.m_figure_type == 8)
draw_rectangle(((m_ead % m_pitch) << 4) | (m_dad & 0xf),(m_ead / m_pitch)); draw_rectangle(((m_ead % eff_pitch) << 4) | (m_dad & 0xf),(m_ead / eff_pitch));
else else
logerror("uPD7220 '%s' Unimplemented command FIGD %02x\n", tag(),m_figs.m_figure_type); logerror("uPD7220 '%s' Unimplemented command FIGD %02x\n", tag(),m_figs.m_figure_type);
@ -1314,7 +1333,7 @@ void upd7220_device::process_fifo()
case COMMAND_GCHRD: /* graphics character draw and area filling start */ case COMMAND_GCHRD: /* graphics character draw and area filling start */
if(m_figs.m_figure_type == 2) if(m_figs.m_figure_type == 2)
draw_char(((m_ead % m_pitch) << 4) | (m_dad & 0xf),(m_ead / m_pitch)); draw_char(((m_ead % eff_pitch) << 4) | (m_dad & 0xf),(m_ead / eff_pitch));
else else
logerror("uPD7220 '%s' Unimplemented command GCHRD %02x\n", tag(),m_figs.m_figure_type); logerror("uPD7220 '%s' Unimplemented command GCHRD %02x\n", tag(),m_figs.m_figure_type);
@ -1568,7 +1587,7 @@ void upd7220_device::update_graphics(bitmap_rgb32 &bitmap, const rectangle &clip
addr = ((sad << 1) & 0x3ffff) + (y * m_pitch * 2); addr = ((sad << 1) & 0x3ffff) + (y * m_pitch * 2);
if (!m_display_cb.isnull()) if (!m_display_cb.isnull())
draw_graphics_line(bitmap, addr, y + bsy/((m_pitch == 40)+1), wd); draw_graphics_line(bitmap, addr, y + (bsy >> !im), wd);
} }
} }
else else

View File

@ -209,6 +209,7 @@ private:
UINT8 m_dir; // figs param 0: drawing direction UINT8 m_dir; // figs param 0: drawing direction
UINT8 m_figure_type; // figs param 1: figure type UINT8 m_figure_type; // figs param 1: figure type
UINT16 m_dc; // figs param 2: UINT16 m_dc; // figs param 2:
UINT8 m_gd; // mixed mode only
UINT16 m_d; // figs param 3: UINT16 m_d; // figs param 3:
UINT16 m_d1; // figs param 4: UINT16 m_d1; // figs param 4:
UINT16 m_d2; // figs param 5: UINT16 m_d2; // figs param 5:

View File

@ -99,6 +99,24 @@ READ16_MEMBER( compis_state::isbx1_tdma_r )
{ {
if (offset < 2) if (offset < 2)
return m_crtc->read(space, offset & 0x01); return m_crtc->read(space, offset & 0x01);
else
// monochrome only, hblank? vblank?
if(offset == 2)
{
switch(m_unk_video)
{
case 0x04:
m_unk_video = 0x44;
break;
case 0x44:
m_unk_video = 0x64;
break;
default:
m_unk_video = 0x04;
break;
}
return m_unk_video;
}
else else
return 0; return 0;
} }
@ -115,7 +133,9 @@ WRITE16_MEMBER( compis_state::isbx1_tdma_w )
{ {
if (ACCESSING_BITS_0_7) if (ACCESSING_BITS_0_7)
{ {
// 0x336 is likely the color plane register
if (offset < 2) m_crtc->write(space, offset & 0x01, data); if (offset < 2) m_crtc->write(space, offset & 0x01, data);
} }
else else
{ {
@ -221,27 +241,6 @@ WRITE16_MEMBER( compis_state::isbx1_dack_w )
} }
//-------------------------------------------------
// vram_r -
//-------------------------------------------------
READ8_MEMBER( compis_state::vram_r )
{
return m_video_ram[offset];
}
//-------------------------------------------------
// vram_w -
//-------------------------------------------------
WRITE8_MEMBER( compis_state::vram_w )
{
m_video_ram[offset] = data;
}
//************************************************************************** //**************************************************************************
// ADDRESS MAPS // ADDRESS MAPS
//************************************************************************** //**************************************************************************
@ -253,7 +252,6 @@ WRITE8_MEMBER( compis_state::vram_w )
static ADDRESS_MAP_START( compis_mem, AS_PROGRAM, 16, compis_state ) static ADDRESS_MAP_START( compis_mem, AS_PROGRAM, 16, compis_state )
ADDRESS_MAP_UNMAP_HIGH ADDRESS_MAP_UNMAP_HIGH
AM_RANGE(0x00000, 0x1ffff) AM_RAM AM_RANGE(0x00000, 0x1ffff) AM_RAM
AM_RANGE(0x40000, 0x5ffff) AM_READWRITE8(vram_r, vram_w, 0xffff)
AM_RANGE(0x60000, 0x63fff) AM_MIRROR(0x1c000) AM_DEVICE(I80130_TAG, i80130_device, rom_map) AM_RANGE(0x60000, 0x63fff) AM_MIRROR(0x1c000) AM_DEVICE(I80130_TAG, i80130_device, rom_map)
AM_RANGE(0xe0000, 0xeffff) AM_MIRROR(0x10000) AM_ROM AM_REGION(I80186_TAG, 0) AM_RANGE(0xe0000, 0xeffff) AM_MIRROR(0x10000) AM_ROM AM_REGION(I80186_TAG, 0)
ADDRESS_MAP_END ADDRESS_MAP_END
@ -265,9 +263,7 @@ ADDRESS_MAP_END
static ADDRESS_MAP_START( compis2_mem, AS_PROGRAM, 16, compis_state ) static ADDRESS_MAP_START( compis2_mem, AS_PROGRAM, 16, compis_state )
ADDRESS_MAP_UNMAP_HIGH ADDRESS_MAP_UNMAP_HIGH
AM_RANGE(0x00000, 0x3ffff) AM_RAM AM_RANGE(0x00000, 0xbffff) AM_RAM
AM_RANGE(0x40000, 0x5ffff) AM_READWRITE8(vram_r, vram_w, 0xffff)
AM_RANGE(0x60000, 0xbffff) AM_RAM
AM_RANGE(0xe0000, 0xeffff) AM_MIRROR(0x10000) AM_ROM AM_REGION(I80186_TAG, 0) AM_RANGE(0xe0000, 0xeffff) AM_MIRROR(0x10000) AM_ROM AM_REGION(I80186_TAG, 0)
ADDRESS_MAP_END ADDRESS_MAP_END
@ -317,8 +313,8 @@ ADDRESS_MAP_END
//------------------------------------------------- //-------------------------------------------------
static ADDRESS_MAP_START( upd7220_map, AS_0, 8, compis_state ) static ADDRESS_MAP_START( upd7220_map, AS_0, 8, compis_state )
ADDRESS_MAP_GLOBAL_MASK(0x1ffff) ADDRESS_MAP_GLOBAL_MASK(0x7fff)
AM_RANGE(0x00000, 0x1ffff) AM_RAM AM_SHARE("video_ram") AM_RANGE(0x00000, 0x7fff) AM_RAM AM_SHARE("video_ram")
ADDRESS_MAP_END ADDRESS_MAP_END
@ -455,11 +451,11 @@ INPUT_PORTS_END
UPD7220_DISPLAY_PIXELS_MEMBER( compis_state::hgdc_display_pixels ) UPD7220_DISPLAY_PIXELS_MEMBER( compis_state::hgdc_display_pixels )
{ {
UINT8 i,gfx = m_video_ram[address]; UINT8 i,gfx = m_video_ram[(address & 0x7fff)];
const pen_t *pen = m_palette->pens(); const pen_t *pen = m_palette->pens();
for(i=0; i<8; i++) for(i=0; i<8; i++)
bitmap.pix32(y, x + i) = pen[BIT(gfx, i)]; bitmap.pix32(y, x + i) = pen[BIT(gfx, 7 - i)];
} }

View File

@ -103,8 +103,6 @@ public:
DECLARE_WRITE16_MEMBER( isbx1_cs_w ); DECLARE_WRITE16_MEMBER( isbx1_cs_w );
DECLARE_READ16_MEMBER( isbx1_dack_r ); DECLARE_READ16_MEMBER( isbx1_dack_r );
DECLARE_WRITE16_MEMBER( isbx1_dack_w ); DECLARE_WRITE16_MEMBER( isbx1_dack_w );
DECLARE_READ8_MEMBER( vram_r );
DECLARE_WRITE8_MEMBER( vram_w );
DECLARE_READ8_MEMBER( compis_irq_callback ); DECLARE_READ8_MEMBER( compis_irq_callback );
@ -125,6 +123,7 @@ public:
DECLARE_WRITE_LINE_MEMBER(write_centronics_select); DECLARE_WRITE_LINE_MEMBER(write_centronics_select);
int m_tmr0; int m_tmr0;
int m_unk_video;
UPD7220_DISPLAY_PIXELS_MEMBER( hgdc_display_pixels ); UPD7220_DISPLAY_PIXELS_MEMBER( hgdc_display_pixels );
}; };