16

C++ オブジェクトをデバイスにコピーできますか?

私が持っていると言う:

class CudaClass
{
public:
int* data;
CudaClass(int x) {
    data = new int[1]; data[0] = x;
}
};

__global__ void useClass(CudaClass cudaClass)
{
    printf("%d" cudaClass.data[0]);
};


int main()
{
    CudaClass c(1);
}

"c" をデバイス メモリにコピーし、カーネル "useClass" を起動するにはどうすればよいですか?

4

1 に答える 1

21

はい、デバイスで使用するためにオブジェクトをデバイスにコピーできます。オブジェクトに動的に割り当てられた領域へのポインターが埋め込まれている場合、プロセスにはいくつかの追加の手順が必要です。

何が関係しているかについての議論については、こちらの私の回答を参照してください。その回答には、それにリンクされたいくつかのサンプルコードの回答もあります。

また、クラス定義で、特定の関数をデバイスで使用できるようにする場合は、それらの関数を適切に (つまり、おそらく で__device__ __host__) 装飾する必要があります。

編集:質問(現在は削除されています)への回答として、提供されたコードに基づいて思いつくことができる最も単純なサンプルコードを次に示します。

#include <stdio.h>

class CudaClass
{
public:
int* data;
CudaClass(int x) {
    data = new int[1]; data[0] = x;
}
};

__global__ void useClass(CudaClass *cudaClass)
{
    printf("%d\n", cudaClass->data[0]);
};




int main()
{
    CudaClass c(1);
    // create class storage on device and copy top level class
    CudaClass *d_c;
    cudaMalloc((void **)&d_c, sizeof(CudaClass));
    cudaMemcpy(d_c, &c, sizeof(CudaClass), cudaMemcpyHostToDevice);
    // make an allocated region on device for use by pointer in class
    int *hostdata;
    cudaMalloc((void **)&hostdata, sizeof(int));
    cudaMemcpy(hostdata, c.data, sizeof(int), cudaMemcpyHostToDevice);
    // copy pointer to allocated device storage to device class
    cudaMemcpy(&(d_c->data), &hostdata, sizeof(int *), cudaMemcpyHostToDevice);
    useClass<<<1,1>>>(d_c);
    cudaDeviceSynchronize();
    return 0;
}

簡潔/明確にするために、通常のcudaエラーチェックを省きました。

質問への回答として、デバイスベースのクラスでポインタを使用してホストからストレージを直接割り当てることはできません。これは、cudaMalloc が次のような通常のホスト ベースのポインター ストレージを想定しているためです。

int *hostdata;

cudaMalloc は、ストレージが既にデバイス上にあるポインタでは機能しません。これは機能しません:

cudaMalloc(&(d_c->data), sizeof(int));

ホスト コードでデバイス ポインター (d_c) を逆参照する必要がありますが、これは許可されていません。

于 2013-04-15T20:41:19.237 に答える