libsidplayfp 2.15.0
SID.h
1/*
2 * This file is part of libsidplayfp, a SID player engine.
3 *
4 * Copyright 2011-2025 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#include <cstdint>
28
29#include "siddefs-fp.h"
30#include "ExternalFilter.h"
31#include "Potentiometer.h"
32#include "Voice.h"
33
34#include "sidcxx11.h"
35
36namespace reSIDfp
37{
38
39class Filter;
40class Filter6581;
41class Filter8580;
42class Resampler;
43
48{
49private:
50 const char* message;
51
52public:
53 SIDError(const char* msg) :
54 message(msg) {}
55 const char* getMessage() const { return message; }
56};
57
61class SID
62{
63private:
65 Filter* filter;
66
68 Filter6581* const filter6581;
69
71 Filter8580* const filter8580;
72
74 std::unique_ptr<Resampler> resampler;
75
80 ExternalFilter externalFilter;
81
83 Potentiometer potX;
84
86 Potentiometer potY;
87
89 Voice voice[3];
90
92 int scaleFactor;
93
95 int busValueTtl;
96
98 int modelTTL;
99
101 unsigned int nextVoiceSync;
102
104 ChipModel model;
105
107 CombinedWaveforms cws;
108
110 unsigned char busValue;
111
117 float envDAC[256];
118
124 float oscDAC[4096];
125
126private:
132 void ageBusValue(unsigned int n);
133
140 void voiceSync(bool sync);
141
142public:
143 SID();
144 ~SID();
145
152 void setChipModel(ChipModel model);
153
157 ChipModel getChipModel() const { return model; }
158
165 void setCombinedWaveforms(CombinedWaveforms cws);
166
170 void reset();
171
180 void input(int value);
181
202 unsigned char read(int offset);
203
210 void write(int offset, unsigned char value);
211
238 double clockFrequency,
239 SamplingMethod method,
240 double samplingFrequency
241 );
242
250 int clock(unsigned int cycles, short* buf);
251
262 void clockSilent(unsigned int cycles);
263
269 void setFilter6581Curve(double filterCurve);
270
276 void setFilter6581Range ( double adjustment );
277
283 void setFilter8580Curve(double filterCurve);
284
290 void enableFilter(bool enable);
291};
292
293} // namespace reSIDfp
294
295#if RESID_INLINING || defined(SID_CPP)
296
297#include <algorithm>
298
299#include "Filter.h"
300#include "ExternalFilter.h"
301#include "Voice.h"
302#include "resample/Resampler.h"
303
304namespace reSIDfp
305{
306
307RESID_INLINE
308void SID::ageBusValue(unsigned int n)
309{
310 if (likely(busValueTtl != 0))
311 {
312 busValueTtl -= n;
313
314 if (unlikely(busValueTtl <= 0))
315 {
316 busValue = 0;
317 busValueTtl = 0;
318 }
319 }
320}
321
322RESID_INLINE
323int SID::clock(unsigned int cycles, short* buf)
324{
325 ageBusValue(cycles);
326 int s = 0;
327
328 while (cycles != 0)
329 {
330 unsigned int delta_t = std::min(nextVoiceSync, cycles);
331
332 if (likely(delta_t > 0))
333 {
334 for (unsigned int i = 0; i < delta_t; i++)
335 {
336 // clock waveform generators
337 voice[0].wave()->clock();
338 voice[1].wave()->clock();
339 voice[2].wave()->clock();
340
341 // clock envelope generators
342 voice[0].envelope()->clock();
343 voice[1].envelope()->clock();
344 voice[2].envelope()->clock();
345
346 const int sidOutput = static_cast<int>(filter->clock(voice[0], voice[1], voice[2]));
347 const int c64Output = externalFilter.clock(sidOutput + INT16_MIN);
348 if (unlikely(resampler->input(c64Output)))
349 {
350 buf[s++] = resampler->getOutput(scaleFactor);
351 }
352 }
353
354 cycles -= delta_t;
355 nextVoiceSync -= delta_t;
356 }
357
358 if (unlikely(nextVoiceSync == 0))
359 {
360 voiceSync(true);
361 }
362 }
363
364 return s;
365}
366
367} // namespace reSIDfp
368
369#endif
370
371#endif
void clock()
Definition EnvelopeGenerator.h:177
Definition ExternalFilter.h:66
int clock(int input)
Definition ExternalFilter.h:113
Definition Filter6581.h:321
Definition Filter.h:38
unsigned short clock(Voice &v1, Voice &v2, Voice &v3)
Definition Filter.h:207
Definition Potentiometer.h:38
Definition SID.h:48
Definition SID.h:62
void setChipModel(ChipModel model)
Definition SID.cpp:217
void input(int value)
Definition SID.cpp:327
unsigned char read(int offset)
Definition SID.cpp:333
void write(int offset, unsigned char value)
Definition SID.cpp:368
void setSamplingParameters(double clockFrequency, SamplingMethod method, double samplingFrequency)
Definition SID.cpp:487
void setFilter6581Range(double adjustment)
Definition SID.cpp:167
ChipModel getChipModel() const
Definition SID.h:157
void setCombinedWaveforms(CombinedWaveforms cws)
Definition SID.cpp:282
void setFilter6581Curve(double filterCurve)
Definition SID.cpp:162
void setFilter8580Curve(double filterCurve)
Definition SID.cpp:172
void enableFilter(bool enable)
Definition SID.cpp:177
void reset()
Definition SID.cpp:306
int clock(unsigned int cycles, short *buf)
Definition SID.h:323
void clockSilent(unsigned int cycles)
Definition SID.cpp:506
Definition Voice.h:37
void clock()
Definition WaveformGenerator.h:287