为了运行cudaMemcpy,我编写了一个从.cpp文件调用的方法。方法如下:
void copy_to_device(uint32_t *host, uint32_t *device, int size)
{
cudaError_t ret;
ret = cudaMemcpy(device, host, size*sizeof(uint32_t), cudaMemcpyHostToDevice);
if(ret == cudaErrorInvalidValue)
printf("1!\n");
else if(ret == cudaErrorInvalidDevicePointer)
printf("2!\n");
else if(ret == cudaErrorInvalidMemcpyDirection)
printf("3!\n");
}
我的.cpp文件这样称呼它:
uint32_t *input_device;
device_malloc(input_device, INPUT_HEIGHT*INPUT_WIDTH);
uint32_t *oneDinput = TwoDtoOneD(input, INPUT_HEIGHT, INPUT_WIDTH);
copy_to_device(oneDinput, input_device, INPUT_HEIGHT*INPUT_WIDTH);
TwoDtoOneD所做的全部工作是接收2D数组并将其转换为1D数组并返回它。每当我尝试使用copy_to_device
方法时,它都会返回cudaErrorInvalidValue,该文件在NVIDIA网站上没有得到很好的记录。你们碰巧知道我要传递给导致此错误的函数的参数出了什么问题吗?这导致内核执行过程中出现问题。如果您需要更多详细信息,请询问。
这里是方法device_malloc
:
void device_malloc(uint32_t *buffer, int size)
{
cudaMalloc((void **) &buffer, size*sizeof(uint32_t));
}
问题在这里:
uint32_t *input_device;
device_malloc(input_device, INPUT_HEIGHT*INPUT_WIDTH);
device_malloc
所做的任何事情,都不会修改input_device
的值。也就是说,除非第一个参数是对指针的引用,但我敢打赌它不是。
您需要将device_malloc
的第一个参数更改为指向该指针的指针,并像这样调用它:
device_malloc(&input_device, INPUT_HEIGHT*INPUT_WIDTH);
或者只是让device_malloc
返回指向分配的内存的指针。
为了更直接地回答您的问题,cudaMemcpy
返回错误,因为它的第一个参数device
不是有效的设备指针,而CUDA运行时可以通过该方法进行检查。它可能包含垃圾值,因为由于上述问题您从未初始化过它。
作为附带说明,与该问题无关,您可能想使用cudaGetErrorString
功能来更方便地打印状态。
我查看了这些问题,它们是相同的东西。它无缘无故地返回无效。
#include "cuda_runtime.h"
#include "device_launch_parameters.h"
#include <stdio.h>
#include <iostream>
#include <vector>
#include <fstream>
#include <algorithm>
#include <string>
#include <iomanip>
#include <nlohmann/json.hpp>
#include <bits/stdc++.h>
using namespace std;
const int dataSize = 100;
const int threads = 10;
struct Player {
int number;
int square;
};
Player players[dataSize];
void getNumbers() {
for (int i = 0; i < dataSize; i++){
Player pl({ i, 0});
players[i] = { pl };
}
}
__global__ void operation(Player* playerInput) {
for (int i = 0; i < dataSize; i++) {
int square = 0;
square = playerInput[i].number * playerInput[i].number;
playerInput[i].square = square;
}
}
int main() {
getNumbers();
Player results[dataSize];
int inputSize = sizeof(Player) * dataSize;
Player* playerInput;
cudaMalloc((void**)& playerInput, inputSize);
cudaMemcpy(playerInput, players, inputSize, cudaMemcpyHostToDevice);
operation << <1, threads >> > (playerInput);
cudaDeviceSynchronize();
cudaMemcpy(results, playerInput, inputSize, cudaMemcpyDeviceToHost);
cudaFree(playerInput);
}