Hi, I’m having issues with pointers doing some whimsical stuff, I have created a minimal viable example to showcase my problem:
#define COMPUTE_SAFE(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);
}
}
struct DensityMapDeviceData {
double* Nodes;
unsigned int* Cells;
unsigned int* CellMap;
};
struct DensityMap {
DensityMapDeviceData* GetDevice() {
auto* temp = new DensityMapDeviceData();
DensityMapDeviceData* device;
temp->Nodes = thrust::raw_pointer_cast(&Nodes[0]);
temp->Cells = thrust::raw_pointer_cast(&Cells[0]);
temp->CellMap = thrust::raw_pointer_cast(&CellMap[0]);
COMPUTE_SAFE(cudaMalloc(reinterpret_cast<void**>(&device), sizeof(DensityMapDeviceData)))
COMPUTE_SAFE(cudaMemcpy(device, temp, sizeof(DensityMapDeviceData), cudaMemcpyHostToDevice))
delete temp;
return device;
}
thrust::device_vector<double> Nodes;
thrust::device_vector<unsigned int> Cells;
thrust::device_vector<unsigned int> CellMap;
};
struct RigidBodyDeviceData {
DensityMapDeviceData* Map;
};
struct RigidBody {
RigidBodyDeviceData* GetDevice() {
auto* temp = new RigidBodyDeviceData();
RigidBodyDeviceData* device;
temp->Map = Map.GetDevice();
COMPUTE_SAFE(cudaMalloc(reinterpret_cast<void**>(&device), sizeof(RigidBodyDeviceData)))
COMPUTE_SAFE(cudaMemcpy(device, temp, sizeof(RigidBodyDeviceData), cudaMemcpyHostToDevice))
delete temp;
return device;
}
DensityMap Map;
};
__global__ void Kernel(RigidBodyDeviceData* data)
{
printf("%u\n", data->Map->Cells[0]); // crashes
// printf("%u\n", data->Map->CellMap[0]); works
}
struct Test
{
void InitData()
{
RigidBody rb;
DensityMap map;
map.Nodes = std::vector<double>(18000, 1.0);
map.Cells = std::vector<unsigned int>(1152000, 2);
map.CellMap = std::vector<unsigned int>(18000, 3);
rb.Map = map;
Data = rb.GetDevice();
}
void Run()
{
Kernel << < 1, 1 >> > (Data);
COMPUTE_SAFE(cudaDeviceSynchronize())
}
RigidBodyDeviceData* Data;
};
int main()
{
Test test;
test.InitData();
test.Run();
}
When I run this program it produces an illegal memory access error when printing the value in the kernel, when I try printing other values (ie. CellMap
) everything works fine, also, when I decrease the size of Cells
to ie. 1000 elements it also works. I’m pretty sure the issue is in how I’m storing the RigidBodyDeviceData
pointer, but I’m not sure what exactly is going wrong. Any help is very much appreciated.