Compute functions#

This page describes the function templates oneapi::mkl::dft::compute_forward and oneapi::mkl::dft::compute_backward, which all pertain to the calculation of a DFT defined by a committed oneapi::mkl::dft::descriptor object desc. These function templates belong to the oneapi::mkl::dft namespace and are declared in oneapi/mkl/dft.hpp (file to be included). The usage of prepended namespace specifiers oneapi::mkl::dft is omitted below for conciseness.

namespace oneapi::mkl::dft {
  /*----------------------- for in-place transforms -----------------------*/
  // using SYCL buffers
  template<typename descriptor_type, typename data_type>
  void compute_forward(descriptor_type &desc,
                       sycl::buffer<data_type, 1> &inout);
  template<typename descriptor_type, typename data_type>
  void compute_backward(descriptor_type &desc,
                        sycl::buffer<data_type, 1> &inout);
  // using device-accessible USM allocations
  template <typename descriptor_type, typename data_type>
  sycl::event compute_forward(descriptor_type &desc,
                              data_type *inout,
                              const std::vector<sycl::event> &dependencies = {});
  template <typename descriptor_type, typename data_type>
  sycl::event compute_backward(descriptor_type &desc,
                               data_type *inout,
                               const std::vector<sycl::event> &dependencies = {});
  /*--------------------- for out-of-place transforms ---------------------*/
  // using SYCL buffers
  template<typename descriptor_type, typename input_type, typename output_type>
  void compute_forward(descriptor_type &desc,
                       sycl::buffer<input_type, 1> &in,
                       sycl::buffer<output_type, 1> &out);
  template<typename descriptor_type, typename input_type, typename output_type>
  void compute_backward(descriptor_type &desc,
                        sycl::buffer<input_type, 1> &in,
                        sycl::buffer<output_type, 1> &out);
  // using device-accessible USM allocations
  template<typename descriptor_type, typename input_type, typename output_type>
  sycl::event compute_forward(descriptor_type &desc,
                              input_type *in,
                              output_type *out,
                              const std::vector<sycl::event> &dependencies = {});
  template<typename descriptor_type, typename input_type, typename output_type>
  sycl::event compute_backward(descriptor_type &desc,
                               input_type *in,
                               output_type *out,
                               const std::vector<sycl::event> &dependencies = {});
}

Description#

The compute_forward (resp. compute_backward) function templates accept a committed descriptor object desc followed by one or more data-containing arguments, and enqueues the computation of the forward (resp. backward) DFT that desc defines, i.e., the transform defined by \(\delta = -1\) (resp. \(\delta = +1\)). The computations are enqueued to the queue to which desc was committed.

Successive computations using the same descriptor object must be serialized to guarantee correct results. This can be done by waiting on the queue passed at commit, or by using an in-order queue. Alternatively, repeated use of the same buffer for any argument will also serialize computations (when using sycl::bufffer objects), or computations can be serialized using the returned event and input dependencies (when using device-accessible USM allocations). These alternate methods will be more performant in most cases. When possible, configuring a descriptor object for batched transforms delivers better performance than such successive computations in most cases.

The number of data-containing arguments to be provided depends exclusively on whether the desired DFT calculations are to be done in-place (output data overwriting the input data) or out-of-place (output data stored separately from the input data). One data-containing argument is required for in-place operations whereas two such arguments are needed for out-of-place calculations. Note that in-place operations require the data layout to satisfy requirements documented in the page dedicated to configuring data layouts.

Warning

  • When using a function designed for in-place (resp. out-of-place) operations, desc (function’s first argument) must have a configuration value of config_value::INPLACE (resp. config_value::NOT_INPLACE) associated with config_param::PLACEMENT. The function’s behavior is undefined otherwise.

  • When using a function designed for out-of-place operations, in and out must not share common elements.

Template parameters#

For in-place operations#

The compute_forward and compute_backward function templates for in-place operations are parameterized by two type template parameters, in the following order:

  • descriptor_type representing the type of desc, an instance of a specialization of the descriptor class template;

  • data_type representing the elementary data type of the data-containing argument being used.

The available specializations are listed in the table below.

Available specializations of the compute function templates for in-place operations.#

function template

descriptor_type

data_type

compute_forward
compute_backward

descriptor<precision::SINGLE, domain::REAL>

float

compute_forward
compute_backward

