_kiss_fft_guts.h
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2003-2010, Mark Borgerding. All rights reserved.
3  * This file is part of KISS FFT - https://github.com/mborgerding/kissfft
4  *
5  * SPDX-License-Identifier: BSD-3-Clause
6  * See COPYING file for more information.
7  */
8 
9 /* kiss_fft.h
10  defines kiss_fft_scalar as either short or a float type
11  and defines
12  typedef struct { kiss_fft_scalar r; kiss_fft_scalar i; }kiss_fft_cpx; */
13 
14 #ifndef _kiss_fft_guts_h
15 #define _kiss_fft_guts_h
16 
17 #include "kiss_fft.h"
18 #include "kiss_fft_log.h"
19 #include <limits.h>
20 
21 #define MAXFACTORS 32
22 /* e.g. an fft of length 128 has 4 factors
23  as far as kissfft is concerned
24  4*4*4*2
25  */
26 
28 {
29  int nfft;
30  int inverse;
31  int factors[2 * MAXFACTORS];
33 };
34 
35 /*
36  Explanation of macros dealing with complex math:
37 
38  C_MUL(m,a,b) : m = a*b
39  C_FIXDIV( c , div ) : if a fixed point impl., c /= div. noop otherwise
40  C_SUB( res, a,b) : res = a - b
41  C_SUBFROM( res , a) : res -= a
42  C_ADDTO( res , a) : res += a
43  * */
44 #ifdef FIXED_POINT
45 #include <stdint.h>
46 #if (FIXED_POINT == 32)
47 #define FRACBITS 31
48 #define SAMPPROD int64_t
49 #define SAMP_MAX INT32_MAX
50 #define SAMP_MIN INT32_MIN
51 #else
52 #define FRACBITS 15
53 #define SAMPPROD int32_t
54 #define SAMP_MAX INT16_MAX
55 #define SAMP_MIN INT16_MIN
56 #endif
57 
58 #if defined(CHECK_OVERFLOW)
59 #define CHECK_OVERFLOW_OP(a, op, b) \
60  if ((SAMPPROD)(a)op(SAMPPROD)(b) > SAMP_MAX || \
61  (SAMPPROD)(a)op(SAMPPROD)(b) < SAMP_MIN) \
62  { \
63  KISS_FFT_WARNING("overflow (%d " #op " %d) = %ld", (a), (b), \
64  (SAMPPROD)(a)op(SAMPPROD)(b)); \
65  }
66 #endif
67 
68 #define smul(a, b) ((SAMPPROD)(a) * (b))
69 #define sround(x) (kiss_fft_scalar)(((x) + (1 << (FRACBITS - 1))) >> FRACBITS)
70 
71 #define S_MUL(a, b) sround(smul(a, b))
72 
73 #define C_MUL(m, a, b) \
74  do \
75  { \
76  (m).r = sround(smul((a).r, (b).r) - smul((a).i, (b).i)); \
77  (m).i = sround(smul((a).r, (b).i) + smul((a).i, (b).r)); \
78  } while (0)
79 
80 #define DIVSCALAR(x, k) (x) = sround(smul(x, SAMP_MAX / k))
81 
82 #define C_FIXDIV(c, div) \
83  do \
84  { \
85  DIVSCALAR((c).r, div); \
86  DIVSCALAR((c).i, div); \
87  } while (0)
88 
89 #define C_MULBYSCALAR(c, s) \
90  do \
91  { \
92  (c).r = sround(smul((c).r, s)); \
93  (c).i = sround(smul((c).i, s)); \
94  } while (0)
95 
96 #else /* not FIXED_POINT*/
97 
98 #define S_MUL(a, b) ((a) * (b))
99 #define C_MUL(m, a, b) \
100  do \
101  { \
102  (m).r = (a).r * (b).r - (a).i * (b).i; \
103  (m).i = (a).r * (b).i + (a).i * (b).r; \
104  } while (0)
105 #define C_FIXDIV(c, div) /* NOOP */
106 #define C_MULBYSCALAR(c, s) \
107  do \
108  { \
109  (c).r *= (s); \
110  (c).i *= (s); \
111  } while (0)
112 #endif
113 
114 #ifndef CHECK_OVERFLOW_OP
115 #define CHECK_OVERFLOW_OP(a, op, b) /* noop */
116 #endif
117 
118 #define C_ADD(res, a, b) \
119  do \
120  { \
121  CHECK_OVERFLOW_OP((a).r, +, (b).r) \
122  CHECK_OVERFLOW_OP((a).i, +, (b).i) \
123  (res).r = (a).r + (b).r; \
124  (res).i = (a).i + (b).i; \
125  } while (0)
126 #define C_SUB(res, a, b) \
127  do \
128  { \
129  CHECK_OVERFLOW_OP((a).r, -, (b).r) \
130  CHECK_OVERFLOW_OP((a).i, -, (b).i) \
131  (res).r = (a).r - (b).r; \
132  (res).i = (a).i - (b).i; \
133  } while (0)
134 #define C_ADDTO(res, a) \
135  do \
136  { \
137  CHECK_OVERFLOW_OP((res).r, +, (a).r) \
138  CHECK_OVERFLOW_OP((res).i, +, (a).i) \
139  (res).r += (a).r; \
140  (res).i += (a).i; \
141  } while (0)
142 
143 #define C_SUBFROM(res, a) \
144  do \
145  { \
146  CHECK_OVERFLOW_OP((res).r, -, (a).r) \
147  CHECK_OVERFLOW_OP((res).i, -, (a).i) \
148  (res).r -= (a).r; \
149  (res).i -= (a).i; \
150  } while (0)
151 
152 #ifdef FIXED_POINT
153 #define KISS_FFT_COS(phase) floor(.5 + SAMP_MAX * cos(phase))
154 #define KISS_FFT_SIN(phase) floor(.5 + SAMP_MAX * sin(phase))
155 #define HALF_OF(x) ((x) >> 1)
156 #elif defined(USE_SIMD)
157 #define KISS_FFT_COS(phase) _mm_set1_ps(cos(phase))
158 #define KISS_FFT_SIN(phase) _mm_set1_ps(sin(phase))
159 #define HALF_OF(x) ((x)*_mm_set1_ps(.5))
160 #else
161 #define KISS_FFT_COS(phase) (kiss_fft_scalar) cos(phase)
162 #define KISS_FFT_SIN(phase) (kiss_fft_scalar) sin(phase)
163 #define HALF_OF(x) ((x) * ((kiss_fft_scalar).5))
164 #endif
165 
166 #define kf_cexp(x, phase) \
167  do \
168  { \
169  (x)->r = KISS_FFT_COS(phase); \
170  (x)->i = KISS_FFT_SIN(phase); \
171  } while (0)
172 
173 /* a debugging function */
174 #define pcpx(c) KISS_FFT_DEBUG("%g + %gi\n", (double)((c)->r), (double)((c)->i))
175 
176 #ifdef KISS_FFT_USE_ALLOCA
177 // define this to allow use of alloca instead of malloc for temporary buffers
178 // Temporary buffers are used in two case:
179 // 1. FFT sizes that have "bad" factors. i.e. not 2,3 and 5
180 // 2. "in-place" FFTs. Notice the quotes, since kissfft does not really do an in-place
181 // transform.
182 #include <alloca.h>
183 #define KISS_FFT_TMP_ALLOC(nbytes) alloca(nbytes)
184 #define KISS_FFT_TMP_FREE(ptr)
185 #else
186 #define KISS_FFT_TMP_ALLOC(nbytes) KISS_FFT_MALLOC(nbytes)
187 #define KISS_FFT_TMP_FREE(ptr) KISS_FFT_FREE(ptr)
188 #endif
189 
190 #endif /* _kiss_fft_guts_h */
kiss_fft.h
MAXFACTORS
#define MAXFACTORS
Definition: _kiss_fft_guts.h:21
kiss_fft_state::inverse
int inverse
Definition: _kiss_fft_guts.h:30
kiss_fft_log.h
kiss_fft_state::factors
int factors[2 *MAXFACTORS]
Definition: _kiss_fft_guts.h:31
kiss_fft_state::twiddles
kiss_fft_cpx twiddles[1]
Definition: _kiss_fft_guts.h:32
kiss_fft_state
Definition: _kiss_fft_guts.h:27
kiss_fft_state::nfft
int nfft
Definition: _kiss_fft_guts.h:29
kiss_fft_cpx
Definition: kiss_fft.h:86


plotjuggler
Author(s): Davide Faconti
autogenerated on Mon Nov 11 2024 03:23:43