diff options
Diffstat (limited to 'src/mess/drivers/apricot.c')
-rw-r--r-- | src/mess/drivers/apricot.c | 227 |
1 files changed, 152 insertions, 75 deletions
diff --git a/src/mess/drivers/apricot.c b/src/mess/drivers/apricot.c index 322ddf731c7..943acc251d2 100644 --- a/src/mess/drivers/apricot.c +++ b/src/mess/drivers/apricot.c @@ -9,8 +9,6 @@ ***************************************************************************/ -#include "bus/centronics/ctronics.h" -#include "bus/rs232/rs232.h" #include "cpu/i86/i86.h" #include "cpu/i8089/i8089.h" #include "machine/ram.h" @@ -21,8 +19,12 @@ #include "machine/wd_fdc.h" #include "video/mc6845.h" #include "sound/sn76496.h" +#include "machine/apricotkb_hle.h" #include "imagedev/flopdrv.h" #include "formats/apridisk.h" +#include "bus/centronics/ctronics.h" +#include "bus/rs232/rs232.h" +#include "bus/apricot/expansion.h" //************************************************************************** @@ -35,9 +37,8 @@ public: apricot_state(const machine_config &mconfig, device_type type, const char *tag) : driver_device(mconfig, type, tag), m_cpu(*this, "ic91"), - m_ram(*this, RAM_TAG), m_iop(*this, "ic71"), - m_sn(*this, "ic7"), + m_ram(*this, RAM_TAG), m_crtc(*this, "ic30"), m_ppi(*this, "ic17"), m_pic(*this, "ic31"), @@ -54,13 +55,46 @@ public: m_data_selector_rts(1), m_video_mode(0), m_display_on(1), - m_display_enabled(0) + m_display_enabled(0), + m_centronics_fault(1), + m_centronics_perror(1), + m_bus_locked(0) { } - required_device<cpu_device> m_cpu; - required_device<ram_device> m_ram; + DECLARE_FLOPPY_FORMATS(floppy_formats); + + DECLARE_WRITE_LINE_MEMBER(i8086_lock_w); + DECLARE_WRITE8_MEMBER(i8089_ca1_w); + DECLARE_WRITE8_MEMBER(i8089_ca2_w); + DECLARE_WRITE8_MEMBER(i8255_portb_w); + DECLARE_READ8_MEMBER(i8255_portc_r); + DECLARE_WRITE8_MEMBER(i8255_portc_w); + DECLARE_WRITE_LINE_MEMBER(timer_out1); + DECLARE_WRITE_LINE_MEMBER(timer_out2); + DECLARE_WRITE_LINE_MEMBER(fdc_intrq_w); + DECLARE_READ8_MEMBER(sio_da_r); + DECLARE_READ8_MEMBER(sio_ca_r); + DECLARE_READ8_MEMBER(sio_db_r); + DECLARE_READ8_MEMBER(sio_cb_r); + + DECLARE_WRITE_LINE_MEMBER(write_centronics_fault); + DECLARE_WRITE_LINE_MEMBER(write_centronics_perror); + + DECLARE_WRITE_LINE_MEMBER(apricot_mc6845_de) { m_display_enabled = state; }; + + DECLARE_WRITE_LINE_MEMBER(data_selector_dtr_w) { m_data_selector_dtr = state; }; + DECLARE_WRITE_LINE_MEMBER(data_selector_rts_w) { m_data_selector_rts = state; }; + + MC6845_UPDATE_ROW(crtc_update_row); + UINT32 screen_update_apricot(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect); + +protected: + virtual void machine_start(); + +private: + required_device<i8086_cpu_device> m_cpu; required_device<i8089_device> m_iop; - required_device<sn76489_device> m_sn; + required_device<ram_device> m_ram; required_device<mc6845_device> m_crtc; required_device<i8255_device> m_ppi; required_device<pic8259_device> m_pic; @@ -68,33 +102,12 @@ public: required_device<z80sio0_device> m_sio; required_device<rs232_port_device> m_rs232; required_device<centronics_device> m_centronics; - required_device<wd2793_t> m_fdc; + required_device<wd2797_t> m_fdc; required_device<floppy_connector> m_floppy0; required_device<floppy_connector> m_floppy1; required_device<palette_device> m_palette; required_shared_ptr<UINT16> m_screen_buffer; - DECLARE_WRITE8_MEMBER( i8089_ca1_w ); - DECLARE_WRITE8_MEMBER( i8089_ca2_w ); - DECLARE_WRITE8_MEMBER( i8255_portb_w ); - DECLARE_READ8_MEMBER( i8255_portc_r ); - DECLARE_WRITE8_MEMBER( i8255_portc_w ); - DECLARE_WRITE_LINE_MEMBER( timer_out1 ); - DECLARE_WRITE_LINE_MEMBER( timer_out2 ); - DECLARE_WRITE_LINE_MEMBER( wd2793_intrq_w ); - - DECLARE_WRITE_LINE_MEMBER( write_centronics_fault ); - DECLARE_WRITE_LINE_MEMBER( write_centronics_perror ); - - DECLARE_WRITE_LINE_MEMBER( apricot_mc6845_de ) { m_display_enabled = state; }; - - DECLARE_WRITE_LINE_MEMBER( data_selector_dtr_w ) { m_data_selector_dtr = state; }; - DECLARE_WRITE_LINE_MEMBER( data_selector_rts_w ) { m_data_selector_rts = state; }; - - MC6845_UPDATE_ROW( crtc_update_row ); - - virtual void machine_start(); - int m_data_selector_dtr; int m_data_selector_rts; @@ -103,10 +116,10 @@ public: int m_display_enabled; - UINT32 screen_update_apricot(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect); - int m_centronics_fault; int m_centronics_perror; + + int m_bus_locked; }; @@ -154,15 +167,29 @@ READ8_MEMBER( apricot_state::i8255_portc_r ) WRITE8_MEMBER( apricot_state::i8255_portb_w ) { + // bit 0, crt reset + // bit 1, not connected + m_display_on = BIT(data, 3); m_video_mode = BIT(data, 4); + floppy_image_device *floppy = NULL; + + // bit 5, enable disk select + // bit 6, disk select if (!BIT(data, 5)) - m_fdc->set_floppy(BIT(data, 6) ? m_floppy1->get_device() : m_floppy0->get_device()); + floppy = BIT(data, 6) ? m_floppy1->get_device() : m_floppy0->get_device(); + + m_fdc->set_floppy(floppy); + + // bit 2, head load (motor on is wired to be active once a disk has been inserted) + // we just let the motor run all the time for now + if (floppy) + floppy->mon_w(0); // switch video modes - m_crtc->set_clock( m_video_mode ? XTAL_15MHz / 10 : XTAL_15MHz / 16); - m_crtc->set_hpixels_per_column( m_video_mode ? 10 : 16); + m_crtc->set_clock(m_video_mode ? XTAL_15MHz / 10 : XTAL_15MHz / 16); + m_crtc->set_hpixels_per_column(m_video_mode ? 10 : 16); // PB7 Centronics transceiver direction. 0 = output, 1 = input } @@ -195,19 +222,56 @@ WRITE_LINE_MEMBER( apricot_state::timer_out2 ) } } +READ8_MEMBER( apricot_state::sio_da_r ) +{ + if (m_bus_locked) + return m_sio->m1_r(); + + return m_sio->da_r(space, offset); +} + +READ8_MEMBER( apricot_state::sio_ca_r ) +{ + if (m_bus_locked) + return m_sio->m1_r(); + + return m_sio->ca_r(space, offset); +} + +READ8_MEMBER( apricot_state::sio_cb_r ) +{ + if (m_bus_locked) + return m_sio->m1_r(); + + return m_sio->cb_r(space, offset); +} + +READ8_MEMBER( apricot_state::sio_db_r ) +{ + if (m_bus_locked) + return m_sio->m1_r(); + + return m_sio->db_r(space, offset); +} + + //************************************************************************** // FLOPPY //************************************************************************** -WRITE_LINE_MEMBER( apricot_state::wd2793_intrq_w ) +WRITE_LINE_MEMBER( apricot_state::fdc_intrq_w ) { m_pic->ir4_w(state); m_iop->ext1_w(state); } +FLOPPY_FORMATS_MEMBER( apricot_state::floppy_formats ) + FLOPPY_APRIDISK_FORMAT +FLOPPY_FORMATS_END + static SLOT_INTERFACE_START( apricot_floppies ) - SLOT_INTERFACE( "d31v", SONY_OA_D31V ) - SLOT_INTERFACE( "d32w", SONY_OA_D32W ) + SLOT_INTERFACE("d31v", SONY_OA_D31V) + SLOT_INTERFACE("d32w", SONY_OA_D32W) SLOT_INTERFACE_END @@ -227,36 +291,36 @@ UINT32 apricot_state::screen_update_apricot(screen_device &screen, bitmap_rgb32 MC6845_UPDATE_ROW( apricot_state::crtc_update_row ) { - UINT8 *ram = m_ram->pointer(); const pen_t *pen = m_palette->pens(); - int i, x; - if (m_video_mode) + for (int i = 0; i < x_count; i++) { - // text mode - for (i = 0; i < x_count; i++) + UINT16 code = m_screen_buffer[(ma + i) & 0x7ff]; + UINT16 offset = ((code & 0x7ff) << 5) | (ra << 1); + UINT16 data = m_cpu->space(AS_PROGRAM).read_word(offset); + + if (m_video_mode) { - UINT16 code = m_screen_buffer[(ma + i) & 0x7ff]; - UINT16 offset = ((code & 0x7ff) << 5) | (ra << 1); - UINT16 data = ram[offset + 1] << 8 | ram[offset]; int fill = 0; + if (i == cursor_x) fill = 1; // cursor? if (BIT(code, 12) && BIT(data, 14)) fill = 1; // strike-through? if (BIT(code, 13) && BIT(data, 15)) fill = 1; // underline? // draw 10 pixels of the character - for (x = 0; x <= 10; x++) + for (int x = 0; x <= 10; x++) { int color = fill ? 1 : BIT(data, x); if (BIT(code, 15)) color = !color; // reverse? bitmap.pix32(y, x + i*10) = pen[color ? 1 + BIT(code, 14) : 0]; } } - } - else - { - // graphics mode - fatalerror("Graphics mode not implemented!\n"); + else + { + // draw 16 pixels of the cell + for (int x = 0; x <= 16; x++) + bitmap.pix32(y, x + i*16) = pen[BIT(data, x)]; + } } } @@ -266,13 +330,12 @@ MC6845_UPDATE_ROW( apricot_state::crtc_update_row ) void apricot_state::machine_start() { - // install shared memory to the main cpu and the iop - m_cpu->space(AS_PROGRAM).install_ram(0x00000, m_ram->size() - 1, m_ram->pointer()); - m_iop->space(AS_PROGRAM).install_ram(0x00000, m_ram->size() - 1, m_ram->pointer()); + membank("ram")->set_base(m_ram->pointer()); +} - // motor on is connected to gnd - m_floppy0->get_device()->mon_w(0); - m_floppy1->get_device()->mon_w(0); +WRITE_LINE_MEMBER( apricot_state::i8086_lock_w ) +{ + m_bus_locked = state; } @@ -281,19 +344,21 @@ void apricot_state::machine_start() //************************************************************************** static ADDRESS_MAP_START( apricot_mem, AS_PROGRAM, 16, apricot_state ) -// AM_RANGE(0x00000, 0x3ffff) AM_RAMBANK("standard_ram") -// AM_RANGE(0x40000, 0xeffff) AM_RAMBANK("expansion_ram") + AM_RANGE(0x00000, 0x3ffff) AM_RAMBANK("ram") AM_RANGE(0xf0000, 0xf0fff) AM_MIRROR(0x7000) AM_RAM AM_SHARE("screen_buffer") AM_RANGE(0xfc000, 0xfffff) AM_MIRROR(0x4000) AM_ROM AM_REGION("bootstrap", 0) ADDRESS_MAP_END static ADDRESS_MAP_START( apricot_io, AS_IO, 16, apricot_state ) AM_RANGE(0x00, 0x03) AM_DEVREADWRITE8("ic31", pic8259_device, read, write, 0x00ff) - AM_RANGE(0x40, 0x47) AM_DEVREADWRITE8("ic68", wd2793_t, read, write, 0x00ff) + AM_RANGE(0x40, 0x47) AM_DEVREADWRITE8("ic68", wd2797_t, read, write, 0x00ff) AM_RANGE(0x48, 0x4f) AM_DEVREADWRITE8("ic17", i8255_device, read, write, 0x00ff) AM_RANGE(0x50, 0x51) AM_MIRROR(0x06) AM_DEVWRITE8("ic7", sn76489_device, write, 0x00ff) AM_RANGE(0x58, 0x5f) AM_DEVREADWRITE8("ic16", pit8253_device, read, write, 0x00ff) - AM_RANGE(0x60, 0x67) AM_DEVREADWRITE8("ic15", z80sio0_device, ba_cd_r, ba_cd_w, 0x00ff) + AM_RANGE(0x60, 0x61) AM_READ8(sio_da_r, 0x00ff) AM_DEVWRITE8("ic15", z80sio0_device, da_w, 0x00ff) + AM_RANGE(0x62, 0x63) AM_READ8(sio_ca_r, 0x00ff) AM_DEVWRITE8("ic15", z80sio0_device, ca_w, 0x00ff) + AM_RANGE(0x64, 0x65) AM_READ8(sio_db_r, 0x00ff) AM_DEVWRITE8("ic15", z80sio0_device, db_w, 0x00ff) + AM_RANGE(0x66, 0x67) AM_READ8(sio_cb_r, 0x00ff) AM_DEVWRITE8("ic15", z80sio0_device, cb_w, 0x00ff) AM_RANGE(0x68, 0x69) AM_MIRROR(0x04) AM_DEVWRITE8("ic30", mc6845_device, address_w, 0x00ff) AM_RANGE(0x6a, 0x6b) AM_MIRROR(0x04) AM_DEVREADWRITE8("ic30", mc6845_device, register_r, register_w, 0x00ff) AM_RANGE(0x70, 0x71) AM_MIRROR(0x04) AM_WRITE8(i8089_ca1_w, 0x00ff) @@ -312,6 +377,7 @@ static MACHINE_CONFIG_START( apricot, apricot_state ) MCFG_CPU_PROGRAM_MAP(apricot_mem) MCFG_CPU_IO_MAP(apricot_io) MCFG_CPU_IRQ_ACKNOWLEDGE_DEVICE("ic31", pic8259_device, inta_cb) + MCFG_I8086_LOCK_HANDLER(WRITELINE(apricot_state, i8086_lock_w)) // i/o cpu MCFG_CPU_ADD("ic71", I8089, XTAL_15MHz / 3) @@ -321,6 +387,10 @@ static MACHINE_CONFIG_START( apricot, apricot_state ) MCFG_I8089_SINTR1(DEVWRITELINE("ic31", pic8259_device, ir0_w)) MCFG_I8089_SINTR2(DEVWRITELINE("ic31", pic8259_device, ir1_w)) + // ram + MCFG_RAM_ADD(RAM_TAG) + MCFG_RAM_DEFAULT_SIZE("256k") + // video hardware MCFG_SCREEN_ADD("screen", RASTER) MCFG_SCREEN_SIZE(800, 400) @@ -331,6 +401,7 @@ static MACHINE_CONFIG_START( apricot, apricot_state ) MCFG_PALETTE_ADD_MONOCHROME_GREEN_HIGHLIGHT("palette") MCFG_MC6845_ADD("ic30", MC6845, "screen", XTAL_15MHz / 10) + MCFG_MC6845_INTERLACE_ADJUST(1) MCFG_MC6845_SHOW_BORDER_AREA(false) MCFG_MC6845_CHAR_WIDTH(10) MCFG_MC6845_UPDATE_ROW_CB(apricot_state, crtc_update_row) @@ -341,11 +412,6 @@ static MACHINE_CONFIG_START( apricot, apricot_state ) MCFG_SOUND_ADD("ic7", SN76489, XTAL_4MHz / 2) MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 1.0) - // internal ram - MCFG_RAM_ADD(RAM_TAG) - MCFG_RAM_DEFAULT_SIZE("256k") - MCFG_RAM_EXTRA_OPTIONS("384k,512k") // with 1 or 2 128k expansion boards - // devices MCFG_DEVICE_ADD("ic17", I8255A, 0) MCFG_I8255_IN_PORTA_CB(DEVREAD8("cent_data_in", input_buffer_device, read)) @@ -369,6 +435,7 @@ static MACHINE_CONFIG_START( apricot, apricot_state ) MCFG_Z80DART_OUT_DTRA_CB(DEVWRITELINE("rs232", rs232_port_device, write_dtr)) MCFG_Z80DART_OUT_RTSA_CB(DEVWRITELINE("rs232", rs232_port_device, write_rts)) MCFG_Z80DART_OUT_WRDYA_CB(DEVWRITELINE("ic71", i8089_device, drq2_w)) + MCFG_Z80DART_OUT_TXDB_CB(DEVWRITELINE("keyboard", apricot_keyboard_hle_device, rxd_w)) MCFG_Z80DART_OUT_DTRB_CB(WRITELINE(apricot_state, data_selector_dtr_w)) MCFG_Z80DART_OUT_RTSB_CB(WRITELINE(apricot_state, data_selector_rts_w)) MCFG_Z80DART_OUT_INT_CB(DEVWRITELINE("ic31", pic8259_device, ir5_w)) @@ -377,10 +444,14 @@ static MACHINE_CONFIG_START( apricot, apricot_state ) MCFG_RS232_PORT_ADD("rs232", default_rs232_devices, NULL) // note: missing a receive clock callback to support external clock mode // (m_data_selector_rts == 1 and m_data_selector_dtr == 0) - MCFG_RS232_RXD_HANDLER(DEVWRITELINE("ic15", z80dart_device, rxa_w)) - MCFG_RS232_DCD_HANDLER(DEVWRITELINE("ic15", z80dart_device, dcda_w)) - MCFG_RS232_DSR_HANDLER(DEVWRITELINE("ic15", z80dart_device, synca_w)) - MCFG_RS232_CTS_HANDLER(DEVWRITELINE("ic15", z80dart_device, ctsa_w)) + MCFG_RS232_RXD_HANDLER(DEVWRITELINE("ic15", z80sio0_device, rxa_w)) + MCFG_RS232_DCD_HANDLER(DEVWRITELINE("ic15", z80sio0_device, dcda_w)) + MCFG_RS232_DSR_HANDLER(DEVWRITELINE("ic15", z80sio0_device, synca_w)) + MCFG_RS232_CTS_HANDLER(DEVWRITELINE("ic15", z80sio0_device, ctsa_w)) + + // keyboard (hle) + MCFG_APRICOT_KEYBOARD_ADD("keyboard") + MCFG_APRICOT_KEYBOARD_TXD_HANDLER(DEVWRITELINE("ic15", z80sio0_device, rxb_w)) // centronics printer MCFG_CENTRONICS_ADD("centronics", centronics_devices, "printer") @@ -395,11 +466,17 @@ static MACHINE_CONFIG_START( apricot, apricot_state ) MCFG_CENTRONICS_OUTPUT_LATCH_ADD("cent_data_out", "centronics") // floppy - MCFG_WD2793x_ADD("ic68", XTAL_4MHz / 2) - MCFG_WD_FDC_INTRQ_CALLBACK(WRITELINE(apricot_state, wd2793_intrq_w)) + MCFG_WD2797_ADD("ic68", XTAL_4MHz / 2) + MCFG_WD_FDC_INTRQ_CALLBACK(WRITELINE(apricot_state, fdc_intrq_w)) MCFG_WD_FDC_DRQ_CALLBACK(DEVWRITELINE("ic71", i8089_device, drq1_w)) - MCFG_FLOPPY_DRIVE_ADD("ic68:0", apricot_floppies, "d32w", floppy_image_device::default_floppy_formats) - MCFG_FLOPPY_DRIVE_ADD("ic68:1", apricot_floppies, "d32w", floppy_image_device::default_floppy_formats) + MCFG_FLOPPY_DRIVE_ADD("ic68:0", apricot_floppies, "d32w", apricot_state::floppy_formats) + MCFG_FLOPPY_DRIVE_ADD("ic68:1", apricot_floppies, "d32w", apricot_state::floppy_formats) + + // expansion bus + MCFG_EXPANSION_ADD("exp", "ic91") + MCFG_EXPANSION_IOP_ADD("ic71") + MCFG_EXPANSION_SLOT_ADD("exp:1", apricot_expansion_cards, NULL) + MCFG_EXPANSION_SLOT_ADD("exp:2", apricot_expansion_cards, NULL) MACHINE_CONFIG_END static MACHINE_CONFIG_DERIVED( apricotxi, apricot ) |