arnaucube
arnaucube/poulpyPublic Self-hosted repository
poulpy/poulpy-backend/src/cpu_spqlios/spqlios-arithmetic/spqlios/cplx/cplx_fft.h
poulpy-backend/src/cpu_spqlios/spqlios-arithmetic/spqlios/cplx/cplx_fft.hRaw
  1#ifndef SPQLIOS_CPLX_FFT_H
  2#define SPQLIOS_CPLX_FFT_H
  3
  4#include "../commons.h"
  5
  6typedef struct cplx_fft_precomp CPLX_FFT_PRECOMP;
  7typedef struct cplx_ifft_precomp CPLX_IFFT_PRECOMP;
  8typedef struct cplx_mul_precomp CPLX_FFTVEC_MUL_PRECOMP;
  9typedef struct cplx_addmul_precomp CPLX_FFTVEC_ADDMUL_PRECOMP;
 10typedef struct cplx_from_znx32_precomp CPLX_FROM_ZNX32_PRECOMP;
 11typedef struct cplx_from_tnx32_precomp CPLX_FROM_TNX32_PRECOMP;
 12typedef struct cplx_to_tnx32_precomp CPLX_TO_TNX32_PRECOMP;
 13typedef struct cplx_to_znx32_precomp CPLX_TO_ZNX32_PRECOMP;
 14typedef struct cplx_from_rnx64_precomp CPLX_FROM_RNX64_PRECOMP;
 15typedef struct cplx_to_rnx64_precomp CPLX_TO_RNX64_PRECOMP;
 16typedef struct cplx_round_to_rnx64_precomp CPLX_ROUND_TO_RNX64_PRECOMP;
 17
 18/**
 19 * @brief precomputes fft tables.
 20 * The FFT tables contains a constant section that is required for efficient FFT operations in dimension nn.
 21 * The resulting pointer is to be passed as "tables" argument to any call to the fft function.
 22 * The user can optionnally allocate zero or more computation buffers, which are scratch spaces that are contiguous to
 23 * the constant tables in memory, and allow for more efficient operations. It is the user's responsibility to ensure
 24 * that each of those buffers are never used simultaneously by two ffts on different threads at the same time. The fft
 25 * table must be deleted by delete_fft_precomp after its last usage.
 26 */
 27EXPORT CPLX_FFT_PRECOMP* new_cplx_fft_precomp(uint32_t m, uint32_t num_buffers);
 28
 29/**
 30 * @brief gets the address of a fft buffer allocated during new_fft_precomp.
 31 * This buffer can be used as data pointer in subsequent calls to fft,
 32 * and does not need to be released afterwards.
 33 */
 34EXPORT void* cplx_fft_precomp_get_buffer(const CPLX_FFT_PRECOMP* tables, uint32_t buffer_index);
 35
 36/**
 37 * @brief allocates a new fft buffer.
 38 * This buffer can be used as data pointer in subsequent calls to fft,
 39 * and must be deleted afterwards by calling delete_fft_buffer.
 40 */
 41EXPORT void* new_cplx_fft_buffer(uint32_t m);
 42
 43/**
 44 * @brief allocates a new fft buffer.
 45 * This buffer can be used as data pointer in subsequent calls to fft,
 46 * and must be deleted afterwards by calling delete_fft_buffer.
 47 */
 48EXPORT void delete_cplx_fft_buffer(void* buffer);
 49
 50/**
 51 * @brief deallocates a fft table and all its built-in buffers.
 52 */
 53#define delete_cplx_fft_precomp free
 54
 55/**
 56 * @brief computes a direct fft in-place over data.
 57 */
 58EXPORT void cplx_fft(const CPLX_FFT_PRECOMP* tables, void* data);
 59
 60EXPORT CPLX_IFFT_PRECOMP* new_cplx_ifft_precomp(uint32_t m, uint32_t num_buffers);
 61EXPORT void* cplx_ifft_precomp_get_buffer(const CPLX_IFFT_PRECOMP* tables, uint32_t buffer_index);
 62EXPORT void cplx_ifft(const CPLX_IFFT_PRECOMP* tables, void* data);
 63#define delete_cplx_ifft_precomp free
 64
 65EXPORT CPLX_FFTVEC_MUL_PRECOMP* new_cplx_fftvec_mul_precomp(uint32_t m);
 66EXPORT void cplx_fftvec_mul(const CPLX_FFTVEC_MUL_PRECOMP* tables, void* r, const void* a, const void* b);
 67#define delete_cplx_fftvec_mul_precomp free
 68
 69EXPORT CPLX_FFTVEC_ADDMUL_PRECOMP* new_cplx_fftvec_addmul_precomp(uint32_t m);
 70EXPORT void cplx_fftvec_addmul(const CPLX_FFTVEC_ADDMUL_PRECOMP* tables, void* r, const void* a, const void* b);
 71#define delete_cplx_fftvec_addmul_precomp free
 72
 73/**
 74 * @brief prepares a conversion from ZnX to the cplx layout.
 75 * All the coefficients must be strictly lower than 2^log2bound in absolute value. Any attempt to use
 76 * this function on a larger coefficient is undefined behaviour. The resulting precomputed data must
 77 * be freed with `new_cplx_from_znx32_precomp`
 78 * @param m the target complex dimension m from C[X] mod X^m-i. Note that the inputs have n=2m
 79 * int32 coefficients in natural order modulo X^n+1
 80 * @param log2bound bound on the input coefficients. Must be between 0 and 32
 81 */
 82EXPORT CPLX_FROM_ZNX32_PRECOMP* new_cplx_from_znx32_precomp(uint32_t m);
 83/**
 84 * @brief converts from ZnX to the cplx layout.
 85 * @param tables precomputed data obtained by new_cplx_from_znx32_precomp.
 86 * @param r resulting array of m complexes coefficients mod X^m-i
 87 * @param x input array of n bounded integer coefficients mod X^n+1
 88 */
 89EXPORT void cplx_from_znx32(const CPLX_FROM_ZNX32_PRECOMP* tables, void* r, const int32_t* a);
 90/** @brief frees a precomputed conversion data initialized with new_cplx_from_znx32_precomp. */
 91#define delete_cplx_from_znx32_precomp free
 92
 93/**
 94 * @brief prepares a conversion from TnX to the cplx layout.
 95 * @param m the target complex dimension m from C[X] mod X^m-i. Note that the inputs have n=2m
 96 * torus32 coefficients. The resulting precomputed data must
 97 * be freed with `delete_cplx_from_tnx32_precomp`
 98 */
 99EXPORT CPLX_FROM_TNX32_PRECOMP* new_cplx_from_tnx32_precomp(uint32_t m);
