나는 cuda와 pycuda에 대해 매우 새로운 기술이다. 동일한 배열을 n 번 단순히 "반복"함으로써 배열 (1xd)의 행렬 (차원 nxd)을 만드는 커널이 필요합니다. 예를 들어, n = 4 및 d = 3이라고 가정하면 배열 [1 2 3]
인 경우 내 커널의 결과가 같아야간단한 pycuda 커널의 이상한 행동
[1 2 3
1 2 3
1 2 3
1 2 3]
(4x3의 행렬). 나는이 코드를 실행하면, 지금
kernel_code_template = """
__global__ void TileKernel(float *in, float *out)
{
// Each thread computes one element of out
int y = blockIdx.y * blockDim.y + threadIdx.y;
int x = blockIdx.x * blockDim.x + threadIdx.x;
if (y > %(n)s || x > %(d)s) return;
out[y * %(d)s + x] = in[x];
}
"""
d = 64
n = 512
blockSizex = 16
blockSizey = 16
gridSizex = (d + blockSizex - 1)/blockSizex
gridSizey = (n + blockSizey - 1)/blockSizey
# get the kernel code from the template
kernel_code = kernel_code_template % {
'd': d,
'n': n
}
mod = SourceModule(kernel_code)
TileKernel = mod.get_function("TileKernel")
vec_cpu = np.arange(d).astype(np.float32) # just as an example
vec_gpu = gpuarray.to_gpu(vec_cpu)
out_gpu = gpuarray.empty((n, d), np.float32)
TileKernel.prepare("PP")
TileKernel.prepared_call((gridSizex, gridSizey), (blockSizex, blockSizey, 1), vec_gpu.gpudata, out_gpu.gpudata)
out_cpu = out_gpu.get()
:
기본적으로,
나는 아래의 코드를 작성했습니다 (N, 1) (배열) numpy.tile을하고 같은입니다 d는 2의 거듭 제곱 = 16입니다. 올바른 결과를 얻습니다. (numpy.tile (vec_cpu, (n, 1))); 하지만 d를 다른 것으로 설정하면 (예를 들어 88이라고 가정 해 봅시다) 출력 매트릭스의 모든 요소에 첫 번째 열을 제외하고 올바른 값이 있습니다. 일부 항목은 올바르지 만 다른 항목은 다른 값을가집니다. 모든 잘못된 요소에 대해 동일하지만 모든 실행마다 다르다. 그리고 잘못된 값을 가진 첫 번째 열의 항목은 매 달리 다르다. 예 :
[0 1 2
0 1 2
6 1 2
0 1 2
6 1 2
...]
, 사전에 감사를 난 정말이 문제의 원인을 알아낼 수는 없지만, 어쩌면
어떤 도움을 이해할 수있을 것이다 ... 단지 내가 부족 간단 뭔가 !
코드로 테스트 한 모든 예는 올바르게 작동하는 것 같습니다 (예 : d = 88, n = 567). np.allclose (np.tile (vec_cpu, (n, 1)), out_cpu) . 귀하의 질문에 맞지 않는 * 정확한 * 사례를 편집 할 수 있습니까? – talonmies
이 오류를 재현하는 방법을 정확히 알았습니다. 먼저 d = 88, n = 32로 스크립트를 실행합니다. 정상적으로 작동합니다. 그럼 내가 d를 128로 바꾼다. 똑같은 n, 여전히 잘 동작한다. 그런 다음 d를 88로 변경하고 동일한 n을 입력하면 첫 번째 열에서 오류가 발생합니다! – Odysseo