1 // license:BSD-3-Clause
2 // copyright-holders:Robbbert
3 /******************************************************************************************
4 
5 2013-09-09 Skeleton of LFT computer system.
6 
7 These are the monitor programs for 80186-based "S100+" systems by L/F Technologies. Many
8 of these boards were distributed under the IMS International name. Documentation available
9 online is woefully inadequate.
10 
11 LFT1230 does extensive testing of devices at boot time. As they are mostly missing,
12 it gets caught in a loop. There's unknown devices in the i/o 008x, 00Ax, 00Cx range.
13 The devices at 008x and 00Cx would appear to be the same type.
14 BUG:If the rtc fails to clear the interrupt pin (first test), it cannot print the error
15 as the SCC hasn't yet been set up.
16 ***Status: hangs at start
17 
18 
19 LFT1510 doesn't bother with the tests. The i/o ports seem to be the same.
20 ***Status: mostly working
21 
22 
23 Note: Backspace/delete performs oddly.
24 
25 ******************************************************************************************/
26 
27 #include "emu.h"
28 #include "cpu/i86/i186.h"
29 #include "machine/mm58167.h"
30 #include "machine/z80scc.h"
31 #include "bus/rs232/rs232.h"
32 //#include "bus/s100/s100.h"
33 
34 
35 class lft_state : public driver_device
36 {
37 public:
lft_state(const machine_config & mconfig,device_type type,const char * tag)38 	lft_state(const machine_config &mconfig, device_type type, const char *tag)
39 		: driver_device(mconfig, type, tag)
40 		, m_maincpu(*this, "maincpu")
41 		, m_rtc(*this, "rtc")
42 		, m_scc(*this, "scc")
43 	{ }
44 
45 	void lft(machine_config &config);
46 
47 private:
48 	void io_map(address_map &map);
49 	void mem_map(address_map &map);
50 
51 	virtual void machine_reset() override;
52 	required_device<cpu_device> m_maincpu;
53 	required_device<mm58167_device> m_rtc;
54 	required_device<scc8530_device> m_scc;
55 };
56 
mem_map(address_map & map)57 void lft_state::mem_map(address_map &map)
58 {
59 	map.unmap_value_high();
60 	map(0x00000, 0x5ffff).ram();
61 	map(0xfc000, 0xfffff).rom().region("roms", 0);
62 }
63 
io_map(address_map & map)64 void lft_state::io_map(address_map &map)
65 {
66 	map.unmap_value_high();
67 	//map.global_mask(0x3ff);
68 	//map(0x0080, 0x0087) // unknown device
69 	//map(0x00a0, 0x00a?) // unknown device
70 	//map(0x00c0, 0x00c7) // unknown device
71 	map(0x0100, 0x0107).rw(m_scc, FUNC(z80scc_device::dc_ab_r), FUNC(z80scc_device::dc_ab_w)).umask16(0x00ff);
72 	map(0x0180, 0x01bf).rw(m_rtc, FUNC(mm58167_device::read), FUNC(mm58167_device::write)).umask16(0x00ff);
73 	//map(0x0200, 0x0207) // unknown device
74 }
75 
76 
77 /* Input ports */
INPUT_PORTS_START(lft)78 static INPUT_PORTS_START( lft )
79 INPUT_PORTS_END
80 
81 void lft_state::machine_reset()
82 {
83 }
84 
lft(machine_config & config)85 void lft_state::lft(machine_config &config)
86 {
87 	/* basic machine hardware */
88 	I80186(config, m_maincpu, 16_MHz_XTAL);
89 	m_maincpu->set_addrmap(AS_PROGRAM, &lft_state::mem_map);
90 	m_maincpu->set_addrmap(AS_IO, &lft_state::io_map);
91 
92 	// Devices
93 	MM58167(config, m_rtc, 32.768_kHz_XTAL);
94 
95 	SCC8530N(config, m_scc, 4.9152_MHz_XTAL);
96 	m_scc->out_txda_callback().set("rs232a", FUNC(rs232_port_device::write_txd));
97 	m_scc->out_dtra_callback().set("rs232a", FUNC(rs232_port_device::write_dtr));
98 	m_scc->out_rtsa_callback().set("rs232a", FUNC(rs232_port_device::write_rts));
99 
100 	rs232_port_device &rs232a(RS232_PORT(config, "rs232a", default_rs232_devices, nullptr));
101 	rs232a.rxd_handler().set(m_scc, FUNC(scc8530_device::rxa_w));
102 	rs232a.dcd_handler().set(m_scc, FUNC(scc8530_device::dcda_w));
103 	rs232a.cts_handler().set(m_scc, FUNC(scc8530_device::ctsa_w));
104 
105 	m_scc->out_txdb_callback().set("rs232b", FUNC(rs232_port_device::write_txd));
106 	m_scc->out_dtrb_callback().set("rs232b", FUNC(rs232_port_device::write_dtr));
107 	m_scc->out_rtsb_callback().set("rs232b", FUNC(rs232_port_device::write_rts));
108 
109 	rs232_port_device &rs232b(RS232_PORT(config, "rs232b", default_rs232_devices, "terminal"));
110 	rs232b.rxd_handler().set(m_scc, FUNC(scc8530_device::rxb_w));
111 	rs232b.dcd_handler().set(m_scc, FUNC(scc8530_device::dcdb_w));
112 	rs232b.cts_handler().set(m_scc, FUNC(scc8530_device::ctsb_w));
113 }
114 
115 
116 /* ROM definition */
117 ROM_START( lft1230 )
118 	ROM_REGION16_LE(0x4000, "roms", 0)
119 	ROM_LOAD16_BYTE( "1230lf29", 0x0000, 0x2000, CRC(11c87367) SHA1(0879650aa98e19a4e6ca7b6ee7874f81c9c8ccfa) )
120 	ROM_LOAD16_BYTE( "1230lf42", 0x0001, 0x2000, CRC(ab82b620) SHA1(8c7d93950703f348e5ce0f9e376d157dd6098c6a) )
121 ROM_END
122 
123 ROM_START( lft1510 )
124 	ROM_REGION16_LE(0x4000, "roms", 0)
125 	ROM_LOAD16_BYTE( "1510lfev", 0x2000, 0x1000, CRC(47dbb290) SHA1(b557e9a54a30d9a16edfdef4a6b12a5393d30bf3) )
126 	ROM_IGNORE(0x1000)
127 	ROM_LOAD16_BYTE( "1510lfod", 0x2001, 0x1000, CRC(ba8c23fc) SHA1(d4b82f69fccd653b31e7bd05ee884b323ff0007b) )
128 	ROM_IGNORE(0x1000)
129 ROM_END
130 
131 /* Driver */
132 
133 //    YEAR  NAME     PARENT   COMPAT  MACHINE  INPUT  CLASS      INIT        COMPANY             FULLNAME                      FLAGS
134 COMP( 1986, lft1510, 0,       0,      lft,     lft,   lft_state, empty_init, "L/F Technologies", "A1510 186 User Processor",   MACHINE_IS_SKELETON | MACHINE_SUPPORTS_SAVE )
135 COMP( 1985, lft1230, lft1510, 0,      lft,     lft,   lft_state, empty_init, "L/F Technologies", "A1230 186 Master Processor", MACHINE_IS_SKELETON | MACHINE_SUPPORTS_SAVE )
136