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
|
// license:BSD-3-Clause
// copyright-holders:Patrick Mackinlay
#ifndef MAME_MACHINE_AM9516_H
#define MAME_MACHINE_AM9516_H
#pragma once
class am9516_device
: public device_t
, public device_memory_interface
{
public:
enum address_reference : unsigned
{
SYSTEM_IO = 0,
SYSTEM_MEM = 1,
NORMAL_IO = 2,
NORMAL_MEM = 3,
};
am9516_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock);
// output lines
auto out_int() { return m_int.bind(); }
auto out_eop() { return m_eop.bind(); }
// input lines
DECLARE_WRITE_LINE_MEMBER(eop_w);
template <unsigned Channel> DECLARE_WRITE_LINE_MEMBER(dreq_w);
template <unsigned Channel> auto flyby_byte_r() { return m_channel[Channel].flyby_byte_r.bind(); }
template <unsigned Channel> auto flyby_byte_w() { return m_channel[Channel].flyby_byte_w.bind(); }
template <unsigned Channel> auto flyby_word_r() { return m_channel[Channel].flyby_word_r.bind(); }
template <unsigned Channel> auto flyby_word_w() { return m_channel[Channel].flyby_word_w.bind(); }
// register access
u16 addr_r() { return m_pointer; }
void addr_w(u16 data) { m_pointer = data; }
u16 data_r();
void data_w(u16 data);
u16 acknowledge();
protected:
// device_t overrides
virtual void device_start() override;
virtual void device_reset() override;
// device_memory_interface overrides
virtual space_config_vector memory_space_config() const override;
private:
void command(u8 data);
template <unsigned Channel> void operate(s32 param);
void complete(unsigned const c, u16 status);
void interrupt();
address_space_config m_space_config[4];
devcb_write_line m_int;
devcb_write_line m_eop;
// i/o line state
bool m_int_state;
bool m_eop_out_state;
bool m_eop_in_state;
// chip-level registers
u8 m_mode;
u8 m_pointer;
u16 m_temporary;
// channels
struct channel
{
channel(am9516_device &parent)
: udc(parent)
, flyby_byte_r(parent)
, flyby_byte_w(parent)
, flyby_word_r(parent)
, flyby_word_w(parent)
{}
u32 address(u16 &aru, u16 &arl, int delta = 0);
u8 read_byte(unsigned &cycles, bool flip = false);
void write_byte(u8 data, unsigned &cycles, bool flip = false);
u16 read_word(unsigned &cycles, bool flip = false);
void write_word(u16 data, unsigned &cycles, bool flip = false);
void interrupt(bool assert);
void chain();
void reload();
void log_mode(unsigned mask, bool high = false) const;
void log_addr(unsigned mask, const char *const name, u16 aru, u16 arl) const;
am9516_device &udc;
devcb_read8 flyby_byte_r;
devcb_write8 flyby_byte_w;
devcb_read16 flyby_word_r;
devcb_write16 flyby_word_w;
emu_timer *run;
u16 cabl; // current address b lower
u16 babl; // base address b lower
u16 caal; // current address a lower
u16 baal; // base address a lower
u16 cabu; // current address b upper
u16 babu; // base address b upper
u16 caau; // current address a upper
u16 baau; // base address a upper
u16 cal; // chain address lower
u16 cau; // chain address upper
u16 is; // interrupt save
u16 status; // status
u16 coc; // current operation count
u16 boc; // base operation count
u16 pattern; // pattern
u16 mask; // mask
u16 cml; // channel mode low
u16 cmh; // channel mode high
u8 iv; // interrupt vector
unsigned const wait_states[4] = { 0, 1, 2, 4 };
}
m_channel[2];
};
DECLARE_DEVICE_TYPE(AM9516, am9516_device)
#endif // MAME_MACHINE_AM9516_H
|