1 // license:BSD-3-Clause
2 // copyright-holders:Phil Bennett
3 /***************************************************************************
4 
5     Fairlight CMI-01A Channel Controller Card
6 
7 ***************************************************************************/
8 
9 #ifndef MAME_AUDIO_CMI01A_H
10 #define MAME_AUDIO_CMI01A_H
11 
12 #include "machine/6821pia.h"
13 #include "machine/6840ptm.h"
14 #include "machine/input_merger.h"
15 
16 #define ENV_DIR_UP              0
17 #define ENV_DIR_DOWN            1
18 
19 #define CHANNEL_STATUS_LOAD     1
20 #define CHANNEL_STATUS_RUN      2
21 
22 class cmi01a_device : public device_t, public device_sound_interface {
23 public:
cmi01a_device(const machine_config & mconfig,const char * tag,device_t * owner,uint32_t clock,uint32_t channel)24 	cmi01a_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock, uint32_t channel)
25 		: cmi01a_device(mconfig, tag, owner, clock)
26 	{
27 		m_channel = channel;
28 	}
29 
30 	cmi01a_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
31 
irq_callback()32 	auto irq_callback() { return m_irq_cb.bind(); }
33 
34 	void write(offs_t offset, uint8_t data);
35 	uint8_t read(offs_t offset);
36 
37 	virtual void sound_stream_update(sound_stream &stream, std::vector<read_stream_view> const &inputs, std::vector<write_stream_view> &outputs) override;
38 
39 protected:
40 	virtual void device_resolve_objects() override;
41 	virtual void device_start() override;
42 	virtual void device_reset() override;
43 	virtual void device_add_mconfig(machine_config &config) override;
44 	virtual void device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr) override;
45 
46 	static const device_timer_id TIMER_ZX = 0;
47 	static const device_timer_id TIMER_EOSI = 1;
48 	static const device_timer_id TIMER_BCAS = 2;
49 
50 	required_device<input_merger_device> m_irq_merger;
51 	required_device_array<pia6821_device, 2> m_pia;
52 	required_device<ptm6840_device> m_ptm;
53 
54 	required_device_array<pia6821_device, 2> m_cmi02_pia;
55 
56 	sound_stream* m_stream;
57 
58 private:
59 	DECLARE_WRITE_LINE_MEMBER(cmi01a_irq);
60 
61 	void bcas_tick();
62 	void reset_bcas_counter();
63 
64 	void clock_envelope();
65 	void tick_ediv();
66 	void set_eclk(bool eclk);
67 	void update_eclk();
68 
69 	void pulse_zcint();
70 	void pulse_gzx();
71 	void reset_waveform_segment();
72 	void check_segment_load();
73 	void wpe_w(int state);
74 	void load_w(int state);
75 
76 	void zx_timer_cb();
77 	void eosi_timer_cb();
78 	void run_voice();
79 	void update_wave_addr(int inc);
80 
81 	uint32_t    m_channel;
82 	emu_timer * m_zx_timer;
83 	uint8_t     m_zx_flag;
84 	uint8_t     m_zx_ff;
85 
86 	emu_timer * m_eosi_timer;
87 
88 	emu_timer * m_bcas_timer;
89 
90 	std::unique_ptr<uint8_t[]>    m_wave_ram;
91 	uint16_t  m_segment_cnt;
92 	uint8_t   m_new_addr;     // Flag
93 	uint8_t   m_vol_latch;
94 	uint8_t   m_flt_latch;
95 	uint8_t   m_rp;
96 	uint8_t   m_ws;
97 	int       m_dir;
98 	int       m_env_dir;
99 	uint8_t   m_env;
100 	int       m_pia0_cb2_state;
101 
102 	uint8_t   m_bcas_q1_ticks;
103 	uint8_t   m_bcas_q1;
104 	uint8_t   m_bcas_q2_ticks;
105 	uint8_t   m_bcas_q2;
106 
107 	double    m_freq;
108 
109 	int       m_ptm_o1;
110 	int       m_ptm_o2;
111 	int       m_ptm_o3;
112 
113 	bool      m_load;
114 	bool      m_run;
115 	bool      m_gzx;
116 	bool      m_nwpe;
117 	bool      m_tri;
118 	bool      m_pia1_ca2;
119 
120 	bool      m_eclk;
121 	bool      m_env_clk;
122 	bool      m_ediv_out;
123 	uint8_t   m_ediv_rate;
124 	uint8_t   m_ediv_count;
125 
126 	uint16_t  m_pitch;
127 	uint8_t   m_octave;
128 
129 	devcb_write_line m_irq_cb;
130 
131 	void rp_w(uint8_t data);
132 	void ws_dir_w(uint8_t data);
133 	uint8_t ws_dir_r();
134 	DECLARE_READ_LINE_MEMBER( tri_r );
135 	DECLARE_WRITE_LINE_MEMBER( pia_0_cb2_w );
136 	DECLARE_WRITE_LINE_MEMBER( eload_w );
137 
138 	DECLARE_READ_LINE_MEMBER( eosi_r );
139 	DECLARE_READ_LINE_MEMBER( zx_r );
140 	uint8_t pia_1_a_r();
141 	void pia_1_a_w(uint8_t data);
142 	void pia_1_b_w(uint8_t data);
143 
144 	DECLARE_WRITE_LINE_MEMBER( ptm_o1 );
145 	DECLARE_WRITE_LINE_MEMBER( ptm_o2 );
146 	DECLARE_WRITE_LINE_MEMBER( ptm_o3 );
147 	DECLARE_WRITE_LINE_MEMBER( ptm_irq );
148 
149 	static const uint8_t s_7497_rate_table[64][64];
150 };
151 
152 // device type definition
153 DECLARE_DEVICE_TYPE(CMI01A_CHANNEL_CARD, cmi01a_device)
154 
155 #endif // MAME_AUDIO_CMI01A_H
156