mirror of
https://github.com/holub/mame
synced 2025-05-12 00:58:53 +03:00
Imported MC6852 SSDA from MESS. (no whatsnew)
This commit is contained in:
parent
5770771c02
commit
21f309929e
2
.gitattributes
vendored
2
.gitattributes
vendored
@ -821,6 +821,8 @@ src/emu/machine/mb87078.c svneol=native#text/plain
|
||||
src/emu/machine/mb87078.h svneol=native#text/plain
|
||||
src/emu/machine/mc146818.c svneol=native#text/plain
|
||||
src/emu/machine/mc146818.h svneol=native#text/plain
|
||||
src/emu/machine/mc6852.c svneol=native#text/plain
|
||||
src/emu/machine/mc6852.h svneol=native#text/plain
|
||||
src/emu/machine/mc68901.c svneol=native#text/plain
|
||||
src/emu/machine/mc68901.h svneol=native#text/plain
|
||||
src/emu/machine/microtch.c svneol=native#text/plain
|
||||
|
@ -188,6 +188,7 @@ EMUMACHINEOBJS = \
|
||||
$(EMUMACHINE)/mb3773.o \
|
||||
$(EMUMACHINE)/mb87078.o \
|
||||
$(EMUMACHINE)/mc146818.o \
|
||||
$(EMUMACHINE)/mc6852.o \
|
||||
$(EMUMACHINE)/mc68901.o \
|
||||
$(EMUMACHINE)/microtch.o \
|
||||
$(EMUMACHINE)/msm6242.o \
|
||||
|
385
src/emu/machine/mc6852.c
Normal file
385
src/emu/machine/mc6852.c
Normal file
@ -0,0 +1,385 @@
|
||||
/**********************************************************************
|
||||
|
||||
Motorola MC6852 Synchronous Serial Data Adapter emulation
|
||||
|
||||
Copyright MESS Team.
|
||||
Visit http://mamedev.org for licensing and usage restrictions.
|
||||
|
||||
**********************************************************************/
|
||||
|
||||
/*
|
||||
|
||||
TODO:
|
||||
|
||||
- FIFO
|
||||
- receive
|
||||
- transmit
|
||||
- parity
|
||||
- 1-sync-character mode
|
||||
- 2-sync-character mode
|
||||
- external sync mode
|
||||
- interrupts
|
||||
|
||||
*/
|
||||
|
||||
#include "emu.h"
|
||||
#include "mc6852.h"
|
||||
#include "machine/devhelpr.h"
|
||||
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// MACROS / CONSTANTS
|
||||
//**************************************************************************
|
||||
|
||||
#define LOG 0
|
||||
|
||||
|
||||
#define S_RDA 0x01
|
||||
#define S_TDRA 0x02
|
||||
#define S_DCD 0x04
|
||||
#define S_CTS 0x08
|
||||
#define S_TUF 0x10
|
||||
#define S_RX_OVRN 0x20
|
||||
#define S_PE 0x40
|
||||
#define S_IRQ 0x80
|
||||
|
||||
|
||||
#define C1_RX_RS 0x01
|
||||
#define C1_TX_RS 0x02
|
||||
#define C1_STRIP_SYNC 0x04
|
||||
#define C1_CLEAR_SYNC 0x08
|
||||
#define C1_TIE 0x10
|
||||
#define C1_RIE 0x20
|
||||
#define C1_AC_MASK 0xc0
|
||||
#define C1_AC_C2 0x00
|
||||
#define C1_AC_C3 0x40
|
||||
#define C1_AC_SYNC 0x80
|
||||
#define C1_AC_TX_FIFO 0xc0
|
||||
|
||||
|
||||
#define C2_PC1 0x01
|
||||
#define C2_PC2 0x02
|
||||
#define C2_1_2_BYTE 0x04
|
||||
#define C2_WS_MASK 0x38
|
||||
#define C2_WS_6_E 0x00
|
||||
#define C2_WS_6_O 0x08
|
||||
#define C2_WS_7 0x10
|
||||
#define C2_WS_8 0x18
|
||||
#define C2_WS_7_E 0x20
|
||||
#define C2_WS_7_O 0x28
|
||||
#define C2_WS_8_E 0x30
|
||||
#define C2_WS_8_O 0x38
|
||||
#define C2_TX_SYNC 0x40
|
||||
#define C2_EIE 0x80
|
||||
|
||||
|
||||
#define C3_E_I_SYNC 0x01
|
||||
#define C3_1_2_SYNC 0x02
|
||||
#define C3_CLEAR_CTS 0x04
|
||||
#define C3_CTUF 0x08
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// GLOBAL VARIABLES
|
||||
//**************************************************************************
|
||||
|
||||
// devices
|
||||
const device_type MC6852 = mc6852_device_config::static_alloc_device_config;
|
||||
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// DEVICE CONFIGURATION
|
||||
//**************************************************************************
|
||||
|
||||
GENERIC_DEVICE_CONFIG_SETUP(mc6852, "MC6852")
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// device_config_complete - perform any
|
||||
// operations now that the configuration is
|
||||
// complete
|
||||
//-------------------------------------------------
|
||||
|
||||
void mc6852_device_config::device_config_complete()
|
||||
{
|
||||
// inherit a copy of the static data
|
||||
const mc6852_interface *intf = reinterpret_cast<const mc6852_interface *>(static_config());
|
||||
if (intf != NULL)
|
||||
*static_cast<mc6852_interface *>(this) = *intf;
|
||||
|
||||
// or initialize to defaults if none provided
|
||||
else
|
||||
{
|
||||
memset(&m_in_rx_data_func, 0, sizeof(m_in_rx_data_func));
|
||||
memset(&m_out_tx_data_func, 0, sizeof(m_out_tx_data_func));
|
||||
memset(&m_out_irq_func, 0, sizeof(m_out_irq_func));
|
||||
memset(&m_in_cts_func, 0, sizeof(m_in_cts_func));
|
||||
memset(&m_in_dcd_func, 0, sizeof(m_in_dcd_func));
|
||||
memset(&m_out_sm_dtr_func, 0, sizeof(m_out_sm_dtr_func));
|
||||
memset(&m_out_tuf_func, 0, sizeof(m_out_tuf_func));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// INLINE HELPERS
|
||||
//**************************************************************************
|
||||
|
||||
inline void mc6852_device::receive()
|
||||
{
|
||||
}
|
||||
|
||||
inline void mc6852_device::transmit()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// LIVE DEVICE
|
||||
//**************************************************************************
|
||||
|
||||
//-------------------------------------------------
|
||||
// mc6852_device - constructor
|
||||
//-------------------------------------------------
|
||||
|
||||
mc6852_device::mc6852_device(running_machine &_machine, const mc6852_device_config &config)
|
||||
: device_t(_machine, config),
|
||||
m_config(config)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// device_start - device-specific startup
|
||||
//-------------------------------------------------
|
||||
|
||||
void mc6852_device::device_start()
|
||||
{
|
||||
// resolve callbacks
|
||||
devcb_resolve_read_line(&m_in_rx_data_func, &m_config.m_in_rx_data_func, this);
|
||||
devcb_resolve_write_line(&m_out_tx_data_func, &m_config.m_out_tx_data_func, this);
|
||||
devcb_resolve_write_line(&m_out_irq_func, &m_config.m_out_irq_func, this);
|
||||
devcb_resolve_read_line(&m_in_cts_func, &m_config.m_in_cts_func, this);
|
||||
devcb_resolve_read_line(&m_in_dcd_func, &m_config.m_in_dcd_func, this);
|
||||
devcb_resolve_write_line(&m_out_sm_dtr_func, &m_config.m_out_sm_dtr_func, this);
|
||||
devcb_resolve_write_line(&m_out_tuf_func, &m_config.m_out_tuf_func, this);
|
||||
|
||||
if (m_config.m_rx_clock > 0)
|
||||
{
|
||||
m_rx_timer = timer_alloc(TIMER_RX);
|
||||
m_rx_timer->adjust(attotime::zero, 0, attotime::from_hz(m_config.m_rx_clock));
|
||||
}
|
||||
|
||||
if (m_config.m_tx_clock > 0)
|
||||
{
|
||||
m_tx_timer = timer_alloc(TIMER_TX);
|
||||
m_tx_timer->adjust(attotime::zero, 0, attotime::from_hz(m_config.m_tx_clock));
|
||||
}
|
||||
|
||||
// register for state saving
|
||||
save_item(NAME(m_status));
|
||||
save_item(NAME(m_cr));
|
||||
save_item(NAME(m_scr));
|
||||
save_item(NAME(m_rx_fifo));
|
||||
save_item(NAME(m_tx_fifo));
|
||||
save_item(NAME(m_tdr));
|
||||
save_item(NAME(m_tsr));
|
||||
save_item(NAME(m_rdr));
|
||||
save_item(NAME(m_rsr));
|
||||
save_item(NAME(m_cts));
|
||||
save_item(NAME(m_dcd));
|
||||
save_item(NAME(m_sm_dtr));
|
||||
save_item(NAME(m_tuf));
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// device_reset - device-specific reset
|
||||
//-------------------------------------------------
|
||||
|
||||
void mc6852_device::device_reset()
|
||||
{
|
||||
/* set receiver shift register to all 1's */
|
||||
m_rsr = 0xff;
|
||||
|
||||
/* reset and inhibit receiver/transmitter sections */
|
||||
m_cr[0] |= (C1_TX_RS | C1_RX_RS);
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// device_timer - handler timer events
|
||||
//-------------------------------------------------
|
||||
|
||||
void mc6852_device::device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr)
|
||||
{
|
||||
switch (id)
|
||||
{
|
||||
case TIMER_RX:
|
||||
receive();
|
||||
break;
|
||||
|
||||
case TIMER_TX:
|
||||
transmit();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// read -
|
||||
//-------------------------------------------------
|
||||
|
||||
READ8_MEMBER( mc6852_device::read )
|
||||
{
|
||||
UINT8 data = 0;
|
||||
|
||||
if (BIT(offset, 0))
|
||||
{
|
||||
/* receive data FIFO */
|
||||
}
|
||||
else
|
||||
{
|
||||
/* status */
|
||||
data = m_status;
|
||||
}
|
||||
|
||||
return data;
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// write -
|
||||
//-------------------------------------------------
|
||||
|
||||
WRITE8_MEMBER( mc6852_device::write )
|
||||
{
|
||||
if (BIT(offset, 0))
|
||||
{
|
||||
switch (m_cr[0] & C1_AC_MASK)
|
||||
{
|
||||
case C1_AC_C2:
|
||||
/* control 2 */
|
||||
m_cr[1] = data;
|
||||
break;
|
||||
|
||||
case C1_AC_C3:
|
||||
/* control 3 */
|
||||
m_cr[2] = data;
|
||||
break;
|
||||
|
||||
case C1_AC_SYNC:
|
||||
/* sync code */
|
||||
m_scr = data;
|
||||
break;
|
||||
|
||||
case C1_AC_TX_FIFO:
|
||||
/* transmit data FIFO */
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* receiver reset */
|
||||
if (data & C1_RX_RS)
|
||||
{
|
||||
/* When Rx Rs is set, it clears the receiver
|
||||
control logic, sync logic, error logic, Rx Data FIFO Control,
|
||||
Parity Error status bit, and DCD interrupt. The Receiver Shift
|
||||
Register is set to ones.
|
||||
*/
|
||||
|
||||
if (LOG) logerror("MC6852 '%s' Receiver Reset\n", tag());
|
||||
|
||||
m_status &= ~(S_RX_OVRN | S_PE | S_DCD | S_RDA);
|
||||
m_rsr = 0xff;
|
||||
}
|
||||
|
||||
/* transmitter reset */
|
||||
if (data & C1_TX_RS)
|
||||
{
|
||||
/* When Tx Rs is set, it clears the transmitter
|
||||
control section, Transmitter Shift Register, Tx Data FIFO
|
||||
Control (the Tx Data FIFO can be reloaded after one E clock
|
||||
pulse), the Transmitter Underflow status bit, and the CTS interrupt,
|
||||
and inhibits the TDRA status bit (in the one-sync-character
|
||||
and two-sync-character modes).*/
|
||||
|
||||
if (LOG) logerror("MC6852 '%s' Transmitter Reset\n", tag());
|
||||
|
||||
m_status &= ~(S_TUF | S_CTS | S_TDRA);
|
||||
}
|
||||
|
||||
if (LOG)
|
||||
{
|
||||
if (data & C1_STRIP_SYNC) logerror("MC6852 '%s' Strip Synchronization Characters\n", tag());
|
||||
if (data & C1_CLEAR_SYNC) logerror("MC6852 '%s' Clear Synchronization\n", tag());
|
||||
}
|
||||
|
||||
m_cr[0] = data;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// rx_clk_w -
|
||||
//-------------------------------------------------
|
||||
|
||||
WRITE_LINE_MEMBER( mc6852_device::rx_clk_w )
|
||||
{
|
||||
if (state) receive();
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// tx_clk_w -
|
||||
//-------------------------------------------------
|
||||
|
||||
WRITE_LINE_MEMBER( mc6852_device::tx_clk_w )
|
||||
{
|
||||
if (state) transmit();
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// cts_w -
|
||||
//-------------------------------------------------
|
||||
|
||||
WRITE_LINE_MEMBER( mc6852_device::cts_w )
|
||||
{
|
||||
m_cts = state;
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// dcd_w -
|
||||
//-------------------------------------------------
|
||||
|
||||
WRITE_LINE_MEMBER( mc6852_device::dcd_w )
|
||||
{
|
||||
m_dcd = state;
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// sm_dtr_r -
|
||||
//-------------------------------------------------
|
||||
|
||||
READ_LINE_MEMBER( mc6852_device::sm_dtr_r )
|
||||
{
|
||||
return m_sm_dtr;
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// tuf_r -
|
||||
//-------------------------------------------------
|
||||
|
||||
READ_LINE_MEMBER( mc6852_device::tuf_r )
|
||||
{
|
||||
return m_tuf;
|
||||
}
|
164
src/emu/machine/mc6852.h
Normal file
164
src/emu/machine/mc6852.h
Normal file
@ -0,0 +1,164 @@
|
||||
/**********************************************************************
|
||||
|
||||
Motorola MC6852 Synchronous Serial Data Adapter emulation
|
||||
|
||||
Copyright MESS Team.
|
||||
Visit http://mamedev.org for licensing and usage restrictions.
|
||||
|
||||
**********************************************************************
|
||||
_____ _____
|
||||
Vss 1 |* \_/ | 24 _CTS
|
||||
Rx DATA 2 | | 23 _DCD
|
||||
Rx CLK 3 | | 22 D0
|
||||
Tx CLK 4 | | 21 D1
|
||||
SM/_DTR 5 | | 20 D2
|
||||
Tx DATA 6 | MC6852 | 19 D3
|
||||
_IRQ 7 | | 18 D4
|
||||
TUF 8 | | 17 D5
|
||||
_RESET 9 | | 16 D6
|
||||
_CS 9 | | 15 D7
|
||||
RS 9 | | 14 E
|
||||
Vcc 10 |_____________| 13 R/_W
|
||||
|
||||
**********************************************************************/
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifndef __MC6852__
|
||||
#define __MC6852__
|
||||
|
||||
#include "emu.h"
|
||||
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// INTERFACE CONFIGURATION MACROS
|
||||
//**************************************************************************
|
||||
|
||||
#define MCFG_MC6852_ADD(_tag, _clock, _config) \
|
||||
MCFG_DEVICE_ADD((_tag), MC6852, _clock) \
|
||||
MCFG_DEVICE_CONFIG(_config)
|
||||
|
||||
#define MC6852_INTERFACE(name) \
|
||||
const mc6852_interface (name) =
|
||||
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// TYPE DEFINITIONS
|
||||
//**************************************************************************
|
||||
|
||||
// ======================> mc6852_interface
|
||||
|
||||
struct mc6852_interface
|
||||
{
|
||||
UINT32 m_rx_clock;
|
||||
UINT32 m_tx_clock;
|
||||
|
||||
devcb_read_line m_in_rx_data_func;
|
||||
devcb_write_line m_out_tx_data_func;
|
||||
|
||||
devcb_write_line m_out_irq_func;
|
||||
|
||||
devcb_read_line m_in_cts_func;
|
||||
devcb_read_line m_in_dcd_func;
|
||||
devcb_write_line m_out_sm_dtr_func;
|
||||
devcb_write_line m_out_tuf_func;
|
||||
};
|
||||
|
||||
|
||||
|
||||
// ======================> mc6852_device_config
|
||||
|
||||
class mc6852_device_config : public device_config,
|
||||
public mc6852_interface
|
||||
{
|
||||
friend class mc6852_device;
|
||||
|
||||
// construction/destruction
|
||||
mc6852_device_config(const machine_config &mconfig, const char *tag, const device_config *owner, UINT32 clock);
|
||||
|
||||
public:
|
||||
// allocators
|
||||
static device_config *static_alloc_device_config(const machine_config &mconfig, const char *tag, const device_config *owner, UINT32 clock);
|
||||
virtual device_t *alloc_device(running_machine &machine) const;
|
||||
|
||||
protected:
|
||||
// device_config overrides
|
||||
virtual void device_config_complete();
|
||||
};
|
||||
|
||||
|
||||
|
||||
// ======================> mc6852_device
|
||||
|
||||
class mc6852_device : public device_t
|
||||
{
|
||||
friend class mc6852_device_config;
|
||||
|
||||
// construction/destruction
|
||||
mc6852_device(running_machine &_machine, const mc6852_device_config &_config);
|
||||
|
||||
public:
|
||||
DECLARE_READ8_MEMBER( read );
|
||||
DECLARE_WRITE8_MEMBER( write );
|
||||
|
||||
DECLARE_WRITE_LINE_MEMBER( rx_clk_w );
|
||||
DECLARE_WRITE_LINE_MEMBER( tx_clk_w );
|
||||
DECLARE_WRITE_LINE_MEMBER( cts_w );
|
||||
DECLARE_WRITE_LINE_MEMBER( dcd_w );
|
||||
|
||||
DECLARE_READ_LINE_MEMBER( sm_dtr_r );
|
||||
DECLARE_READ_LINE_MEMBER( tuf_r );
|
||||
|
||||
protected:
|
||||
// device-level overrides
|
||||
virtual void device_start();
|
||||
virtual void device_reset();
|
||||
virtual void device_timer(emu_timer &timer, device_timer_id id, int m_param, void *ptr);
|
||||
|
||||
private:
|
||||
static const device_timer_id TIMER_RX = 0;
|
||||
static const device_timer_id TIMER_TX = 1;
|
||||
|
||||
inline void receive();
|
||||
inline void transmit();
|
||||
|
||||
devcb_resolved_read_line m_in_rx_data_func;
|
||||
devcb_resolved_write_line m_out_tx_data_func;
|
||||
devcb_resolved_write_line m_out_irq_func;
|
||||
devcb_resolved_read_line m_in_cts_func;
|
||||
devcb_resolved_read_line m_in_dcd_func;
|
||||
devcb_resolved_write_line m_out_sm_dtr_func;
|
||||
devcb_resolved_write_line m_out_tuf_func;
|
||||
|
||||
// registers
|
||||
UINT8 m_status; // status register
|
||||
UINT8 m_cr[3]; // control registers
|
||||
UINT8 m_scr; // sync code register
|
||||
UINT8 m_rx_fifo[3]; // receiver FIFO
|
||||
UINT8 m_tx_fifo[3]; // transmitter FIFO
|
||||
UINT8 m_tdr; // transmit data register
|
||||
UINT8 m_tsr; // transmit shift register
|
||||
UINT8 m_rdr; // receive data register
|
||||
UINT8 m_rsr; // receive shift register
|
||||
|
||||
int m_cts; // clear to send
|
||||
int m_dcd; // data carrier detect
|
||||
int m_sm_dtr; // sync match/data terminal ready
|
||||
int m_tuf; // transmitter underflow
|
||||
|
||||
// timers
|
||||
emu_timer *m_rx_timer;
|
||||
emu_timer *m_tx_timer;
|
||||
|
||||
const mc6852_device_config &m_config;
|
||||
};
|
||||
|
||||
|
||||
// device type definition
|
||||
extern const device_type MC6852;
|
||||
|
||||
|
||||
|
||||
#endif
|
Loading…
Reference in New Issue
Block a user