src/mess/machine/gamepock.c
| r0 | r1685 | |
| 1 | #include "driver.h" |
| 2 | #include "includes/gamepock.h" |
| 3 | |
| 4 | typedef struct { |
| 5 | UINT8 enabled; |
| 6 | UINT8 start_page; |
| 7 | UINT8 address; |
| 8 | UINT8 y_inc; |
| 9 | UINT8 ram[256]; /* There are actually 50 x 4 x 8 bits. This just makes addressing easier. */ |
| 10 | } HD44102CH; |
| 11 | |
| 12 | static UINT8 gamepock_port_a; |
| 13 | static UINT8 gamepock_port_b; |
| 14 | static HD44102CH hd44102ch[3]; |
| 15 | |
| 16 | static void hd44102ch_w( int which, int c_d, UINT8 data ) { |
| 17 | //logerror("HD44102CH #%d write %s %02X ", which, ( c_d ) ? "data" : "command", data ); |
| 18 | if ( c_d ) { |
| 19 | UINT8 y; |
| 20 | /* Data */ |
| 21 | //logerror("write to %02X", hd44102ch[which].address ); |
| 22 | hd44102ch[which].ram[ hd44102ch[which].address ] = data; |
| 23 | |
| 24 | /* Increment/decrement Y counter */ |
| 25 | y = ( hd44102ch[which].address & 0x3F ) + hd44102ch[which].y_inc; |
| 26 | if ( y == 0xFF ) { |
| 27 | y = 49; |
| 28 | } |
| 29 | if ( y == 50 ) { |
| 30 | y = 0; |
| 31 | } |
| 32 | hd44102ch[which].address = ( hd44102ch[which].address & 0xC0 ) | y; |
| 33 | } else { |
| 34 | /* Command */ |
| 35 | switch ( data ) { |
| 36 | case 0x38: /* Display off */ |
| 37 | //logerror("display off"); |
| 38 | hd44102ch[which].enabled = 0; |
| 39 | break; |
| 40 | case 0x39: /* Display on */ |
| 41 | //logerror("display on"); |
| 42 | hd44102ch[which].enabled = 1; |
| 43 | break; |
| 44 | case 0x3A: /* Y decrement mode */ |
| 45 | //logerror("y decrement mode"); |
| 46 | hd44102ch[which].y_inc = 0xFF; |
| 47 | break; |
| 48 | case 0x3B: /* Y increment mode */ |
| 49 | //logerror("y increment mode"); |
| 50 | hd44102ch[which].y_inc = 0x01; |
| 51 | break; |
| 52 | case 0x3E: /* Display start page #0 */ |
| 53 | case 0x7E: /* Display start page #1 */ |
| 54 | case 0xBE: /* Display start page #2 */ |
| 55 | case 0xFE: /* Display start page #3 */ |
| 56 | //logerror("set start page %d", data >> 6 ); |
| 57 | hd44102ch[which].start_page = data & 0xC0; |
| 58 | break; |
| 59 | default: |
| 60 | if ( ( data & 0x3F ) < 50 ) { |
| 61 | //logerror("set X/Y address %02X", data ); |
| 62 | hd44102ch[which].address = data; |
| 63 | } |
| 64 | break; |
| 65 | } |
| 66 | } |
| 67 | //logerror("\n"); |
| 68 | } |
| 69 | |
| 70 | static void hd44102ch_init( int which ) { |
| 71 | memset( &hd44102ch[which], 0, sizeof( HD44102CH ) ); |
| 72 | hd44102ch[which].y_inc = 0x01; |
| 73 | } |
| 74 | |
| 75 | static void gamepock_lcd_update(void) { |
| 76 | if ( gamepock_port_a & 0x02 ) { |
| 77 | /* Check whether HD44102CH #1 is enabled */ |
| 78 | if ( gamepock_port_a & 0x08 ) { |
| 79 | hd44102ch_w( 0, gamepock_port_a & 0x04, gamepock_port_b ); |
| 80 | } |
| 81 | |
| 82 | /* Check whether HD44102CH #2 is enabled */ |
| 83 | if ( gamepock_port_a & 0x10 ) { |
| 84 | hd44102ch_w( 1, gamepock_port_a & 0x04, gamepock_port_b ); |
| 85 | } |
| 86 | |
| 87 | /* Check whether HD44102CH #3 is enabled */ |
| 88 | if ( gamepock_port_a & 0x20 ) { |
| 89 | hd44102ch_w( 2, gamepock_port_a & 0x04, gamepock_port_b ); |
| 90 | } |
| 91 | } |
| 92 | } |
| 93 | |
| 94 | WRITE8_HANDLER( gamepock_port_a_w ) { |
| 95 | gamepock_port_a = data; |
| 96 | |
| 97 | gamepock_lcd_update(); |
| 98 | } |
| 99 | |
| 100 | WRITE8_HANDLER( gamepock_port_b_w ) { |
| 101 | gamepock_port_b = data; |
| 102 | |
| 103 | gamepock_lcd_update(); |
| 104 | } |
| 105 | |
| 106 | READ8_HANDLER( gamepock_port_b_r ) { |
| 107 | logerror("gamepock_port_b_r: not implemented\n"); |
| 108 | return 0xFF; |
| 109 | } |
| 110 | |
| 111 | READ8_HANDLER( gamepock_port_c_r ) { |
| 112 | UINT8 data = 0xFF; |
| 113 | |
| 114 | if ( gamepock_port_a & 0x80 ) { |
| 115 | data &= readinputport(0); |
| 116 | } |
| 117 | |
| 118 | if ( gamepock_port_a & 0x40 ) { |
| 119 | data &= readinputport(1); |
| 120 | } |
| 121 | |
| 122 | return data; |
| 123 | } |
| 124 | |
| 125 | MACHINE_RESET( gamepock ) { |
| 126 | hd44102ch_init( 0 ); |
| 127 | hd44102ch_init( 1 ); |
| 128 | hd44102ch_init( 2 ); |
| 129 | } |
| 130 | |
| 131 | VIDEO_UPDATE( gamepock ) { |
| 132 | UINT8 ad; |
| 133 | int i,j; |
| 134 | |
| 135 | /* Handle HD44102CH #0 */ |
| 136 | ad = hd44102ch[0].start_page; |
| 137 | for ( i = 0; i < 4; i++ ) { |
| 138 | for ( j = 0; j < 50; j++ ) { |
| 139 | *BITMAP_ADDR16(bitmap, i * 8 + 0, 49 - j ) = ( hd44102ch[0].ram[ad+j] & 0x01 ) ? machine->pens[0] : machine->pens[1]; |
| 140 | *BITMAP_ADDR16(bitmap, i * 8 + 1, 49 - j ) = ( hd44102ch[0].ram[ad+j] & 0x02 ) ? machine->pens[0] : machine->pens[1]; |
| 141 | *BITMAP_ADDR16(bitmap, i * 8 + 2, 49 - j ) = ( hd44102ch[0].ram[ad+j] & 0x04 ) ? machine->pens[0] : machine->pens[1]; |
| 142 | *BITMAP_ADDR16(bitmap, i * 8 + 3, 49 - j ) = ( hd44102ch[0].ram[ad+j] & 0x08 ) ? machine->pens[0] : machine->pens[1]; |
| 143 | *BITMAP_ADDR16(bitmap, i * 8 + 4, 49 - j ) = ( hd44102ch[0].ram[ad+j] & 0x10 ) ? machine->pens[0] : machine->pens[1]; |
| 144 | *BITMAP_ADDR16(bitmap, i * 8 + 5, 49 - j ) = ( hd44102ch[0].ram[ad+j] & 0x20 ) ? machine->pens[0] : machine->pens[1]; |
| 145 | *BITMAP_ADDR16(bitmap, i * 8 + 6, 49 - j ) = ( hd44102ch[0].ram[ad+j] & 0x40 ) ? machine->pens[0] : machine->pens[1]; |
| 146 | *BITMAP_ADDR16(bitmap, i * 8 + 7, 49 - j ) = ( hd44102ch[0].ram[ad+j] & 0x80 ) ? machine->pens[0] : machine->pens[1]; |
| 147 | } |
| 148 | ad += 0x40; |
| 149 | } |
| 150 | |
| 151 | /* Handle HD44102CH #1 */ |
| 152 | ad = hd44102ch[1].start_page; |
| 153 | for ( i = 4; i < 8; i++ ) { |
| 154 | for ( j = 0; j < 50; j++ ) { |
| 155 | *BITMAP_ADDR16(bitmap, i * 8 + 0, j ) = ( hd44102ch[1].ram[ad+j] & 0x01 ) ? machine->pens[0] : machine->pens[1]; |
| 156 | *BITMAP_ADDR16(bitmap, i * 8 + 1, j ) = ( hd44102ch[1].ram[ad+j] & 0x02 ) ? machine->pens[0] : machine->pens[1]; |
| 157 | *BITMAP_ADDR16(bitmap, i * 8 + 2, j ) = ( hd44102ch[1].ram[ad+j] & 0x04 ) ? machine->pens[0] : machine->pens[1]; |
| 158 | *BITMAP_ADDR16(bitmap, i * 8 + 3, j ) = ( hd44102ch[1].ram[ad+j] & 0x08 ) ? machine->pens[0] : machine->pens[1]; |
| 159 | *BITMAP_ADDR16(bitmap, i * 8 + 4, j ) = ( hd44102ch[1].ram[ad+j] & 0x10 ) ? machine->pens[0] : machine->pens[1]; |
| 160 | *BITMAP_ADDR16(bitmap, i * 8 + 5, j ) = ( hd44102ch[1].ram[ad+j] & 0x20 ) ? machine->pens[0] : machine->pens[1]; |
| 161 | *BITMAP_ADDR16(bitmap, i * 8 + 6, j ) = ( hd44102ch[1].ram[ad+j] & 0x40 ) ? machine->pens[0] : machine->pens[1]; |
| 162 | *BITMAP_ADDR16(bitmap, i * 8 + 7, j ) = ( hd44102ch[1].ram[ad+j] & 0x80 ) ? machine->pens[0] : machine->pens[1]; |
| 163 | } |
| 164 | ad += 0x40; |
| 165 | } |
| 166 | |
| 167 | /* Handle HD44102CH #2 */ |
| 168 | ad = hd44102ch[2].start_page; |
| 169 | for ( i = 0; i < 4; i++ ) { |
| 170 | for ( j = 0; j < 25; j++ ) { |
| 171 | *BITMAP_ADDR16(bitmap, i * 8 + 0, 50 + j ) = ( hd44102ch[2].ram[ad+j] & 0x01 ) ? machine->pens[0] : machine->pens[1]; |
| 172 | *BITMAP_ADDR16(bitmap, i * 8 + 1, 50 + j ) = ( hd44102ch[2].ram[ad+j] & 0x02 ) ? machine->pens[0] : machine->pens[1]; |
| 173 | *BITMAP_ADDR16(bitmap, i * 8 + 2, 50 + j ) = ( hd44102ch[2].ram[ad+j] & 0x04 ) ? machine->pens[0] : machine->pens[1]; |
| 174 | *BITMAP_ADDR16(bitmap, i * 8 + 3, 50 + j ) = ( hd44102ch[2].ram[ad+j] & 0x08 ) ? machine->pens[0] : machine->pens[1]; |
| 175 | *BITMAP_ADDR16(bitmap, i * 8 + 4, 50 + j ) = ( hd44102ch[2].ram[ad+j] & 0x10 ) ? machine->pens[0] : machine->pens[1]; |
| 176 | *BITMAP_ADDR16(bitmap, i * 8 + 5, 50 + j ) = ( hd44102ch[2].ram[ad+j] & 0x20 ) ? machine->pens[0] : machine->pens[1]; |
| 177 | *BITMAP_ADDR16(bitmap, i * 8 + 6, 50 + j ) = ( hd44102ch[2].ram[ad+j] & 0x40 ) ? machine->pens[0] : machine->pens[1]; |
| 178 | *BITMAP_ADDR16(bitmap, i * 8 + 7, 50 + j ) = ( hd44102ch[2].ram[ad+j] & 0x80 ) ? machine->pens[0] : machine->pens[1]; |
| 179 | } |
| 180 | for ( j = 25; j < 50; j++ ) { |
| 181 | *BITMAP_ADDR16(bitmap, 32 + i * 8 + 0, 25 + j ) = ( hd44102ch[2].ram[ad+j] & 0x01 ) ? machine->pens[0] : machine->pens[1]; |
| 182 | *BITMAP_ADDR16(bitmap, 32 + i * 8 + 1, 25 + j ) = ( hd44102ch[2].ram[ad+j] & 0x02 ) ? machine->pens[0] : machine->pens[1]; |
| 183 | *BITMAP_ADDR16(bitmap, 32 + i * 8 + 2, 25 + j ) = ( hd44102ch[2].ram[ad+j] & 0x04 ) ? machine->pens[0] : machine->pens[1]; |
| 184 | *BITMAP_ADDR16(bitmap, 32 + i * 8 + 3, 25 + j ) = ( hd44102ch[2].ram[ad+j] & 0x08 ) ? machine->pens[0] : machine->pens[1]; |
| 185 | *BITMAP_ADDR16(bitmap, 32 + i * 8 + 4, 25 + j ) = ( hd44102ch[2].ram[ad+j] & 0x10 ) ? machine->pens[0] : machine->pens[1]; |
| 186 | *BITMAP_ADDR16(bitmap, 32 + i * 8 + 5, 25 + j ) = ( hd44102ch[2].ram[ad+j] & 0x20 ) ? machine->pens[0] : machine->pens[1]; |
| 187 | *BITMAP_ADDR16(bitmap, 32 + i * 8 + 6, 25 + j ) = ( hd44102ch[2].ram[ad+j] & 0x40 ) ? machine->pens[0] : machine->pens[1]; |
| 188 | *BITMAP_ADDR16(bitmap, 32 + i * 8 + 7, 25 + j ) = ( hd44102ch[2].ram[ad+j] & 0x80 ) ? machine->pens[0] : machine->pens[1]; |
| 189 | } |
| 190 | ad += 0x40; |
| 191 | } |
| 192 | |
| 193 | return 0; |
| 194 | } |
| 195 | |
src/mess/drivers/gamepock.c
| r0 | r1685 | |
| 1 | #include "driver.h" |
| 2 | #include "cpu/upd7810/upd7810.h" |
| 3 | #include "devices/cartslot.h" |
| 4 | #include "includes/gamepock.h" |
| 5 | |
| 6 | static ADDRESS_MAP_START(gamepock_mem, ADDRESS_SPACE_PROGRAM, 8) |
| 7 | ADDRESS_MAP_FLAGS( AMEF_UNMAP(1) ) |
| 8 | AM_RANGE(0x0000,0x0fff) AM_ROM |
| 9 | AM_RANGE(0x1000,0x3fff) AM_NOP |
| 10 | AM_RANGE(0x4000,0xBfff) AM_ROMBANK(1) |
| 11 | AM_RANGE(0xC000,0xC7ff) AM_MIRROR(0x0800) AM_RAM |
| 12 | AM_RANGE(0xff80,0xffff) AM_RAM /* 128 bytes microcontroller RAM */ |
| 13 | ADDRESS_MAP_END |
| 14 | |
| 15 | static ADDRESS_MAP_START(gamepock_io, ADDRESS_SPACE_IO, 8 ) |
| 16 | AM_RANGE( 0x00, 0x00 ) AM_WRITE( gamepock_port_a_w ) |
| 17 | AM_RANGE( 0x01, 0x01 ) AM_READWRITE( gamepock_port_b_r, gamepock_port_b_w ) |
| 18 | AM_RANGE( 0x02, 0x02 ) AM_READ( gamepock_port_c_r ) |
| 19 | ADDRESS_MAP_END |
| 20 | |
| 21 | static INPUT_PORTS_START( gamepock ) |
| 22 | PORT_START |
| 23 | PORT_BIT ( 0x01, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_8WAY |
| 24 | PORT_BIT ( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_8WAY |
| 25 | PORT_BIT ( 0x04, IP_ACTIVE_LOW, IPT_START ) |
| 26 | PORT_BIT ( 0x08, IP_ACTIVE_LOW, IPT_BUTTON1 ) |
| 27 | PORT_BIT ( 0x10, IP_ACTIVE_LOW, IPT_BUTTON2 ) |
| 28 | |
| 29 | PORT_START |
| 30 | PORT_BIT ( 0x01, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_8WAY |
| 31 | PORT_BIT ( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) PORT_8WAY |
| 32 | PORT_BIT ( 0x04, IP_ACTIVE_LOW, IPT_SELECT ) |
| 33 | PORT_BIT ( 0x08, IP_ACTIVE_LOW, IPT_BUTTON3 ) |
| 34 | PORT_BIT ( 0x10, IP_ACTIVE_LOW, IPT_BUTTON4 ) |
| 35 | INPUT_PORTS_END |
| 36 | |
| 37 | static const UPD7810_CONFIG gamepock_cpu_config = { TYPE_78C06, NULL }; |
| 38 | |
| 39 | static MACHINE_DRIVER_START( gamepock ) |
| 40 | MDRV_CPU_ADD_TAG("main", UPD78C06, 6000000) /* uPD78C06AG */ |
| 41 | MDRV_CPU_PROGRAM_MAP( gamepock_mem, 0 ) |
| 42 | MDRV_CPU_IO_MAP( gamepock_io, 0 ) |
| 43 | MDRV_CPU_CONFIG( gamepock_cpu_config ) |
| 44 | |
| 45 | MDRV_MACHINE_RESET( gamepock ) |
| 46 | |
| 47 | MDRV_SCREEN_REFRESH_RATE( 60 ) |
| 48 | MDRV_VIDEO_ATTRIBUTES( VIDEO_TYPE_RASTER ) |
| 49 | MDRV_SCREEN_FORMAT( BITMAP_FORMAT_INDEXED16 ) |
| 50 | MDRV_SCREEN_SIZE( 75, 64 ) |
| 51 | MDRV_SCREEN_VISIBLE_AREA( 0, 74, 0, 63 ) |
| 52 | |
| 53 | MDRV_PALETTE_LENGTH( 2 ) |
| 54 | MDRV_PALETTE_INIT(black_and_white) |
| 55 | MDRV_VIDEO_UPDATE( gamepock ) |
| 56 | |
| 57 | MACHINE_DRIVER_END |
| 58 | |
| 59 | static DEVICE_LOAD(gamepock_cart) { |
| 60 | UINT8 *cart = memory_region( REGION_USER1 ); |
| 61 | int size = image_length( image ); |
| 62 | |
| 63 | if ( image_fread( image, cart, size ) != size ) { |
| 64 | image_seterror( image, IMAGE_ERROR_UNSPECIFIED, "Unable to fully read from file" ); |
| 65 | return INIT_FAIL; |
| 66 | } |
| 67 | |
| 68 | memory_set_bankptr( 1, cart ); |
| 69 | return INIT_PASS; |
| 70 | } |
| 71 | |
| 72 | static void gamepock_cartslot_getinfo(const device_class *devclass, UINT32 state, union devinfo *info) { |
| 73 | switch( state ) { |
| 74 | case DEVINFO_INT_COUNT: info->i = 1; break; |
| 75 | case DEVINFO_INT_MUST_BE_LOADED: info->i = 0; break; |
| 76 | case DEVINFO_PTR_LOAD: info->load = device_load_gamepock_cart; break; |
| 77 | case DEVINFO_STR_FILE_EXTENSIONS: strcpy( info->s = device_temp_str(), "bin" ); break; |
| 78 | default: cartslot_device_getinfo(devclass, state, info); break; |
| 79 | } |
| 80 | } |
| 81 | |
| 82 | SYSTEM_CONFIG_START(gamepock) |
| 83 | CONFIG_DEVICE(gamepock_cartslot_getinfo) |
| 84 | SYSTEM_CONFIG_END |
| 85 | |
| 86 | ROM_START( gamepock ) |
| 87 | ROM_REGION( 0x1000, REGION_CPU1, 0 ) |
| 88 | ROM_LOAD( "egpcboot.bin", 0x0000, 0x1000, CRC(ee1ea65d) SHA1(9c7731b5ead721d2cc7f7e2655c5fed9e56db8b0) ) |
| 89 | ROM_REGION( 0x8000, REGION_USER1, ROMREGION_ERASEFF ) |
| 90 | ROM_END |
| 91 | |
| 92 | CONS( 1984, gamepock, 0, 0, gamepock, gamepock, 0, gamepock, "Epoch", "Game Pocket Computer", 0 ) |
| 93 | |