hitachi/b16.cpp: hookup PIT and PICs

This commit is contained in:
angelosa 2024-09-21 23:11:09 +02:00
parent 882c8bca03
commit 7eabbf19fd

View File

@ -6,8 +6,12 @@
Hitachi B(asic Master?) 16000 series?
TODO:
- Barely anything is known about the HW
- b16ex2: "error message 1101"
- Barely anything is known about the HW;
- Requires a system disk to make it go further;
- b16ex2: "error message 1101", bypassed between ports $80 and $48
- b16ex2: prints gibberish before the "insert disk" screen, uses $b4000 for the upper tile bank
in an unidentified kanji format (so bit 7 high for lr, then low)
\- 0x2517 - 0x2519 - 0x2526 - 0x2d00 - 0x254f - 0x26b0 - 0x23e6
===================================================================================================
@ -36,6 +40,11 @@ Several connectors scattered across the board
Centronics port CN9, Serial port CN8
2 empty sockets for CN10 / CN11 (DE-9 options?)
===================================================================================================
Error codes (TODO: RE them all)
0301 PIT failure
1101 b16ex2 bus config error?
**************************************************************************************************/
@ -43,6 +52,8 @@ Centronics port CN9, Serial port CN8
#include "cpu/i86/i86.h"
#include "cpu/i86/i286.h"
#include "machine/am9517a.h"
#include "machine/pic8259.h"
#include "machine/pit8253.h"
#include "video/mc6845.h"
#include "emupal.h"
#include "screen.h"
@ -56,9 +67,12 @@ public:
b16_state(const machine_config &mconfig, device_type type, const char *tag)
: driver_device(mconfig, type, tag)
, m_maincpu(*this, "maincpu")
, m_pit(*this, "pit")
, m_intm(*this, "intm")
, m_ints(*this, "ints")
, m_vram(*this, "vram")
, m_mc6845(*this, "crtc")
, m_dma8237(*this, "8237dma")
, m_crtc(*this, "crtc")
, m_dma(*this, "8237dma")
, m_gfxdecode(*this, "gfxdecode")
, m_palette(*this, "palette")
, m_char_rom(*this, "pcg")
@ -77,19 +91,19 @@ private:
uint8_t m_crtc_vreg[0x100]{}, m_crtc_index = 0;
required_device<cpu_device> m_maincpu;
required_device<pit8253_device> m_pit;
required_device<pic8259_device> m_intm;
required_device<pic8259_device> m_ints;
required_shared_ptr<uint16_t> m_vram;
required_device<mc6845_device> m_mc6845;
required_device<am9517a_device> m_dma8237;
required_device<mc6845_device> m_crtc;
required_device<am9517a_device> m_dma;
required_device<gfxdecode_device> m_gfxdecode;
required_device<palette_device> m_palette;
required_region_ptr<uint8_t> m_char_rom;
uint16_t vblank_r();
void b16_pcg_w(offs_t offset, uint8_t data);
void b16_6845_address_w(uint8_t data);
void b16_6845_data_w(uint8_t data);
uint8_t unk_dev_r(offs_t offset);
void unk_dev_w(offs_t offset, uint8_t data);
void pcg_w(offs_t offset, uint8_t data);
void crtc_address_w(uint8_t data);
void crtc_data_w(uint8_t data);
uint8_t memory_read_byte(offs_t offset);
void memory_write_byte(offs_t offset, uint8_t data);
@ -146,7 +160,7 @@ uint32_t b16_state::screen_update(screen_device &screen, bitmap_ind16 &bitmap, c
return 0;
}
void b16_state::b16_pcg_w(offs_t offset, uint8_t data)
void b16_state::pcg_w(offs_t offset, uint8_t data)
{
m_char_rom[offset] = data;
@ -158,116 +172,50 @@ void b16_state::b16_map(address_map &map)
map.unmap_value_high();
map(0x00000, 0x9ffff).ram(); // probably not all of it.
map(0xa0000, 0xaffff).ram(); // bitmap?
map(0xb0000, 0xb7fff).ram().share("vram"); // tvram
map(0xb8000, 0xbbfff).w(FUNC(b16_state::b16_pcg_w)).umask16(0x00ff); // pcg
map(0xb0000, 0xb7fff).ram().share("vram");
map(0xb8000, 0xbbfff).w(FUNC(b16_state::pcg_w)).umask16(0x00ff); // pcg
map(0xfc000, 0xfffff).rom().region("ipl", 0);
}
void b16_state::b16ex2_map(address_map &map)
{
b16_state::b16_map(map);
// map(0x0e****) bus slot ROM?
map(0x0f8000, 0x0fffff).rom().region("ipl", 0);
map(0xff8000, 0xffffff).rom().region("ipl", 0);
}
uint16_t b16_state::vblank_r()
{
return ioport("SYSTEM")->read();
}
void b16_state::b16_6845_address_w(uint8_t data)
void b16_state::crtc_address_w(uint8_t data)
{
m_crtc_index = data;
m_mc6845->address_w(data);
m_crtc->address_w(data);
}
void b16_state::b16_6845_data_w(uint8_t data)
void b16_state::crtc_data_w(uint8_t data)
{
m_crtc_vreg[m_crtc_index] = data;
m_mc6845->register_w(data);
}
/*
Pretty weird protocol, dunno what it is ...
8a (06) W
(04) R
ff (04) W
(04) R
ff (04) W
36 (0e) W
ff (08) W
ff (08) W
06 (0e) W
(08) R
(08) R
36 (0e) W
40 (08) W
9c (08) W
76 (0e) W
ff (0a) W
ff (0a) W
46 (0e) W
(0a) R
(0a) R
76 (0e) W
1a (0a) W
00 (0a) W
b6 (0e) W
ff (0c) W
ff (0c) W
86 (0e) W
(0c) R
(0c) R
b6 (0e) W
34 (0c) W
00 (0c) W
36 (0e) W
b6 (0e) W
40 (08) W
9c (08) W
34 (0c) W
00 (0c) W
8a (06) W
06 (06) W
05 (06) W
*/
uint8_t b16_state::unk_dev_r(offs_t offset)
{
static int test;
printf("(%02x) R\n",offset << 1);
if(offset == 0x8/2 || offset == 0x0a/2 || offset == 0x0c/2) // quick hack
{
test^=1;
return test ? 0x9f : 0x92;
}
return 0xff;
}
void b16_state::unk_dev_w(offs_t offset, uint8_t data)
{
printf("%02x (%02x) W\n",data,offset << 1);
m_crtc->register_w(data);
}
void b16_state::b16_io(address_map &map)
{
map.unmap_value_high();
map(0x00, 0x0f).rw(FUNC(b16_state::unk_dev_r), FUNC(b16_state::unk_dev_w)).umask16(0x00ff); // DMA device?
map(0x20, 0x20).w(FUNC(b16_state::b16_6845_address_w));
map(0x22, 0x22).w(FUNC(b16_state::b16_6845_data_w));
// map(0x00, 0x07).umask16(0x00ff); // DMA device? PIT mirror?
map(0x08, 0x0f).rw(m_pit, FUNC(pit8253_device::read), FUNC(pit8253_device::write)).umask16(0x00ff);
map(0x10, 0x13).rw(m_intm, FUNC(pic8259_device::read), FUNC(pic8259_device::write)).umask16(0x00ff);
map(0x18, 0x1b).rw(m_ints, FUNC(pic8259_device::read), FUNC(pic8259_device::write)).umask16(0x00ff);
map(0x20, 0x20).w(FUNC(b16_state::crtc_address_w));
map(0x22, 0x22).w(FUNC(b16_state::crtc_data_w));
// b16ex2: jumps to $e0000 if bit 7 high
map(0x48, 0x48).lr8(NAME([] () { return 0; }));
//0x79 bit 0 DSW?
map(0x80, 0x81).r(FUNC(b16_state::vblank_r)); // TODO
map(0x80, 0x81).portr("SYSTEM");
}
/* Input ports */
static INPUT_PORTS_START( b16 )
PORT_START("SYSTEM")
PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_VBLANK("screen")
PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_VBLANK("screen")
INPUT_PORTS_END
@ -308,8 +256,27 @@ void b16_state::b16(machine_config &config)
I8086(config, m_maincpu, XTAL(14'318'181)/2); // unknown xtal, should be 8088 for base machine?
m_maincpu->set_addrmap(AS_PROGRAM, &b16_state::b16_map);
m_maincpu->set_addrmap(AS_IO, &b16_state::b16_io);
m_maincpu->set_irq_acknowledge_callback(m_intm, FUNC(pic8259_device::inta_cb));
PIT8253(config, m_pit);
// TODO: unconfirmed, just enough to make it surpass POST checks
m_pit->set_clk<0>(XTAL(14'318'181) / 8);
// m_pit->out_handler<0>()
m_pit->set_clk<1>(XTAL(14'318'181) / 4);
// m_pit->out_handler<1>()
m_pit->set_clk<2>(XTAL(14'318'181) / 4);
// m_pit->out_handler<2>()
// TODO: wrong type
AM9517A(config, m_dma, XTAL(14'318'181)/2);
m_dma->in_memr_callback().set(FUNC(b16_state::memory_read_byte));
m_dma->out_memw_callback().set(FUNC(b16_state::memory_write_byte));
MC6845(config, m_crtc, XTAL(14'318'181)/5); /* unknown variant, unknown clock, hand tuned to get ~60 fps */
m_crtc->set_screen("screen");
m_crtc->set_show_border_area(false);
m_crtc->set_char_width(8);
/* video hardware */
screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_RASTER));
screen.set_refresh_hz(60);
screen.set_vblank_time(ATTOSECONDS_IN_USEC(2500)); /* not accurate */
@ -318,18 +285,18 @@ void b16_state::b16(machine_config &config)
screen.set_visarea_full();
screen.set_palette(m_palette);
MC6845(config, m_mc6845, XTAL(14'318'181)/5); /* unknown variant, unknown clock, hand tuned to get ~60 fps */
m_mc6845->set_screen("screen");
m_mc6845->set_show_border_area(false);
m_mc6845->set_char_width(8);
PIC8259(config, m_intm);
m_intm->out_int_callback().set_inputline(m_maincpu, 0);
m_intm->in_sp_callback().set_constant(1);
// m_intm->read_slave_ack_callback()
AM9517A(config, m_dma8237, XTAL(14'318'181)/2);
m_dma8237->in_memr_callback().set(FUNC(b16_state::memory_read_byte));
m_dma8237->out_memw_callback().set(FUNC(b16_state::memory_write_byte));
PIC8259(config, m_ints, 0);
// m_ints->out_int_callback().set(m_intm, FUNC(pic8259_device::ir?_w));
m_ints->in_sp_callback().set_constant(0);
GFXDECODE(config, m_gfxdecode, m_palette, gfx_b16);
PALETTE(config, m_palette).set_entries(8);
// MCFG_PALETTE_INIT_STANDARD(black_and_white) // TODO
// TODO: palette format is a guess
PALETTE(config, m_palette, palette_device::BRG_3BIT).set_entries(8);
}
void b16_state::b16ex2(machine_config &config)
@ -338,6 +305,14 @@ void b16_state::b16ex2(machine_config &config)
I80286(config.replace(), m_maincpu, XTAL(16'000'000) / 2); // A80286-8 / S
m_maincpu->set_addrmap(AS_PROGRAM, &b16_state::b16ex2_map);
m_maincpu->set_addrmap(AS_IO, &b16_state::b16_io);
// TODO: as above
m_pit->set_clk<0>(XTAL(16'000'000) / 4);
// m_pit->out_handler<0>()
m_pit->set_clk<1>(XTAL(16'000'000) / 4);
// m_pit->out_handler<1>()
m_pit->set_clk<2>(XTAL(16'000'000) / 2);
// m_pit->out_handler<2>()
}