descriptor<precision::SINGLE, domain::REAL>

std::complex<float>

compute_forward
compute_backward

descriptor<precision::SINGLE, domain::COMPLEX>

float

compute_forward
compute_backward

descriptor<precision::SINGLE, domain::COMPLEX>

std::complex<float>

compute_forward
compute_backward

descriptor<precision::DOUBLE, domain::REAL>

double

compute_forward
compute_backward

descriptor<precision::DOUBLE, domain::REAL>

std::complex<double>

compute_forward
compute_backward

descriptor<precision::DOUBLE, domain::COMPLEX>

double

compute_forward
compute_backward

descriptor<precision::DOUBLE, domain::COMPLEX>

std::complex<double>

For out-of-place operations#

The compute_forward and compute_backward function templates for out-of-place operations are parameterized by three type template parameters, in the following order:

  • descriptor_type representing the type of desc, an instance of a specialization of the descriptor class template;

  • input_type representing the elementary data type of the first (input) data-containing argument being used;

  • output_type representing the elementary data type of the second (output) data-containing argument being used.

The available specializations are listed in the table below.

Available specializations of the compute function templates for out-of-place operations.#

function template

descriptor_type

input_type

output_type

compute_forward
compute_backward

descriptor<precision::SINGLE, domain::REAL>

float

float

compute_forward
compute_backward

descriptor<precision::SINGLE, domain::REAL>

std::complex<float>

std::complex<float>

compute_forward
compute_backward

descriptor<precision::SINGLE, domain::COMPLEX>

float

float

compute_forward
compute_backward

descriptor<precision::SINGLE, domain::COMPLEX>

std::complex<float>

std::complex<float>

compute_forward

descriptor<precision::SINGLE, domain::REAL>

float

std::complex<float>

compute_backward

descriptor<precision::SINGLE, domain::REAL>

std::complex<float>

float

compute_forward
compute_backward

descriptor<precision::DOUBLE, domain::REAL>

double

double

compute_forward
compute_backward

descriptor<precision::DOUBLE, domain::REAL>

std::complex<double>

std::complex<double>

compute_forward
compute_backward

descriptor<precision::DOUBLE, domain::COMPLEX>

double

double

compute_forward
compute_backward

descriptor<precision::DOUBLE, domain::COMPLEX>

std::complex<double>

std::complex<double>

compute_forward

descriptor<precision::DOUBLE, domain::REAL>

double

std::complex<double>

compute_backward

descriptor<precision::DOUBLE, domain::REAL>

std::complex<double>

double

Input parameters and returned value#

The compute_forward and compute_backward template functions’ input parameters are documented below. If device-accessible USM allocations are used, these functions return a sycl::event object that may be used to track the completion of the computations that the function call enqueues.

For in-place operations#

Input parameters for the in-place compute functions.#

Name

Supported types

Description

desc

descriptor_type

Committed instance of a specialization of a descriptor class template, defining the DFT to compute

inout

i. sycl::buffer<data_type, 1>
ii. data_type*

Data-containing argument for the DFT (input data on input, output results on output)

dependencies

std::vector<sycl::event>

Vector of dependencies to be honored by the enqueued DFT computation
(only if using device-accessible USM allocations arguments)

For out-of-place operations#

Input parameters for the out-of-place compute functions.#

Name

Supported types

Description

desc

descriptor_type

Committed instance of a specialization of a descriptor class template, defining the DFT to compute

in

i. sycl::buffer<input_type, 1>
ii. input_type*

Data-containing argument for the input data of the DFT

out

i. sycl::buffer<output_type, 1>
ii. output_type*

Data-containing argument for the output data of the DFT

dependencies

std::vector<sycl::event>

Vector of dependencies to be honored by the enqueued DFT computation
(only if using device-accessible USM allocations arguments)

Exceptions#

The compute_forward and compute_backward template functions may throw an std::runtime_error if

  • an issue is found with desc;

  • desc is uncommitted;

  • desc is configured to use an externally-allocated workspace yet it was not provided with one;

  • desc is configured to use an externally-allocated workspace and the form of data-containing arguments used is different from the form of workspace that was provided;

  • a failure is detected when computing the DFT.

If using SYCL buffers, some code paths do not support sub-buffers as data-containing arguments and may throw an std::invalid_argument exception if sub-buffers are used.