2017-11-25 13 views
1

저는 CUDA 프로그래밍 초보자이며 질문이 있습니다.커널 함수에 값을 매개 변수로 전달할 때 매개 변수가 복사되는 위치는 무엇입니까?

는 I이 같은 값으로 파라미터를 전달하는 경우 :

__global__ void add(int a, int b, int *c) { 
    // some operations 
} 

가변B 때문에 함수 함수 호출 스택에 복사 값 추가 커널 전달, I는 일부 메모리 추측 복사에 공간이 필요합니다.

맞습니다. 해당 매개 변수가 GPU 또는 호스트의 주 메모리에 복사 된인 추가 메모리 공간입니까?

이 문제가 궁금한 이유는 커다란 구조체를 커널 함수에 전달해야한다는 것입니다.

구조체의 포인터를 전달할 수도 있지만 struct와 각 멤버 변수에 대해 cudamalloc을 호출해야합니다.

+1

커널 호출에 대한 값 별 인수는 특별한 종류의 장치 메모리 인'__constant__' 메모리에 저장됩니다. 커널 코드 (일반적으로)의 시작 부분에서, 필요한 인자는'__constant__' 메모리에서 레지스터로 복사됩니다. 이 내용은 프로그래밍 안내서 [여기] (http://docs.nvidia.com/cuda/cuda-c-programming-guide/index.html#function-parameters)에서 다룹니다. –

답변

1

아주 짧은 대답은 CUDA 커널에 대한 모든 인수가 값에 의해 전달되며 이러한 인수는 API를 통해 호스트를 GPU의 전용 메모리 인수 버퍼에 복사한다는 것입니다. 현재이 버퍼는 상수 메모리에 저장되어 있으며 커널 시작 당 4KB의 제한이 있습니다 (here 참조).


더 자세한에서 PTX 표준 (연산 능력 2.0 하드웨어와 CUDA ABI가 나타난 기술적 이후) 전용 논리 상태 공간 통화 커널과 디바이스 파라미터 인수를 개최 .param을 정의합니다. here을 참조하십시오. 해당 설명서에서 인용 :

각 커널 함수 정의는 매개 변수의 선택적 목록을 포함합니다. 이러한 매개 변수는 주소 지정이 가능하며 읽기 전용 변수 은 .param 상태 공간에 선언되어 있습니다. 호스트에서 커널로 전달 된 값은 ld.param 명령어를 사용하여 이러한 매개 변수 변수를 통해 액세스됩니다. 커널 매개 변수 변수는 그리드 내의 모든 CTA에서 공유됩니다.

그것은 더 노트가 :

참고 : 매개 변수 공간의 위치는 구현 고유의 것입니다. 예를 들어, 일부 구현에서 커널 매개 변수는 전역 메모리에 있습니다. 이 경우에는 매개 변수와 전역 공간 사이에 액세스 보호가 제공되지 않습니다. 마찬가지로, 함수 매개 변수는 응용 프로그램 바이너리 인터페이스 (ABI)의 함수 호출 규칙에 따라 매개 변수 전달 레지스터 및/또는 스택 위치에 으로 매핑됩니다.

따라서 매개 변수 상태 공간의 정확한 위치는 구현에 따라 다릅니다. CUDA 하드웨어의 첫 번째 반복에서는 실제로 커널 인수와 디바이스 함수 인수에 대한 레지스터가 공유 메모리에 매핑되었습니다. 그러나 compute 2.0 하드웨어와 PTX 2.2 표준 이후로 대부분의 상황에서 커널에 대한 상수 메모리에 매핑됩니다.문서는 following on the matter 말한다 :

상수 (.const) 상태 공간은 읽기 전용 메모리가 호스트에 의해 를 초기화합니다. 상수 메모리는 ld.const 명령으로 액세스됩니다. 상수 메모리의 크기는 제한적이며, 현재 ~ 64KB로 제한되어 있습니다. 정적 크기의 상수 인 을 보유하는 데 사용할 수 있습니다. 추가 640KB의 상수 메모리가 있습니다. 은 10 개의 독립적 인 64KB 영역으로 구성되어 있습니다. 드라이버는 을 할당하고 이러한 영역에서 상수 버퍼를 초기화하고 커널 기능 매개 변수로 버퍼를 에 전달할 수 있습니다. 10 개 영역이 인접하지 않으므로 드라이버는 연속 버퍼가 인지 확인하여 각 버퍼가 전체적으로 64KB 영역에 들어가고 이 영역 경계를 넘지 않도록해야합니다.

정적 크기 상수 변수에는 선택적 변수 이니셜 라이저가 있습니다. 명시 적 초기화자가없는 상수 변수는 기본적으로 으로 초기화됩니다. 드라이버에 의해 할당 된 상수 버퍼는 호스트에 의해 초기화되고 해당 버퍼에 대한 포인터는 이 매개 변수로 커널에 전달됩니다.,이 CUDA C 또는에 __constant__ 등의 변수를 정의하여 접근 .const 상태 공간에 매핑 동일한 상수 메모리 [강조 광산]

그래서

커널 인자 상수 메모리에 저장되는 동안 아니다

Fortran 또는 Python에서 이에 상응하는 것. 오히려 그것은 드라이버에 의해 관리되고 프로그래머가 직접 액세스 할 수없는 장치 메모리의 내부 풀입니다.