【发布时间】:2016-10-03 04:46:22
【问题描述】:
在下面的代码中,我只是从 main 连续两次调用函数 foo。该函数只是简单地进行设备内存分配,然后递增这个指针。然后它退出并返回主程序。
第一次调用 foo 时,内存已正确分配。但是现在,当我再次调用 foo 时,您可以在输出中看到,cuda 内存分配失败并出现错误 invalid device pointer
我尝试在两个 foo 调用之间使用 cudaThreadSynchronize(),但没有任何收获。为什么内存分配失败?
其实这个错误是因为
矩阵 += 3;
因为如果我不这样做,错误就会消失。
但是为什么,即使我使用的是 cudaFree() ?
请帮助我理解这一点。
我的输出在这里
Calling foo for the first time
Allocation of matrixd passed:
I came back to main safely :-)
I am going back to foo again :-)
Allocation of matrixd failed, the reason is: invalid device pointer
我的 main() 在这里
#include<stdio.h>
#include <cstdlib> // malloc(), free()
#include <iostream> // cout, stream
#include <math.h>
#include <ctime> // time(), clock()
#include <bitset>
bool foo( );
/***************************************
Main method.
****************************************/
int main()
{
// Perform one warm-up pass and validate
std::cout << "Calling foo for the first time"<<std::endl;
foo();
std::cout << "I came back to main safely :-) "<<std::endl;
std::cout << "I am going back to foo again :-) "<<std::endl;
foo( );
getchar();
return 0;
}
foo() 的定义在这个文件中:
#include <cuda.h>
#include <cuda_runtime_api.h>
#include <device_launch_parameters.h>
#include <iostream>
bool foo( )
{
// Error return value
cudaError_t status;
// Number of bytes in the matrix.
int bytes = 9 *sizeof(float);
// Pointers to the device arrays
float *matrixd=NULL;
// Allocate memory on the device to store matrix
cudaMalloc((void**) &matrixd, bytes);
status = cudaGetLastError(); //To check the error
if (status != cudaSuccess) {
std::cout << "Allocation of matrixd failed, the reason is: " << cudaGetErrorString(status) <<
std::endl;
cudaFree(matrixd); //Free call for memory
return false;
}
std::cout << "Allocation of matrixd passed: "<<std::endl;
////// Increment address
for (int i=0; i<3; i++){
matrixd += 3;
}
// Free device memory
cudaFree(matrixd);
return true;
}
更新
具有更好的错误检查。此外,我对设备指针只有一次增量主义。这次我得到以下输出:
Calling foo for the first time
Allocation of matrixd passed:
Increamented the pointer and going to free cuda memory:
GPUassert: invalid device pointer C:/Users/user/Desktop/Gauss/Gauss/GaussianElem
inationGPU.cu 44
第 44 行是 cudaFree()。为什么还是失败?
#define gpuErrchk(ans) { gpuAssert((ans), __FILE__, __LINE__); }
inline void gpuAssert(cudaError_t code, const char *file, int line, bool abort=true)
{
if (code != cudaSuccess)
{
fprintf(stderr,"GPUassert: %s %s %d\n", cudaGetErrorString(code), file, line);
if (abort) exit(code);
}
}
// GPU function for direct method Gross Jorden method.
bool foo( )
{
// Error return value
cudaError_t status;
// Number of bytes in the matrix.
int bytes = 9 *sizeof(float);
// Pointers to the device arrays
float *matrixd=NULL;
// Allocate memory on the device to store each matrix
gpuErrchk( cudaMalloc((void**) &matrixd, bytes));
//cudaMemset(outputMatrixd, 0, bytes);
std::cout << "Allocation of matrixd passed: "<<std::endl;
////// Incerament address
matrixd += 1;
std::cout << "Increamented the pointer and going to free cuda memory: "<<std::endl;
// Free device memory
gpuErrchk( cudaFree(matrixd));
return true;
}
【问题讨论】:
-
如果检查
cudaFree调用的返回状态会发生什么? -
@talonmies 你是对的,刚刚检查过,我在 cudafree 下面使用了 cudagetlasterror(),是的,它显示了,它失败了但是为什么?
-
对。所以你的问题基本上是由不完整的错误检查引起的。你可以看到如何正确地做到这一点here。内存分配没有失败。
-
我会在链接中查看你的答案,但是你确定解除分配没有错误(cuadgetlasterror报错)?
标签: cuda