mirror of
https://github.com/holub/mame
synced 2025-04-19 07:00:31 +03:00
New machines marked as NOT_WORKING
---------------------------------- JoMoX XBase 09 Midi Controlled Analogue Drum Module [DBWBP] Add disassembler for PIC17 family and preliminary PIC17C4X emulation [AJR]
This commit is contained in:
parent
ff46a6025f
commit
0b345e7bb6
@ -1308,6 +1308,25 @@ if (CPUS["PIC16"]~=null or _OPTIONS["with-tools"]) then
|
||||
table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pic16/pic16d.h")
|
||||
end
|
||||
|
||||
--------------------------------------------------
|
||||
-- Microchip PIC17
|
||||
--@src/devices/cpu/pic17/pic17.h,CPUS["PIC17"] = true
|
||||
--------------------------------------------------
|
||||
|
||||
if (CPUS["PIC17"]~=null) then
|
||||
files {
|
||||
MAME_DIR .. "src/devices/cpu/pic17/pic17.cpp",
|
||||
MAME_DIR .. "src/devices/cpu/pic17/pic17.h",
|
||||
MAME_DIR .. "src/devices/cpu/pic17/pic17c4x.cpp",
|
||||
MAME_DIR .. "src/devices/cpu/pic17/pic17c4x.h",
|
||||
}
|
||||
end
|
||||
|
||||
if (CPUS["PIC17"]~=null or _OPTIONS["with-tools"]) then
|
||||
table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pic17/pic17d.cpp")
|
||||
table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pic17/pic17d.h")
|
||||
end
|
||||
|
||||
--------------------------------------------------
|
||||
-- MIPS R3000 (MIPS I/II) series
|
||||
--@src/devices/cpu/mips/mips1.h,CPUS["MIPS1"] = true
|
||||
|
@ -65,6 +65,7 @@ CPUS["DSP16"] = true
|
||||
CPUS["DSP32C"] = true
|
||||
CPUS["PIC16C5X"] = true
|
||||
CPUS["PIC16C62X"] = true
|
||||
CPUS["PIC17"] = true
|
||||
CPUS["G65816"] = true
|
||||
CPUS["SPC700"] = true
|
||||
CPUS["E1"] = true
|
||||
@ -2819,6 +2820,8 @@ files {
|
||||
MAME_DIR .. "src/mame/drivers/ergo201.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/microterm.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/microterm_f8.cpp",
|
||||
MAME_DIR .. "src/mame/machine/ergo201_kbd.cpp",
|
||||
MAME_DIR .. "src/mame/machine/ergo201_kbd.h",
|
||||
}
|
||||
|
||||
createMESSProjects(_target, _subtarget, "mips")
|
||||
@ -4466,6 +4469,7 @@ files {
|
||||
MAME_DIR .. "src/mame/drivers/vp415.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/vsmilepro.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/wicat.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/xbase09.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/xor100.cpp",
|
||||
MAME_DIR .. "src/mame/includes/xor100.h",
|
||||
MAME_DIR .. "src/mame/drivers/zms8085.cpp",
|
||||
|
1096
src/devices/cpu/pic17/pic17.cpp
Normal file
1096
src/devices/cpu/pic17/pic17.cpp
Normal file
File diff suppressed because it is too large
Load Diff
180
src/devices/cpu/pic17/pic17.h
Normal file
180
src/devices/cpu/pic17/pic17.h
Normal file
@ -0,0 +1,180 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:AJR
|
||||
|
||||
#ifndef MAME_CPU_PIC17_PIC17_H
|
||||
#define MAME_CPU_PIC17_PIC17_H
|
||||
|
||||
#pragma once
|
||||
|
||||
class pic17_cpu_device : public cpu_device
|
||||
{
|
||||
public:
|
||||
enum {
|
||||
PIC17_PC,
|
||||
PIC17_PCLATH,
|
||||
PIC17_STKPTR,
|
||||
PIC17_TOS,
|
||||
PIC17_WREG,
|
||||
PIC17_PROD,
|
||||
PIC17_ALUSTA,
|
||||
PIC17_CPUSTA,
|
||||
PIC17_INTSTA,
|
||||
PIC17_FSR0,
|
||||
PIC17_FSR1,
|
||||
PIC17_BSR,
|
||||
PIC17_TBLPTR,
|
||||
PIC17_TABLAT,
|
||||
PIC17_TLWT,
|
||||
PIC17_T0STA,
|
||||
PIC17_TMR0,
|
||||
PIC17_PS
|
||||
};
|
||||
|
||||
enum class mode {
|
||||
MICROPROCESSOR,
|
||||
MICROCONTROLLER,
|
||||
EXTENDED_MICROCONTROLLER
|
||||
};
|
||||
|
||||
// misc. configuration
|
||||
void set_mode(mode m) { m_mode = m; }
|
||||
|
||||
protected:
|
||||
pic17_cpu_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, u16 rom_size, address_map_constructor data_map);
|
||||
|
||||
// device-level overrides
|
||||
virtual void device_start() override;
|
||||
virtual void device_reset() override;
|
||||
|
||||
// device_execute_interface overrides
|
||||
virtual void execute_run() override;
|
||||
|
||||
// device_disasm_interface overrides
|
||||
virtual std::unique_ptr<util::disasm_interface> create_disassembler() override;
|
||||
|
||||
// device_memory_interface overrides
|
||||
virtual space_config_vector memory_space_config() const override;
|
||||
|
||||
// device_state_interface overrides
|
||||
virtual void state_string_export(const device_state_entry &entry, std::string &str) const override;
|
||||
|
||||
// internal data map
|
||||
void core_data_map(address_map &map);
|
||||
|
||||
// helpers for derived classes
|
||||
void int_edge(bool rising);
|
||||
void t0cki_edge(bool rising);
|
||||
void set_peif(bool state);
|
||||
virtual void increment_timers();
|
||||
|
||||
private:
|
||||
enum class exec_phase : u8 { Q1, Q2, Q3, Q4 };
|
||||
|
||||
enum exec_flags : u8 {
|
||||
REGWT = 1 << 0U,
|
||||
FORCENOP = 1 << 1U,
|
||||
SKIP = 1 << 2U,
|
||||
INTRPT = 1 << 3U,
|
||||
TBLPTRI = 1 << 4U,
|
||||
TABLRD = 1 << 5U,
|
||||
TABLWT = 1 << 6U,
|
||||
SLEEP = 1 << 7U
|
||||
};
|
||||
|
||||
// internal register accessors
|
||||
u8 pcl_r();
|
||||
void pcl_w(u8 data);
|
||||
void debug_set_pc(u16 data);
|
||||
u8 pclath_r();
|
||||
void pclath_w(u8 data);
|
||||
u8 wreg_r();
|
||||
void wreg_w(u8 data);
|
||||
u8 alusta_r();
|
||||
void alusta_w(u8 data);
|
||||
u8 cpusta_r();
|
||||
void cpusta_w(u8 data);
|
||||
u8 intsta_r();
|
||||
void intsta_w(u8 data);
|
||||
u8 t0sta_r();
|
||||
void t0sta_w(u8 data);
|
||||
u8 tmr0l_r();
|
||||
void tmr0l_w(u8 data);
|
||||
u8 tmr0h_r();
|
||||
void tmr0h_w(u8 data);
|
||||
void increment_tmr0();
|
||||
u8 fsr0_r();
|
||||
void fsr0_w(u8 data);
|
||||
u8 fsr1_r();
|
||||
void fsr1_w(u8 data);
|
||||
u8 bsr_r();
|
||||
void bsr_w(u8 data);
|
||||
u8 tblptrl_r();
|
||||
void tblptrl_w(u8 data);
|
||||
u8 tblptrh_r();
|
||||
void tblptrh_w(u8 data);
|
||||
u8 prodl_r();
|
||||
void prodl_w(u8 data);
|
||||
u8 prodh_r();
|
||||
void prodh_w(u8 data);
|
||||
|
||||
// execution helpers
|
||||
void set_skip();
|
||||
void clear_watchdog_timer();
|
||||
u16 banked_register(u8 r);
|
||||
void stack_push(u16 addr);
|
||||
u16 stack_pop();
|
||||
u16 interrupt_vector();
|
||||
void set_zero(bool z);
|
||||
void set_carry(bool c);
|
||||
void add_with_carry(u8 augend, bool cin);
|
||||
void decimal_adjust();
|
||||
void q1_decode();
|
||||
void q2_read();
|
||||
void q3_execute();
|
||||
void q4_write();
|
||||
|
||||
// address map constructor
|
||||
void program_map(address_map &map);
|
||||
|
||||
// address spaces
|
||||
const address_space_config m_program_config;
|
||||
const address_space_config m_data_config;
|
||||
const u16 m_rom_size;
|
||||
memory_access<16, 1, -1, ENDIANNESS_LITTLE>::cache m_cache;
|
||||
memory_access<16, 1, -1, ENDIANNESS_LITTLE>::specific m_program;
|
||||
memory_access<12, 0, 0, ENDIANNESS_LITTLE>::specific m_data;
|
||||
|
||||
// mode configuration
|
||||
mode m_mode;
|
||||
|
||||
// execution state
|
||||
u16 m_pc;
|
||||
u16 m_ppc;
|
||||
u16 m_paddr;
|
||||
u16 m_raddr;
|
||||
u16 m_ir;
|
||||
u8 m_tmp;
|
||||
exec_phase m_execphase;
|
||||
u8 m_execflags;
|
||||
s32 m_icount;
|
||||
|
||||
// internal status and control registers
|
||||
u8 m_pclath;
|
||||
u8 m_wreg;
|
||||
u8 m_alusta;
|
||||
u8 m_cpusta;
|
||||
u8 m_intsta;
|
||||
u16 m_tblptr;
|
||||
u16 m_tablat;
|
||||
u16 m_tlwt;
|
||||
u16 m_prod;
|
||||
u8 m_fsr[2];
|
||||
u8 m_bsr;
|
||||
u8 m_stkptr;
|
||||
u16 m_stack[16];
|
||||
u8 m_t0sta;
|
||||
u16 m_tmr0;
|
||||
u8 m_ps;
|
||||
};
|
||||
|
||||
#endif // MAME_CPU_PIC17_PIC17_H
|
537
src/devices/cpu/pic17/pic17c4x.cpp
Normal file
537
src/devices/cpu/pic17/pic17c4x.cpp
Normal file
@ -0,0 +1,537 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:AJR
|
||||
/**********************************************************************
|
||||
|
||||
Microchip PIC17C4X microcontrollers
|
||||
|
||||
Comparative list of features:
|
||||
|
||||
Clock frequency 33 MHz maximum (PIC17C42: 25 MHz maximum)
|
||||
EPROM (PIC17C42(A)) 2K (mask ROM on PIC17CR42)
|
||||
EPROM (PIC17C43) 4K (mask ROM on PIC17CR43)
|
||||
EPROM (PIC17C44) 8K
|
||||
RAM (PIC17C42(A)) 232 bytes
|
||||
RAM (PIC17C43/44) 454 bytes
|
||||
Pin count 40 (PDIP, CERDIP) or 44 (PLCC, MQFP, TQFP)
|
||||
Port pins 33 (19 shared with external bus)
|
||||
Interrupt sources 11
|
||||
8-bit timers 2 (cascadable)
|
||||
16-bit timers 16 (including TMR0)
|
||||
Capture inputs 2
|
||||
PWM outputs 2
|
||||
USART 1
|
||||
|
||||
The original PIC17C42 lacks a hardware multiplier and has a few
|
||||
CPU core bugs that were corrected in PIC17C42A and the rest of
|
||||
the family.
|
||||
|
||||
**********************************************************************/
|
||||
|
||||
#include "emu.h"
|
||||
#include "pic17c4x.h"
|
||||
|
||||
// device type definitions
|
||||
DEFINE_DEVICE_TYPE(PIC17C43, pic17c43_device, "pic17c43", "Microchip PIC17C43")
|
||||
DEFINE_DEVICE_TYPE(PIC17C44, pic17c44_device, "pic17c44", "Microchip PIC17C44")
|
||||
|
||||
pic17c4x_device::pic17c4x_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, u16 rom_size, address_map_constructor data_map)
|
||||
: pic17_cpu_device(mconfig, type, tag, owner, clock, rom_size, data_map)
|
||||
, m_port_out_cb(*this)
|
||||
, m_rain(0x3f)
|
||||
, m_lata(0)
|
||||
, m_rbpu(false)
|
||||
, m_ddrb(0)
|
||||
, m_latb(0)
|
||||
, m_tmr8bit{0, 0}
|
||||
, m_pr8bit{0, 0}
|
||||
, m_tmr3(0)
|
||||
, m_ca16bit{0, 0}
|
||||
, m_tcon1(0)
|
||||
, m_tcon2(0)
|
||||
, m_rcsta(0)
|
||||
, m_txsta(0)
|
||||
, m_spbrg(0)
|
||||
, m_pir(0)
|
||||
, m_pie(0)
|
||||
{
|
||||
}
|
||||
|
||||
pic17c43_device::pic17c43_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, u16 rom_size)
|
||||
: pic17c4x_device(mconfig, type, tag, owner, clock, rom_size, address_map_constructor(FUNC(pic17c43_device::data_map), this))
|
||||
{
|
||||
}
|
||||
|
||||
pic17c43_device::pic17c43_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock)
|
||||
: pic17c43_device(mconfig, PIC17C43, tag, owner, clock, 0x1000)
|
||||
{
|
||||
}
|
||||
|
||||
pic17c44_device::pic17c44_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock)
|
||||
: pic17c43_device(mconfig, PIC17C44, tag, owner, clock, 0x2000)
|
||||
{
|
||||
}
|
||||
|
||||
void pic17c4x_device::data_map(address_map &map)
|
||||
{
|
||||
core_data_map(map);
|
||||
|
||||
// TODO: add handlers for more of these SFRs
|
||||
map(0x010, 0x010).rw(FUNC(pic17c4x_device::porta_r), FUNC(pic17c4x_device::porta_w));
|
||||
map(0x011, 0x011).rw(FUNC(pic17c4x_device::ddrb_r), FUNC(pic17c4x_device::ddrb_w));
|
||||
map(0x012, 0x012).rw(FUNC(pic17c4x_device::portb_r), FUNC(pic17c4x_device::portb_w));
|
||||
map(0x013, 0x013).rw(FUNC(pic17c4x_device::rcsta_r), FUNC(pic17c4x_device::rcsta_w));
|
||||
//map(0x014, 0x014).r(FUNC(pic17c4x_device::rcreg_r));
|
||||
map(0x015, 0x015).rw(FUNC(pic17c4x_device::txsta_r), FUNC(pic17c4x_device::txsta_w));
|
||||
map(0x016, 0x016).w(FUNC(pic17c4x_device::txreg_w));
|
||||
map(0x017, 0x017).rw(FUNC(pic17c4x_device::spbrg_r), FUNC(pic17c4x_device::spbrg_w));
|
||||
//map(0x110, 0x110).rw(FUNC(pic17c4x_device::ddrc_r), FUNC(pic17c4x_device::ddrc_w));
|
||||
//map(0x111, 0x111).rw(FUNC(pic17c4x_device::portc_r), FUNC(pic17c4x_device::portc_w));
|
||||
//map(0x112, 0x112).rw(FUNC(pic17c4x_device::ddrd_r), FUNC(pic17c4x_device::ddrd_w));
|
||||
//map(0x113, 0x113).rw(FUNC(pic17c4x_device::portd_r), FUNC(pic17c4x_device::portd_w));
|
||||
//map(0x114, 0x114).rw(FUNC(pic17c4x_device::ddre_r), FUNC(pic17c4x_device::ddre_w));
|
||||
//map(0x115, 0x115).rw(FUNC(pic17c4x_device::porte_r), FUNC(pic17c4x_device::porte_w));
|
||||
map(0x116, 0x116).rw(FUNC(pic17c4x_device::pir_r), FUNC(pic17c4x_device::pir_w));
|
||||
map(0x117, 0x117).rw(FUNC(pic17c4x_device::pie_r), FUNC(pic17c4x_device::pie_w));
|
||||
map(0x210, 0x210).rw(FUNC(pic17c4x_device::tmr1_r), FUNC(pic17c4x_device::tmr1_w));
|
||||
map(0x211, 0x211).rw(FUNC(pic17c4x_device::tmr2_r), FUNC(pic17c4x_device::tmr2_w));
|
||||
map(0x212, 0x212).rw(FUNC(pic17c4x_device::tmr3l_r), FUNC(pic17c4x_device::tmr3l_w));
|
||||
map(0x213, 0x213).rw(FUNC(pic17c4x_device::tmr3h_r), FUNC(pic17c4x_device::tmr3h_w));
|
||||
map(0x214, 0x214).rw(FUNC(pic17c4x_device::pr1_r), FUNC(pic17c4x_device::pr1_w));
|
||||
map(0x215, 0x215).rw(FUNC(pic17c4x_device::pr2_r), FUNC(pic17c4x_device::pr2_w));
|
||||
map(0x216, 0x216).rw(FUNC(pic17c4x_device::pr3l_ca1l_r), FUNC(pic17c4x_device::pr3l_ca1l_w));
|
||||
map(0x217, 0x217).rw(FUNC(pic17c4x_device::pr3h_ca1h_r), FUNC(pic17c4x_device::pr3h_ca1h_w));
|
||||
//map(0x310, 0x310).rw(FUNC(pic17c4x_device::pw1dcl_r), FUNC(pic17c4x_device::pw1dcl_w));
|
||||
//map(0x311, 0x311).rw(FUNC(pic17c4x_device::pw2dcl_r), FUNC(pic17c4x_device::pw2dcl_w));
|
||||
//map(0x312, 0x312).rw(FUNC(pic17c4x_device::pw1dch_r), FUNC(pic17c4x_device::pw1dch_w));
|
||||
//map(0x313, 0x313).rw(FUNC(pic17c4x_device::pw2dch_r), FUNC(pic17c4x_device::pw2dch_w));
|
||||
map(0x314, 0x314).r(FUNC(pic17c4x_device::ca2l_r));
|
||||
map(0x315, 0x315).r(FUNC(pic17c4x_device::ca2h_r));
|
||||
map(0x316, 0x316).rw(FUNC(pic17c4x_device::tcon1_r), FUNC(pic17c4x_device::tcon1_w));
|
||||
map(0x317, 0x317).rw(FUNC(pic17c4x_device::tcon2_r), FUNC(pic17c4x_device::tcon2_w));
|
||||
}
|
||||
|
||||
void pic17c43_device::data_map(address_map &map)
|
||||
{
|
||||
pic17c4x_device::data_map(map);
|
||||
|
||||
// RAM: 454 bytes
|
||||
map(0x01a, 0x0ff).ram();
|
||||
map(0x120, 0x1ff).ram();
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::porta_r()
|
||||
{
|
||||
// RA2 and RA3 are open-drain I/O
|
||||
// TODO: RA4 and RA5 carry USART signals
|
||||
u8 porta = (m_rain & 0x33) | (m_rain & m_lata & 0x0c);
|
||||
if (m_rbpu)
|
||||
porta |= 0x80;
|
||||
return porta;
|
||||
}
|
||||
|
||||
void pic17c4x_device::porta_w(u8 data)
|
||||
{
|
||||
// RA0 and RA1 have no output drivers
|
||||
// RA4 and RA5 can only be output from USART
|
||||
m_lata = (m_lata & 0x30) | (data & 0x0c);
|
||||
m_port_out_cb[0](m_lata);
|
||||
|
||||
if (m_rbpu != BIT(data, 7))
|
||||
{
|
||||
m_rbpu = BIT(data, 7);
|
||||
if (m_ddrb != 0)
|
||||
m_port_out_cb[1](m_rbpu ? (m_latb | m_ddrb) : (m_latb & m_ddrb));
|
||||
}
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::ddrb_r()
|
||||
{
|
||||
return m_ddrb;
|
||||
}
|
||||
|
||||
void pic17c4x_device::ddrb_w(u8 data)
|
||||
{
|
||||
if (m_ddrb != data)
|
||||
{
|
||||
m_ddrb = data;
|
||||
m_port_out_cb[1](m_rbpu ? (m_latb | m_ddrb) : (m_latb & m_ddrb));
|
||||
}
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::portb_r()
|
||||
{
|
||||
return m_latb | (m_rbpu ? m_ddrb : 0);
|
||||
}
|
||||
|
||||
void pic17c4x_device::portb_w(u8 data)
|
||||
{
|
||||
m_latb = data;
|
||||
m_port_out_cb[1](m_rbpu ? (m_latb | m_ddrb) : (m_latb & m_ddrb));
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::rcsta_r()
|
||||
{
|
||||
return m_rcsta;
|
||||
}
|
||||
|
||||
void pic17c4x_device::rcsta_w(u8 data)
|
||||
{
|
||||
// FERR, OERR and RX9D are read-only; bit 3 is unimplemented
|
||||
m_rcsta = (data & 0xf0) | (m_rcsta & 0x07);
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::txsta_r()
|
||||
{
|
||||
return m_txsta;
|
||||
}
|
||||
|
||||
void pic17c4x_device::txsta_w(u8 data)
|
||||
{
|
||||
// TRMT is read-only; bits 2 & 3 are unimplemented
|
||||
m_txsta = (data & 0xf1) | (m_txsta & 0x02);
|
||||
}
|
||||
|
||||
void pic17c4x_device::txreg_w(u8 data)
|
||||
{
|
||||
logerror("%s: Writing %02X to TXREG\n", machine().describe_context(), data);
|
||||
|
||||
// Clear TXIF
|
||||
m_pir &= 0xfd;
|
||||
if ((m_pir & m_pie) == 0)
|
||||
set_peif(false);
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::spbrg_r()
|
||||
{
|
||||
return m_spbrg;
|
||||
}
|
||||
|
||||
void pic17c4x_device::spbrg_w(u8 data)
|
||||
{
|
||||
m_spbrg = data;
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::tmr1_r()
|
||||
{
|
||||
return m_tmr8bit[0];
|
||||
}
|
||||
|
||||
void pic17c4x_device::tmr1_w(u8 data)
|
||||
{
|
||||
m_tmr8bit[0] = data;
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::tmr2_r()
|
||||
{
|
||||
return m_tmr8bit[1];
|
||||
}
|
||||
|
||||
void pic17c4x_device::tmr2_w(u8 data)
|
||||
{
|
||||
m_tmr8bit[1] = data;
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::tmr3l_r()
|
||||
{
|
||||
return m_tmr3 & 0x00ff;
|
||||
}
|
||||
|
||||
void pic17c4x_device::tmr3l_w(u8 data)
|
||||
{
|
||||
m_tmr3 = (m_tmr3 & 0xff00) | data;
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::tmr3h_r()
|
||||
{
|
||||
return m_tmr3 >> 8;
|
||||
}
|
||||
|
||||
void pic17c4x_device::tmr3h_w(u8 data)
|
||||
{
|
||||
m_tmr3 = u16(data) << 8 | (m_tmr3 & 0x00ff);
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::pr1_r()
|
||||
{
|
||||
return m_pr8bit[0];
|
||||
}
|
||||
|
||||
void pic17c4x_device::pr1_w(u8 data)
|
||||
{
|
||||
m_pr8bit[0] = data;
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::pr2_r()
|
||||
{
|
||||
return m_pr8bit[1];
|
||||
}
|
||||
|
||||
void pic17c4x_device::pr2_w(u8 data)
|
||||
{
|
||||
m_pr8bit[1] = data;
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::pr3l_ca1l_r()
|
||||
{
|
||||
return m_ca16bit[0] & 0x00ff;
|
||||
}
|
||||
|
||||
void pic17c4x_device::pr3l_ca1l_w(u8 data)
|
||||
{
|
||||
m_ca16bit[0] = (m_ca16bit[0] & 0xff00) | data;
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::pr3h_ca1h_r()
|
||||
{
|
||||
return m_ca16bit[0] >> 8;
|
||||
}
|
||||
|
||||
void pic17c4x_device::pr3h_ca1h_w(u8 data)
|
||||
{
|
||||
m_ca16bit[0] = u16(data) << 8 | (m_ca16bit[0] & 0x00ff);
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::ca2l_r()
|
||||
{
|
||||
return m_ca16bit[1] & 0x00ff;
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::ca2h_r()
|
||||
{
|
||||
return m_ca16bit[1] >> 8;
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::tcon1_r()
|
||||
{
|
||||
return m_tcon1;
|
||||
}
|
||||
|
||||
void pic17c4x_device::tcon1_w(u8 data)
|
||||
{
|
||||
m_tcon1 = data;
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::tcon2_r()
|
||||
{
|
||||
return m_tcon2;
|
||||
}
|
||||
|
||||
void pic17c4x_device::tcon2_w(u8 data)
|
||||
{
|
||||
// CA1OVF and CA2OVF are read-only
|
||||
m_tcon2 = (m_tcon2 & 0xc0) | (data & 0x3f);
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::pir_r()
|
||||
{
|
||||
return m_pir;
|
||||
}
|
||||
|
||||
void pic17c4x_device::pir_w(u8 data)
|
||||
{
|
||||
// TXIF and RCIF are read-only
|
||||
m_pir = (data & 0xfc) | (m_pir & 0x03);
|
||||
set_peif((m_pie & m_pir) != 0);
|
||||
}
|
||||
|
||||
u8 pic17c4x_device::pie_r()
|
||||
{
|
||||
return m_pie;
|
||||
}
|
||||
|
||||
void pic17c4x_device::pie_w(u8 data)
|
||||
{
|
||||
m_pie = data;
|
||||
set_peif((m_pie & m_pir) != 0);
|
||||
}
|
||||
|
||||
void pic17c4x_device::increment_timers()
|
||||
{
|
||||
pic17_cpu_device::increment_timers();
|
||||
|
||||
// Advance TMR1
|
||||
if (BIT(m_tcon2, 0) && !BIT(m_tcon1, 0))
|
||||
{
|
||||
if (BIT(m_tcon1, 3))
|
||||
{
|
||||
// T16 mode: TMR1 and TMR2 cascaded
|
||||
if (m_tmr8bit[0] == m_pr8bit[0] && m_tmr8bit[1] == m_pr8bit[1])
|
||||
{
|
||||
// Roll over and set TMR1IF
|
||||
m_tmr8bit[0] = 0;
|
||||
m_tmr8bit[1] = 0;
|
||||
m_pir |= 0x10;
|
||||
if (BIT(m_pie, 4))
|
||||
set_peif(true);
|
||||
}
|
||||
else
|
||||
{
|
||||
++m_tmr8bit[0];
|
||||
if (m_tmr8bit[0] == 0 && BIT(m_tcon2, 1))
|
||||
++m_tmr8bit[1];
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (m_tmr8bit[0] == m_pr8bit[0])
|
||||
{
|
||||
// Roll over and set TMR1IF
|
||||
m_tmr8bit[0] = 0;
|
||||
m_pir |= 0x10;
|
||||
if (BIT(m_pie, 4))
|
||||
set_peif(true);
|
||||
}
|
||||
else
|
||||
++m_tmr8bit[0];
|
||||
}
|
||||
}
|
||||
|
||||
// Advance TMR2 (as 8-bit counter only)
|
||||
if (BIT(m_tcon2, 1) && (m_tcon1 & 0x0a) == 0)
|
||||
{
|
||||
if (m_tmr8bit[1] == m_pr8bit[1])
|
||||
{
|
||||
// Roll over and set TMR2IF
|
||||
m_tmr8bit[1] = 0;
|
||||
m_pir |= 0x20;
|
||||
if (BIT(m_pie, 5))
|
||||
set_peif(true);
|
||||
}
|
||||
else
|
||||
++m_tmr8bit[1];
|
||||
}
|
||||
|
||||
// Advance TMR3
|
||||
if (BIT(m_tcon2, 2) && !BIT(m_tcon1, 2))
|
||||
{
|
||||
// Period register is not used to determine overflow when CA1 mode is selected
|
||||
if (m_tmr3 == (BIT(m_tcon2, 3) ? 0xffff : m_ca16bit[0]))
|
||||
{
|
||||
// Roll over and set TMR3IF
|
||||
m_tmr3 = 0;
|
||||
m_pir |= 0x40;
|
||||
if (BIT(m_pie, 6))
|
||||
set_peif(true);
|
||||
}
|
||||
else
|
||||
++m_tmr3;
|
||||
}
|
||||
}
|
||||
|
||||
void pic17c4x_device::device_resolve_objects()
|
||||
{
|
||||
// Resolve callback objects
|
||||
m_port_out_cb.resolve_all_safe();
|
||||
}
|
||||
|
||||
void pic17c4x_device::device_start()
|
||||
{
|
||||
pic17_cpu_device::device_start();
|
||||
|
||||
// Register debug state
|
||||
state_add(PIC17_LATA, "LATA", m_lata).mask(0x3c);
|
||||
state_add(PIC17_DDRB, "DDRB", m_ddrb);
|
||||
state_add(PIC17_LATB, "LATB", m_latb);
|
||||
state_add(PIC17_TMR1, "TMR1", m_tmr8bit[0]);
|
||||
state_add(PIC17_TMR2, "TMR2", m_tmr8bit[1]);
|
||||
state_add(PIC17_TMR3, "TMR3", m_tmr3);
|
||||
state_add(PIC17_PR1, "PR1", m_pr8bit[0]);
|
||||
state_add(PIC17_PR2, "PR2", m_pr8bit[1]);
|
||||
state_add(PIC17_CA1, "CA1", m_ca16bit[0]);
|
||||
state_add(PIC17_CA2, "CA2", m_ca16bit[1]);
|
||||
state_add(PIC17_TCON1, "TCON1", m_tcon1);
|
||||
state_add(PIC17_TCON2, "TCON2", m_tcon2);
|
||||
state_add(PIC17_RCSTA, "RCSTA", m_rcsta).mask(0xf7);
|
||||
state_add(PIC17_TXSTA, "TXSTA", m_txsta).mask(0xf3);
|
||||
state_add(PIC17_SPBRG, "SPBRG", m_spbrg);
|
||||
state_add(PIC17_PIE, "PIE", m_pie);
|
||||
state_add(PIC17_PIR, "PIR", m_pir);
|
||||
|
||||
// Save state
|
||||
save_item(NAME(m_lata));
|
||||
save_item(NAME(m_rbpu));
|
||||
save_item(NAME(m_ddrb));
|
||||
save_item(NAME(m_latb));
|
||||
save_item(NAME(m_tmr8bit));
|
||||
save_item(NAME(m_pr8bit));
|
||||
save_item(NAME(m_tmr3));
|
||||
save_item(NAME(m_ca16bit));
|
||||
save_item(NAME(m_tcon1));
|
||||
save_item(NAME(m_tcon2));
|
||||
save_item(NAME(m_rcsta));
|
||||
save_item(NAME(m_txsta));
|
||||
save_item(NAME(m_spbrg));
|
||||
save_item(NAME(m_pie));
|
||||
save_item(NAME(m_pir));
|
||||
}
|
||||
|
||||
void pic17c4x_device::device_reset()
|
||||
{
|
||||
pic17_cpu_device::device_reset();
|
||||
|
||||
// Reset ports
|
||||
m_lata = 0x3c;
|
||||
m_rbpu = false;
|
||||
m_ddrb = 0xff;
|
||||
m_port_out_cb[0](0x3c);
|
||||
m_port_out_cb[1](0xff);
|
||||
|
||||
// Reset timers
|
||||
//m_pw2dcl &= 0xc0;
|
||||
m_tcon1 = 0;
|
||||
m_tcon2 = 0;
|
||||
|
||||
// Reset USART
|
||||
m_rcsta &= 0x01;
|
||||
m_txsta = (m_txsta & 0x01) | 0x02;
|
||||
|
||||
// Reset peripheral interrupts
|
||||
m_pir = 0x02;
|
||||
m_pie = 0;
|
||||
}
|
||||
|
||||
void pic17c4x_device::execute_set_input(int linenum, int state)
|
||||
{
|
||||
switch (linenum)
|
||||
{
|
||||
case RA0_LINE:
|
||||
if (state != CLEAR_LINE && BIT(m_rain, 0))
|
||||
{
|
||||
// Falling edge
|
||||
m_rain &= 0x3e;
|
||||
int_edge(false);
|
||||
}
|
||||
else if (state == CLEAR_LINE && !BIT(m_rain, 0))
|
||||
{
|
||||
// Rising edge
|
||||
m_rain |= 0x01;
|
||||
int_edge(true);
|
||||
}
|
||||
break;
|
||||
|
||||
case RA1_LINE:
|
||||
if (state != CLEAR_LINE && BIT(m_rain, 1))
|
||||
{
|
||||
// Falling edge
|
||||
m_rain &= 0x3d;
|
||||
t0cki_edge(false);
|
||||
}
|
||||
else if (state == CLEAR_LINE && !BIT(m_rain, 1))
|
||||
{
|
||||
// Rising edge
|
||||
m_rain |= 0x02;
|
||||
t0cki_edge(true);
|
||||
}
|
||||
break;
|
||||
|
||||
case RA2_LINE:
|
||||
case RA3_LINE:
|
||||
case RA4_LINE:
|
||||
case RA5_LINE:
|
||||
if (state == ASSERT_LINE)
|
||||
m_rain &= ~(1 << (linenum - RA0_LINE));
|
||||
else
|
||||
m_rain |= 1 << (linenum - RA0_LINE);
|
||||
break;
|
||||
}
|
||||
}
|
181
src/devices/cpu/pic17/pic17c4x.h
Normal file
181
src/devices/cpu/pic17/pic17c4x.h
Normal file
@ -0,0 +1,181 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:AJR
|
||||
/**********************************************************************
|
||||
_____ _____
|
||||
Vdd 1 |* \__/ | 40 RD0/AD8
|
||||
RC0/AD0 2 | | 39 RD1/AD9
|
||||
RC1/AD1 3 | | 38 RD2/AD10
|
||||
RC2/AD2 4 | | 37 RD3/AD11
|
||||
RC3/AD3 5 | | 36 RD4/AD12
|
||||
RC4/AD4 6 | | 35 RD5/AD13
|
||||
RC5/AD5 7 | | 34 RD6/AD14
|
||||
RC6/AD6 8 | | 33 RD7/AD15
|
||||
RC7/AD7 9 | | 32 _MCLR/Vpp
|
||||
Vss 10 | PIC17C4X | 31 Vss
|
||||
RB0/CAP1 11 | | 30 RE0/ALE
|
||||
RB1/CAP2 12 | | 29 RE1/_OE
|
||||
RB2/PWM1 13 | | 28 RE2/_WR
|
||||
RB3/PWM2 14 | | 27 TEST
|
||||
RB4/TCLK12 15 | | 26 RA0/INT
|
||||
RB5/TCLK3 16 | | 25 RA1/T0CKI
|
||||
RB6 17 | | 24 RA2
|
||||
RB7 18 | | 23 RA3
|
||||
OSC1/CLKIN 19 | | 22 RA4/RX/DT
|
||||
OSC2/CLKOUT 20 |______________| 21 RA5/TX/CK
|
||||
|
||||
**********************************************************************/
|
||||
|
||||
#ifndef MAME_CPU_PIC17_PIC17C4X_H
|
||||
#define MAME_CPU_PIC17_PIC17C4X_H
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "pic17.h"
|
||||
|
||||
class pic17c4x_device : public pic17_cpu_device
|
||||
{
|
||||
public:
|
||||
enum {
|
||||
RA0_LINE = 0,
|
||||
INT_LINE = RA0_LINE,
|
||||
RA1_LINE = 1,
|
||||
T0CKI_LINE = RA1_LINE,
|
||||
RA2_LINE = 2,
|
||||
RA3_LINE = 3,
|
||||
RA4_LINE = 4,
|
||||
RX_LINE = RA4_LINE,
|
||||
RA5_LINE = 5
|
||||
};
|
||||
|
||||
enum {
|
||||
PIC17_LATA = PIC17_PS + 1,
|
||||
PIC17_DDRB,
|
||||
PIC17_LATB,
|
||||
PIC17_TMR1,
|
||||
PIC17_TMR2,
|
||||
PIC17_TMR3,
|
||||
PIC17_PR1,
|
||||
PIC17_PR2,
|
||||
PIC17_CA1,
|
||||
PIC17_CA2,
|
||||
PIC17_TCON1,
|
||||
PIC17_TCON2,
|
||||
PIC17_RCSTA,
|
||||
PIC17_TXSTA,
|
||||
PIC17_SPBRG,
|
||||
PIC17_PIE,
|
||||
PIC17_PIR
|
||||
};
|
||||
|
||||
// callback configuration
|
||||
auto ra_out_cb() { return m_port_out_cb[0].bind(); }
|
||||
auto rb_out_cb() { return m_port_out_cb[1].bind(); }
|
||||
auto rc_out_cb() { return m_port_out_cb[2].bind(); }
|
||||
auto rd_out_cb() { return m_port_out_cb[3].bind(); }
|
||||
auto re_out_cb() { return m_port_out_cb[4].bind(); }
|
||||
|
||||
protected:
|
||||
pic17c4x_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, u16 rom_size, address_map_constructor data_map);
|
||||
|
||||
// device-level overrides
|
||||
virtual void device_resolve_objects() override;
|
||||
virtual void device_start() override;
|
||||
virtual void device_reset() override;
|
||||
|
||||
// device_execute_interface overrides
|
||||
virtual u32 execute_input_lines() const noexcept override { return 6; } // for now
|
||||
virtual bool execute_input_edge_triggered(int linenum) const noexcept override { return linenum == INT_LINE || linenum == T0CKI_LINE; }
|
||||
virtual void execute_set_input(int linenum, int state) override;
|
||||
|
||||
void data_map(address_map &map);
|
||||
|
||||
virtual void increment_timers() override;
|
||||
|
||||
private:
|
||||
u8 porta_r();
|
||||
void porta_w(u8 data);
|
||||
u8 ddrb_r();
|
||||
void ddrb_w(u8 data);
|
||||
u8 portb_r();
|
||||
void portb_w(u8 data);
|
||||
u8 tmr1_r();
|
||||
void tmr1_w(u8 data);
|
||||
u8 tmr2_r();
|
||||
void tmr2_w(u8 data);
|
||||
u8 tmr3l_r();
|
||||
void tmr3l_w(u8 data);
|
||||
u8 tmr3h_r();
|
||||
void tmr3h_w(u8 data);
|
||||
u8 pr1_r();
|
||||
void pr1_w(u8 data);
|
||||
u8 pr2_r();
|
||||
void pr2_w(u8 data);
|
||||
u8 pr3l_ca1l_r();
|
||||
void pr3l_ca1l_w(u8 data);
|
||||
u8 pr3h_ca1h_r();
|
||||
void pr3h_ca1h_w(u8 data);
|
||||
u8 ca2l_r();
|
||||
u8 ca2h_r();
|
||||
u8 tcon1_r();
|
||||
void tcon1_w(u8 data);
|
||||
u8 tcon2_r();
|
||||
void tcon2_w(u8 data);
|
||||
u8 rcsta_r();
|
||||
void rcsta_w(u8 data);
|
||||
u8 txsta_r();
|
||||
void txsta_w(u8 data);
|
||||
void txreg_w(u8 data);
|
||||
u8 spbrg_r();
|
||||
void spbrg_w(u8 data);
|
||||
u8 pir_r();
|
||||
void pir_w(u8 data);
|
||||
u8 pie_r();
|
||||
void pie_w(u8 data);
|
||||
|
||||
// callback objects
|
||||
devcb_write8::array<5> m_port_out_cb;
|
||||
|
||||
// internal state
|
||||
u8 m_rain;
|
||||
u8 m_lata;
|
||||
bool m_rbpu;
|
||||
u8 m_ddrb;
|
||||
u8 m_latb;
|
||||
u8 m_tmr8bit[2];
|
||||
u8 m_pr8bit[2];
|
||||
u16 m_tmr3;
|
||||
u16 m_ca16bit[2];
|
||||
u8 m_tcon1;
|
||||
u8 m_tcon2;
|
||||
u8 m_rcsta;
|
||||
u8 m_txsta;
|
||||
u8 m_spbrg;
|
||||
u8 m_pir;
|
||||
u8 m_pie;
|
||||
};
|
||||
|
||||
class pic17c43_device : public pic17c4x_device
|
||||
{
|
||||
public:
|
||||
// device type constructor
|
||||
pic17c43_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock);
|
||||
|
||||
protected:
|
||||
pic17c43_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, u16 rom_size);
|
||||
|
||||
private:
|
||||
void data_map(address_map &map);
|
||||
};
|
||||
|
||||
class pic17c44_device : public pic17c43_device
|
||||
{
|
||||
public:
|
||||
// device type constructor
|
||||
pic17c44_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock);
|
||||
};
|
||||
|
||||
// device type declarations
|
||||
DECLARE_DEVICE_TYPE(PIC17C43, pic17c43_device)
|
||||
DECLARE_DEVICE_TYPE(PIC17C44, pic17c44_device)
|
||||
|
||||
#endif // MAME_CPU_PIC17_PIC17C4X_H
|
239
src/devices/cpu/pic17/pic17d.cpp
Normal file
239
src/devices/cpu/pic17/pic17d.cpp
Normal file
@ -0,0 +1,239 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:AJR
|
||||
/***************************************************************************
|
||||
|
||||
Microchip PIC17 disassembler
|
||||
|
||||
***************************************************************************/
|
||||
|
||||
#include "emu.h"
|
||||
#include "pic17d.h"
|
||||
|
||||
const char *const pic17_disassembler::s_peripheral_regs[0x20] =
|
||||
{
|
||||
"INDF0", "FSR0", "PCL", "PCLATH", "ALUSTA", "T0STA", "CPUSTA", "INTSTA",
|
||||
"INDF1", "FSR1", "WREG", "TMR0L", "TMR0H", "TBLPTRL", "TBLPTRH", "BSR",
|
||||
nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, // banked
|
||||
"PRODL", "PRODH", nullptr, nullptr, nullptr, nullptr, nullptr, nullptr
|
||||
};
|
||||
|
||||
const char *const pic17_disassembler::s_tb_ops[4] =
|
||||
{
|
||||
"TLRD", "TLWT", "TABLRD", "TABLWT"
|
||||
};
|
||||
|
||||
const char *const pic17_disassembler::s_bit_ops[4] =
|
||||
{
|
||||
"BSF", "BCF", "BTFSS", "BTFSC"
|
||||
};
|
||||
|
||||
const char *const pic17_disassembler::s_cp_ops[4] =
|
||||
{
|
||||
"CPFSLT", "CPFSEQ", "CPFSGT", "TSTFSZ"
|
||||
};
|
||||
|
||||
const char *const pic17_disassembler::s_alu_ops[0x30 / 2] =
|
||||
{
|
||||
"MOVWF", "SUBWFB", "SUBWF", "DECF", "IORWF", "ANDWF", "XORWF", "ADDWF",
|
||||
"ADDWFC", "COMF", "INCF", "DECFSZ", "RRCF", "RLCF", "SWAPF", "INCFSZ",
|
||||
"RRNCF", "RLNCF", "INFSNZ", "DCFSNZ", "CLRF", "SETF", "NEGW", "DAW"
|
||||
};
|
||||
|
||||
pic17_disassembler::pic17_disassembler()
|
||||
: util::disasm_interface()
|
||||
{
|
||||
}
|
||||
|
||||
u32 pic17_disassembler::opcode_alignment() const
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
void pic17_disassembler::format_register(std::ostream &stream, u8 reg) const
|
||||
{
|
||||
if (reg < 0x20 && s_peripheral_regs[reg] != nullptr)
|
||||
stream << s_peripheral_regs[reg];
|
||||
else
|
||||
util::stream_format(stream, "R%02X", reg);
|
||||
}
|
||||
|
||||
void pic17_disassembler::format_literal(std::ostream &stream, u8 data) const
|
||||
{
|
||||
util::stream_format(stream, "%02Xh", data);
|
||||
}
|
||||
|
||||
void pic17_disassembler::format_address(std::ostream &stream, u16 dst) const
|
||||
{
|
||||
util::stream_format(stream, "%04Xh", dst);
|
||||
}
|
||||
|
||||
offs_t pic17_disassembler::disassemble(std::ostream &stream, offs_t pc, const pic17_disassembler::data_buffer &opcodes, const pic17_disassembler::data_buffer ¶ms)
|
||||
{
|
||||
u16 opcode = opcodes.r16(pc);
|
||||
offs_t words = 1;
|
||||
|
||||
if (opcode >= 0xc000)
|
||||
{
|
||||
if (BIT(opcode, 13))
|
||||
{
|
||||
util::stream_format(stream, "%-8s", "CALL");
|
||||
words |= STEP_OVER;
|
||||
}
|
||||
else
|
||||
util::stream_format(stream, "%-8s", "GOTO");
|
||||
format_address(stream, ((pc + 1) & 0xe000) | (opcode & 0x1fff));
|
||||
}
|
||||
else if (opcode >= 0xb000)
|
||||
{
|
||||
// Literal and control operations
|
||||
switch (opcode & 0x0f00)
|
||||
{
|
||||
case 0x000:
|
||||
util::stream_format(stream, "%-8s", "MOVLW");
|
||||
format_literal(stream, opcode & 0x00ff);
|
||||
break;
|
||||
|
||||
case 0x100:
|
||||
util::stream_format(stream, "%-8s", "ADDLW");
|
||||
format_literal(stream, opcode & 0x00ff);
|
||||
break;
|
||||
|
||||
case 0x200:
|
||||
util::stream_format(stream, "%-8s", "SUBLW");
|
||||
format_literal(stream, opcode & 0x00ff);
|
||||
break;
|
||||
|
||||
case 0x300:
|
||||
util::stream_format(stream, "%-8s", "IORLW");
|
||||
format_literal(stream, opcode & 0x00ff);
|
||||
break;
|
||||
|
||||
case 0x400:
|
||||
util::stream_format(stream, "%-8s", "XORLW");
|
||||
format_literal(stream, opcode & 0x00ff);
|
||||
break;
|
||||
|
||||
case 0x500:
|
||||
util::stream_format(stream, "%-8s", "ANDLW");
|
||||
format_literal(stream, opcode & 0x00ff);
|
||||
break;
|
||||
|
||||
case 0x600:
|
||||
util::stream_format(stream, "%-8s", "RETLW");
|
||||
format_literal(stream, opcode & 0x00ff);
|
||||
words |= STEP_OUT;
|
||||
break;
|
||||
|
||||
case 0x700:
|
||||
util::stream_format(stream, "%-8s", "LCALL");
|
||||
format_literal(stream, opcode & 0x00ff);
|
||||
words |= STEP_OVER;
|
||||
break;
|
||||
|
||||
case 0x800:
|
||||
util::stream_format(stream, "%-8s%d", "MOVLB", opcode & 0x000f);
|
||||
break;
|
||||
|
||||
case 0xa00: case 0xb00:
|
||||
util::stream_format(stream, "%-8s%d", "MOVLR", (opcode & 0x00f0) >> 4);
|
||||
break;
|
||||
|
||||
case 0xc00:
|
||||
util::stream_format(stream, "%-8s", "MULLW");
|
||||
format_literal(stream, opcode & 0x00ff);
|
||||
break;
|
||||
|
||||
default:
|
||||
util::stream_format(stream, "%-8s%04Xh", "DW", opcode);
|
||||
break;
|
||||
}
|
||||
}
|
||||
else if (opcode >= 0xa000)
|
||||
{
|
||||
util::stream_format(stream, "%-8s%d,", s_tb_ops[BIT(opcode, 10, 2)], BIT(opcode, 9));
|
||||
if (BIT(opcode, 11))
|
||||
util::stream_format(stream, "%d,", BIT(opcode, 8));
|
||||
format_register(stream, opcode & 0x00ff);
|
||||
}
|
||||
else if (opcode >= 0x8000)
|
||||
{
|
||||
// Bit-oriented file register operations
|
||||
util::stream_format(stream, "%-8s", s_bit_ops[BIT(opcode, 11, 2)]);
|
||||
format_register(stream, opcode & 0x00ff);
|
||||
util::stream_format(stream, ",%d", BIT(opcode, 8, 3));
|
||||
}
|
||||
else if (opcode >= 0x6000)
|
||||
{
|
||||
// Byte-to-byte move operations
|
||||
util::stream_format(stream, "%-8s", "MOVFP");
|
||||
format_register(stream, opcode & 0x00ff);
|
||||
stream << ",";
|
||||
format_register(stream, (opcode & 0x1f00) >> 8);
|
||||
}
|
||||
else if (opcode >= 0x4000)
|
||||
{
|
||||
util::stream_format(stream, "%-8s", "MOVPF");
|
||||
format_register(stream, (opcode & 0x1f00) >> 8);
|
||||
stream << ",";
|
||||
format_register(stream, opcode & 0x00ff);
|
||||
}
|
||||
else if (opcode >= 0x3800)
|
||||
{
|
||||
util::stream_format(stream, "%-8s", "BTG");
|
||||
format_register(stream, opcode & 0x00ff);
|
||||
util::stream_format(stream, ",%d", BIT(opcode, 8, 3));
|
||||
}
|
||||
else if (opcode >= 0x3000)
|
||||
{
|
||||
if (opcode < 0x3400)
|
||||
{
|
||||
util::stream_format(stream, "%-8s", s_cp_ops[BIT(opcode, 8, 2)]);
|
||||
format_register(stream, opcode & 0x00ff);
|
||||
}
|
||||
else if (opcode < 0x3500)
|
||||
{
|
||||
util::stream_format(stream, "%-8s", "MULWF");
|
||||
format_register(stream, opcode & 0x00ff);
|
||||
}
|
||||
else
|
||||
util::stream_format(stream, "%-8s%04Xh", "DW", opcode);
|
||||
}
|
||||
else if (opcode >= 0x0100)
|
||||
{
|
||||
// Byte-oriented file register operations
|
||||
util::stream_format(stream, "%-8s", s_alu_ops[BIT(opcode, 9, 5)]);
|
||||
format_register(stream, opcode & 0x00ff);
|
||||
if (opcode >= 0x0200)
|
||||
util::stream_format(stream, ",%c", BIT(opcode, 8) ? 'F' : 'W');
|
||||
}
|
||||
else switch (opcode)
|
||||
{
|
||||
case 0x0000:
|
||||
stream << "NOP";
|
||||
break;
|
||||
|
||||
case 0x0002:
|
||||
stream << "RETURN";
|
||||
words |= STEP_OUT;
|
||||
break;
|
||||
|
||||
case 0x0003:
|
||||
stream << "SLEEP";
|
||||
break;
|
||||
|
||||
case 0x0004:
|
||||
stream << "CLRWDT";
|
||||
break;
|
||||
|
||||
case 0x0005:
|
||||
stream << "RETFIE";
|
||||
words |= STEP_OUT;
|
||||
break;
|
||||
|
||||
default:
|
||||
util::stream_format(stream, "%-8s%04Xh", "DW", opcode);
|
||||
break;
|
||||
}
|
||||
|
||||
return words;
|
||||
}
|
36
src/devices/cpu/pic17/pic17d.h
Normal file
36
src/devices/cpu/pic17/pic17d.h
Normal file
@ -0,0 +1,36 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:AJR
|
||||
|
||||
#ifndef MAME_CPU_PIC17_PIC17D_H
|
||||
#define MAME_CPU_PIC17_PIC17D_H
|
||||
|
||||
#pragma once
|
||||
|
||||
class pic17_disassembler : public util::disasm_interface
|
||||
{
|
||||
public:
|
||||
// construction/destruction
|
||||
pic17_disassembler();
|
||||
|
||||
protected:
|
||||
// disassembler overrides
|
||||
virtual u32 opcode_alignment() const override;
|
||||
virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override;
|
||||
|
||||
private:
|
||||
// register names
|
||||
static const char *const s_peripheral_regs[0x20];
|
||||
|
||||
// instruction mnemonics
|
||||
static const char *const s_tb_ops[4];
|
||||
static const char *const s_bit_ops[4];
|
||||
static const char *const s_cp_ops[4];
|
||||
static const char *const s_alu_ops[0x30 / 2];
|
||||
|
||||
// internal helpers
|
||||
void format_register(std::ostream &stream, u8 reg) const;
|
||||
void format_literal(std::ostream &stream, u8 data) const;
|
||||
void format_address(std::ostream &stream, u16 dst) const;
|
||||
};
|
||||
|
||||
#endif // MAME_CPU_PIC17_PIC17D_H
|
@ -32,7 +32,7 @@
|
||||
*/
|
||||
|
||||
#include "emu.h"
|
||||
#include "cpu/pic16c5x/pic16c5x.h"
|
||||
#include "cpu/pic17/pic17c4x.h"
|
||||
#include "machine/nvram.h"
|
||||
#include "sound/okim6376.h"
|
||||
#include "speaker.h"
|
||||
@ -59,7 +59,7 @@ INPUT_PORTS_END
|
||||
|
||||
void teamjocs_state::teamjocs(machine_config &config)
|
||||
{
|
||||
PIC16C55(config, m_maincpu, 4_MHz_XTAL); // actually PIC17C44-16
|
||||
PIC17C44(config, m_maincpu, 4_MHz_XTAL);
|
||||
|
||||
SPEAKER(config, "mono").front_center();
|
||||
|
||||
|
197
src/mame/drivers/xbase09.cpp
Normal file
197
src/mame/drivers/xbase09.cpp
Normal file
@ -0,0 +1,197 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:AJR
|
||||
/****************************************************************************
|
||||
|
||||
Skeleton driver for XBase 09 drum machine by JoMoX GmbH.
|
||||
|
||||
****************************************************************************/
|
||||
|
||||
#include "emu.h"
|
||||
#include "cpu/pic17/pic17c4x.h"
|
||||
#include "machine/nvram.h"
|
||||
|
||||
class xbase09_state : public driver_device
|
||||
{
|
||||
public:
|
||||
xbase09_state(const machine_config &mconfig, device_type type, const char *tag)
|
||||
: driver_device(mconfig, type, tag)
|
||||
, m_maincpu(*this, "maincpu")
|
||||
, m_analog_ports(*this, "ANALOG%02X", 0U)
|
||||
, m_port_select(0)
|
||||
{
|
||||
}
|
||||
|
||||
void xbase09(machine_config &config);
|
||||
|
||||
protected:
|
||||
virtual void machine_start() override;
|
||||
|
||||
private:
|
||||
void portb_w(u8 data);
|
||||
u16 ram_r(offs_t offset);
|
||||
void ram_w(offs_t offset, u16 data);
|
||||
void mem_map(address_map &map);
|
||||
|
||||
required_device<pic17c4x_device> m_maincpu;
|
||||
required_ioport_array<0x16> m_analog_ports;
|
||||
|
||||
std::unique_ptr<u8[]> m_nvram_data;
|
||||
u8 m_port_select;
|
||||
};
|
||||
|
||||
void xbase09_state::machine_start()
|
||||
{
|
||||
m_nvram_data = std::make_unique<u8[]>(0x8000);
|
||||
subdevice<nvram_device>("nvram")->set_base(m_nvram_data.get(), 0x8000);
|
||||
|
||||
save_pointer(NAME(m_nvram_data), 0x8000);
|
||||
save_item(NAME(m_port_select));
|
||||
}
|
||||
|
||||
|
||||
void xbase09_state::portb_w(u8 data)
|
||||
{
|
||||
m_port_select = data >> 3;
|
||||
}
|
||||
|
||||
u16 xbase09_state::ram_r(offs_t offset)
|
||||
{
|
||||
return m_nvram_data[offset] | 0xff00;
|
||||
}
|
||||
|
||||
void xbase09_state::ram_w(offs_t offset, u16 data)
|
||||
{
|
||||
switch (offset)
|
||||
{
|
||||
case 0x0007:
|
||||
// Successive-approximation ADC implemented using software algorithm and LM393 comparator
|
||||
if (m_port_select < 0x16 && m_analog_ports[m_port_select]->read() < (data >> 8))
|
||||
m_maincpu->set_input_line(pic17c4x_device::RA0_LINE, ASSERT_LINE);
|
||||
else
|
||||
m_maincpu->set_input_line(pic17c4x_device::RA0_LINE, CLEAR_LINE);
|
||||
break;
|
||||
|
||||
default:
|
||||
if ((data & 0xff00) != 0)
|
||||
logerror("%s: Writing %04X to %04X\n", machine().describe_context(), data, offset + 0x8000);
|
||||
break;
|
||||
}
|
||||
|
||||
m_nvram_data[offset] = data & 0x00ff;
|
||||
}
|
||||
|
||||
|
||||
void xbase09_state::mem_map(address_map &map)
|
||||
{
|
||||
map(0x0000, 0x7fff).rom().region("firmware", 0);
|
||||
map(0x8000, 0xffff).rw(FUNC(xbase09_state::ram_r), FUNC(xbase09_state::ram_w));
|
||||
}
|
||||
|
||||
|
||||
static INPUT_PORTS_START(xbase09)
|
||||
PORT_START("ANALOG00")
|
||||
PORT_BIT(0xff, 0x00, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG01")
|
||||
PORT_BIT(0xff, 0x01, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG02")
|
||||
PORT_BIT(0xff, 0x02, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG03")
|
||||
PORT_BIT(0xff, 0x03, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG04")
|
||||
PORT_BIT(0xff, 0x04, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG05")
|
||||
PORT_BIT(0xff, 0x05, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG06")
|
||||
PORT_BIT(0xff, 0x06, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG07")
|
||||
PORT_BIT(0xff, 0x07, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG08")
|
||||
PORT_BIT(0xff, 0x08, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG09")
|
||||
PORT_BIT(0xff, 0x09, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG0A")
|
||||
PORT_BIT(0xff, 0x0a, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG0B")
|
||||
PORT_BIT(0xff, 0x14, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG0C")
|
||||
PORT_BIT(0xff, 0x1e, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG0D")
|
||||
PORT_BIT(0xff, 0x28, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG0E")
|
||||
PORT_BIT(0xff, 0x32, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG0F")
|
||||
PORT_BIT(0xff, 0x3c, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG10")
|
||||
PORT_BIT(0xff, 0x46, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG11")
|
||||
PORT_BIT(0xff, 0x50, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG12")
|
||||
PORT_BIT(0xff, 0x5a, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG13")
|
||||
PORT_BIT(0xff, 0x64, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG14")
|
||||
PORT_BIT(0xff, 0xc8, IPT_UNKNOWN)
|
||||
|
||||
PORT_START("ANALOG15")
|
||||
PORT_BIT(0xff, 0xff, IPT_UNKNOWN)
|
||||
INPUT_PORTS_END
|
||||
|
||||
void xbase09_state::xbase09(machine_config &config)
|
||||
{
|
||||
PIC17C43(config, m_maincpu, 16_MHz_XTAL); // PIC17C43-16/P
|
||||
m_maincpu->set_mode(pic17c43_device::mode::MICROPROCESSOR);
|
||||
m_maincpu->set_addrmap(AS_PROGRAM, &xbase09_state::mem_map);
|
||||
m_maincpu->rb_out_cb().set(FUNC(xbase09_state::portb_w));
|
||||
|
||||
NVRAM(config, "nvram", nvram_device::DEFAULT_ALL_0); // SRM2B256SLMX10, NEC D43256BGU-70LL or equivalent + battery
|
||||
|
||||
//MAX509(config, "dac"); // MAX509BWCP (near top of PCB)
|
||||
}
|
||||
|
||||
// IC positions are not labeled on PCB except for stickered PLDs
|
||||
ROM_START(xbase09)
|
||||
ROM_REGION16_LE(0x10000, "firmware", 0)
|
||||
ROM_DEFAULT_BIOS("v209")
|
||||
ROM_SYSTEM_BIOS(0, "v132", "Version 1.32")
|
||||
ROMX_LOAD("xbase_09__1.32l.bin", 0x0000, 0x8000, CRC(30dc47c6) SHA1(ee79f9e98c06edd8a5963fcd325da3490e8e5b76), ROM_BIOS(0) | ROM_SKIP(1))
|
||||
ROMX_LOAD("xbase_09__1.32h.bin", 0x0001, 0x8000, CRC(ce2df930) SHA1(56922d069b53013f2a3646dcd63fbbc9b609cf5b), ROM_BIOS(0) | ROM_SKIP(1))
|
||||
ROM_SYSTEM_BIOS(1, "v208", "Version 2.08 (without Tempo lock)")
|
||||
ROMX_LOAD("xbase_09__2.08l.bin", 0x0000, 0x8000, CRC(c0f06ef6) SHA1(912f0b01cf5cfdc37ce61b3eacf933174f80171d), ROM_BIOS(1) | ROM_SKIP(1))
|
||||
ROMX_LOAD("xbase_09__2.08h.bin", 0x0001, 0x8000, CRC(f1287888) SHA1(ee162887af1cfe968004b8c2e1c5417be42b2e9f), ROM_BIOS(1) | ROM_SKIP(1))
|
||||
ROM_SYSTEM_BIOS(2, "v209", "Version 2.09 (with Tempo lock)")
|
||||
ROMX_LOAD("xbase_09__2.09l.bin", 0x0000, 0x8000, CRC(60667060) SHA1(6a004934dd3f5f729f59bcbcb79e86e0e5f97fe9), ROM_BIOS(2) | ROM_SKIP(1))
|
||||
ROMX_LOAD("xbase_09__2.09h.bin", 0x0001, 0x8000, CRC(64645c77) SHA1(35cc18774d9e4cc61af0469144c49dddfabc92b7), ROM_BIOS(2) | ROM_SKIP(1))
|
||||
ROM_SYSTEM_BIOS(3, "sx209", "SX Version 2.09") // "requires hardware update," so may need to be a separate system
|
||||
ROMX_LOAD("xbase09sx_2.09l.bin", 0x0000, 0x8000, CRC(7e87c30d) SHA1(2237f235749ae583327f1f8d893ceb3bb6502ae9), ROM_BIOS(3) | ROM_SKIP(1))
|
||||
ROMX_LOAD("xbase09sx_2.09h.bin", 0x0001, 0x8000, CRC(ac9ad2e3) SHA1(8977e4520072b4ef6b603bcb0574663f10ba2629), ROM_BIOS(3) | ROM_SKIP(1))
|
||||
|
||||
ROM_REGION(0x10000, "hhrom", 0)
|
||||
ROM_LOAD("xbase_09__rom_0.bin", 0x00000, 0x10000, NO_DUMP) // size unknown
|
||||
|
||||
ROM_REGION(0x3000, "plds", 0)
|
||||
ROM_LOAD("xbase.ic17", 0x0000, 0x0a92, NO_DUMP) // next to CPU
|
||||
ROM_LOAD("xbase.ic59", 0x1000, 0x0a92, NO_DUMP) // right side of HH ROM
|
||||
ROM_LOAD("xbase.ic60", 0x2000, 0x0a92, NO_DUMP) // left side of HH ROM; confirmed to be a PALCE20V8H-15PC/4
|
||||
ROM_END
|
||||
|
||||
SYST(1997, xbase09, 0, 0, xbase09, xbase09, xbase09_state, empty_init, "JoMoX", "XBase 09 Midi Controlled Analogue Drum Module", MACHINE_IS_SKELETON)
|
@ -41756,6 +41756,9 @@ ltv_naru //
|
||||
domfitad //
|
||||
dombikec //
|
||||
|
||||
@source:xbase09.cpp
|
||||
xbase09 //
|
||||
|
||||
@source:xbox.cpp
|
||||
xbox //
|
||||
|
||||
|
@ -1081,6 +1081,7 @@ x1twin.cpp
|
||||
x68k.cpp
|
||||
xavix.cpp
|
||||
xavix2.cpp
|
||||
xbase09.cpp
|
||||
xbox.cpp
|
||||
xerox820.cpp
|
||||
xor100.cpp
|
||||
|
@ -119,6 +119,7 @@ using util::BIT;
|
||||
#include "cpu/pic16/pic16d.h"
|
||||
#include "cpu/pic16c5x/16c5xdsm.h"
|
||||
#include "cpu/pic16c62x/16c62xdsm.h"
|
||||
#include "cpu/pic17/pic17d.h"
|
||||
#include "cpu/powerpc/ppc_dasm.h"
|
||||
#include "cpu/pps4/pps4dasm.h"
|
||||
#include "cpu/psx/psxdasm.h"
|
||||
@ -480,6 +481,7 @@ static const dasm_table_entry dasm_table[] =
|
||||
{ "pic16", le, -1, []() -> util::disasm_interface * { return new pic16_disassembler; } },
|
||||
{ "pic16c5x", le, -1, []() -> util::disasm_interface * { return new pic16c5x_disassembler; } },
|
||||
{ "pic16c62x", le, -1, []() -> util::disasm_interface * { return new pic16c62x_disassembler; } },
|
||||
{ "pic17", le, -1, []() -> util::disasm_interface * { return new pic17_disassembler; } },
|
||||
{ "powerpc", be, 0, []() -> util::disasm_interface * { return new powerpc_disassembler; } },
|
||||
{ "pps4", le, 0, []() -> util::disasm_interface * { return new pps4_disassembler; } },
|
||||
{ "psxcpu", le, 0, []() -> util::disasm_interface * { return new psxcpu_disassembler; } },
|
||||
|
Loading…
Reference in New Issue
Block a user