1 #include <math.h>
2 #include "driver.h"
3 #include "ay8910.h"
4 #include "fm.h"
5
6
7 static int stream[MAX_2203];
8
9 static const struct YM2203interface *intf;
10
11 static void *Timer[MAX_2203][2];
12
13 /* IRQ Handler */
IRQHandler(int n,int irq)14 static void IRQHandler(int n,int irq)
15 {
16 if(intf->handler[n]) intf->handler[n](irq);
17 }
18
19 /* Timer overflow callback from timer.c */
timer_callback_2203(int param)20 static void timer_callback_2203(int param)
21 {
22 int n=param&0x7f;
23 int c=param>>7;
24
25 YM2203TimerOver(n,c);
26 }
27
28 /* update request from fm.c */
YM2203UpdateRequest(int chip)29 void YM2203UpdateRequest(int chip)
30 {
31 stream_update(stream[chip],0);
32 }
33
34 #if 0
35 /* update callback from stream.c */
36 static void YM2203UpdateCallback(int chip,void *buffer,int length)
37 {
38 YM2203UpdateOne(chip,buffer,length);
39 }
40 #endif
41
42 /* TimerHandler from fm.c */
TimerHandler(int n,int c,int count,double stepTime)43 static void TimerHandler(int n,int c,int count,double stepTime)
44 {
45 if( count == 0 )
46 { /* Reset FM Timer */
47 timer_enable(Timer[n][c], 0);
48 }
49 else
50 { /* Start FM Timer */
51 double timeSec = (double)count * stepTime;
52 if (!timer_enable(Timer[n][c], 1))
53 timer_adjust(Timer[n][c], timeSec, (c<<7)|n, 0);
54 }
55 }
56
FMTimerInit(void)57 static void FMTimerInit( void )
58 {
59 int i;
60
61 for( i = 0 ; i < MAX_2203 ; i++ )
62 {
63 Timer[i][0] = timer_alloc(timer_callback_2203);
64 Timer[i][1] = timer_alloc(timer_callback_2203);
65 }
66 }
67
YM2203_sh_start(const struct MachineSound * msound)68 int YM2203_sh_start(const struct MachineSound *msound)
69 {
70 int i;
71
72 if (AY8910_sh_start_ym(msound)) return 1;
73
74 intf = msound->sound_interface;
75
76 /* Timer Handler set */
77 FMTimerInit();
78 /* stream system initialize */
79 for (i = 0;i < intf->num;i++)
80 {
81 int volume;
82 char name[20];
83 sprintf(name,"%s #%d FM",sound_name(msound),i);
84 volume = intf->mixing_level[i]>>16; /* high 16 bit */
85 stream[i] = stream_init(name,volume,Machine->sample_rate,i,YM2203UpdateOne/*YM2203UpdateCallback*/);
86 }
87 /* Initialize FM emurator */
88 #if 0 /* QUASI88 */
89 if (YM2203Init(intf->num,intf->baseclock,Machine->sample_rate,TimerHandler,IRQHandler) == 0)
90 #else /* QUASI88 */
91 if (YM2203Init(intf->num,intf->baseclock,Machine->sample_rate,0,0) == 0)
92 #endif /* QUASI88 */
93 {
94 /* Ready */
95 return 0;
96 }
97 /* error */
98 /* stream close */
99 return 1;
100 }
101
YM2203_sh_stop(void)102 void YM2203_sh_stop(void)
103 {
104 YM2203Shutdown();
105 AY8910_sh_stop_ym();
106 }
107
YM2203_sh_reset(void)108 void YM2203_sh_reset(void)
109 {
110 int i;
111
112 for (i = 0;i < intf->num;i++)
113 YM2203ResetChip(i);
114 }
115
116
117
READ_HANDLER(YM2203_status_port_0_r)118 READ_HANDLER( YM2203_status_port_0_r ) { return YM2203Read(0,0); }
READ_HANDLER(YM2203_status_port_1_r)119 READ_HANDLER( YM2203_status_port_1_r ) { return YM2203Read(1,0); }
READ_HANDLER(YM2203_status_port_2_r)120 READ_HANDLER( YM2203_status_port_2_r ) { return YM2203Read(2,0); }
READ_HANDLER(YM2203_status_port_3_r)121 READ_HANDLER( YM2203_status_port_3_r ) { return YM2203Read(3,0); }
READ_HANDLER(YM2203_status_port_4_r)122 READ_HANDLER( YM2203_status_port_4_r ) { return YM2203Read(4,0); }
123
READ_HANDLER(YM2203_read_port_0_r)124 READ_HANDLER( YM2203_read_port_0_r ) { return YM2203Read(0,1); }
READ_HANDLER(YM2203_read_port_1_r)125 READ_HANDLER( YM2203_read_port_1_r ) { return YM2203Read(1,1); }
READ_HANDLER(YM2203_read_port_2_r)126 READ_HANDLER( YM2203_read_port_2_r ) { return YM2203Read(2,1); }
READ_HANDLER(YM2203_read_port_3_r)127 READ_HANDLER( YM2203_read_port_3_r ) { return YM2203Read(3,1); }
READ_HANDLER(YM2203_read_port_4_r)128 READ_HANDLER( YM2203_read_port_4_r ) { return YM2203Read(4,1); }
129
WRITE_HANDLER(YM2203_control_port_0_w)130 WRITE_HANDLER( YM2203_control_port_0_w )
131 {
132 YM2203Write(0,0,data);
133 }
WRITE_HANDLER(YM2203_control_port_1_w)134 WRITE_HANDLER( YM2203_control_port_1_w )
135 {
136 YM2203Write(1,0,data);
137 }
WRITE_HANDLER(YM2203_control_port_2_w)138 WRITE_HANDLER( YM2203_control_port_2_w )
139 {
140 YM2203Write(2,0,data);
141 }
WRITE_HANDLER(YM2203_control_port_3_w)142 WRITE_HANDLER( YM2203_control_port_3_w )
143 {
144 YM2203Write(3,0,data);
145 }
WRITE_HANDLER(YM2203_control_port_4_w)146 WRITE_HANDLER( YM2203_control_port_4_w )
147 {
148 YM2203Write(4,0,data);
149 }
150
WRITE_HANDLER(YM2203_write_port_0_w)151 WRITE_HANDLER( YM2203_write_port_0_w )
152 {
153 YM2203Write(0,1,data);
154 }
WRITE_HANDLER(YM2203_write_port_1_w)155 WRITE_HANDLER( YM2203_write_port_1_w )
156 {
157 YM2203Write(1,1,data);
158 }
WRITE_HANDLER(YM2203_write_port_2_w)159 WRITE_HANDLER( YM2203_write_port_2_w )
160 {
161 YM2203Write(2,1,data);
162 }
WRITE_HANDLER(YM2203_write_port_3_w)163 WRITE_HANDLER( YM2203_write_port_3_w )
164 {
165 YM2203Write(3,1,data);
166 }
WRITE_HANDLER(YM2203_write_port_4_w)167 WRITE_HANDLER( YM2203_write_port_4_w )
168 {
169 YM2203Write(4,1,data);
170 }
171
WRITE_HANDLER(YM2203_word_0_w)172 WRITE_HANDLER( YM2203_word_0_w )
173 {
174 if (offset)
175 YM2203_write_port_0_w(0,data);
176 else
177 YM2203_control_port_0_w(0,data);
178 }
179
WRITE_HANDLER(YM2203_word_1_w)180 WRITE_HANDLER( YM2203_word_1_w )
181 {
182 if (offset)
183 YM2203_write_port_1_w(0,data);
184 else
185 YM2203_control_port_1_w(0,data);
186 }
187