1 #ifndef VIENNACL_FFT_HPP
2 #define VIENNACL_FFT_HPP
41 namespace FFT_DATA_ORDER {
56 inline bool is_radix2(std::size_t data_size) {
57 return !((data_size > 2) && (data_size & (data_size - 1)));
61 inline std::size_t next_power_2(std::size_t n) {
64 std::size_t power = 1;
66 while(power <
sizeof(std::size_t) * 8) {
74 inline std::size_t num_bits(std::size_t
size)
76 std::size_t bits_datasize = 0;
95 template<
class SCALARTYPE>
100 std::size_t batch_num,
101 SCALARTYPE sign = -1.0f,
105 viennacl::linalg::kernels::matrix_row<SCALARTYPE, 1>::init();
106 std::string program_string = viennacl::linalg::kernels::matrix_row<SCALARTYPE, 1>::program_name();
109 viennacl::linalg::kernels::matrix_col<SCALARTYPE, 1>::init();
110 program_string = viennacl::linalg::kernels::matrix_col<SCALARTYPE, 1>::program_name();
113 viennacl::ocl::enqueue(kernel(in, out, static_cast<cl_uint>(size), static_cast<cl_uint>(stride), static_cast<cl_uint>(batch_num), sign));
120 template <
typename SCALARTYPE>
124 std::size_t bits_datasize,
125 std::size_t batch_num,
129 viennacl::linalg::kernels::matrix_row<SCALARTYPE, 1>::init();
130 std::string program_string = viennacl::linalg::kernels::matrix_row<SCALARTYPE, 1>::program_name();
133 viennacl::linalg::kernels::matrix_col<SCALARTYPE, 1>::init();
134 program_string = viennacl::linalg::kernels::matrix_col<SCALARTYPE, 1>::program_name();
141 static_cast<cl_uint>(bits_datasize),
142 static_cast<cl_uint>(size),
143 static_cast<cl_uint>(stride),
144 static_cast<cl_uint>(batch_num)
156 template<
class SCALARTYPE>
160 std::size_t batch_num,
161 SCALARTYPE sign = -1.0f,
165 viennacl::linalg::kernels::fft<SCALARTYPE, 1>::init();
167 assert(batch_num != 0);
168 assert(is_radix2(size));
170 viennacl::linalg::kernels::matrix_row<SCALARTYPE, 1>::init();
171 std::string program_string = viennacl::linalg::kernels::matrix_row<SCALARTYPE, 1>::program_name();
174 viennacl::linalg::kernels::matrix_col<SCALARTYPE, 1>::init();
175 program_string = viennacl::linalg::kernels::matrix_col<SCALARTYPE, 1>::program_name();
178 std::size_t bits_datasize = num_bits(size);
187 static_cast<cl_uint>(bits_datasize),
188 static_cast<cl_uint>(size),
189 static_cast<cl_uint>(stride),
190 static_cast<cl_uint>(batch_num),
195 reorder<SCALARTYPE>(in,
size, stride, bits_datasize, batch_num);
197 for(std::size_t step = 0; step < bits_datasize; step++)
203 static_cast<cl_uint>(step),
204 static_cast<cl_uint>(bits_datasize),
205 static_cast<cl_uint>(size),
206 static_cast<cl_uint>(stride),
207 static_cast<cl_uint>(batch_num),
221 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
224 std::size_t batch_num,
225 SCALARTYPE sign = -1.0
228 viennacl::linalg::kernels::fft<SCALARTYPE, 1>::init();
230 std::size_t size = in.
size() >> 1;
231 std::size_t ext_size = next_power_2(2 * size - 1);
240 .
get_program(viennacl::linalg::kernels::fft<SCALARTYPE, 1>::program_name())
245 static_cast<cl_uint>(ext_size)
251 .
get_program(viennacl::linalg::kernels::fft<SCALARTYPE, 1>::program_name())
257 static_cast<cl_uint>(size),
258 static_cast<cl_uint>(ext_size)
266 .
get_program(viennacl::linalg::kernels::fft<SCALARTYPE, 1>::program_name())
271 static_cast<cl_uint>(size)
276 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
281 viennacl::linalg::kernels::fft<SCALARTYPE, 1>::init();
282 std::size_t size = input1.
size() >> 1;
284 .
get_program(viennacl::linalg::kernels::fft<SCALARTYPE, 1>::program_name())
289 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
292 viennacl::linalg::kernels::fft<SCALARTYPE, 1>::init();
294 .
get_program(viennacl::linalg::kernels::fft<SCALARTYPE, 1>::program_name())
296 std::size_t size = input.
size() >> 1;
297 SCALARTYPE norm_factor =
static_cast<SCALARTYPE
>(
size);
301 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
304 viennacl::linalg::kernels::fft<SCALARTYPE, 1>::init();
306 .
get_program(viennacl::linalg::kernels::fft<SCALARTYPE, 1>::program_name())
313 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
317 viennacl::linalg::kernels::fft<SCALARTYPE, 1>::init();
320 .
get_program(viennacl::linalg::kernels::fft<SCALARTYPE, 1>::program_name())
329 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
334 viennacl::linalg::kernels::fft<SCALARTYPE, 1>::init();
336 .
get_program(viennacl::linalg::kernels::fft<SCALARTYPE, 1>::program_name())
341 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
346 viennacl::linalg::kernels::fft<SCALARTYPE, 1>::init();
348 .
get_program(viennacl::linalg::kernels::fft<SCALARTYPE, 1>::program_name())
353 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
356 viennacl::linalg::kernels::fft<SCALARTYPE, 1>::init();
357 std::size_t size = in.
size();
359 .
get_program(viennacl::linalg::kernels::fft<SCALARTYPE, 1>::program_name())
375 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
377 std::size_t batch_num = 1,
378 SCALARTYPE sign = -1.0)
380 std::size_t size = (input.
size() >> 1) / batch_num;
382 if(!detail::fft::is_radix2(size))
385 detail::fft::direct(input.
handle(),
406 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
409 std::size_t batch_num = 1,
410 SCALARTYPE sign = -1.0
413 std::size_t size = (input.
size() >> 1) / batch_num;
415 if(detail::fft::is_radix2(size))
418 detail::fft::radix2(output.
handle(),
size,
size, batch_num, sign);
420 detail::fft::direct(input.
handle(),
435 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
437 SCALARTYPE sign = -1.0)
439 std::size_t rows_num = input.
size1();
440 std::size_t cols_num = input.
size2() >> 1;
445 if(detail::fft::is_radix2(cols_num))
453 detail::fft::direct(input.
handle(),
466 if (detail::fft::is_radix2(rows_num)) {
471 detail::fft::direct(input.
handle(),
491 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
494 SCALARTYPE sign = -1.0)
496 std::size_t rows_num = input.
size1();
497 std::size_t cols_num = input.
size2() >> 1;
502 if(detail::fft::is_radix2(cols_num))
509 detail::fft::direct(input.
handle(),
520 if(detail::fft::is_radix2(rows_num))
529 detail::fft::direct(tmp.
handle(),
548 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
550 std::size_t batch_num = 1)
552 viennacl::inplace_fft(input, batch_num, SCALARTYPE(1.0));
553 detail::fft::normalize(input);
566 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
569 std::size_t batch_num = 1
572 viennacl::fft(input, output, batch_num, SCALARTYPE(1.0));
573 detail::fft::normalize(output);
587 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
593 assert(input1.
size() == input2.
size());
594 assert(input1.
size() == output.
size());
602 viennacl::fft(input1, tmp1);
603 viennacl::fft(input2, tmp2);
606 viennacl::detail::fft::multiply(tmp1, tmp2, tmp3);
608 viennacl::ifft(tmp3, output);
620 template<
class SCALARTYPE,
unsigned int ALIGNMENT>
626 assert(input1.
size() == input2.
size());
627 assert(input1.
size() == output.
size());
629 viennacl::inplace_fft(input1);
630 viennacl::inplace_fft(input2);
632 viennacl::detail::fft::multiply(input1, input2, output);
634 viennacl::inplace_ifft(output);