2017-12-21 4 views
0

OpenGL API에 액세스하려면 OpenTK에서 C#을 사용합니다. 내 프로젝트는 모자이크를 사용하여 하이트 맵을 렌더링합니다. 내 tessellation 컨트롤 셰이더는 정사각형을 64 개의 사각형으로 분할하고 테셀레이션 평가 셰이더는 이러한 포인트에 수직 오프셋을 추가합니다. 수직 오프셋은 다음과 같이 균일 한 float 버퍼에 저장됩니다Nvidia GPU의 균일 버퍼 크기

uniform float HeightmapBuffer[65 * 65]; 

모든 것이 잘 작동, 내가 AMD 라데온 8250 GPU와 내 노트북에 프로젝트를 실행할 때. 문제는 Nvidia 그래픽 카드에서 실행하려고 할 때 시작됩니다. 나는 이전 GT 430과 새로운 GTX 1060을 시도했지만 결과는 동일합니다 :이 문제를 연구로서

Tessellation evaluation info 
---------------------------- 
0(13) : error C5041: cannot locate suitable resource to bind variable "HeightmapBuffer". Possibly large array. 

, 내가 AMD 모두 엔비디아 칩에 65.54 킬로바이트에 ~이 500MB 반환 GL_MAX_UNIFORM_BLOCK_SIZE 변수를 발견했다. 내 배열은 실제로 16.9 kB만을 사용하기 때문에 조금 이상합니다. 따라서 "BLOCK SIZE"가 실제로 하나의 변수의 크기를 제한하는지 확실하지 않습니다. 어쩌면 하나의 셰이더에 전달 된 모든 유니폼의 크기를 제한 할 수 있습니까? 그럼에도 불구하고, 나는 내 프로그램이 65 kB를 사용한다고 믿을 수 없다.

텍스처를 사용하여 '일반적인'방법으로 시도했지만, 보간에 문제가 있다고 생각합니다. 두 개의 인접한 높이 맵을 함께 배치하면 테두리가 일치하지 않습니다. 다른쪽에 균일 한 버퍼 배열을 사용하면 모든 것이 완벽하게 작동합니다.

GL_MAX_UNIFORM_BLOCK_SIZE의 실제 의미는 무엇입니까? 왜 Nvidia GPU에서이 값이 그렇게 낮습니까? 셰이더에 큰 배열을 전달하는 다른 방법이 있습니까?

+1

'float' 유니폼은 실제로'vec4'의 크기이므로'4 바이트 * 4 * 65 * 65' ='67.6 KiB'입니다. – genpfault

+0

흠, GL 사양에서 정보를 소싱하는 데 어려움을 겪고 있습니다. 그래서 소금 한 알씩 가져 가야합니다. ES 2.0 사양을 기억할 수도 있습니다. – genpfault

+0

[큰 배열의 기하학 쉐이더 오류] (https://stackoverflow.com/questions/29262469/error-in-geometry-shader-from-large-array) – Gusman

답변

3

이 문제를 조사한 결과, NVIDIA 칩에서 AMD는 ~ 500MB, NVIDIA 칩은 65.54KB를 반환하는 변수는 GL_MAX_UNIFORM_BLOCK_SIZE입니다.

GL_MAX_UNIFORM_BLOCK_SIZE은 잘못된 제한입니다. 이는 Uniform Buffer Objects에만 적용됩니다.

는 그냥 배열을 균일 블록

uniform float HeightmapBuffer[65 * 65]; 

외부 선언. 테셀레이션 평가 쉐이더에서 이것을 사용하는 것으로 보이기 때문에 관련 제한은 MAX_TESS_EVALUATION_UNIFORM_COMPONENTS입니다 (각 프로그램 가능 스테이지에 대해 이와 같은 제한이 별도로 있습니다). 이 구성 요소 제한은 플로트 구성 요소의 수를 계산하므로 vec4은 4 개 구성 요소 (float) 만 사용합니다. 특정 경우

, 최신 GL 사양, [GL 4.6 핵심 프로필]이 글을 쓰는 시점에서 (https://www.khronos.org/registry/OpenGL/specs/gl/glspec46.core.pdf) , 그냥 최소한의 그 1024의 값 (= 4kiB)을 보장하고, 당신은 방법 그 한도를 넘는.

그런 양의 데이터에 일반 유니폼을 사용하는 것은 실제로 매우 나쁜 생각입니다. 배열을 저장하려면 UBOs, Texture Buffer Objects, Shader Storage Buffer Objects 또는 일반 텍스처를 고려해야합니다. UBO는 아마도 시나리오에서 가장 자연스러운 선택 일 것입니다.

+0

@PeterMcG :이 질문에 명확하게 컨트롤 평가 쉐이더가 아니라 테셀레이션 평가 쉐이더에 관한 것입니다. 디폴트 유니폼 블록은 UBO에만 적용되는'GL_MAX_UNIFORM_BLOCK_SIZE'의 관점에서 획일 화 된 블록이 아닙니다. 명명은 불행 할 수도 있지만 사양은 매우 분명합니다. – derhass