Question

I am receiving the error:

Cufft error in file

I am using this file in order to load the FFT and pass them to another file.

//----function to check for errors-------------------------------------------------
#define gpuErrchk(ans) { gpuAssert((ans), __FILE__, __LINE__); }
inline void gpuAssert(cudaError_t code, char *file, int line, bool abort=true)
{
   if (code != cudaSuccess) 
   {
      fprintf(stderr,"\nGPUassert: %s %s %d\n", cudaGetErrorString(code), file, line);
      if (abort) exit(code);
   }
}
//function to check for cuFFT errors --------------------------------------------------
#define CUFFT_SAFE_CALL( call) do { \
cufftResult err = call; \
if (err != CUFFT_SUCCESS) { \
fprintf(stderr, "Cufft error in file '%s' in line %i : %s.\n", \
__FILE__, __LINE__, "error" ); \
exit(EXIT_FAILURE); \
} \
} while (0)



#define NX 128*128      
#define NY 16       
#define BATCH 16    
#define NRANK 2     



void FFT_transform(cufftDoubleComplex** B_in)
{
    int n[NRANK] = {NX, NY};

    //size of B
    int Bsize=NX*NY*BATCH;

    //allocate host memory 
    *B_in=(cufftDoubleComplex*)malloc(Bsize*sizeof(cufftDoubleComplex));

    for (int i=0;i<NX*NY;i++){
        for (int j=0;j<BATCH;j++){
            (*B_in)[i*BATCH+j].x=(i*BATCH+j)*2;
            (*B_in)[i*BATCH+j].y=(i*BATCH+j)*2+1;

        }
    }

    //allocate device memory
    cufftDoubleComplex* B_dev;
    gpuErrchk(cudaMalloc((void**) &B_dev,Bsize* sizeof(cufftDoubleComplex)));

    if (cudaGetLastError() != cudaSuccess){
        fprintf(stderr, "Cuda error: Failed to allocate\n");
        return; 
    }

    // copy arrays from host to device
    gpuErrchk(cudaMemcpy(B_dev, *B_in,Bsize* sizeof(cufftDoubleComplex), cudaMemcpyHostToDevice));


    // Create a 2D FFT plan
    cufftHandle plan;
        CUFFT_SAFE_CALL(cufftPlan2d(&plan,NX,NY,CUFFT_Z2Z));

    if (cufftPlanMany(&plan, NRANK, n,NULL, 1, 0,NULL, 1, 0,CUFFT_Z2Z,BATCH) != CUFFT_SUCCESS){
        fprintf(stderr, "CUFFT Error: Unable to create plan\n");
        return; 
    }

    if (cufftSetCompatibilityMode(plan, CUFFT_COMPATIBILITY_NATIVE)!= CUFFT_SUCCESS){
        fprintf(stderr, "CUFFT Error: Unable to set compatibility mode to native\n");
        return;     
    }


    // perform transform
    CUFFT_SAFE_CALL(cufftExecZ2Z(plan,(cufftDoubleComplex *)(*B_in), (cufftDoubleComplex *)B_dev, CUFFT_FORWARD));

    if (cufftExecZ2Z(plan,*B_in,B_dev,CUFFT_FORWARD) != CUFFT_SUCCESS){
        fprintf(stderr, "CUFFT Error: Unable to execute plan\n");
        return;     
    }

    if (cudaThreadSynchronize() != cudaSuccess){
        fprintf(stderr, "Cuda error: Failed to synchronize\n");
        return;
    }

        // copy result from device to host
        gpuErrchk(cudaMemcpy(*B_in, B_dev,Bsize*sizeof(cufftDoubleComplex), cudaMemcpyDeviceToHost));




    //Destroy CUFFT context
    CUFFT_SAFE_CALL(cufftDestroy(plan));

        //clean up device memory
        gpuErrchk(cudaFree(B_dev));


}

I am receiving the error at line:

CUFFT_SAFE_CALL(cufftExecZ2Z(plan,(cufftDoubleComplex *)(*B_in), (cufftDoubleComplex *)B_dev, CUFFT_FORWARD));
Was it helpful?

Solution

You are getting the error because B_in is a pointer to host memory and not to device memory, which is illegal. In CUFFT, inputs are always in device memory. You need to use cudaMemcpy to transfer the contents of B_in to B_dev before performing the transform, and then supply B_dev as both the input and output, which will result in an in place transform. This is clearly described in the CUFFT API documentation here.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top