annotate Plugins/Input/console/Nes_Oscs.cpp @ 352:f13ab2d8e9cf trunk

[svn] various fixes :(
author nenolod
date Mon, 26 Dec 2005 14:12:35 -0800
parents 252843aac42f
children 7c5e886205ef
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
90
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
1
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
2 // Nes_Snd_Emu 0.1.6. http://www.slack.net/~ant/libs/
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
3
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
4 #include "Nes_Apu.h"
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
5
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
6 /* Copyright (C) 2003-2005 Shay Green. This module is free software; you
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
7 can redistribute it and/or modify it under the terms of the GNU Lesser
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
8 General Public License as published by the Free Software Foundation; either
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
9 version 2.1 of the License, or (at your option) any later version. This
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
10 module is distributed in the hope that it will be useful, but WITHOUT ANY
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
11 WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
12 FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
13 more details. You should have received a copy of the GNU Lesser General
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
14 Public License along with this module; if not, write to the Free Software
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
15 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
16
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
17 #include BLARGG_SOURCE_BEGIN
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
18
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
19 // Nes_Osc
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
20
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
21 void Nes_Osc::clock_length( int halt_mask )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
22 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
23 if ( length_counter && !(regs [0] & halt_mask) )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
24 length_counter--;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
25 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
26
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
27 void Nes_Envelope::clock_envelope()
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
28 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
29 int period = regs [0] & 15;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
30 if ( reg_written [3] ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
31 reg_written [3] = false;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
32 env_delay = period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
33 envelope = 15;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
34 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
35 else if ( --env_delay < 0 ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
36 env_delay = period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
37 if ( envelope | (regs [0] & 0x20) )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
38 envelope = (envelope - 1) & 15;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
39 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
40 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
41
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
42 int Nes_Envelope::volume() const
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
43 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
44 return length_counter == 0 ? 0 : (regs [0] & 0x10) ? (regs [0] & 15) : envelope;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
45 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
46
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
47 // Nes_Square
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
48
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
49 void Nes_Square::clock_sweep( int negative_adjust )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
50 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
51 int sweep = regs [1];
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
52
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
53 if ( --sweep_delay < 0 )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
54 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
55 reg_written [1] = true;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
56
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
57 int period = this->period();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
58 int shift = sweep & shift_mask;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
59 if ( shift && (sweep & 0x80) && period >= 8 )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
60 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
61 int offset = period >> shift;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
62
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
63 if ( sweep & negate_flag )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
64 offset = negative_adjust - offset;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
65
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
66 if ( period + offset < 0x800 )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
67 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
68 period += offset;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
69 // rewrite period
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
70 regs [2] = period & 0xff;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
71 regs [3] = (regs [3] & ~7) | ((period >> 8) & 7);
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
72 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
73 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
74 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
75
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
76 if ( reg_written [1] ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
77 reg_written [1] = false;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
78 sweep_delay = (sweep >> 4) & 7;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
79 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
80 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
81
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
82 void Nes_Square::run( nes_time_t time, nes_time_t end_time )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
83 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
84 if ( !output )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
85 return;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
86
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
87 const int volume = this->volume();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
88 const int period = this->period();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
89 int offset = period >> (regs [1] & shift_mask);
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
90 if ( regs [1] & negate_flag )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
91 offset = 0;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
92
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
93 const int timer_period = (period + 1) * 2;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
94 if ( volume == 0 || period < 8 || (period + offset) >= 0x800 )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
95 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
96 if ( last_amp ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
97 synth->offset( time, -last_amp, output );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
98 last_amp = 0;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
99 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
100
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
101 time += delay;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
102 if ( time < end_time )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
103 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
104 // maintain proper phase
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
105 int count = (end_time - time + timer_period - 1) / timer_period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
106 phase = (phase + count) & (phase_range - 1);
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
107 time += (long) count * timer_period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
108 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
109 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
110 else
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
111 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
112 // handle duty select
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
113 int duty_select = (regs [0] >> 6) & 3;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
114 int duty = 1 << duty_select; // 1, 2, 4, 2
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
115 int amp = 0;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
116 if ( duty_select == 3 ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
117 duty = 2; // negated 25%
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
118 amp = volume;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
119 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
120 if ( phase < duty )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
121 amp ^= volume;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
122
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
123 int delta = update_amp( amp );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
124 if ( delta )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
125 synth->offset( time, delta, output );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
126
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
127 time += delay;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
128 if ( time < end_time )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
129 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
130 Blip_Buffer* const output = this->output;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
131 const Synth* synth = this->synth;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
132 int delta = amp * 2 - volume;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
133 int phase = this->phase;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
134
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
135 do {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
136 phase = (phase + 1) & (phase_range - 1);
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
137 if ( phase == 0 || phase == duty ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
138 delta = -delta;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
139 synth->offset_inline( time, delta, output );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
140 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
141 time += timer_period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
142 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
143 while ( time < end_time );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
144
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
145 last_amp = (delta + volume) >> 1;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
146 this->phase = phase;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
147 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
148 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
149
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
150 delay = time - end_time;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
151 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
152
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
153 // Nes_Triangle
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
154
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
155 void Nes_Triangle::clock_linear_counter()
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
156 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
157 if ( reg_written [3] )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
158 linear_counter = regs [0] & 0x7f;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
159 else if ( linear_counter )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
160 linear_counter--;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
161
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
162 if ( !(regs [0] & 0x80) )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
163 reg_written [3] = false;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
164 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
165
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
166 void Nes_Triangle::run( nes_time_t time, nes_time_t end_time )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
167 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
168 if ( !output )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
169 return;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
170
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
171 // to do: track phase when period < 3
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
172 // to do: Output 7.5 on dac when period < 2? More accurate, but results in more clicks.
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
173
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
174 time += delay;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
175 const int timer_period = period() + 1;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
176 if ( length_counter == 0 || linear_counter == 0 || timer_period < 3 )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
177 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
178 time = end_time;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
179 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
180 else if ( time < end_time )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
181 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
182 Blip_Buffer* const output = this->output;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
183
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
184 int phase = this->phase;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
185 int volume = 1;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
186 if ( phase > phase_range ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
187 phase -= phase_range;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
188 volume = -volume;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
189 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
190
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
191 do {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
192 if ( --phase == 0 ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
193 phase = phase_range;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
194 volume = -volume;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
195 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
196 else {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
197 synth.offset_inline( time, volume, output );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
198 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
199
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
200 time += timer_period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
201 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
202 while ( time < end_time );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
203
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
204 if ( volume < 0 )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
205 phase += phase_range;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
206 this->phase = phase;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
207 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
208 delay = time - end_time;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
209 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
210
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
211 // Nes_Dmc
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
212
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
213 void Nes_Dmc::reset()
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
214 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
215 address = 0;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
216 dac = 0;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
217 buf = 0;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
218 bits_remain = 1;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
219 bits = 0;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
220 buf_empty = true;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
221 silence = true;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
222 next_irq = Nes_Apu::no_irq;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
223 irq_flag = false;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
224 irq_enabled = false;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
225
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
226 Nes_Osc::reset();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
227 period = 0x036;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
228 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
229
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
230 void Nes_Dmc::recalc_irq()
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
231 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
232 nes_time_t irq = Nes_Apu::no_irq;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
233 if ( irq_enabled && length_counter )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
234 irq = apu->last_time + delay +
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
235 ((length_counter - 1) * 8 + bits_remain - 1) * nes_time_t (period) + 1;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
236 if ( irq != next_irq ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
237 next_irq = irq;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
238 apu->irq_changed();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
239 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
240 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
241
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
242 int Nes_Dmc::count_reads( nes_time_t time, nes_time_t* last_read ) const
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
243 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
244 if ( last_read )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
245 *last_read = time;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
246
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
247 if ( length_counter == 0 )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
248 return 0; // not reading
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
249
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
250 long first_read = apu->last_time + delay + long (bits_remain - 1) * period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
251 long avail = time - first_read;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
252 if ( avail <= 0 )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
253 return 0;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
254
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
255 int count = (avail - 1) / (period * 8) + 1;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
256 if ( !(regs [0] & loop_flag) && count > length_counter )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
257 count = length_counter;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
258
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
259 if ( last_read ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
260 *last_read = first_read + (count - 1) * (period * 8) + 1;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
261 assert( *last_read <= time );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
262 assert( count == count_reads( *last_read, NULL ) );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
263 assert( count - 1 == count_reads( *last_read - 1, NULL ) );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
264 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
265
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
266 return count;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
267 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
268
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
269 static const short dmc_period_table [2] [16] = {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
270 0x1ac, 0x17c, 0x154, 0x140, 0x11e, 0x0fe, 0x0e2, 0x0d6, // NTSC
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
271 0x0be, 0x0a0, 0x08e, 0x080, 0x06a, 0x054, 0x048, 0x036,
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
272
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
273 0x18e, 0x161, 0x13c, 0x129, 0x10a, 0x0ec, 0x0d2, 0x0c7, // PAL (totally untested)
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
274 0x0b1, 0x095, 0x084, 0x077, 0x062, 0x04e, 0x043, 0x032 // to do: verify PAL periods
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
275 };
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
276
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
277 inline void Nes_Dmc::reload_sample()
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
278 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
279 address = 0x4000 + regs [2] * 0x40;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
280 length_counter = regs [3] * 0x10 + 1;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
281 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
282
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
283 static const unsigned char dac_table [128] = {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
284 0, 0, 1, 2, 2, 3, 3, 4, 5, 5, 6, 7, 7, 8, 8, 9,
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
285 10, 10, 11, 11, 12, 13, 13, 14, 14, 15, 15, 16, 17, 17, 18, 18,
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
286 19, 19, 20, 20, 21, 21, 22, 22, 23, 23, 24, 24, 25, 25, 26, 26,
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
287 27, 27, 28, 28, 29, 29, 30, 30, 31, 31, 32, 32, 32, 33, 33, 34,
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
288 34, 35, 35, 35, 36, 36, 37, 37, 38, 38, 38, 39, 39, 40, 40, 40,
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
289 41, 41, 42, 42, 42, 43, 43, 44, 44, 44, 45, 45, 45, 46, 46, 47,
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
290 47, 47, 48, 48, 48, 49, 49, 49, 50, 50, 50, 51, 51, 51, 52, 52,
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
291 52, 53, 53, 53, 54, 54, 54, 55, 55, 55, 56, 56, 56, 57, 57, 57
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
292 };
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
293
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
294 void Nes_Dmc::write_register( int addr, int data )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
295 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
296 if ( addr == 0 ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
297 period = dmc_period_table [pal_mode] [data & 15];
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
298 irq_enabled = (data & 0xc0) == 0x80; // enabled only if loop disabled
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
299 irq_flag &= irq_enabled;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
300 recalc_irq();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
301 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
302 else if ( addr == 1 )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
303 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
304 if ( !nonlinear )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
305 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
306 // adjust last_amp so that "pop" amplitude will be properly non-linear
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
307 // with respect to change in dac
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
308 int old_amp = dac_table [dac];
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
309 dac = data & 0x7F;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
310 int diff = dac_table [dac] - old_amp;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
311 last_amp = dac - diff;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
312 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
313
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
314 dac = data & 0x7F;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
315 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
316 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
317
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
318 void Nes_Dmc::start()
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
319 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
320 reload_sample();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
321 fill_buffer();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
322 recalc_irq();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
323 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
324
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
325 void Nes_Dmc::fill_buffer()
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
326 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
327 if ( buf_empty && length_counter )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
328 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
329 require( rom_reader ); // dmc_reader must be set
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
330 buf = rom_reader( rom_reader_data, 0x8000u + address );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
331 address = (address + 1) & 0x7FFF;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
332 buf_empty = false;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
333 if ( --length_counter == 0 )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
334 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
335 if ( regs [0] & loop_flag ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
336 reload_sample();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
337 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
338 else {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
339 apu->osc_enables &= ~0x10;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
340 irq_flag = irq_enabled;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
341 next_irq = Nes_Apu::no_irq;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
342 apu->irq_changed();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
343 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
344 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
345 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
346 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
347
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
348 void Nes_Dmc::run( nes_time_t time, nes_time_t end_time )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
349 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
350 if ( !output )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
351 return;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
352
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
353 int delta = update_amp( dac );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
354 if ( delta )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
355 synth.offset( time, delta, output );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
356
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
357 time += delay;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
358 if ( time < end_time )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
359 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
360 int bits_remain = this->bits_remain;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
361 if ( silence && buf_empty )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
362 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
363 int count = (end_time - time + period - 1) / period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
364 bits_remain = (bits_remain - 1 + 8 - (count % 8)) % 8 + 1;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
365 time += count * period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
366 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
367 else
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
368 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
369 Blip_Buffer* const output = this->output;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
370 const int period = this->period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
371 int bits = this->bits;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
372 int dac = this->dac;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
373
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
374 do
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
375 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
376 if ( !silence )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
377 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
378 const int step = (bits & 1) * 4 - 2;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
379 bits >>= 1;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
380 if ( unsigned (dac + step) <= 0x7F ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
381 dac += step;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
382 synth.offset_inline( time, step, output );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
383 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
384 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
385
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
386 time += period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
387
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
388 if ( --bits_remain == 0 )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
389 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
390 bits_remain = 8;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
391 if ( buf_empty ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
392 silence = true;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
393 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
394 else {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
395 silence = false;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
396 bits = buf;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
397 buf_empty = true;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
398 fill_buffer();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
399 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
400 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
401 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
402 while ( time < end_time );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
403
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
404 this->dac = dac;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
405 this->last_amp = dac;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
406 this->bits = bits;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
407 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
408 this->bits_remain = bits_remain;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
409 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
410 delay = time - end_time;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
411 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
412
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
413 // Nes_Noise
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
414
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
415 #include BLARGG_ENABLE_OPTIMIZER
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
416
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
417 static const short noise_period_table [16] = {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
418 0x004, 0x008, 0x010, 0x020, 0x040, 0x060, 0x080, 0x0A0,
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
419 0x0CA, 0x0FE, 0x17C, 0x1FC, 0x2FA, 0x3F8, 0x7F2, 0xFE4
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
420 };
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
421
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
422 void Nes_Noise::run( nes_time_t time, nes_time_t end_time )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
423 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
424 if ( !output )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
425 return;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
426
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
427 const int volume = this->volume();
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
428 int amp = (noise & 1) ? volume : 0;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
429 int delta = update_amp( amp );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
430 if ( delta )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
431 synth.offset( time, delta, output );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
432
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
433 time += delay;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
434 if ( time < end_time )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
435 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
436 const int mode_flag = 0x80;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
437
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
438 int period = noise_period_table [regs [2] & 15];
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
439 if ( !volume )
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
440 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
441 // round to next multiple of period
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
442 time += (end_time - time + period - 1) / period * period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
443
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
444 // approximate noise cycling while muted, by shuffling up noise register a bit
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
445 // to do: precise muted noise cycling?
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
446 if ( !(regs [2] & mode_flag) ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
447 int feedback = (noise << 13) ^ (noise << 14);
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
448 noise = (feedback & 0x4000) | (noise >> 1);
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
449 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
450 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
451 else
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
452 {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
453 Blip_Buffer* const output = this->output;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
454
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
455 // using resampled time avoids conversion in synth.offset()
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
456 Blip_Buffer::resampled_time_t rperiod = output->resampled_duration( period );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
457 Blip_Buffer::resampled_time_t rtime = output->resampled_time( time );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
458
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
459 int noise = this->noise;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
460 int delta = amp * 2 - volume;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
461 const int tap = (regs [2] & mode_flag ? 8 : 13);
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
462
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
463 do {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
464 int feedback = (noise << tap) ^ (noise << 14);
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
465 time += period;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
466
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
467 if ( (noise + 1) & 2 ) {
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
468 // bits 0 and 1 of noise differ
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
469 delta = -delta;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
470 synth.offset_resampled( rtime, delta, output );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
471 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
472
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
473 rtime += rperiod;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
474 noise = (feedback & 0x4000) | (noise >> 1);
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
475 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
476 while ( time < end_time );
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
477
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
478 last_amp = (delta + volume) >> 1;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
479 this->noise = noise;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
480 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
481 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
482
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
483 delay = time - end_time;
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
484 }
252843aac42f [svn] Import the initial sources for console music support.
nenolod
parents:
diff changeset
485