s2000 improved d-latch

This commit is contained in:
hap 2015-02-01 13:27:28 +01:00
parent 09b6ec9869
commit 80fd679d31
5 changed files with 50 additions and 36 deletions

View File

@ -5,9 +5,9 @@
American Microsystems, Inc.(AMI) S2000-family 4-bit MCU cores, introduced late 1970s
TODO:
- bug(s)? - MESS wildfire.c doesn't work yet
- unemulated opcodes (need more testing material)
- support external program map
- STATUS pin(wildfire.c sound?)
- add 50/60hz timer
- add S2200/S2400
@ -16,6 +16,8 @@
#include "amis2000.h"
#include "debugger.h"
#include "amis2000op.inc"
// S2000 is the most basic one, 64 nibbles internal RAM and 1KB internal ROM
// S2150 increased RAM to 80 nibbles and ROM to 1.5KB
@ -31,7 +33,8 @@ ADDRESS_MAP_END
static ADDRESS_MAP_START(program_1_5k, AS_PROGRAM, 8, amis2000_device)
AM_RANGE(0x0000, 0x03ff) AM_ROM
AM_RANGE(0x0400, 0x05ff) AM_ROM AM_MIRROR(0x200)
AM_RANGE(0x0400, 0x05ff) AM_NOP
AM_RANGE(0x0600, 0x07ff) AM_ROM
ADDRESS_MAP_END
@ -151,6 +154,8 @@ void amis2000_device::device_start()
m_i = 0;
m_k = 0;
m_d = 0;
m_d_active = false;
m_d_polarity = 0;
m_a = 0;
// register for savestates
@ -170,6 +175,8 @@ void amis2000_device::device_start()
save_item(NAME(m_i));
save_item(NAME(m_k));
save_item(NAME(m_d));
save_item(NAME(m_d_active));
save_item(NAME(m_d_polarity));
save_item(NAME(m_a));
// register state for debugger
@ -199,10 +206,11 @@ void amis2000_device::device_reset()
m_op = 0;
// clear i/o
m_d_polarity = 0;
m_d = 0; d_latch_out(false);
m_a = 0; m_write_a(0, 0, 0xffff);
m_i = 0;
m_k = 0;
m_d = 0; m_write_d(0, 0, 0xff);
m_a = 0; m_write_a(0, 0, 0xffff);
}
@ -211,8 +219,6 @@ void amis2000_device::device_reset()
// execute
//-------------------------------------------------
#include "amis2000op.inc"
void amis2000_device::execute_run()
{
while (m_icount > 0)
@ -246,7 +252,7 @@ void amis2000_device::execute_run()
switch (m_op)
{
case 0x00: op_nop(); break;
case 0x01: op_illegal(); break; // reserved for devkit-use
case 0x01: op_halt(); break;
case 0x02: op_rt(); break;
case 0x03: op_rts(); break;
case 0x04: op_psh(); break;

View File

@ -92,6 +92,8 @@ protected:
UINT8 m_i; // 4-bit i-pins latch
UINT8 m_k; // 4-bit k-pins latch
UINT8 m_d; // 8-bit d-pins latch
bool m_d_active; // d-pins available for direct i/o(floating), or outputting d-latch
UINT8 m_d_polarity; // invert d-latch output
UINT16 m_a; // 13-bit a-pins latch (master strobe latch)
devcb_read8 m_read_k;
@ -106,7 +108,7 @@ protected:
void ram_w(UINT8 data);
void pop_callstack();
void push_callstack();
void op_illegal();
void d_latch_out(bool active);
void op_lai();
void op_lab();
@ -141,6 +143,7 @@ protected:
void op_rt();
void op_rts();
void op_nop();
void op_halt();
void op_szc();
void op_szm();

View File

@ -17,9 +17,8 @@ enum e_mnemonics
mLAM, mXC, mXCI, mXCD, mSTM, mRSM,
mADD, mADCS, mADIS, mAND, mXOR, mCMA, mSTC, mRSC, mSF1, mRF1, mSF2, mRF2,
mSAM, mSZM, mSBE, mSZC, mSOS, mSZK, mSZI, mTF1, mTF2,
mPP, mJMP, mJMS, mRT, mRTS, mNOP,
mINP, mOUT, mDISB, mDISN, mMVS, mPSH, mPSL, mEUR,
mILL
mPP, mJMP, mJMS, mRT, mRTS, mNOP, mHALT,
mINP, mOUT, mDISB, mDISN, mMVS, mPSH, mPSL, mEUR
};
static const char *const s_mnemonics[] =
@ -28,9 +27,8 @@ static const char *const s_mnemonics[] =
"LAM", "XC", "XCI", "XCD", "STM", "RSM",
"ADD", "ADCS", "ADIS", "AND", "XOR", "CMA", "STC", "RSC", "SF1", "RF1", "SF2", "RF2",
"SAM", "SZM", "SBE", "SZC", "SOS", "SZK", "SZI", "TF1", "TF2",
"PP", "JMP", "JMS", "RT", "RTS", "NOP",
"INP", "OUT", "DISB", "DISN", "MVS", "PSH", "PSL", "EUR",
"?"
"PP", "JMP", "JMS", "RT", "RTS", "NOP", "HALT",
"INP", "OUT", "DISB", "DISN", "MVS", "PSH", "PSL", "EUR"
};
@ -43,9 +41,8 @@ static const UINT32 s_flags[] =
0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, _OVER, _OUT, _OUT, 0,
0, 0, 0, 0, 0, 0, 0, 0,
0
0, 0, _OVER, _OUT, _OUT, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0
};
@ -55,16 +52,15 @@ static const int s_bits[] =
-2, -2, -2, -2, 2, 2,
0, 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 2, 0, 0, 0, 0, 0, 0, 0,
-4, 6, 6, 0, 0, 0,
-4, 6, 6, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0,
0
};
static const UINT8 s2000_mnemonic[0x100] =
{
/* 0x00 */
mNOP, mILL, mRT, mRTS, mPSH, mPSL, mAND, mSOS,
mNOP, mHALT, mRT, mRTS, mPSH, mPSL, mAND, mSOS,
mSBE, mSZC, mSTC, mRSC, mLAE, mXAE, mINP, mEUR,
/* 0x10 */
mCMA, mXABU, mLAB, mXAB, mADCS, mXOR, mADD, mSAM,

View File

@ -33,9 +33,10 @@ void amis2000_device::push_callstack()
m_callstack[0] = m_pc & m_callstack_mask;
}
void amis2000_device::op_illegal()
void amis2000_device::d_latch_out(bool active)
{
logerror("%s unknown opcode $%02X at $%04X\n", tag(), m_op, m_pc);
m_write_d(0, active ? (m_d ^ m_d_polarity) : 0, 0xff);
m_d_active = active;
}
@ -195,21 +196,22 @@ void amis2000_device::op_rsm()
void amis2000_device::op_inp()
{
// INP: input D-pins to ACC and RAM
op_illegal();
UINT8 in = m_d_active ? m_d : m_read_d(0, 0xff);
m_acc = in & 0xf;
ram_w(in >> 4 & 0xf);
}
void amis2000_device::op_out()
{
// OUT: pulse output ACC and RAM to D-pins
op_illegal();
logerror("%s unknown opcode $%02X at $%04X\n", tag(), m_op, m_pc);
}
void amis2000_device::op_disb()
{
// DISB: set D-latch to ACC and RAM directly
m_d = m_acc | ram_r() << 4;
m_write_d(0, m_d, 0xff);
// TODO: exit from floating mode on D-pins
d_latch_out(true);
}
void amis2000_device::op_disn()
@ -221,15 +223,14 @@ void amis2000_device::op_disn()
0x7e, 0x30, 0x6d, 0x79, 0x33, 0x5b, 0x5f, 0x70, 0x7f, 0x7b, 0x77, 0x1f, 0x4e, 0x3d, 0x4f, 0x47
};
m_d = lut_segment_decoder[m_acc] | (m_carry ? 0x80 : 0x00);
m_write_d(0, m_d, 0xff);
// TODO: exit from floating mode on D-pins
d_latch_out(true);
}
void amis2000_device::op_mvs()
{
// MVS: output master strobe latch to A-pins
d_latch_out(false);
m_write_a(0, m_a, 0xffff);
// TODO: enter floating mode on D-pins
}
void amis2000_device::op_psh()
@ -244,7 +245,7 @@ void amis2000_device::op_psh()
case 0xe:
// exit from floating mode on D-pins
// ?
d_latch_out(true);
break;
case 0xf:
@ -271,7 +272,7 @@ void amis2000_device::op_psl()
case 0xe:
// enter floating mode on D-pins
// ?
d_latch_out(false);
break;
case 0xf:
@ -288,8 +289,9 @@ void amis2000_device::op_psl()
void amis2000_device::op_eur()
{
// EUR: set timer frequency(European) and D-latch polarity
op_illegal();
// EUR: set timer frequency(European) and D-latch polarity, via ACC
m_d_polarity = (m_acc & 1) ? 0x00 : 0xff;
d_latch_out(m_d_active); // refresh
}
@ -350,6 +352,12 @@ void amis2000_device::op_nop()
// NOP: no operation
}
void amis2000_device::op_halt()
{
// HALT: debugger breakpoint for devkit-use
logerror("%s unknown opcode $%02X at $%04X\n", tag(), m_op, m_pc);
}
// Skip Instructions
@ -393,7 +401,7 @@ void amis2000_device::op_sam()
void amis2000_device::op_sos()
{
// SOS: skip next on SF(timer output), clear SF
op_illegal();
logerror("%s unknown opcode $%02X at $%04X\n", tag(), m_op, m_pc);
}
void amis2000_device::op_tf1()

View File

@ -108,8 +108,9 @@ MACHINE_CONFIG_END
***************************************************************************/
ROM_START( wildfire )
ROM_REGION( 0x0600, "maincpu", 0 )
ROM_LOAD( "us4341385", 0x0000, 0x0600, CRC(84ac0f1f) SHA1(1e00ddd402acfc2cc267c34eed4b89d863e2144f) ) // from patent US4334679, data should be correct (it included checksums)
ROM_REGION( 0x0800, "maincpu", ROMREGION_ERASE00 )
ROM_LOAD( "us4341385", 0x0000, 0x0400, CRC(84ac0f1f) SHA1(1e00ddd402acfc2cc267c34eed4b89d863e2144f) ) // from patent US4334679, data should be correct (it included checksums)
ROM_CONTINUE( 0x0600, 0x0200 )
ROM_END