1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
|
/**********************************************************************
WARNING: DO NOT USE! WILL BE REMOVED IN FAVOR OF machine/mos6526.h
**********************************************************************
MOS 6526/8520 Complex Interface Adapter emulation
Copyright MESS Team.
Visit http://mamedev.org for licensing and usage restrictions.
**********************************************************************
_____ _____
Vss 1 |* \_/ | 40 CNT
PA0 2 | | 39 SP
PA1 3 | | 38 RS0
PA2 4 | | 37 RS1
PA3 5 | | 36 RS2
PA4 6 | | 35 RS3
PA5 7 | | 34 _RES
PA6 8 | | 33 DB0
PA7 9 | | 32 DB1
PB0 10 | MOS6526 | 31 DB2
PB1 11 | MOS8520 | 30 DB3
PB2 12 | | 29 DB4
PB3 13 | | 28 DB5
PB4 14 | | 27 DB6
PB5 15 | | 26 DB7
PB6 16 | | 25 phi2
PB7 17 | | 24 _FLAG
_PC 18 | | 23 _CS
TOD 19 | | 22 R/W
Vcc 20 |_____________| 21 _IRQ
**********************************************************************/
#pragma once
#ifndef __6526CIA_H__
#define __6526CIA_H__
#include "emu.h"
//**************************************************************************
// INTERFACE CONFIGURATION MACROS
//**************************************************************************
#define MCFG_MOS6526_TOD(_clock) \
legacy_mos6526_device::static_set_tod_clock(*device, _clock);
#define MCFG_MOS6526_IRQ_CALLBACK(_write) \
devcb = &legacy_mos6526_device::set_irq_wr_callback(*device, DEVCB2_##_write);
#define MCFG_MOS6526_CNT_CALLBACK(_write) \
devcb = &legacy_mos6526_device::set_cnt_wr_callback(*device, DEVCB2_##_write);
#define MCFG_MOS6526_SP_CALLBACK(_write) \
devcb = &legacy_mos6526_device::set_sp_wr_callback(*device, DEVCB2_##_write);
#define MCFG_MOS6526_PA_INPUT_CALLBACK(_read) \
devcb = &legacy_mos6526_device::set_pa_rd_callback(*device, DEVCB2_##_read);
#define MCFG_MOS6526_PA_OUTPUT_CALLBACK(_write) \
devcb = &legacy_mos6526_device::set_pa_wr_callback(*device, DEVCB2_##_write);
#define MCFG_MOS6526_PB_INPUT_CALLBACK(_read) \
devcb = &legacy_mos6526_device::set_pb_rd_callback(*device, DEVCB2_##_read);
#define MCFG_MOS6526_PB_OUTPUT_CALLBACK(_write) \
devcb = &legacy_mos6526_device::set_pb_wr_callback(*device, DEVCB2_##_write);
#define MCFG_MOS6526_PC_CALLBACK(_write) \
devcb = &legacy_mos6526_device::set_pc_wr_callback(*device, DEVCB2_##_write);
/***************************************************************************
TYPE DEFINITIONS
***************************************************************************/
// ======================> legacy_mos6526_device
class legacy_mos6526_device : public device_t
{
public:
// construction/destruction
legacy_mos6526_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, const char *shortname, const char *source);
static void static_set_tod_clock(device_t &device, int clock) { downcast<legacy_mos6526_device &>(device).m_tod_clock = clock; }
template<class _Object> static devcb2_base &set_irq_wr_callback(device_t &device, _Object object) { return downcast<legacy_mos6526_device &>(device).m_write_irq.set_callback(object); }
template<class _Object> static devcb2_base &set_cnt_wr_callback(device_t &device, _Object object) { return downcast<legacy_mos6526_device &>(device).m_write_sp.set_callback(object); }
template<class _Object> static devcb2_base &set_sp_wr_callback(device_t &device, _Object object) { return downcast<legacy_mos6526_device &>(device).m_write_cnt.set_callback(object); }
template<class _Object> static devcb2_base &set_pa_rd_callback(device_t &device, _Object object) { return downcast<legacy_mos6526_device &>(device).m_read_pa.set_callback(object); }
template<class _Object> static devcb2_base &set_pa_wr_callback(device_t &device, _Object object) { return downcast<legacy_mos6526_device &>(device).m_write_pa.set_callback(object); }
template<class _Object> static devcb2_base &set_pb_rd_callback(device_t &device, _Object object) { return downcast<legacy_mos6526_device &>(device).m_read_pb.set_callback(object); }
template<class _Object> static devcb2_base &set_pb_wr_callback(device_t &device, _Object object) { return downcast<legacy_mos6526_device &>(device).m_write_pb.set_callback(object); }
template<class _Object> static devcb2_base &set_pc_wr_callback(device_t &device, _Object object) { return downcast<legacy_mos6526_device &>(device).m_write_pc.set_callback(object); }
DECLARE_READ8_MEMBER( read );
DECLARE_WRITE8_MEMBER( write );
UINT8 reg_r(UINT8 offset);
void reg_w(UINT8 offset, UINT8 data);
/* port access */
UINT8 pa_r(UINT8 offset) { return (m_port[0].m_latch | ~m_port[0].m_ddr); }
UINT8 pb_r(UINT8 offset) { return (m_port[1].m_latch | ~m_port[1].m_ddr); }
/* interrupt request */
DECLARE_READ_LINE_MEMBER( irq_r ) { return m_irq; }
/* time of day clock */
DECLARE_WRITE_LINE_MEMBER( tod_w ) { if(state) clock_tod(); }
/* serial counter */
DECLARE_READ_LINE_MEMBER( cnt_r ) { return m_cnt; }
DECLARE_WRITE_LINE_MEMBER( cnt_w );
/* serial port */
DECLARE_READ_LINE_MEMBER( sp_r ) { return m_sp; }
DECLARE_WRITE_LINE_MEMBER( sp_w ) { m_sp = state; }
/* flag */
DECLARE_WRITE_LINE_MEMBER( flag_w );
/* port mask */
void set_port_mask_value(int port, int data);
protected:
// device-level overrides
virtual void device_start();
virtual void device_reset();
virtual void device_post_load() { }
virtual void device_clock_changed() { }
virtual void device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr);
static TIMER_CALLBACK( timer_proc );
static TIMER_CALLBACK( clock_tod_callback );
private:
enum
{
TIMER_PC,
TIMER_TOD
};
inline attotime cycles_to_time(int c);
void update_pc();
void update_interrupts();
void timer_bump(int timer);
void timer_underflow(int timer);
void increment();
void clock_tod();
struct cia_timer
{
public:
cia_timer() { }
UINT16 get_count();
void update(int which, INT32 new_count);
UINT32 m_clock;
UINT16 m_latch;
UINT16 m_count;
UINT8 m_mode;
UINT8 m_irq;
emu_timer* m_timer;
legacy_mos6526_device* m_cia;
};
struct cia_port
{
public:
UINT8 m_ddr;
UINT8 m_latch;
UINT8 m_in;
UINT8 m_out;
UINT8 m_mask_value; /* in READ operation the value can be forced by a extern electric circuit */
};
devcb2_write_line m_write_irq;
devcb2_write_line m_write_pc;
devcb2_write_line m_write_cnt;
devcb2_write_line m_write_sp;
devcb2_read8 m_read_pa;
devcb2_write8 m_write_pa;
devcb2_read8 m_read_pb;
devcb2_write8 m_write_pb;
cia_port m_port[2];
cia_timer m_timer[2];
/* Time Of the Day clock (TOD) */
int m_tod_clock;
UINT32 m_tod;
UINT32 m_tod_latch;
UINT8 m_tod_latched;
UINT8 m_tod_running;
UINT32 m_alarm;
/* Interrupts */
UINT8 m_icr;
UINT8 m_ics;
UINT8 m_irq;
int m_flag;
/* Serial */
UINT8 m_loaded;
UINT8 m_sdr;
UINT8 m_sp;
UINT8 m_cnt;
UINT8 m_shift;
UINT8 m_serial;
emu_timer *m_pc_timer;
emu_timer *m_tod_timer;
};
class legacy_mos6526r1_device : public legacy_mos6526_device
{
public:
legacy_mos6526r1_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
};
class legacy_mos6526r2_device : public legacy_mos6526_device
{
public:
legacy_mos6526r2_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
};
class legacy_mos8520_device : public legacy_mos6526_device
{
public:
legacy_mos8520_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
};
class legacy_mos5710_device : public legacy_mos6526_device
{
public:
legacy_mos5710_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
};
// device type definition
extern const ATTR_DEPRECATED device_type LEGACY_MOS6526R1;
extern const ATTR_DEPRECATED device_type LEGACY_MOS6526R2;
extern const ATTR_DEPRECATED device_type LEGACY_MOS8520;
extern const ATTR_DEPRECATED device_type LEGACY_MOS5710;
/***************************************************************************
FUNCTION PROTOTYPES
***************************************************************************/
/* port mask */
void cia_set_port_mask_value(device_t *device, int port, int data);
#endif /* __6526CIA_H__ */
|