libsidplayfp 2.8.0
SID.h
1/*
2 * This file is part of libsidplayfp, a SID player engine.
3 *
4 * Copyright 2011-2024 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 <memory>
27
28#include "siddefs-fp.h"
29
30#include "sidcxx11.h"
31
32namespace reSIDfp
33{
34
35class Filter;
36class Filter6581;
37class Filter8580;
38class ExternalFilter;
39class Potentiometer;
40class Voice;
41class Resampler;
42
47{
48private:
49 const char* message;
50
51public:
52 SIDError(const char* msg) :
53 message(msg) {}
54 const char* getMessage() const { return message; }
55};
56
60class SID
61{
62private:
64 Filter* filter;
65
67 Filter6581* const filter6581;
68
70 Filter8580* const filter8580;
71
76 ExternalFilter* const externalFilter;
77
79 std::unique_ptr<Resampler> resampler;
80
82 Potentiometer* const potX;
83
85 Potentiometer* const potY;
86
88 std::unique_ptr<Voice> voice[3];
89
91 int scaleFactor;
92
94 int busValueTtl;
95
97 int modelTTL;
98
100 unsigned int nextVoiceSync;
101
103 ChipModel model;
104
106 CombinedWaveforms cws;
107
109 unsigned char busValue;
110
112 bool muted[3];
113
119 float envDAC[256];
120
126 float oscDAC[4096];
127
128private:
134 void ageBusValue(unsigned int n);
135
141 int output() const;
142
149 void voiceSync(bool sync);
150
151public:
152 SID();
153 ~SID();
154
161 void setChipModel(ChipModel model);
162
166 ChipModel getChipModel() const { return model; }
167
174 void setCombinedWaveforms(CombinedWaveforms cws);
175
179 void reset();
180
189 void input(int value);
190
211 unsigned char read(int offset);
212
219 void write(int offset, unsigned char value);
220
227 void mute(int channel, bool enable) { muted[channel] = enable; }
228
254 void setSamplingParameters(double clockFrequency, SamplingMethod method, double samplingFrequency, double highestAccurateFrequency);
255
263 int clock(unsigned int cycles, short* buf);
264
275 void clockSilent(unsigned int cycles);
276
282 void setFilter6581Curve(double filterCurve);
283
289 void setFilter6581Range ( double adjustment );
290
296 void setFilter8580Curve(double filterCurve);
297
303 void enableFilter(bool enable);
304};
305
306} // namespace reSIDfp
307
308#if RESID_INLINING || defined(SID_CPP)
309
310#include <algorithm>
311
312#include "Filter.h"
313#include "ExternalFilter.h"
314#include "Voice.h"
315#include "resample/Resampler.h"
316
317namespace reSIDfp
318{
319
320RESID_INLINE
321void SID::ageBusValue(unsigned int n)
322{
323 if (likely(busValueTtl != 0))
324 {
325 busValueTtl -= n;
326
327 if (unlikely(busValueTtl <= 0))
328 {
329 busValue = 0;
330 busValueTtl = 0;
331 }
332 }
333}
334
335RESID_INLINE
336int SID::output() const
337{
338 const float v1 = voice[0]->output(voice[2]->wave());
339 const float v2 = voice[1]->output(voice[0]->wave());
340 const float v3 = voice[2]->output(voice[1]->wave());
341
342 const int input = static_cast<int>(filter->clock(v1, v2, v3));
343 return externalFilter->clock(input);
344}
345
346
347RESID_INLINE
348int SID::clock(unsigned int cycles, short* buf)
349{
350 ageBusValue(cycles);
351 int s = 0;
352
353 while (cycles != 0)
354 {
355 unsigned int delta_t = std::min(nextVoiceSync, cycles);
356
357 if (likely(delta_t > 0))
358 {
359 for (unsigned int i = 0; i < delta_t; i++)
360 {
361 // clock waveform generators
362 voice[0]->wave()->clock();
363 voice[1]->wave()->clock();
364 voice[2]->wave()->clock();
365
366 // clock envelope generators
367 voice[0]->envelope()->clock();
368 voice[1]->envelope()->clock();
369 voice[2]->envelope()->clock();
370
371 if (unlikely(resampler->input(output())))
372 {
373 buf[s++] = resampler->getOutput(scaleFactor);
374 }
375 }
376
377 cycles -= delta_t;
378 nextVoiceSync -= delta_t;
379 }
380
381 if (unlikely(nextVoiceSync == 0))
382 {
383 voiceSync(true);
384 }
385 }
386
387 return s;
388}
389
390} // namespace reSIDfp
391
392#endif
393
394#endif
Definition ExternalFilter.h:65
int clock(int input)
Definition ExternalFilter.h:111
Definition Filter6581.h:320
Definition Filter.h:39
unsigned short clock(float v1, float v2, float v3)
Definition Filter.h:197
Definition Potentiometer.h:38
Definition SID.h:47
Definition SID.h:61
void setChipModel(ChipModel model)
Definition SID.cpp:220
void input(int value)
Definition SID.cpp:329
unsigned char read(int offset)
Definition SID.cpp:335
void setSamplingParameters(double clockFrequency, SamplingMethod method, double samplingFrequency, double highestAccurateFrequency)
Definition SID.cpp:489
void write(int offset, unsigned char value)
Definition SID.cpp:370
void setFilter6581Range(double adjustment)
Definition SID.cpp:170
ChipModel getChipModel() const
Definition SID.h:166
void setCombinedWaveforms(CombinedWaveforms cws)
Definition SID.cpp:284
void setFilter6581Curve(double filterCurve)
Definition SID.cpp:165
void setFilter8580Curve(double filterCurve)
Definition SID.cpp:175
void enableFilter(bool enable)
Definition SID.cpp:180
void reset()
Definition SID.cpp:308
int clock(unsigned int cycles, short *buf)
Definition SID.h:348
void clockSilent(unsigned int cycles)
Definition SID.cpp:508
void mute(int channel, bool enable)
Definition SID.h:227