From cc82442e48c236f1ef9134d62d5eed87e45f192f Mon Sep 17 00:00:00 2001 From: cracyc Date: Sat, 25 Nov 2017 14:16:51 -0600 Subject: [PATCH] cga: support 400 line text modes (nw) --- src/devices/bus/isa/cga.cpp | 314 +++++++++--------------------------- src/devices/bus/isa/cga.h | 10 +- 2 files changed, 78 insertions(+), 246 deletions(-) diff --git a/src/devices/bus/isa/cga.cpp b/src/devices/bus/isa/cga.cpp index a578881be7e..e2f98c6cfe9 100644 --- a/src/devices/bus/isa/cga.cpp +++ b/src/devices/bus/isa/cga.cpp @@ -190,22 +190,22 @@ MC6845_UPDATE_ROW( isa8_cga_device::crtc_update_row ) switch (m_update_row_type) { case CGA_TEXT_INTEN: - cga_text_inten_update_row(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); + cga_text(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); break; case CGA_TEXT_INTEN_ALT: - cga_text_inten_alt_update_row(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); + cga_text(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); break; case CGA_TEXT_INTEN_CG: - cga_text_inten_comp_grey_update_row(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); + cga_text(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); break; case CGA_TEXT_BLINK: - cga_text_blink_update_row(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); + cga_text(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); break; case CGA_TEXT_BLINK_ALT: - cga_text_blink_alt_update_row(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); + cga_text(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); break; case CGA_TEXT_BLINK_SI: - cga_text_blink_update_row_si(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); + cga_text(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); break; case CGA_GFX_1BPP: cga_gfx_1bpp_update_row(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); @@ -467,200 +467,41 @@ isa8_cga_superimpose_device::isa8_cga_superimpose_device(const machine_config &m m_superimpose = true; } -/*************************************************************************** - Draw text mode with 40x25 characters (default) with high intensity bg. - The character cell size is 16x8 -***************************************************************************/ - -MC6845_UPDATE_ROW( isa8_cga_device::cga_text_inten_update_row ) +template +MC6845_UPDATE_ROW( isa8_cga_device::cga_text ) { uint8_t *videoram = &m_vram[m_start_offset]; uint32_t *p = &bitmap.pix32(y); const rgb_t *palette = m_palette->palette()->entry_list_raw(); int i; - if ( y == 0 ) CGA_LOG(1,"cga_text_inten_update_row",("\n")); + if ( y == 0 ) CGA_LOG(1,"cga_text_8",("\n")); for ( i = 0; i < x_count; i++ ) { uint16_t offset = ( ( ma + i ) << 1 ) & 0x3fff; uint8_t chr = videoram[ offset ]; uint8_t attr = videoram[ offset +1 ]; - uint8_t data = m_chr_gen[ chr * 8 + ra ]; - uint16_t fg = attr & 0x0F; - uint16_t bg = attr >> 4; - - if ( i == cursor_x && ( m_framecnt & 0x08 ) ) - { - data = 0xFF; - } - - *p = palette[( data & 0x80 ) ? fg : bg]; p++; - *p = palette[( data & 0x40 ) ? fg : bg]; p++; - *p = palette[( data & 0x20 ) ? fg : bg]; p++; - *p = palette[( data & 0x10 ) ? fg : bg]; p++; - *p = palette[( data & 0x08 ) ? fg : bg]; p++; - *p = palette[( data & 0x04 ) ? fg : bg]; p++; - *p = palette[( data & 0x02 ) ? fg : bg]; p++; - *p = palette[( data & 0x01 ) ? fg : bg]; p++; - } -} - - -/*************************************************************************** - Draw text mode with 40x25 characters (default) with high intensity bg. - The character cell size is 16x8. Composite monitor, greyscale. -***************************************************************************/ - -MC6845_UPDATE_ROW( isa8_cga_device::cga_text_inten_comp_grey_update_row ) -{ - uint8_t *videoram = &m_vram[m_start_offset]; - uint32_t *p = &bitmap.pix32(y); - const rgb_t *palette = m_palette->palette()->entry_list_raw(); - int i; - - if ( y == 0 ) CGA_LOG(1,"cga_text_inten_comp_grey_update_row",("\n")); - for ( i = 0; i < x_count; i++ ) - { - uint16_t offset = ( ( ma + i ) << 1 ) & 0x3fff; - uint8_t chr = videoram[ offset ]; - uint8_t attr = videoram[ offset +1 ]; - uint8_t data = m_chr_gen[ chr * 8 + ra ]; - uint16_t fg = 0x10 + ( attr & 0x0F ); - uint16_t bg = 0x10 + ( ( attr >> 4 ) & 0x07 ); - - if ( i == cursor_x && ( m_framecnt & 0x08 ) ) - { - data = 0xFF; - } - - *p = palette[( data & 0x80 ) ? fg : bg]; p++; - *p = palette[( data & 0x40 ) ? fg : bg]; p++; - *p = palette[( data & 0x20 ) ? fg : bg]; p++; - *p = palette[( data & 0x10 ) ? fg : bg]; p++; - *p = palette[( data & 0x08 ) ? fg : bg]; p++; - *p = palette[( data & 0x04 ) ? fg : bg]; p++; - *p = palette[( data & 0x02 ) ? fg : bg]; p++; - *p = palette[( data & 0x01 ) ? fg : bg]; p++; - } -} - -/*************************************************************************** - Draw text mode with 40x25 characters (default) with high intensity bg. - The character cell size is 16x8 -***************************************************************************/ - -MC6845_UPDATE_ROW( isa8_cga_device::cga_text_inten_alt_update_row ) -{ - uint8_t *videoram = &m_vram[m_start_offset]; - uint32_t *p = &bitmap.pix32(y); - const rgb_t *palette = m_palette->palette()->entry_list_raw(); - int i; - - if ( y == 0 ) CGA_LOG(1,"cga_text_inten_alt_update_row",("\n")); - for ( i = 0; i < x_count; i++ ) - { - uint16_t offset = ( ( ma + i ) << 1 ) & 0x3fff; - uint8_t chr = videoram[ offset ]; - uint8_t attr = videoram[ offset +1 ]; - uint8_t data = m_chr_gen[ chr * 8 + ra ]; - uint16_t fg = attr & 0x0F; - - if ( i == cursor_x && ( m_framecnt & 0x08 ) ) - { - data = 0xFF; - } - - *p = palette[( data & 0x80 ) ? fg : 0]; p++; - *p = palette[( data & 0x40 ) ? fg : 0]; p++; - *p = palette[( data & 0x20 ) ? fg : 0]; p++; - *p = palette[( data & 0x10 ) ? fg : 0]; p++; - *p = palette[( data & 0x08 ) ? fg : 0]; p++; - *p = palette[( data & 0x04 ) ? fg : 0]; p++; - *p = palette[( data & 0x02 ) ? fg : 0]; p++; - *p = palette[( data & 0x01 ) ? fg : 0]; p++; - } -} - - -/*************************************************************************** - Draw text mode with 40x25 characters (default) and blinking colors. - The character cell size is 16x8 -***************************************************************************/ - -MC6845_UPDATE_ROW( isa8_cga_device::cga_text_blink_update_row ) -{ - uint8_t *videoram = &m_vram[m_start_offset]; - uint32_t *p = &bitmap.pix32(y); - const rgb_t *palette = m_palette->palette()->entry_list_raw(); - int i; - - if ( y == 0 ) CGA_LOG(1,"cga_text_blink_update_row",("\n")); - for ( i = 0; i < x_count; i++ ) - { - uint16_t offset = ( ( ma + i ) << 1 ) & 0x3fff; - uint8_t chr = videoram[ offset ]; - uint8_t attr = videoram[ offset +1 ]; - uint8_t data = m_chr_gen[ chr * 8 + ra ]; - uint16_t fg = attr & 0x0F; - uint16_t bg = (attr >> 4) & 0x07; - - if ( i == cursor_x ) - { - if ( m_framecnt & 0x08 ) - { - data = 0xFF; - } - } - else - { - if ( ( attr & 0x80 ) && ( m_framecnt & 0x10 ) ) - { - data = 0x00; - } - } - - *p = palette[( data & 0x80 ) ? fg : bg]; p++; - *p = palette[( data & 0x40 ) ? fg : bg]; p++; - *p = palette[( data & 0x20 ) ? fg : bg]; p++; - *p = palette[( data & 0x10 ) ? fg : bg]; p++; - *p = palette[( data & 0x08 ) ? fg : bg]; p++; - *p = palette[( data & 0x04 ) ? fg : bg]; p++; - *p = palette[( data & 0x02 ) ? fg : bg]; p++; - *p = palette[( data & 0x01 ) ? fg : bg]; p++; - } -} - -MC6845_UPDATE_ROW( isa8_cga_device::cga_text_blink_update_row_si ) -{ - uint8_t *videoram = &m_vram[m_start_offset]; - uint32_t *p = &bitmap.pix32(y); - const rgb_t *palette = m_palette->palette()->entry_list_raw(); - int i; - - if ( y == 0 ) CGA_LOG(1,"cga_text_blink_update_row_si",("\n")); - for ( i = 0; i < x_count; i++ ) - { - uint16_t offset = ( ( ma + i ) << 1 ) & 0x3fff; - uint8_t chr = videoram[ offset ]; - uint8_t attr = videoram[ offset +1 ]; - uint8_t data = m_chr_gen[ chr * 8 + ra ]; - uint16_t fg = attr & 0x0F; - uint16_t bg = (attr >> 4) & 0x07; + uint8_t data = m_chr_gen[ chr * width + ra ]; + uint16_t fg, bg; uint8_t xi; - if ( i == cursor_x ) + if ( comp ) { - if ( m_framecnt & 0x08 ) - { - data = 0xFF; - } + fg = 0x10 + ( attr & 0x0F ); + bg = alt ? 0 : ( 0x10 + ( ( attr >> 4 ) & 0x07 ) ); } else { - if ( ( attr & 0x80 ) && ( m_framecnt & 0x10 ) ) - { - data = 0x00; - } + fg = attr & 0x0F; + bg = alt ? 0 : ( ( attr >> 4 ) & ( blink ? 0x07 : 0x0f ) ); + } + + if ( ( i == cursor_x ) && ( m_framecnt & 0x08 ) ) + data = 0xFF; + else if ( blink && ( attr & 0x80 ) && ( m_framecnt & 0x10 ) ) + { + data = 0x00; + bg = ( attr >> 4 ) & 0x07; } for(xi=0;xi<8;xi++) @@ -669,62 +510,13 @@ MC6845_UPDATE_ROW( isa8_cga_device::cga_text_blink_update_row_si ) dot = (data & (1 << (7-xi))); pen_data = dot ? fg : bg; - if(pen_data || dot) + if(!si || (pen_data || dot)) *p = palette[pen_data]; p++; } } } -/*************************************************************************** - Draw text mode with 40x25 characters (default) and blinking colors. - The character cell size is 16x8 -***************************************************************************/ - -MC6845_UPDATE_ROW( isa8_cga_device::cga_text_blink_alt_update_row ) -{ - uint8_t *videoram = &m_vram[m_start_offset]; - uint32_t *p = &bitmap.pix32(y); - const rgb_t *palette = m_palette->palette()->entry_list_raw(); - int i; - - if ( y == 0 ) CGA_LOG(1,"cga_text_blink_alt_update_row",("\n")); - for ( i = 0; i < x_count; i++ ) - { - uint16_t offset = ( ( ma + i ) << 1 ) & 0x3fff; - uint8_t chr = videoram[ offset ]; - uint8_t attr = videoram[ offset +1 ]; - uint8_t data = m_chr_gen[ chr * 8 + ra ]; - uint16_t fg = attr & 0x07; - uint16_t bg = 0; - - if ( i == cursor_x ) - { - if ( m_framecnt & 0x08 ) - { - data = 0xFF; - } - } - else - { - if ( ( attr & 0x80 ) && ( m_framecnt & 0x10 ) ) - { - data = 0x00; - bg = ( attr >> 4 ) & 0x07; - } - } - - *p = palette[( data & 0x80 ) ? fg : bg]; p++; - *p = palette[( data & 0x40 ) ? fg : bg]; p++; - *p = palette[( data & 0x20 ) ? fg : bg]; p++; - *p = palette[( data & 0x10 ) ? fg : bg]; p++; - *p = palette[( data & 0x08 ) ? fg : bg]; p++; - *p = palette[( data & 0x04 ) ? fg : bg]; p++; - *p = palette[( data & 0x02 ) ? fg : bg]; p++; - *p = palette[( data & 0x01 ) ? fg : bg]; p++; - } -} - /* The lo-res (320x200) graphics mode on a colour composite monitor */ @@ -2076,18 +1868,18 @@ void isa8_cga_cportiii_device::device_reset() m_isa->install_device(0x13c6, 0x13c7, read8_delegate(FUNC(isa8_cga_cportiii_device::port_13c6_r), this), write8_delegate(FUNC(isa8_cga_cportiii_device::port_13c6_w), this)); m_isa->install_device(0x23c6, 0x23c7, read8_delegate(FUNC(isa8_cga_cportiii_device::port_23c6_r), this), write8_delegate(FUNC(isa8_cga_cportiii_device::port_23c6_w), this)); m_palette->set_pen_color(0, 100, 25, 0); - + m_chr_gen_offset[0] = m_chr_gen_offset[2] = 0x0000; + m_chr_gen_offset[1] = m_chr_gen_offset[3] = 0x1000; } WRITE8_MEMBER(isa8_cga_cportiii_device::char_ram_write) { - if(!BIT(offset, 0)) // FIXME: the font is 16 chars high, this needs it's own text drawing - m_chr_gen_base[(offset >> 1) + 0x1000] = data; + m_chr_gen_base[offset] = data; } READ8_MEMBER(isa8_cga_cportiii_device::char_ram_read) { - return m_chr_gen_base[(offset >> 1) + 0x1000]; + return m_chr_gen_base[offset]; } READ8_MEMBER(isa8_cga_cportiii_device::port_13c6_r) @@ -2106,9 +1898,55 @@ READ8_MEMBER(isa8_cga_cportiii_device::port_23c6_r) WRITE8_MEMBER(isa8_cga_cportiii_device::port_23c6_w) { - io_write(space, 0x0e, BIT(data, 0)); + m_mode2 = data & 1; if(BIT(data, 3)) m_isa->install_memory(0xb8000, 0xb9fff, read8_delegate(FUNC(isa8_cga_cportiii_device::char_ram_read), this), write8_delegate(FUNC(isa8_cga_cportiii_device::char_ram_write), this)); else m_isa->install_bank(0xb8000, 0xb8000 + 0x8000 - 1, "bank_cga", &m_vram[0]); } + +MC6845_UPDATE_ROW(isa8_cga_cportiii_device::crtc_update_row) +{ + if(m_mode2 & 1) + m24_gfx_1bpp_m24_update_row(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); + + if (m_update_row_type == -1) + return; + + y = m_y; + if(m_y >= bitmap.height()) + return; + + switch (m_update_row_type) + { + case CGA_TEXT_INTEN: + cga_text(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); + break; + case CGA_TEXT_INTEN_ALT: + cga_text(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); + break; + case CGA_TEXT_INTEN_CG: // this hardware doesn't support composite + break; + case CGA_TEXT_BLINK: + cga_text(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); + break; + case CGA_TEXT_BLINK_ALT: + cga_text(bitmap, cliprect, ma, ra, y, x_count, cursor_x, de, hbp, vbp); + break; + case CGA_TEXT_BLINK_SI: + break; + case CGA_GFX_1BPP: + cga_gfx_1bpp_update_row(bitmap, cliprect, ma, ra >> 1, y, x_count, cursor_x, de, hbp, vbp); + break; + case CGA_GFX_2BPP: + cga_gfx_2bpp_update_row(bitmap, cliprect, ma, ra >> 1, y, x_count, cursor_x, de, hbp, vbp); + break; + case CGA_GFX_4BPPL: + cga_gfx_4bppl_update_row(bitmap, cliprect, ma, ra >> 1, y, x_count, cursor_x, de, hbp, vbp); + break; + case CGA_GFX_4BPPH: + cga_gfx_4bpph_update_row(bitmap, cliprect, ma, ra >> 1, y, x_count, cursor_x, de, hbp, vbp); + break; + } +} + diff --git a/src/devices/bus/isa/cga.h b/src/devices/bus/isa/cga.h index a69030070fb..8711d9b188e 100644 --- a/src/devices/bus/isa/cga.h +++ b/src/devices/bus/isa/cga.h @@ -31,12 +31,7 @@ public: isa8_cga_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); virtual MC6845_UPDATE_ROW( crtc_update_row ); - MC6845_UPDATE_ROW( cga_text_inten_update_row ); - MC6845_UPDATE_ROW( cga_text_inten_comp_grey_update_row ); - MC6845_UPDATE_ROW( cga_text_inten_alt_update_row ); - MC6845_UPDATE_ROW( cga_text_blink_update_row ); - MC6845_UPDATE_ROW( cga_text_blink_update_row_si ); - MC6845_UPDATE_ROW( cga_text_blink_alt_update_row ); + template MC6845_UPDATE_ROW( cga_text ); MC6845_UPDATE_ROW( cga_gfx_4bppl_update_row ); MC6845_UPDATE_ROW( cga_gfx_4bpph_update_row ); MC6845_UPDATE_ROW( cga_gfx_2bpp_update_row ); @@ -289,8 +284,6 @@ protected: virtual void device_reset() override; // optional information overrides virtual void device_add_mconfig(machine_config &config) override; - -private: uint8_t m_mode2, m_index; }; @@ -308,6 +301,7 @@ public: DECLARE_WRITE8_MEMBER(port_23c6_w); DECLARE_READ8_MEMBER(char_ram_read); DECLARE_WRITE8_MEMBER(char_ram_write); + virtual MC6845_UPDATE_ROW( crtc_update_row ) override; protected: virtual void device_reset() override; virtual void device_add_mconfig(machine_config &config) override;