CUDA측 Tree자료구조 메모리 줄이기.

맨날 테스트하는 복셀 1500만개짜리 맵에서 tree구조의 메모리를 71MB 소모했었다. 정확히는 node의 메모리는 얼마 안되고 말단 node(leaf)에서 들고있는 삼각형 데이터의 메모리가 대부분이다. 교차 테스트를 위해서 leaf마다 삼각형배열을 가지고 있는데 이게 메모리를 제법 차지한다. 외장 그래픽 카드를 장착한 데스크탑이나 게이밍 노트북에선 이 정도 메모리 소모는 별 문제가 아니다. 하지만 내 테스트머신중 하나인 Surface book 1은 GPU메모리가 1GB밖에 되지 않기 때문에 단 10MB도 소중히 사용해야한다. 그래서 이걸 줄이기로 했다.

36 bytes 삼각형을 float3 base + 4bits offset방식의 8bytes짜리 자료구조로 바꿨다.

  1. 삼각형 한개의 메모리 사이즈는 float*3*3 = 36 bytes.
  2. 복셀 오브젝트의 크기가 4m x 4m x 4m.
  3. 가장 작은 복셀 크기가 0.5m x 0.5m x 0.5m.
  4. 버텍스 좌표를 오브젝트의 aabb의 min 좌표로부터의 offset으로 저장할 경우 0 <= p[x,y,z] <= 8.
  5. 따라서 버텍스 한개당 x,y,z 각 4bits면 충분. 총 12 bits로 표현.
  6. 삼각형 하나는 버텍스 3개이므로 12 bits x 3 = 36 bits.
  7. 4 bytes align을 감안하며 삼각형 한개의 사이즈는 8 bytes.
  8. 삼각형 메모리를 1 / 4.5로 줄일수 있다.

그러고나서 트리 자료구조 메모리(node + 삼각형 데이터)가 71MB -> 28MB로 줄었다.

base + offset 의 좌표를 float3로 변환할때의 오버헤드 때문에 약간은 느려질걸 예상했으나 CUDA에서 라이트맵 계산 속도는 오히려 약간 더 빨라졌다.
메모리 억세스 범위가 1/4 정도로 줄어들어서 캐시히트율이 높아졌기 때문인걸로 추측한다.
CUDA에선 산술연산 몇개 더 하는건 별거 아니지만 메모리에 읽기/쓰기 작업은 엄청 큰 일이니까.

base_offset_vertex

2018-05-16


답글 남기기

아래 항목을 채우거나 오른쪽 아이콘 중 하나를 클릭하여 로그 인 하세요:

WordPress.com 로고

WordPress.com의 계정을 사용하여 댓글을 남깁니다. 로그아웃 /  변경 )

Google+ photo

Google+의 계정을 사용하여 댓글을 남깁니다. 로그아웃 /  변경 )

Twitter 사진

Twitter의 계정을 사용하여 댓글을 남깁니다. 로그아웃 /  변경 )

Facebook 사진

Facebook의 계정을 사용하여 댓글을 남깁니다. 로그아웃 /  변경 )

%s에 연결하는 중