diff --git a/src/emu/video/h63484.c b/src/emu/video/h63484.c index 8c459e0b645..b6876616847 100644 --- a/src/emu/video/h63484.c +++ b/src/emu/video/h63484.c @@ -7,12 +7,198 @@ #include "emu.h" #include "video/h63484.h" +#define LOG 1 + typedef struct _h63484_state h63484_state; struct _h63484_state { h63484_display_pixels_func display_func; screen_device *screen; /* screen */ + UINT8 vram[0x40000]; + UINT8 ar; + UINT8 vreg[0x100]; + UINT8 sr; + + UINT8 fifo[16]; /* FIFO data queue */ + int fifo_flag[16]; /* FIFO flag queue */ + int fifo_ptr; /* FIFO pointer */ + int fifo_dir; /* FIFO direction */ + + UINT8 cr; + UINT8 pr[17]; /* parameter byte register */ + int param_ptr; /* parameter pointer */ +}; + +enum +{ + FIFO_READ = 0, + FIFO_WRITE +}; + +enum +{ + FIFO_EMPTY = -1, + FIFO_PARAMETER, + FIFO_COMMAND +}; + +#define H63484_SR_CER 0x80 // Command Error +#define H63484_SR_ARD 0x40 // Area Detect +#define H63484_SR_CED 0x20 // Command End +#define H63484_SR_LPD 0x10 // Light Pen Strobe Detect +#define H63484_SR_RFF 0x08 // Read FIFO Full +#define H63484_SR_RFR 0x04 // Read FIFO Ready +#define H63484_SR_WFR 0x02 // Write FIFO Ready +#define H63484_SR_WFE 0x01 // Write FIFO Empty + + +#define CCR 0x02 +// Command Control +#define ABT 0x8000 + + +static const char *const acrtc_regnames[0x100/2] = +{ + "FIFO Entry", // 0x00 + "Command Control (CCR)", // 0x02 + "Operation Mode (OMR)", // 0x04 + "Display Control (DCR)", // 0x06 + "(Undefined)", // 0x08 + "(Undefined)", // 0x0a + "(Undefined)", // 0x0c + "(Undefined)", // 0x0e + "(Undefined)", // 0x10 + "(Undefined)", // 0x12 + "(Undefined)", // 0x14 + "(Undefined)", // 0x16 + "(Undefined)", // 0x18 + "(Undefined)", // 0x1a + "(Undefined)", // 0x1c + "(Undefined)", // 0x1e + "(Undefined)", // 0x20 + "(Undefined)", // 0x22 + "(Undefined)", // 0x24 + "(Undefined)", // 0x26 + "(Undefined)", // 0x28 + "(Undefined)", // 0x2a + "(Undefined)", // 0x2c + "(Undefined)", // 0x2e + "(Undefined)", // 0x30 + "(Undefined)", // 0x32 + "(Undefined)", // 0x34 + "(Undefined)", // 0x36 + "(Undefined)", // 0x38 + "(Undefined)", // 0x3a + "(Undefined)", // 0x3c + "(Undefined)", // 0x3e + "(Undefined)", // 0x40 + "(Undefined)", // 0x42 + "(Undefined)", // 0x44 + "(Undefined)", // 0x46 + "(Undefined)", // 0x48 + "(Undefined)", // 0x4a + "(Undefined)", // 0x4c + "(Undefined)", // 0x4e + "(Undefined)", // 0x50 + "(Undefined)", // 0x52 + "(Undefined)", // 0x54 + "(Undefined)", // 0x56 + "(Undefined)", // 0x58 + "(Undefined)", // 0x5a + "(Undefined)", // 0x5c + "(Undefined)", // 0x5e + "(Undefined)", // 0x60 + "(Undefined)", // 0x62 + "(Undefined)", // 0x64 + "(Undefined)", // 0x66 + "(Undefined)", // 0x68 + "(Undefined)", // 0x6a + "(Undefined)", // 0x6c + "(Undefined)", // 0x6e + "(Undefined)", // 0x70 + "(Undefined)", // 0x72 + "(Undefined)", // 0x74 + "(Undefined)", // 0x76 + "(Undefined)", // 0x78 + "(Undefined)", // 0x7a + "(Undefined)", // 0x7c + "(Undefined)", // 0x7e + "Raster Count (RCR)", // 0x80 + "Horizontal Sync (HSR)", // 0x82 + "Horizontal Display (HDR)", // 0x84 + "Vertical Sync (VSR)", // 0x86 + "Vertical Display (VDR)", // 0x88 + "Split Screen Width (SSW) 0x8a", // 0x8a + "Split Screen Width (SSW) 0x8c", // 0x8c + "Split Screen Width (SSW) 0x8e", // 0x8e + "Blink Control (BCR)", // 0x90 + "Horizontal Window Display (HWR)", // 0x92 + "Vertical Window Display (VWR) 0x94", // 0x94 + "Vertical Window Display (VWR) 0x96", // 0x96 + "Graphic Cursor (GCR0)", // 0x98 + "Graphic Cursor (GCR1)", // 0x9a + "Graphic Cursor (GCR2)", // 0x9c + "(Undefined)", // 0x9e + "(Undefined)", // 0xa0 + "(Undefined)", // 0xa2 + "(Undefined)", // 0xa4 + "(Undefined)", // 0xa6 + "(Undefined)", // 0xa8 + "(Undefined)", // 0xaa + "(Undefined)", // 0xac + "(Undefined)", // 0xae + "(Undefined)", // 0xb0 + "(Undefined)", // 0xb2 + "(Undefined)", // 0xb4 + "(Undefined)", // 0xb6 + "(Undefined)", // 0xb8 + "(Undefined)", // 0xba + "(Undefined)", // 0xbc + "(Undefined)", // 0xbe + // upper screen + "Raster Address 0 (RAR0)", // 0xc0 + "Memory Width 0 (MWR0)", // 0xc2 + "Start Address 0 (SAR0) 0xc4", // 0xc4 + "Start Address 0 (SAR0) 0xc6", // 0xc6 + // base screen + "Raster Address 1 (RAR1)", // 0xc8 + "Memory Width 1 (MWR1)", // 0xca + "Start Address 1 (SAR1) 0xcc", // 0xcc + "Start Address 1 (SAR1) 0xce", // 0xce + // lower screen + "Raster Address 2 (RAR2)", // 0xd0 + "Memory Width 2 (MWR2)", // 0xd2 + "Start Address 2 (SAR2) 0xd4", // 0xd4 + "Start Address 2 (SAR2) 0xd6", // 0xd6 + // window screen + "Raster Address 3 (RAR3)", // 0xd8 + "Memory Width 3 (MWR3)", // 0xda + "Start Address 3 (SAR3) 0xdc", // 0xdc + "Start Address 3 (SAR3) 0xde", // 0xde + // block cursor 1 + "Block Cursor 1 (BCUR1) 0xe0", + "Block Cursor 1 (BCUR1) 0xe2", + // block cursor 2 + "Block Cursor 2 (BCUR2) 0xe4", + "Block Cursor 2 (BCUR2) 0xe6", + "Cursor Definition (CDR)", + "Zoom Factor (ZFR)", + "Lightpen Address (LPAR) 0xec", + "Lightpen Address (LPAR) 0xee", + "(Undefined)", // 0xf0 + "(Undefined)", // 0xf2 + "(Undefined)", // 0xf4 + "(Undefined)", // 0xf6 + "(Undefined)", // 0xf8 + "(Undefined)", // 0xfa + "(Undefined)", // 0xfc + "(Undefined)" // 0xfe +}; + +enum +{ + COMMAND_INVALID = -1 }; /***************************************************************************** @@ -34,6 +220,94 @@ INLINE const h63484_interface *get_interface( device_t *device ) return (const h63484_interface *) device->static_config(); } + +INLINE void fifo_clear(h63484_state *h63484) +{ + int i; + + for (i = 0; i < 16; i++) + { + h63484->fifo[i] = 0; + h63484->fifo_flag[i] = FIFO_EMPTY; + } + + h63484->fifo_ptr = -1; + + h63484->sr |= H63484_SR_WFR; + h63484->sr |= H63484_SR_WFE; +} + +INLINE int fifo_param_count(h63484_state *h63484) +{ + int i; + + for (i = 0; i < 16; i++) + { + if (h63484->fifo_flag[i] != FIFO_PARAMETER) break; + } + + return i; +} + +INLINE void fifo_set_direction(h63484_state *h63484, int dir) +{ + if (h63484->fifo_dir != dir) + { + fifo_clear(h63484); + } + + h63484->fifo_dir = dir; +} + +INLINE void queue(h63484_state *h63484, UINT8 data, int flag) +{ + if (h63484->fifo_ptr < 15) + { + h63484->fifo_ptr++; + + h63484->fifo[h63484->fifo_ptr] = data; + h63484->fifo_flag[h63484->fifo_ptr] = flag; + + if (h63484->fifo_ptr == 16) + h63484->sr &= ~H63484_SR_WFR; + + h63484->sr &= ~H63484_SR_WFE; + } + else + { + // TODO what happen? somebody set us up the bomb + printf("FIFO?\n"); + } +} + +INLINE void dequeue(h63484_state *h63484, UINT8 *data, int *flag) +{ + int i; + + *data = h63484->fifo[0]; + *flag = h63484->fifo_flag[0]; + + if (h63484->fifo_ptr > -1) + { + for (i = 0; i < 15; i++) + { + h63484->fifo[i] = h63484->fifo[i + 1]; + h63484->fifo_flag[i] = h63484->fifo_flag[i + 1]; + } + + h63484->fifo[15] = 0; + h63484->fifo_flag[15] = 0; + + h63484->fifo_ptr--; + + h63484->sr |= H63484_SR_WFR; + + if (h63484->fifo_ptr == -1) + h63484->sr |= H63484_SR_WFE; + + } +} + /*------------------------------------------------- ROM( h63484 ) -------------------------------------------------*/ @@ -43,15 +317,103 @@ ROM_START( h63484 ) ROM_LOAD( "h63484.bin", 0x000, 0x100, NO_DUMP ) /* internal control ROM */ ROM_END +/*------------------------------------------------- + ADDRESS_MAP( upd7220 ) +-------------------------------------------------*/ + +READ8_DEVICE_HANDLER( h63484_vram_r ) +{ + h63484_state *h63484 = get_safe_token(device); + + return h63484->vram[offset]; +} + +WRITE8_DEVICE_HANDLER( h63484_vram_w ) +{ + h63484_state *h63484 = get_safe_token(device); + + h63484->vram[offset] = data; +} + /***************************************************************************** IMPLEMENTATION *****************************************************************************/ +static int translate_command(UINT8 data) +{ + int command = COMMAND_INVALID; + + switch (data) + { + + } + + return command; +} + +static void process_fifo(device_t *device) +{ + h63484_state *h63484 = get_safe_token(device); + UINT8 data; + int flag; + + dequeue(h63484, &data, &flag); + + if (flag == FIFO_COMMAND) + { + h63484->cr = (data & 0xff00) >> 8; + h63484->param_ptr = 1; + h63484->sr &= ~H63484_SR_CED; + dequeue(h63484, &data, &flag); + h63484->pr[h63484->param_ptr] = data & 0xff; + h63484->param_ptr++; + } + else + { + h63484->pr[h63484->param_ptr] = (data & 0xff00) >> 8; + h63484->param_ptr++; + dequeue(h63484, &data, &flag); + h63484->pr[h63484->param_ptr] = data & 0xff; + h63484->param_ptr++; + } + + switch (translate_command(h63484->cr)) + { + // ... + } +} + +static void exec_abort_sequence(device_t *device) +{ + h63484_state *h63484 = get_safe_token(device); + + fifo_clear(h63484); + h63484->sr = H63484_SR_WFR | H63484_SR_WFE | H63484_SR_CED; // set to 0x23 +} + +static void check_video_registers(device_t *device, int offset) +{ + h63484_state *h63484 = get_safe_token(device); + UINT16 vreg_data; + + vreg_data = (h63484->vreg[offset]<<8)|(h63484->vreg[offset+1]&0xff); + + switch(offset) + { + case 0x00: // FIFO entry, not covered there + break; + case CCR: // Command Entry + if(vreg_data & ABT) // abort sequence + exec_abort_sequence(device); + break; + } +} + READ16_DEVICE_HANDLER( h63484_status_r ) { - //h63484_state *h63484 = get_safe_token(device); + h63484_state *h63484 = get_safe_token(device); - return 0; + return h63484->sr; } READ16_DEVICE_HANDLER( h63484_data_r ) @@ -66,12 +428,39 @@ READ16_DEVICE_HANDLER( h63484_data_r ) WRITE16_DEVICE_HANDLER( h63484_address_w ) { - //h63484_state *h63484 = get_safe_token(device); + h63484_state *h63484 = get_safe_token(device); + + if(ACCESSING_BITS_0_7) + h63484->ar = data & 0xff; } WRITE16_DEVICE_HANDLER( h63484_data_w ) { - //h63484_state *h63484 = get_safe_token(device); + h63484_state *h63484 = get_safe_token(device); + + if(LOG) printf("%s -> %02x\n",acrtc_regnames[h63484->ar/2],data); + + if(ACCESSING_BITS_8_15) + h63484->vreg[h63484->ar] = (data & 0xff00) >> 8; + + if(ACCESSING_BITS_0_7) + h63484->vreg[h63484->ar+1] = (data & 0xff); + + if(h63484->ar == 0) + { + fifo_set_direction(h63484, FIFO_WRITE); + queue(h63484, (data & 0xff00) >> 8, (h63484->sr & H63484_SR_CED) >> 5); + queue(h63484, (data & 0x00ff) >> 0, 0); + process_fifo(device); + } + else + check_video_registers(device,h63484->ar); + + if(h63484->ar & 0x80) + { + h63484->ar+=2; + h63484->ar &= 0xff; // TODO: what happens if it overflows? + } } static DEVICE_START( h63484 ) diff --git a/src/emu/video/h63484.h b/src/emu/video/h63484.h index 94771540734..3dc90e45bd4 100644 --- a/src/emu/video/h63484.h +++ b/src/emu/video/h63484.h @@ -51,6 +51,9 @@ READ16_DEVICE_HANDLER( h63484_data_r ); WRITE16_DEVICE_HANDLER( h63484_address_w ); WRITE16_DEVICE_HANDLER( h63484_data_w ); +READ8_DEVICE_HANDLER( h63484_vram_r ); +WRITE8_DEVICE_HANDLER( h63484_vram_w ); + #endif /* __H63484_H__ */ diff --git a/src/mame/drivers/adp.c b/src/mame/drivers/adp.c index 1f614510faf..e3f2789f839 100644 --- a/src/mame/drivers/adp.c +++ b/src/mame/drivers/adp.c @@ -643,12 +643,12 @@ static READ8_HANDLER( h63484_rom_r ) } static ADDRESS_MAP_START( adp_h63484_map, AS_0, 8 ) - AM_RANGE(0x00000, 0x3ffff) AM_RAM + AM_RANGE(0x00000, 0x3ffff) AM_DEVREADWRITE("h63484",h63484_vram_r,h63484_vram_w) AM_RANGE(0x40000, 0x7ffff) AM_READ(h63484_rom_r) ADDRESS_MAP_END static ADDRESS_MAP_START( fashiong_h63484_map, AS_0, 8 ) - AM_RANGE(0x00000, 0x3ffff) AM_RAM + AM_RANGE(0x00000, 0x3ffff) AM_DEVREADWRITE("h63484",h63484_vram_r,h63484_vram_w) // AM_RANGE(0x40000, 0x7ffff) AM_ROM AM_REGION("gfx1", 0) ADDRESS_MAP_END