I have a working code (not shown) that performs a series of complex->complex fast fourier transforms using the cufft library. I have been attempting to simplify this code by using the thrust library and its thrust::complex type. In order to keep the program code similar to the underlying mathematics, I define host_vectors of iterators (pointers), p1 and p2, which point to different locations in the device_vector, pr.
I attempt to cast to cufftDoubleComplex type in _V1 and _V2 for use in the cufft call. However, it is _V1 that is giving me an issue in: cufftExecZ2Z(qr_to_qk, _V1, _V2, cuFFTFORWARD)
, since _V1 doesn't have the .data() member.
The code (cut-down version) is as follows:
#include <stdlib.h>
#include <cuda.h>
#include <cufft.h>
#include <thrust/host_vector.h>
#include <thrust/device_vector.h>
#include <thrust/complex.h>
#define cuFFTFORWARD -1
#define cuFFTINVERSE 1
using namespace std;
int main ()
{
int m[3], M, r, n;
cufftHandle pr_to_pk;
n = 90;
m[0] = 16;
m[1] = m[0];
m[2] = m[0];
M = m[0]*m[1]*m[2];
// allocate memory for the propagators
thrust::device_vector<thrust::complex<double>> pr(2*(n+1)*M);
// fill pr with a number sequence (dummy data)
thrust::sequence(pr.begin(), pr.end());
// allocate memory to store iterators pointing to device vector elements
thrust::host_vector<thrust::device_vector<thrust::complex<double>>::iterator> p1(n+1);
thrust::host_vector<thrust::device_vector<thrust::complex<double>>::iterator> p2(n+1);
// save interators pointing to start of memory for p1 and p2
for (r=0; r<=n; r++) {
p1[r] = pr.begin()+2*r*M;
p2[(n+1-r)%(n+1)] = pr.begin()+(2*r+1)*M;
}
// set up the cufft plan
cufftPlanMany(&pr_to_pk,3,m,NULL,1,0,NULL,1,0, CUFFT_Z2Z,2);
// allocate memory for q(k)
thrust::device_vector<thrust::complex<double>> pk(2*M);
// attempt to cast to cufftDoubleComplex
cufftDoubleComplex* _V1 = (cufftDoubleComplex*)thrust::raw_pointer_cast(p1[1]);
cufftDoubleComplex* _V2 = (cufftDoubleComplex*)thrust::raw_pointer_cast(pk.data());
// attempt the first cufft
cufftExecZ2Z(pr_to_pk, _V1, _V2, cuFFTFORWARD);
cout << "complete" << endl;
}
Upon compilation, I get the following:
error: class "thrust::detail::pointer_raw_pointerthrust::detail::normal_iterator<thrust::device_ptr<thrust::complex<double>>>" has no member "type" detected during instantiation of class "thrust::detail::pointer_traits [with Ptr=thrust::detail::normal_iteratorthrust::device_ptr<thrust::complex<double>>]"
Unfortunately, in spite of many different attempts of casting for _V1, I have been unable to get the code to successfully compile and run. If anyone can help shed some light on how to get the call to cufftExecZ2Z(pr_to_pk, _V1, _V2, cuFFTFORWARD);
working, it would be greatly appreciated. I'm trying to avoid creating n number of p1 and p2 vectors, which I think would solve the problem but get very messy.