Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
RishiRecon
GitHub Repository: RishiRecon/exploits
Path: blob/main/misc/emulator/xnes/snes9x/apu/linear_resampler.h
28798 views
1
/* Simple fixed-point linear resampler by BearOso*/
2
3
#ifndef __LINEAR_RESAMPLER_H
4
#define __LINEAR_RESAMPLER_H
5
6
#include "resampler.h"
7
#include "snes9x.h"
8
9
static const int f_prec = 15;
10
static const uint32 f__one = (1 << f_prec);
11
12
#define lerp(t, a, b) (((((b) - (a)) * (t)) >> f_prec) + (a))
13
14
class LinearResampler : public Resampler
15
{
16
protected:
17
uint32 f__r_step;
18
uint32 f__inv_r_step;
19
uint32 f__r_frac;
20
int r_left, r_right;
21
22
public:
23
LinearResampler (int num_samples) : Resampler (num_samples)
24
{
25
f__r_frac = 0;
26
}
27
28
~LinearResampler ()
29
{
30
}
31
32
void
33
time_ratio (double ratio)
34
{
35
if (ratio == 0.0)
36
ratio = 1.0;
37
f__r_step = (uint32) (ratio * f__one);
38
f__inv_r_step = (uint32) (f__one / ratio);
39
clear ();
40
}
41
42
void
43
clear (void)
44
{
45
ring_buffer::clear ();
46
f__r_frac = 0;
47
r_left = 0;
48
r_right = 0;
49
}
50
51
void
52
read (short *data, int num_samples)
53
{
54
int i_position = start >> 1;
55
short *internal_buffer = (short *) buffer;
56
int o_position = 0;
57
int consumed = 0;
58
int max_samples = (buffer_size >> 1);
59
60
while (o_position < num_samples && consumed < buffer_size)
61
{
62
if (f__r_step == f__one)
63
{
64
data[o_position] = internal_buffer[i_position];
65
data[o_position + 1] = internal_buffer[i_position + 1];
66
67
o_position += 2;
68
i_position += 2;
69
if (i_position >= max_samples)
70
i_position -= max_samples;
71
consumed += 2;
72
73
continue;
74
}
75
76
while (f__r_frac <= f__one && o_position < num_samples)
77
{
78
data[o_position] = lerp (f__r_frac,
79
r_left,
80
internal_buffer[i_position]);
81
data[o_position + 1] = lerp (f__r_frac,
82
r_right,
83
internal_buffer[i_position + 1]);
84
85
o_position += 2;
86
87
f__r_frac += f__r_step;
88
}
89
90
if (f__r_frac > f__one)
91
{
92
f__r_frac -= f__one;
93
r_left = internal_buffer[i_position];
94
r_right = internal_buffer[i_position + 1];
95
i_position += 2;
96
if (i_position >= max_samples)
97
i_position -= max_samples;
98
consumed += 2;
99
}
100
}
101
102
size -= consumed << 1;
103
start += consumed << 1;
104
if (start >= buffer_size)
105
start -= buffer_size;
106
}
107
108
inline int
109
avail (void)
110
{
111
return (((size >> 2) * f__inv_r_step) - ((f__r_frac * f__inv_r_step) >> f_prec)) >> (f_prec - 1);
112
}
113
};
114
115
#endif /* __LINEAR_RESAMPLER_H */
116
117