100/**
101 * @brief converts from TnX to the cplx layout.
102 * @param tables precomputed data obtained by new_cplx_from_tnx32_precomp.
103 * @param r resulting array of m complexes coefficients mod X^m-i
104 * @param x input array of n torus32 coefficients mod X^n+1
105 */
106EXPORT void cplx_from_tnx32(const CPLX_FROM_TNX32_PRECOMP* tables, void* r, const int32_t* a);
107/** @brief frees a precomputed conversion data initialized with new_cplx_from_tnx32_precomp. */
108#define delete_cplx_from_tnx32_precomp free
109
110/**
111 * @brief prepares a rescale and conversion from the cplx layout to TnX.
112 * @param m the target complex dimension m from C[X] mod X^m-i. Note that the outputs have n=2m
113 * torus32 coefficients.
114 * @param divisor must be a power of two. The inputs are rescaled by divisor before being reduced modulo 1.
115 * Remember that the output of an iFFT must be divided by m.
116 * @param log2overhead all inputs absolute values must be within divisor.2^log2overhead.
117 * For any inputs outside of these bounds, the conversion is undefined behaviour.
118 * The maximum supported log2overhead is 52, and the algorithm is faster for log2overhead=18.
119 */
120EXPORT CPLX_TO_TNX32_PRECOMP* new_cplx_to_tnx32_precomp(uint32_t m, double divisor, uint32_t log2overhead);
121/**
122 * @brief rescale, converts and reduce mod 1 from cplx layout to torus32.
123 * @param tables precomputed data obtained by new_cplx_from_tnx32_precomp.
124 * @param r resulting array of n torus32 coefficients mod X^n+1
125 * @param x input array of m cplx coefficients mod X^m-i
126 */
127EXPORT void cplx_to_tnx32(const CPLX_TO_TNX32_PRECOMP* tables, int32_t* r, const void* a);
128#define delete_cplx_to_tnx32_precomp free
129
130EXPORT CPLX_TO_ZNX32_PRECOMP* new_cplx_to_znx32_precomp(uint32_t m, double divisor);
131EXPORT void cplx_to_znx32(const CPLX_TO_ZNX32_PRECOMP* precomp, int32_t* r, const void* x);
132#define delete_cplx_to_znx32_simple free
133
134EXPORT CPLX_FROM_RNX64_PRECOMP* new_cplx_from_rnx64_simple(uint32_t m);
135EXPORT void cplx_from_rnx64(const CPLX_FROM_RNX64_PRECOMP* precomp, void* r, const double* x);
136#define delete_cplx_from_rnx64_simple free
137
138EXPORT CPLX_TO_RNX64_PRECOMP* new_cplx_to_rnx64(uint32_t m, double divisor);
139EXPORT void cplx_to_rnx64(const CPLX_TO_RNX64_PRECOMP* precomp, double* r, const void* x);
140#define delete_cplx_round_to_rnx64_simple free
141
142EXPORT CPLX_ROUND_TO_RNX64_PRECOMP* new_cplx_round_to_rnx64(uint32_t m, double divisor, uint32_t log2bound);
143EXPORT void cplx_round_to_rnx64(const CPLX_ROUND_TO_RNX64_PRECOMP* precomp, double* r, const void* x);
144#define delete_cplx_round_to_rnx64_simple free
145
146/**
147 * @brief Simpler API for the fft function.
148 * For each dimension, the precomputed tables for this dimension are generated automatically.
149 * It is advised to do one dry-run per desired dimension before using in a multithread environment */
150EXPORT void cplx_fft_simple(uint32_t m, void* data);
151/**
152 * @brief Simpler API for the ifft function.
153 * For each dimension, the precomputed tables for this dimension are generated automatically the first time.
154 * It is advised to do one dry-run call per desired dimension in the main thread before using in a multithread
155 * environment */
156EXPORT void cplx_ifft_simple(uint32_t m, void* data);
157/**
158 * @brief Simpler API for the fftvec multiplication function.
159 * For each dimension, the precomputed tables for this dimension are generated automatically the first time.
160 * It is advised to do one dry-run call per desired dimension before using in a multithread environment */
161EXPORT void cplx_fftvec_mul_simple(uint32_t m, void* r, const void* a, const void* b);
162/**
163 * @brief Simpler API for the fftvec addmul function.
164 * For each dimension, the precomputed tables for this dimension are generated automatically the first time.
165 * It is advised to do one dry-run call per desired dimension before using in a multithread environment */
166EXPORT void cplx_fftvec_addmul_simple(uint32_t m, void* r, const void* a, const void* b);
167/**
168 * @brief Simpler API for the znx32 to cplx conversion.
169 * For each dimension, the precomputed tables for this dimension are generated automatically the first time.
170 * It is advised to do one dry-run call per desired dimension before using in a multithread environment */
171EXPORT void cplx_from_znx32_simple(uint32_t m, void* r, const int32_t* x);
172/**
173 * @brief Simpler API for the tnx32 to cplx conversion.
174 * For each dimension, the precomputed tables for this dimension are generated automatically the first time.
175 * It is advised to do one dry-run call per desired dimension before using in a multithread environment */
176EXPORT void cplx_from_tnx32_simple(uint32_t m, void* r, const int32_t* x);
177/**
178 * @brief Simpler API for the cplx to tnx32 conversion.
179 * For each dimension, the precomputed tables for this dimension are generated automatically the first time.
180 * It is advised to do one dry-run call per desired dimension before using in a multithread environment */
181EXPORT void cplx_to_tnx32_simple(uint32_t m, double divisor, uint32_t log2overhead, int32_t* r, const void* x);
182
183/**
184 * @brief converts, divides and round from cplx to znx32 (simple API)
185 * @param m the complex dimension
186 * @param divisor the divisor: a power of two, often m after an ifft
187 * @param r the result: must be a double array of size 2m. r must be distinct from x
188 * @param x the input: must hold m complex numbers.
189 */
190EXPORT void cplx_to_znx32_simple(uint32_t m, double divisor, int32_t* r, const void* x);
191
192/**
193 * @brief converts from rnx64 to cplx (simple API)
194 * The bound on the output is assumed to be within ]2^-31,2^31[.
195 * Any coefficient that would fall outside this range is undefined behaviour.
196 * @param m the complex dimension
197 * @param r the result: must be an array of m complex numbers. r must be distinct from x
198 * @param x the input: must be an array of 2m doubles.
199 */
200EXPORT void cplx_from_rnx64_simple(uint32_t m, void* r, const double* x);
201
202/**
203 * @brief converts, divides from cplx to rnx64 (simple API)
204 * @param m the complex dimension
205 * @param divisor the divisor: a power of two, often m after an ifft
206 * @param r the result: must be a double array of size 2m. r must be distinct from x
207 * @param x the input: must hold m complex numbers.
208 */
209EXPORT void cplx_to_rnx64_simple(uint32_t m, double divisor, double* r, const void* x);
210
211/**
212 * @brief converts, divides and round to integer from cplx to rnx32 (simple API)
213 * @param m the complex dimension
214 * @param divisor the divisor: a power of two, often m after an ifft
215 * @param log2bound a guarantee on the log2bound of the output. log2bound<=48 will use a more efficient algorithm.
216 * @param r the result: must be a double array of size 2m. r must be distinct from x
217 * @param x the input: must hold m complex numbers.
218 */
219EXPORT void cplx_round_to_rnx64_simple(uint32_t m, double divisor, uint32_t log2bound, double* r, const void* x);
220
221#endif  // SPQLIOS_CPLX_FFT_H