Reputation: 1030
I'm trying to do a wrapper in a С++ DLL for CUDA, to be able to use it in C# (yeah, I know there's managedCuda and cudafy, but I still would like to try this)
The thing is, to be able to pass the pointer reference back to c#, i cant just do as usual and do the cuda malloc with float*. I was trying to manage everything with CUdeviceptr, but, even though cudaMalloc apparently works (no error given by cudaGetLastError), when I do the cudaMemcpy using the CUdevicptr variable it breaks and gives the "Invalid argument" error.
extern "C" __declspec(dllexport) void __cdecl allocateDeviceMemory(float*, CUdeviceptr, unsigned int);
extern void allocateDeviceMemory(float* data, CUdeviceptr device_pointer, unsigned int numElements){
cudaMalloc((void**)&device_pointer,numElements * sizeof(float));
cudaError_t error = cudaGetLastError();
printf("CudaError.... 1 %s\n", cudaGetErrorString(error));
cudaMemcpy((void*)&device_pointer ,data,numElements * sizeof(float), cudaMemcpyHostToDevice);
error = cudaGetLastError();
printf("CudaError.... 2 %s\n", cudaGetErrorString(error));
}
Does anybody have any ideas about how can this be done?
Upvotes: 1
Views: 3788
Reputation: 12109
Change
cudaMemcpy((void*)&device_pointer ,data,numElements * sizeof(float), cudaMemcpyHostToDevice)
to
cudaMemcpy((void *)device_pointer ,data,numElements * sizeof(float), cudaMemcpyHostToDevice
CUdeviceptr
itself is a device pointer. When you are doing &device_pointer
, you are sending in the pointer to the device pointer. cudaMalloc
expects a pointer to pointer and works fine. cudaMemcpy
however expects only a device pointer (not pointer to pointer).
If you want to use the driver API (i.e. use CUdeviceptr
), use cuMemAlloc
and cuMemcpyHtoD
If you want to use the runtime API use void *
for memory pointers and cast them to the required type. You can use cudaMalloc
and cudaMemcpy
with the runtime API.
EDIT: Added edit to explicitly cast CUdeviceptr
to void *
. Added information about driver and device API.
Upvotes: 5