libsidplayfp  1.8.3
SID.h
1 /*
2  * This file is part of libsidplayfp, a SID player engine.
3  *
4  * Copyright 2011-2014 Leandro Nini <drfiemost@users.sourceforge.net>
5  * Copyright 2007-2010 Antti Lankila
6  * Copyright 2004 Dag Lem <resid@nimrod.no>
7  *
8  * This program is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License as published by
10  * the Free Software Foundation; either version 2 of the License, or
11  * (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
21  */
22 
23 #ifndef SIDFP_H
24 #define SIDFP_H
25 
26 #include "siddefs-fp.h"
27 
28 namespace reSIDfp
29 {
30 
31 class Filter;
32 class Filter6581;
33 class Filter8580;
34 class ExternalFilter;
35 class Potentiometer;
36 class Voice;
37 class Resampler;
38 
42 class SIDError
43 {
44 private:
45  const char* message;
46 
47 public:
48  SIDError(const char* msg) :
49  message(msg) {}
50  const char* getMessage() { return message; }
51 };
52 
56 class SID
57 {
58 private:
60  static const int BUS_TTL;
61 
63  Filter* filter;
64 
66  Filter6581* filter6581;
67 
69  Filter8580* filter8580;
70 
75  ExternalFilter* externalFilter;
76 
78  Resampler* resampler;
79 
81  Potentiometer* potX;
82 
84  Potentiometer* potY;
85 
87  Voice* voice[3];
88 
90  int busValueTtl;
91 
93  int modelTTL;
94 
96  int nextVoiceSync;
97 
99  int delayedOffset;
100 
102  ChipModel model;
103 
105  unsigned char delayedValue;
106 
108  unsigned char busValue;
109 
111  bool muted[3];
112 
113 private:
120  void writeImmediate(int offset, unsigned char value);
121 
127  void ageBusValue(int n);
128 
134  int output() const;
135 
142  void voiceSync(bool sync);
143 
144 public:
145  SID();
146  ~SID();
147 
153  void setChipModel(ChipModel model);
154 
158  ChipModel getChipModel() const { return model; }
159 
163  void reset();
164 
173  void input(int value);
174 
195  unsigned char read(int offset);
196 
203  void write(int offset, unsigned char value);
204 
211  void mute(int channel, bool enable) { muted[channel] = enable; }
212 
237  void setSamplingParameters(double clockFrequency, SamplingMethod method, double samplingFrequency, double highestAccurateFrequency);
238 
246  int clock(int cycles, short* buf);
247 
258  void clockSilent(int cycles);
259 
265  void setFilter6581Curve(double filterCurve);
266 
272  void setFilter8580Curve(double filterCurve);
273 
279  void enableFilter(bool enable);
280 };
281 
282 } // namespace reSIDfp
283 
284 #if RESID_INLINING || defined(SID_CPP)
285 
286 #include <algorithm>
287 
288 #include "Filter.h"
289 #include "ExternalFilter.h"
290 #include "Voice.h"
291 #include "resample/Resampler.h"
292 
293 namespace reSIDfp
294 {
295 
296 RESID_INLINE
297 void SID::ageBusValue(int n)
298 {
299  if (likely(busValueTtl != 0))
300  {
301  busValueTtl -= n;
302 
303  if (unlikely(busValueTtl <= 0))
304  {
305  busValue = 0;
306  busValueTtl = 0;
307  }
308  }
309 }
310 
311 RESID_INLINE
312 int SID::output() const
313 {
314  const int v1 = voice[0]->output(voice[2]->wave());
315  const int v2 = voice[1]->output(voice[0]->wave());
316  const int v3 = voice[2]->output(voice[1]->wave());
317 
318  return externalFilter->clock(filter->clock(v1, v2, v3));
319 }
320 
321 
322 RESID_INLINE
323 int SID::clock(int cycles, short* buf)
324 {
325  ageBusValue(cycles);
326  int s = 0;
327 
328  while (cycles != 0)
329  {
330  int delta_t = std::min(nextVoiceSync, cycles);
331 
332  if (likely(delta_t > 0))
333  {
334  if (unlikely(delayedOffset != -1))
335  {
336  delta_t = 1;
337  }
338 
339  for (int i = 0; i < delta_t; i++)
340  {
341  /* clock waveform generators */
342  voice[0]->wave()->clock();
343  voice[1]->wave()->clock();
344  voice[2]->wave()->clock();
345 
346  /* clock envelope generators */
347  voice[0]->envelope()->clock();
348  voice[1]->envelope()->clock();
349  voice[2]->envelope()->clock();
350 
351  if (unlikely(resampler->input(output())))
352  {
353  buf[s++] = resampler->getOutput();
354  }
355  }
356 
357  if (unlikely(delayedOffset != -1))
358  {
359  writeImmediate(delayedOffset, delayedValue);
360  delayedOffset = -1;
361  }
362 
363  cycles -= delta_t;
364  nextVoiceSync -= delta_t;
365  }
366 
367  if (unlikely(nextVoiceSync == 0))
368  {
369  voiceSync(true);
370  }
371  }
372 
373  return s;
374 }
375 
376 } // namespace reSIDfp
377 
378 #endif
379 
380 #endif
Definition: Filter8580.h:85
Definition: SID.h:42
Definition: Potentiometer.h:37
void clockSilent(int cycles)
Definition: SID.cpp:378
Definition: Voice.h:36
void setFilter6581Curve(double filterCurve)
Definition: SID.cpp:83
Definition: SID.h:56
short getOutput() const
Definition: Resampler.h:55
void clock()
Definition: EnvelopeGenerator.h:208
void input(int value)
Definition: SID.cpp:302
Definition: Dac.cpp:25
virtual int clock(int v1, int v2, int v3)=0
void enableFilter(bool enable)
Definition: SID.cpp:93
int clock(int cycles, short *buf)
Definition: SID.h:323
Definition: ExternalFilter.h:47
Definition: Resampler.h:32
void setSamplingParameters(double clockFrequency, SamplingMethod method, double samplingFrequency, double highestAccurateFrequency)
Definition: SID.cpp:357
Definition: Filter6581.h:320
virtual bool input(int sample)=0
unsigned char read(int offset)
Definition: SID.cpp:308
void write(int offset, unsigned char value)
Definition: SID.cpp:341
void clock()
Definition: WaveformGenerator.h:282
RESID_INLINE int output(const WaveformGenerator *ringModulator) const
Definition: Voice.h:59
void mute(int channel, bool enable)
Definition: SID.h:211
Definition: Filter.h:32
void setChipModel(ChipModel model)
Definition: SID.cpp:248
ChipModel getChipModel() const
Definition: SID.h:158
void setFilter8580Curve(double filterCurve)
Definition: SID.cpp:88
void reset()
Definition: SID.cpp:280
int clock(int Vi)
Definition: ExternalFilter.h:94