mirror of
https://github.com/holub/mame
synced 2025-04-17 22:13:04 +03:00
cpu/tlcs900: Added the TMP94C241 variant (used by the Technics SX-KN5000). (#13220)
matsushita/kn5000.cpp: Use TMP94C241 CPU, hooked up I/O to onboard CPU peripherals.
This commit is contained in:
parent
803b85fb0f
commit
2905f85348
@ -2982,6 +2982,8 @@ if CPUS["TLCS900"] then
|
||||
MAME_DIR .. "src/devices/cpu/tlcs900/tlcs900.h",
|
||||
MAME_DIR .. "src/devices/cpu/tlcs900/900tbl.hxx",
|
||||
MAME_DIR .. "src/devices/cpu/tlcs900/900htbl.hxx",
|
||||
MAME_DIR .. "src/devices/cpu/tlcs900/tmp94c241.cpp",
|
||||
MAME_DIR .. "src/devices/cpu/tlcs900/tmp94c241.h",
|
||||
MAME_DIR .. "src/devices/cpu/tlcs900/tmp95c061.cpp",
|
||||
MAME_DIR .. "src/devices/cpu/tlcs900/tmp95c061.h",
|
||||
MAME_DIR .. "src/devices/cpu/tlcs900/tmp95c063.cpp",
|
||||
|
@ -138,7 +138,7 @@ void tlcs900_device::device_start()
|
||||
save_item( NAME(m_dmac) );
|
||||
save_item( NAME(m_dmam) );
|
||||
save_item( NAME(m_timer_pre) );
|
||||
save_item( NAME(m_timer) );
|
||||
save_item( NAME(m_timer_8) );
|
||||
save_item( NAME(m_timer_change) );
|
||||
save_item( NAME(m_level) );
|
||||
save_item( NAME(m_check_irqs) );
|
||||
|
@ -20,6 +20,9 @@ enum tlcs900_inputs
|
||||
TLCS900_INT6,
|
||||
TLCS900_INT7,
|
||||
TLCS900_INT8,
|
||||
TLCS900_INT9,
|
||||
TLCS900_INTA,
|
||||
TLCS900_INTB,
|
||||
TLCS900_TIO,
|
||||
TLCS900_NUM_INPUTS
|
||||
};
|
||||
@ -102,8 +105,8 @@ protected:
|
||||
|
||||
/* Internal timers, irqs, etc */
|
||||
uint32_t m_timer_pre;
|
||||
uint8_t m_timer[6];
|
||||
int m_timer_change[4];
|
||||
uint8_t m_timer_8[6];
|
||||
int m_timer_change[8];
|
||||
bool m_prefetch_clear;
|
||||
uint8_t m_prefetch_index;
|
||||
uint8_t m_prefetch[4];
|
||||
|
1332
src/devices/cpu/tlcs900/tmp94c241.cpp
Normal file
1332
src/devices/cpu/tlcs900/tmp94c241.cpp
Normal file
File diff suppressed because it is too large
Load Diff
279
src/devices/cpu/tlcs900/tmp94c241.h
Normal file
279
src/devices/cpu/tlcs900/tmp94c241.h
Normal file
@ -0,0 +1,279 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:AJR,Felipe Sanches
|
||||
/****************************************************************************
|
||||
|
||||
Toshiba TMP94C241 microcontroller
|
||||
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef MAME_CPU_TLCS900_TMP94C241_H
|
||||
#define MAME_CPU_TLCS900_TMP94C241_H
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "tlcs900.h"
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// TYPE DEFINITIONS
|
||||
//**************************************************************************
|
||||
|
||||
// ======================> tmp94c241_device
|
||||
|
||||
class tmp94c241_device : public tlcs900h_device
|
||||
{
|
||||
static constexpr uint8_t PORT_0 = 0; // 8 bit I/O. Shared with d0-d7
|
||||
static constexpr uint8_t PORT_1 = 1; // 8 bit I/O. Shared with d8-d15
|
||||
static constexpr uint8_t PORT_2 = 2; // 8 bit I/O. Shared with d16-d23
|
||||
static constexpr uint8_t PORT_3 = 3; // 8 bit I/O. Shared with d24-d31
|
||||
static constexpr uint8_t PORT_4 = 4; // 8 bit I/O. Shared with a0-a7
|
||||
static constexpr uint8_t PORT_5 = 5; // 8 bit I/O. Shared with a8-a15
|
||||
static constexpr uint8_t PORT_6 = 6; // 8 bit I/O. Shared with a16-a23
|
||||
static constexpr uint8_t PORT_7 = 7; // 8 bit I/O. Shared with external memory & bus signals
|
||||
static constexpr uint8_t PORT_8 = 8; // 7 bit I/O. Shared with chip-select signals
|
||||
static constexpr uint8_t PORT_A = 9; // 5 bit I/O. Shared with external DRAM (channel 0)
|
||||
static constexpr uint8_t PORT_B = 10; // 5 bit I/O. Shared with external DRAM (channel 1)
|
||||
static constexpr uint8_t PORT_C = 11; // 2 bit I/O. Shared with outputs for 8-bit or 16-bit timers
|
||||
static constexpr uint8_t PORT_D = 12; // 6 bit I/O. Shared with 16-bit timer I/O and interrupt input
|
||||
static constexpr uint8_t PORT_E = 13; // 6 bit I/O. Shared with 8-bit or 16-bit timer output and interrupt input
|
||||
static constexpr uint8_t PORT_F = 14; // 6 bit I/O. Shared with I/O functions of serial interface
|
||||
static constexpr uint8_t PORT_G = 15; // 8 bit input-only. Shared with AD converter.
|
||||
static constexpr uint8_t PORT_H = 16; // 5 bit I/O. Shared with /INT0 and micro DMA
|
||||
static constexpr uint8_t PORT_Z = 17; // 8 bit I/O.
|
||||
static constexpr uint8_t NUM_PORTS = 18;
|
||||
|
||||
static constexpr uint8_t TREG0 = 0;
|
||||
static constexpr uint8_t TREG1 = 1;
|
||||
static constexpr uint8_t TREG2 = 2;
|
||||
static constexpr uint8_t TREG3 = 3;
|
||||
static constexpr uint8_t TREG4 = 0;
|
||||
static constexpr uint8_t TREG5 = 1;
|
||||
static constexpr uint8_t TREG6 = 2;
|
||||
static constexpr uint8_t TREG7 = 3;
|
||||
static constexpr uint8_t TREG8 = 4;
|
||||
static constexpr uint8_t TREG9 = 5;
|
||||
static constexpr uint8_t TREGA = 6;
|
||||
static constexpr uint8_t TREGB = 7;
|
||||
|
||||
static constexpr uint8_t CAP4 = 0;
|
||||
static constexpr uint8_t CAP5 = 1;
|
||||
static constexpr uint8_t CAP6 = 2;
|
||||
static constexpr uint8_t CAP7 = 3;
|
||||
static constexpr uint8_t CAP8 = 4;
|
||||
static constexpr uint8_t CAP9 = 5;
|
||||
static constexpr uint8_t CAPA = 6;
|
||||
static constexpr uint8_t CAPB = 7;
|
||||
|
||||
public:
|
||||
// device type constructor
|
||||
tmp94c241_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock);
|
||||
|
||||
// configuration helpers
|
||||
auto port0_read() { return m_port_read[PORT_0].bind(); }
|
||||
auto port0_write() { return m_port_write[PORT_0].bind(); }
|
||||
auto port1_read() { return m_port_read[PORT_1].bind(); }
|
||||
auto port1_write() { return m_port_write[PORT_1].bind(); }
|
||||
auto port2_read() { return m_port_read[PORT_2].bind(); }
|
||||
auto port2_write() { return m_port_write[PORT_2].bind(); }
|
||||
auto port3_read() { return m_port_read[PORT_3].bind(); }
|
||||
auto port3_write() { return m_port_write[PORT_3].bind(); }
|
||||
auto port4_read() { return m_port_read[PORT_4].bind(); }
|
||||
auto port4_write() { return m_port_write[PORT_4].bind(); }
|
||||
auto port5_read() { return m_port_read[PORT_5].bind(); }
|
||||
auto port5_write() { return m_port_write[PORT_5].bind(); }
|
||||
auto port6_read() { return m_port_read[PORT_6].bind(); }
|
||||
auto port6_write() { return m_port_write[PORT_6].bind(); }
|
||||
auto port7_read() { return m_port_read[PORT_7].bind(); }
|
||||
auto port7_write() { return m_port_write[PORT_7].bind(); }
|
||||
auto port8_read() { return m_port_read[PORT_8].bind(); }
|
||||
auto port8_write() { return m_port_write[PORT_8].bind(); }
|
||||
auto porta_read() { return m_port_read[PORT_A].bind(); }
|
||||
auto porta_write() { return m_port_write[PORT_A].bind(); }
|
||||
auto portb_read() { return m_port_read[PORT_B].bind(); }
|
||||
auto portb_write() { return m_port_write[PORT_B].bind(); }
|
||||
auto portc_read() { return m_port_read[PORT_C].bind(); }
|
||||
auto portc_write() { return m_port_write[PORT_C].bind(); }
|
||||
auto portd_read() { return m_port_read[PORT_D].bind(); }
|
||||
auto portd_write() { return m_port_write[PORT_D].bind(); }
|
||||
auto porte_read() { return m_port_read[PORT_E].bind(); }
|
||||
auto porte_write() { return m_port_write[PORT_E].bind(); }
|
||||
auto portf_read() { return m_port_read[PORT_F].bind(); }
|
||||
auto portf_write() { return m_port_write[PORT_F].bind(); }
|
||||
auto portg_read() { return m_port_read[PORT_G].bind(); }
|
||||
auto porth_read() { return m_port_read[PORT_H].bind(); }
|
||||
auto porth_write() { return m_port_write[PORT_H].bind(); }
|
||||
auto portz_read() { return m_port_read[PORT_Z].bind(); }
|
||||
auto portz_write() { return m_port_write[PORT_Z].bind(); }
|
||||
|
||||
protected:
|
||||
// device_t implementation
|
||||
virtual void device_config_complete() override ATTR_COLD;
|
||||
virtual void device_resolve_objects() override ATTR_COLD;
|
||||
virtual void device_start() override ATTR_COLD;
|
||||
virtual void device_reset() override ATTR_COLD;
|
||||
|
||||
// device_execute_interface overrides
|
||||
virtual void execute_set_input(int inputnum, int state) override;
|
||||
|
||||
// tlcs900_device overrides
|
||||
virtual void tlcs900_check_hdma() override;
|
||||
virtual void tlcs900_check_irqs() override;
|
||||
virtual void tlcs900_handle_ad() override;
|
||||
virtual void tlcs900_handle_timers() override;
|
||||
|
||||
// device_disasm_interface overrides
|
||||
virtual std::unique_ptr<util::disasm_interface> create_disassembler() override;
|
||||
|
||||
private:
|
||||
void change_timer_flipflop(uint8_t flipflop, uint8_t operation);
|
||||
|
||||
// Ports
|
||||
template <uint8_t P> uint8_t port_r();
|
||||
template <uint8_t P> void port_w(uint8_t data);
|
||||
template <uint8_t P> void port_cr_w(uint8_t data);
|
||||
template <uint8_t P> void port_fc_w(uint8_t data);
|
||||
|
||||
// Special Function Registers
|
||||
template <uint8_t N> void bNcs_w(offs_t offset, uint16_t data, uint16_t mem_mask);
|
||||
template <uint8_t Timer> uint16_t cap_r();
|
||||
template <uint8_t N> uint8_t mamr_r();
|
||||
template <uint8_t N> void mamr_w(uint8_t data);
|
||||
template <uint8_t N> uint8_t msar_r();
|
||||
template <uint8_t N> void msar_w(uint8_t data);
|
||||
template <uint8_t Timer> void treg_8_w(uint8_t data);
|
||||
template <uint8_t Timer> void treg_16_w(uint16_t data);
|
||||
template <uint8_t Channel> uint8_t scNbuf_r();
|
||||
template <uint8_t Channel> void scNbuf_w(uint8_t data);
|
||||
template <uint8_t Channel> uint8_t scNcr_r();
|
||||
template <uint8_t Channel> void scNcr_w(uint8_t data);
|
||||
template <uint8_t Channel> uint8_t scNmod_r();
|
||||
template <uint8_t Channel> void scNmod_w(uint8_t data);
|
||||
template <uint8_t Channel> uint8_t brNcr_r();
|
||||
template <uint8_t Channel> void brNcr_w(uint8_t data);
|
||||
uint8_t t8run_r();
|
||||
void t8run_w(uint8_t data);
|
||||
uint8_t t01mod_r();
|
||||
void t01mod_w(uint8_t data);
|
||||
uint8_t tffcr_r();
|
||||
void tffcr_w(uint8_t data);
|
||||
uint8_t t23mod_r();
|
||||
void t23mod_w(uint8_t data);
|
||||
uint8_t trdc_r();
|
||||
void trdc_w(uint8_t data);
|
||||
uint8_t t4mod_r();
|
||||
uint8_t t6mod_r();
|
||||
uint8_t t8mod_r();
|
||||
uint8_t tamod_r();
|
||||
void t4mod_w(uint8_t data);
|
||||
void t6mod_w(uint8_t data);
|
||||
void t8mod_w(uint8_t data);
|
||||
void tamod_w(uint8_t data);
|
||||
uint8_t t4ffcr_r();
|
||||
void t4ffcr_w(uint8_t data);
|
||||
uint8_t t8ffcr_r();
|
||||
void t8ffcr_w(uint8_t data);
|
||||
uint8_t t6ffcr_r();
|
||||
void t6ffcr_w(uint8_t data);
|
||||
uint8_t taffcr_r();
|
||||
void taffcr_w(uint8_t data);
|
||||
uint8_t t16run_r();
|
||||
void t16run_w(uint8_t data);
|
||||
uint8_t wdmod_r();
|
||||
void wdmod_w(uint8_t data);
|
||||
void wdcr_w(uint8_t data);
|
||||
uint8_t ode_r();
|
||||
void ode_w(uint8_t data);
|
||||
uint8_t admod1_r();
|
||||
void admod1_w(uint8_t data);
|
||||
uint8_t admod2_r();
|
||||
void admod2_w(uint8_t data);
|
||||
uint8_t adreg_r(offs_t offset);
|
||||
uint8_t inte_r(offs_t offset);
|
||||
void inte_w(offs_t offset, uint8_t data);
|
||||
uint8_t intnmwdt_r(offs_t offset);
|
||||
void intnmwdt_w(offs_t offset, uint8_t data);
|
||||
void iimc_w(uint8_t data);
|
||||
void intclr_w(uint8_t data);
|
||||
void dmav_w(offs_t offset, uint8_t data);
|
||||
uint8_t drefcr1_r();
|
||||
void drefcr1_w(uint8_t data);
|
||||
uint8_t dmemcr1_r();
|
||||
void dmemcr1_w(uint8_t data);
|
||||
uint8_t drefcr3_r();
|
||||
void drefcr3_w(uint8_t data);
|
||||
uint8_t dmemcr3_r();
|
||||
void dmemcr3_w(uint8_t data);
|
||||
uint8_t dadrv_r();
|
||||
void dadrv_w(uint8_t data);
|
||||
void dareg_w(offs_t offset, uint8_t data);
|
||||
|
||||
void internal_mem(address_map &map);
|
||||
|
||||
// analogue inputs, sampled at 10 bits
|
||||
devcb_read16::array<8> m_an_read;
|
||||
|
||||
// I/O Ports
|
||||
devcb_read8::array<NUM_PORTS> m_port_read;
|
||||
devcb_write8::array<NUM_PORTS> m_port_write;
|
||||
uint8_t m_port_latch[NUM_PORTS];
|
||||
uint8_t m_port_control[NUM_PORTS];
|
||||
uint8_t m_port_function[NUM_PORTS];
|
||||
|
||||
// Timer Control
|
||||
bool m_timer_flipflops[12];
|
||||
uint8_t m_t8run;
|
||||
uint8_t m_t01mod;
|
||||
uint8_t m_t23mod;
|
||||
uint8_t m_t4mod;
|
||||
uint8_t m_t6mod;
|
||||
uint8_t m_t8mod;
|
||||
uint8_t m_tamod;
|
||||
uint8_t m_tffcr;
|
||||
uint8_t m_t4ffcr;
|
||||
uint8_t m_t6ffcr;
|
||||
uint8_t m_t8ffcr;
|
||||
uint8_t m_taffcr;
|
||||
uint8_t m_trdc;
|
||||
uint8_t m_t16run;
|
||||
uint8_t m_treg_8[4]; // TREG0 - TREG3
|
||||
uint16_t m_treg_16[8]; //TREG4 - TREGB
|
||||
uint16_t m_t16_cap[8]; //CAP4 - CAPB
|
||||
uint16_t m_timer_16[4]; // UPCOUNTERA - UPCOUNTERB
|
||||
|
||||
// Watchdog Timer
|
||||
uint8_t m_watchdog_mode;
|
||||
|
||||
// Serial Channel
|
||||
uint8_t m_serial_control[2];
|
||||
uint8_t m_serial_mode[2];
|
||||
uint8_t m_baud_rate[2];
|
||||
uint8_t m_od_enable;
|
||||
|
||||
// A/D Converter Control
|
||||
uint8_t m_ad_mode1;
|
||||
uint8_t m_ad_mode2;
|
||||
uint16_t m_ad_result[4];
|
||||
|
||||
// Interrupt Control
|
||||
uint8_t m_int_reg[18];
|
||||
uint8_t m_iimc;
|
||||
uint8_t m_dma_vector[4];
|
||||
|
||||
// Chip Select/Wait Control
|
||||
uint16_t m_block_cs[6];
|
||||
uint8_t m_external_cs;
|
||||
uint8_t m_msar[6];
|
||||
uint8_t m_mamr[6];
|
||||
|
||||
// DRAM Control
|
||||
uint8_t m_dram_refresh[2];
|
||||
uint8_t m_dram_access[2];
|
||||
|
||||
// D/A Converter Control
|
||||
uint8_t m_da_drive;
|
||||
};
|
||||
|
||||
// device type declaration
|
||||
DECLARE_DEVICE_TYPE(TMP94C241, tmp94c241_device)
|
||||
|
||||
#endif // MAME_CPU_TLCS900_TMP94C241_H
|
@ -191,6 +191,15 @@ void tmp95c061_device::device_config_complete()
|
||||
}
|
||||
|
||||
|
||||
void tmp95c061_device::device_resolve_objects()
|
||||
{
|
||||
m_nmi_state = CLEAR_LINE;
|
||||
for( int i = 0; i < TLCS900_NUM_INPUTS; i++ )
|
||||
{
|
||||
m_level[i] = CLEAR_LINE;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void tmp95c061_device::device_start()
|
||||
{
|
||||
@ -239,7 +248,6 @@ void tmp95c061_device::device_reset()
|
||||
m_to3 = 0;
|
||||
|
||||
m_ad_cycles_left = 0;
|
||||
m_nmi_state = CLEAR_LINE;
|
||||
m_timer_pre = 0;
|
||||
m_timer_change[0] = 0;
|
||||
m_timer_change[1] = 0;
|
||||
@ -289,11 +297,6 @@ void tmp95c061_device::device_reset()
|
||||
std::fill_n(&m_mem_start_mask[0], 4, 0xff);
|
||||
m_dram_refresh = 0x00;
|
||||
m_dram_access = 0x80;
|
||||
|
||||
for (int i = 0; i < TLCS900_NUM_INPUTS; i++)
|
||||
{
|
||||
m_level[i] = CLEAR_LINE;
|
||||
}
|
||||
}
|
||||
|
||||
enum
|
||||
@ -492,11 +495,6 @@ void tmp95c061_device::tlcs900_check_hdma()
|
||||
|
||||
void tmp95c061_device::tlcs900_check_irqs()
|
||||
{
|
||||
int irq_vectors[9] = { -1, -1, -1, -1, -1, -1, -1, -1, -1 };
|
||||
int level = 0;
|
||||
int irq = -1;
|
||||
int i;
|
||||
|
||||
/* Check for NMI */
|
||||
if ( m_nmi_state == ASSERT_LINE )
|
||||
{
|
||||
@ -516,7 +514,8 @@ void tmp95c061_device::tlcs900_check_irqs()
|
||||
}
|
||||
|
||||
/* Check regular irqs */
|
||||
for( i = 0; i < NUM_MASKABLE_IRQS; i++ )
|
||||
int irq_vectors[9] = { -1, -1, -1, -1, -1, -1, -1, -1, -1 };
|
||||
for( int i = 0; i < NUM_MASKABLE_IRQS; i++ )
|
||||
{
|
||||
if ( m_int_reg[tmp95c061_irq_vector_map[i].reg] & tmp95c061_irq_vector_map[i].iff )
|
||||
{
|
||||
@ -533,7 +532,9 @@ void tmp95c061_device::tlcs900_check_irqs()
|
||||
}
|
||||
|
||||
/* Check highest allowed priority irq */
|
||||
for ( i = std::max( 1, ( ( m_sr.b.h & 0x70 ) >> 4 ) ); i < 7; i++ )
|
||||
int irq = -1;
|
||||
int level = 0;
|
||||
for ( int i = std::max( 1, ( ( m_sr.b.h & 0x70 ) >> 4 ) ); i < 7; i++ )
|
||||
{
|
||||
if ( irq_vectors[i] >= 0 )
|
||||
{
|
||||
@ -690,8 +691,8 @@ void tmp95c061_device::tlcs900_handle_timers()
|
||||
|
||||
for( ; m_timer_change[0] > 0; m_timer_change[0]-- )
|
||||
{
|
||||
m_timer[0] += 1;
|
||||
if ( m_timer[0] == m_t8_reg[0] )
|
||||
m_timer_8[0] += 1;
|
||||
if ( m_timer_8[0] == m_t8_reg[0] )
|
||||
{
|
||||
if ( ( m_trun & 0x02 ) && ( m_t8_mode[0] & 0x0c ) == 0x00 )
|
||||
{
|
||||
@ -701,7 +702,7 @@ void tmp95c061_device::tlcs900_handle_timers()
|
||||
/* In 16bit timer mode the timer should not be reset */
|
||||
if ( ( m_t8_mode[0] & 0xc0 ) != 0x40 )
|
||||
{
|
||||
m_timer[0] = 0;
|
||||
m_timer_8[0] = 0;
|
||||
m_int_reg[INTET10] |= 0x08;
|
||||
}
|
||||
}
|
||||
@ -728,10 +729,10 @@ void tmp95c061_device::tlcs900_handle_timers()
|
||||
|
||||
for( ; m_timer_change[1] > 0; m_timer_change[1]-- )
|
||||
{
|
||||
m_timer[1] += 1;
|
||||
if ( m_timer[1] == m_t8_reg[1] )
|
||||
m_timer_8[1] += 1;
|
||||
if ( m_timer_8[1] == m_t8_reg[1] )
|
||||
{
|
||||
m_timer[1] = 0;
|
||||
m_timer_8[1] = 0;
|
||||
m_int_reg[INTET10] |= 0x80;
|
||||
|
||||
if ( m_t8_invert & 0x02 )
|
||||
@ -742,7 +743,7 @@ void tmp95c061_device::tlcs900_handle_timers()
|
||||
/* In 16bit timer mode also reset timer 0 */
|
||||
if ( ( m_t8_mode[0] & 0xc0 ) == 0x40 )
|
||||
{
|
||||
m_timer[0] = 0;
|
||||
m_timer_8[0] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -767,8 +768,8 @@ void tmp95c061_device::tlcs900_handle_timers()
|
||||
|
||||
for( ; m_timer_change[2] > 0; m_timer_change[2]-- )
|
||||
{
|
||||
m_timer[2] += 1;
|
||||
if ( m_timer[2] == m_t8_reg[2] )
|
||||
m_timer_8[2] += 1;
|
||||
if ( m_timer_8[2] == m_t8_reg[2] )
|
||||
{
|
||||
if ( ( m_trun & 0x08 ) && ( m_t8_mode[1] & 0x0c ) == 0x00 )
|
||||
{
|
||||
@ -778,7 +779,7 @@ void tmp95c061_device::tlcs900_handle_timers()
|
||||
/* In 16bit timer mode the timer should not be reset */
|
||||
if ( ( m_t8_mode[1] & 0xc0 ) != 0x40 )
|
||||
{
|
||||
m_timer[2] = 0;
|
||||
m_timer_8[2] = 0;
|
||||
m_int_reg[INTET32] |= 0x08;
|
||||
}
|
||||
}
|
||||
@ -805,10 +806,10 @@ void tmp95c061_device::tlcs900_handle_timers()
|
||||
|
||||
for( ; m_timer_change[3] > 0; m_timer_change[3]-- )
|
||||
{
|
||||
m_timer[3] += 1;
|
||||
if ( m_timer[3] == m_t8_reg[3] )
|
||||
m_timer_8[3] += 1;
|
||||
if ( m_timer_8[3] == m_t8_reg[3] )
|
||||
{
|
||||
m_timer[3] = 0;
|
||||
m_timer_8[3] = 0;
|
||||
m_int_reg[INTET32] |= 0x80;
|
||||
|
||||
if ( m_t8_invert & 0x20 )
|
||||
@ -819,7 +820,7 @@ void tmp95c061_device::tlcs900_handle_timers()
|
||||
/* In 16bit timer mode also reset timer 2 */
|
||||
if ( ( m_t8_mode[1] & 0xc0 ) == 0x40 )
|
||||
{
|
||||
m_timer[2] = 0;
|
||||
m_timer_8[2] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -916,28 +917,28 @@ void tmp95c061_device::trun_w(uint8_t data)
|
||||
{
|
||||
if ( ! ( data & 0x01 ) )
|
||||
{
|
||||
m_timer[0] = 0;
|
||||
m_timer_8[0] = 0;
|
||||
m_timer_change[0] = 0;
|
||||
}
|
||||
if ( ! ( data & 0x02 ) )
|
||||
{
|
||||
m_timer[1] = 0;
|
||||
m_timer_8[1] = 0;
|
||||
m_timer_change[1] = 0;
|
||||
}
|
||||
if ( ! ( data & 0x04 ) )
|
||||
{
|
||||
m_timer[2] = 0;
|
||||
m_timer_8[2] = 0;
|
||||
m_timer_change[2] = 0;
|
||||
}
|
||||
if ( ! ( data & 0x08 ) )
|
||||
{
|
||||
m_timer[3] = 0;
|
||||
m_timer_8[3] = 0;
|
||||
m_timer_change[3] = 0;
|
||||
}
|
||||
if ( ! ( data & 0x10 ) )
|
||||
m_timer[4] = 0;
|
||||
m_timer_8[4] = 0;
|
||||
if ( ! ( data & 0x20 ) )
|
||||
m_timer[5] = 0;
|
||||
m_timer_8[5] = 0;
|
||||
|
||||
m_trun = data;
|
||||
}
|
||||
|
@ -47,7 +47,8 @@ public:
|
||||
template <size_t Bit> auto an_read() { return m_an_read[Bit].bind(); }
|
||||
|
||||
protected:
|
||||
virtual void device_config_complete() override;
|
||||
virtual void device_config_complete() override ATTR_COLD;
|
||||
virtual void device_resolve_objects() override ATTR_COLD;
|
||||
virtual void device_start() override ATTR_COLD;
|
||||
virtual void device_reset() override ATTR_COLD;
|
||||
|
||||
|
@ -271,8 +271,8 @@ void tmp95c063_device::tlcs900_handle_timers()
|
||||
|
||||
for( ; m_timer_change[0] > 0; m_timer_change[0]-- )
|
||||
{
|
||||
m_timer[0] += 1;
|
||||
if ( m_timer[0] == m_t8_reg[0] )
|
||||
m_timer_8[0] += 1;
|
||||
if ( m_timer_8[0] == m_t8_reg[0] )
|
||||
{
|
||||
if ( ( m_t8run & 0x02 ) && ( m_t8_mode[0] & 0x0c ) == 0x00 )
|
||||
{
|
||||
@ -282,7 +282,7 @@ void tmp95c063_device::tlcs900_handle_timers()
|
||||
/* In 16bit timer mode the timer should not be reset */
|
||||
if ( ( m_t8_mode[0] & 0xc0 ) != 0x40 )
|
||||
{
|
||||
m_timer[0] = 0;
|
||||
m_timer_8[0] = 0;
|
||||
m_int_reg[INTET01] |= 0x08;
|
||||
}
|
||||
}
|
||||
@ -309,10 +309,10 @@ void tmp95c063_device::tlcs900_handle_timers()
|
||||
|
||||
for( ; m_timer_change[1] > 0; m_timer_change[1]-- )
|
||||
{
|
||||
m_timer[1] += 1;
|
||||
if ( m_timer[1] == m_t8_reg[1] )
|
||||
m_timer_8[1] += 1;
|
||||
if ( m_timer_8[1] == m_t8_reg[1] )
|
||||
{
|
||||
m_timer[1] = 0;
|
||||
m_timer_8[1] = 0;
|
||||
m_int_reg[INTET01] |= 0x80;
|
||||
|
||||
if ( m_t8_invert[0] & 0x02 )
|
||||
@ -323,7 +323,7 @@ void tmp95c063_device::tlcs900_handle_timers()
|
||||
/* In 16bit timer mode also reset timer 0 */
|
||||
if ( ( m_t8_mode[0] & 0xc0 ) == 0x40 )
|
||||
{
|
||||
m_timer[0] = 0;
|
||||
m_timer_8[0] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -348,8 +348,8 @@ void tmp95c063_device::tlcs900_handle_timers()
|
||||
|
||||
for( ; m_timer_change[2] > 0; m_timer_change[2]-- )
|
||||
{
|
||||
m_timer[2] += 1;
|
||||
if ( m_timer[2] == m_t8_reg[2] )
|
||||
m_timer_8[2] += 1;
|
||||
if ( m_timer_8[2] == m_t8_reg[2] )
|
||||
{
|
||||
if ( ( m_t8run & 0x08 ) && ( m_t8_mode[1] & 0x0c ) == 0x00 )
|
||||
{
|
||||
@ -359,7 +359,7 @@ void tmp95c063_device::tlcs900_handle_timers()
|
||||
/* In 16bit timer mode the timer should not be reset */
|
||||
if ( ( m_t8_mode[1] & 0xc0 ) != 0x40 )
|
||||
{
|
||||
m_timer[2] = 0;
|
||||
m_timer_8[2] = 0;
|
||||
m_int_reg[INTET23] |= 0x08;
|
||||
}
|
||||
}
|
||||
@ -386,10 +386,10 @@ void tmp95c063_device::tlcs900_handle_timers()
|
||||
|
||||
for( ; m_timer_change[3] > 0; m_timer_change[3]-- )
|
||||
{
|
||||
m_timer[3] += 1;
|
||||
if ( m_timer[3] == m_t8_reg[3] )
|
||||
m_timer_8[3] += 1;
|
||||
if ( m_timer_8[3] == m_t8_reg[3] )
|
||||
{
|
||||
m_timer[3] = 0;
|
||||
m_timer_8[3] = 0;
|
||||
m_int_reg[INTET23] |= 0x80;
|
||||
|
||||
if ( m_t8_invert[1] & 0x20 )
|
||||
@ -400,7 +400,7 @@ void tmp95c063_device::tlcs900_handle_timers()
|
||||
/* In 16bit timer mode also reset timer 2 */
|
||||
if ( ( m_t8_mode[1] & 0xc0 ) == 0x40 )
|
||||
{
|
||||
m_timer[2] = 0;
|
||||
m_timer_8[2] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -416,11 +416,6 @@ void tmp95c063_device::tlcs900_check_hdma()
|
||||
|
||||
void tmp95c063_device::tlcs900_check_irqs()
|
||||
{
|
||||
int irq_vectors[9] = { -1, -1, -1, -1, -1, -1, -1, -1, -1 };
|
||||
int level = 0;
|
||||
int irq = -1;
|
||||
int i;
|
||||
|
||||
/* Check for NMI */
|
||||
if ( m_nmi_state == ASSERT_LINE )
|
||||
{
|
||||
@ -440,7 +435,8 @@ void tmp95c063_device::tlcs900_check_irqs()
|
||||
}
|
||||
|
||||
/* Check regular irqs */
|
||||
for( i = 0; i < NUM_MASKABLE_IRQS; i++ )
|
||||
int irq_vectors[9] = { -1, -1, -1, -1, -1, -1, -1, -1, -1 };
|
||||
for( int i = 0; i < NUM_MASKABLE_IRQS; i++ )
|
||||
{
|
||||
if ( m_int_reg[tmp95c063_irq_vector_map[i].reg] & tmp95c063_irq_vector_map[i].iff )
|
||||
{
|
||||
@ -457,7 +453,9 @@ void tmp95c063_device::tlcs900_check_irqs()
|
||||
}
|
||||
|
||||
/* Check highest allowed priority irq */
|
||||
for ( i = std::max( 1, ( ( m_sr.b.h & 0x70 ) >> 4 ) ); i < 7; i++ )
|
||||
int irq = -1;
|
||||
int level = 0;
|
||||
for ( int i = std::max( 1, ( ( m_sr.b.h & 0x70 ) >> 4 ) ); i < 7; i++ )
|
||||
{
|
||||
if ( irq_vectors[i] >= 0 )
|
||||
{
|
||||
@ -557,6 +555,15 @@ void tmp95c063_device::tlcs900_handle_ad()
|
||||
}
|
||||
|
||||
|
||||
void tmp95c063_device::device_resolve_objects()
|
||||
{
|
||||
m_nmi_state = CLEAR_LINE;
|
||||
for( int i = 0; i < TLCS900_NUM_INPUTS; i++ )
|
||||
{
|
||||
m_level[i] = CLEAR_LINE;
|
||||
}
|
||||
}
|
||||
|
||||
void tmp95c063_device::device_start()
|
||||
{
|
||||
tlcs900h_device::device_start();
|
||||
@ -602,7 +609,6 @@ void tmp95c063_device::device_reset()
|
||||
tlcs900h_device::device_reset();
|
||||
|
||||
m_ad_cycles_left = 0;
|
||||
m_nmi_state = CLEAR_LINE;
|
||||
m_timer_pre = 0;
|
||||
m_timer_change[0] = 0;
|
||||
m_timer_change[1] = 0;
|
||||
@ -655,9 +661,6 @@ void tmp95c063_device::device_reset()
|
||||
std::fill_n(&m_dram_refresh[0], 2, 0x00);
|
||||
std::fill_n(&m_dram_access[0], 2, 0x80);
|
||||
m_da_drive = 0x00;
|
||||
|
||||
for (int i = 0; i < TLCS900_NUM_INPUTS; i++)
|
||||
m_level[i] = CLEAR_LINE;
|
||||
}
|
||||
|
||||
uint8_t tmp95c063_device::t8run_r()
|
||||
@ -669,28 +672,28 @@ void tmp95c063_device::t8run_w(uint8_t data)
|
||||
{
|
||||
if ( ! ( data & 0x01 ) )
|
||||
{
|
||||
m_timer[0] = 0;
|
||||
m_timer_8[0] = 0;
|
||||
m_timer_change[0] = 0;
|
||||
}
|
||||
if ( ! ( data & 0x02 ) )
|
||||
{
|
||||
m_timer[1] = 0;
|
||||
m_timer_8[1] = 0;
|
||||
m_timer_change[1] = 0;
|
||||
}
|
||||
if ( ! ( data & 0x04 ) )
|
||||
{
|
||||
m_timer[2] = 0;
|
||||
m_timer_8[2] = 0;
|
||||
m_timer_change[2] = 0;
|
||||
}
|
||||
if ( ! ( data & 0x08 ) )
|
||||
{
|
||||
m_timer[3] = 0;
|
||||
m_timer_8[3] = 0;
|
||||
m_timer_change[3] = 0;
|
||||
}
|
||||
if ( ! ( data & 0x10 ) )
|
||||
m_timer[4] = 0;
|
||||
m_timer_8[4] = 0;
|
||||
if ( ! ( data & 0x20 ) )
|
||||
m_timer[5] = 0;
|
||||
m_timer_8[5] = 0;
|
||||
|
||||
m_t8run = data;
|
||||
}
|
||||
|
@ -57,7 +57,8 @@ public:
|
||||
template <size_t Bit> auto an_read() { return m_an_read[Bit].bind(); }
|
||||
|
||||
protected:
|
||||
virtual void device_config_complete() override;
|
||||
virtual void device_config_complete() override ATTR_COLD;
|
||||
virtual void device_resolve_objects() override ATTR_COLD;
|
||||
virtual void device_start() override ATTR_COLD;
|
||||
virtual void device_reset() override ATTR_COLD;
|
||||
|
||||
|
@ -7,7 +7,7 @@
|
||||
******************************************************************************/
|
||||
|
||||
#include "emu.h"
|
||||
#include "cpu/tlcs900/tmp95c061.h" // TODO: tmp94c241.h
|
||||
#include "cpu/tlcs900/tmp94c241.h"
|
||||
#include "imagedev/floppy.h"
|
||||
#include "machine/gen_latch.h"
|
||||
#include "machine/upd765.h"
|
||||
@ -109,8 +109,8 @@ public:
|
||||
void kn5000(machine_config &config);
|
||||
|
||||
private:
|
||||
required_device<tmp95c061_device> m_maincpu;
|
||||
required_device<tmp95c061_device> m_subcpu;
|
||||
required_device<tmp94c241_device> m_maincpu;
|
||||
required_device<tmp94c241_device> m_subcpu;
|
||||
required_device<generic_latch_8_device> m_maincpu_latch;
|
||||
required_device<generic_latch_8_device> m_subcpu_latch;
|
||||
required_device<upd72067_device> m_fdc;
|
||||
@ -197,6 +197,37 @@ static INPUT_PORTS_START(kn5000)
|
||||
PORT_DIPSETTING( 0xb0, "PC2")
|
||||
PORT_DIPSETTING( 0x70, "Mac")
|
||||
|
||||
PORT_START("AREA")
|
||||
PORT_DIPNAME(0x06, 0x06, "Area Selection")
|
||||
PORT_DIPSETTING( 0x02, "Thailand, Indonesia, Iran, U.A.E., Panama, Argentina, Peru, Brazil")
|
||||
PORT_DIPSETTING( 0x04, "USA, Mexico")
|
||||
PORT_DIPSETTING( 0x06, "Other")
|
||||
|
||||
/*
|
||||
Actual full list of regions (but it is unclear if there's any
|
||||
other hardware difference among them):
|
||||
|
||||
PORT_DIPSETTING( 0x04, "(M): U.S.A.")
|
||||
PORT_DIPSETTING( 0x06, "(MC): Canada")
|
||||
PORT_DIPSETTING( 0x04, "(XM): Mexico")
|
||||
PORT_DIPSETTING( 0x06, "(EN): Norway, Sweden, Denmark, Finland")
|
||||
PORT_DIPSETTING( 0x06, "(EH): Holland, Belgium")
|
||||
PORT_DIPSETTING( 0x06, "(EF): France, Italy")
|
||||
PORT_DIPSETTING( 0x06, "(EZ): Germany")
|
||||
PORT_DIPSETTING( 0x06, "(EW): Switzerland")
|
||||
PORT_DIPSETTING( 0x06, "(EA): Austria")
|
||||
PORT_DIPSETTING( 0x06, "(EP): Spain, Portugal, Greece, South Africa")
|
||||
PORT_DIPSETTING( 0x06, "(EK): United Kingdom")
|
||||
PORT_DIPSETTING( 0x06, "(XL): New Zealand")
|
||||
PORT_DIPSETTING( 0x06, "(XR): Australia")
|
||||
PORT_DIPSETTING( 0x06, "(XS): Malaysia")
|
||||
PORT_DIPSETTING( 0x06, "(MD): Saudi Arabia, Hong Kong, Kuwait")
|
||||
PORT_DIPSETTING( 0x06, "(XT): Taiwan")
|
||||
PORT_DIPSETTING( 0x02, "(X): Thailand, Indonesia, Iran, U.A.E., Panama, Argentina, Peru, Brazil")
|
||||
PORT_DIPSETTING( 0x06, "(XP): Philippines")
|
||||
PORT_DIPSETTING( 0x06, "(XW): Singapore")
|
||||
*/
|
||||
|
||||
PORT_START("CPR_SEG0")
|
||||
PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_UNUSED )
|
||||
PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_UNUSED )
|
||||
@ -604,7 +635,7 @@ void kn5000_state::machine_reset()
|
||||
void kn5000_state::kn5000(machine_config &config)
|
||||
{
|
||||
// Note: The CPU has an internal clock doubler
|
||||
TMP95C061(config, m_maincpu, 2 * 8_MHz_XTAL); // actual cpu is TMP94C241F @ IC5
|
||||
TMP94C241(config, m_maincpu, 2 * 8_MHz_XTAL); // TMP94C241F @ IC5
|
||||
// Address bus is set to 32 bits by the pins AM1=+5v and AM0=GND
|
||||
m_maincpu->set_addrmap(AS_PROGRAM, &kn5000_state::maincpu_mem);
|
||||
// Interrupt 4: FDCINT
|
||||
@ -636,14 +667,16 @@ void kn5000_state::kn5000(machine_config &config)
|
||||
// MAINCPU PORT C:
|
||||
// bit 0 (input) = "check terminal" switch
|
||||
// bit 1 (output) = "check terminal" LED
|
||||
// TODO: m_maincpu->portc_read().set([this] { return ioport("CN11")->read(); });
|
||||
// TODO: m_maincpu->portc_write().set([this] (u8 data) { m_checking_device_led_cn11 = (BIT(data, 1) == 0); });
|
||||
m_maincpu->portc_read().set_ioport("CN11");
|
||||
m_maincpu->portc_write().set([this] (u8 data) {
|
||||
m_checking_device_led_cn11 = (BIT(data, 1) == 0);
|
||||
});
|
||||
|
||||
|
||||
// MAINCPU PORT D:
|
||||
// bit 0 (output) = FDCRST
|
||||
// bit 6 (input) = FD.I/O
|
||||
// TODO: m_maincpu->portd_write().set([this] (u8 data) { m_fdc->reset_w(BIT(data, 0)); });
|
||||
m_maincpu->portd_write().set(m_fdc, FUNC(upd72067_device::reset_w)).bit(0);
|
||||
// TODO: bit 6!
|
||||
|
||||
|
||||
@ -651,7 +684,7 @@ void kn5000_state::kn5000(machine_config &config)
|
||||
// bit 0 (input) = +5v
|
||||
// bit 2 (input) = HDDRDY
|
||||
// bit 4 (?) = MICSNS
|
||||
// TODO: m_maincpu->porte_read().set([] { return 1; }); //checked at EF05A6 (v10 ROM)
|
||||
m_maincpu->porte_read().set_constant(1); //checked at EF05A6 (v10 ROM)
|
||||
// FIXME: Bit 0 should only be 1 if the
|
||||
// optional hard-drive extension board is disabled;
|
||||
|
||||
@ -670,10 +703,7 @@ void kn5000_state::kn5000(machine_config &config)
|
||||
|
||||
|
||||
// MAINCPU PORT H:
|
||||
// bit 1 = TC1 Terminal count - microDMA
|
||||
// TODO: m_maincpu->porth_read().set([] { return 2; }); // area/region detection: checked at EF083E (v10 ROM)
|
||||
// FIXME: These are resistors on the pcb, but could be declared
|
||||
// in the driver as a 2 bit DIP-Switch for area/region selection.
|
||||
m_maincpu->porth_read().set_ioport("AREA"); // checked at EF083E (v10 ROM)
|
||||
|
||||
|
||||
// MAINCPU PORT Z:
|
||||
@ -701,15 +731,18 @@ void kn5000_state::kn5000(machine_config &config)
|
||||
// AN1 = AFT
|
||||
|
||||
// Note: The CPU has an internal clock doubler
|
||||
TMP95C061(config, m_subcpu, 2*10_MHz_XTAL); // actual cpu is TMP94C241F @ IC27
|
||||
TMP94C241(config, m_subcpu, 2*10_MHz_XTAL); // TMP94C241F @ IC27
|
||||
// Address bus is set to 8 bits by the pins AM1=GND and AM0=GND
|
||||
m_subcpu->set_addrmap(AS_PROGRAM, &kn5000_state::subcpu_mem);
|
||||
|
||||
// SUBCPU PORT C:
|
||||
// bit 0 (input) = "check terminal" switch
|
||||
// bit 1 (output) = "check terminal" LED
|
||||
// TODO: m_subcpu->portc_read().set([this] { return ioport("CN12")->read(); });
|
||||
// TODO: m_subcpu->portc_write().set([this] (u8 data) { m_checking_device_led_cn12 = (BIT(data, 1) == 0); });
|
||||
m_subcpu->portc_read().set_ioport("CN12");
|
||||
m_subcpu->portc_write().set([this] (u8 data) {
|
||||
m_checking_device_led_cn12 = (BIT(data, 1) == 0);
|
||||
});
|
||||
|
||||
|
||||
// SUBCPU PORT D:
|
||||
// bit 0 = (output) SSTAT0
|
||||
@ -717,12 +750,12 @@ void kn5000_state::kn5000(machine_config &config)
|
||||
// bit 2 = (input) MSTAT0
|
||||
// bit 3 (not used)
|
||||
// bit 4 = (input) MSTAT1
|
||||
// TODO: m_subcpu->portd_read().set([this] {
|
||||
// TODO: return (BIT(m_mstat, 0) << 2) | (BIT(m_mstat, 1) << 4);
|
||||
// TODO: });
|
||||
// TODO: m_subcpu->portd_write().set([this] (u8 data) {
|
||||
// TODO: m_sstat = data & 3;
|
||||
// TODO: });
|
||||
m_subcpu->portd_read().set([this] {
|
||||
return (BIT(m_mstat, 0) << 2) | (BIT(m_mstat, 1) << 4);
|
||||
});
|
||||
m_subcpu->portd_write().set([this] (u8 data) {
|
||||
m_sstat = data & 3;
|
||||
});
|
||||
|
||||
|
||||
GENERIC_LATCH_8(config, m_maincpu_latch); // @ IC23
|
||||
|
Loading…
Reference in New Issue
Block a user