이제 렌더링 하드웨어 인터페이스(Rendering Hardware Interface, RHI)는 Xbox One에 비동기 계산(AsyncCompute) 을 지원합니다. 이는 미사용 GPU 리소스(컴퓨트 유닛, 레지스터, 대역폭)를 활용하기 좋은 방식으로, 렌더링과 함께 dispatch() 호출을 비동기 실행하는 것입니다. 비동기 계산은 별도의 컨텍스트를 사용하며, 컨텍스트 계산 및 렌더링 동기화를 위한 RHI 함수를 제공합니다. 비동기 계산으로 이득을 볼 수 있는 영역을 확인하는 데는 Dr PIX가 좋습니다. 예를 들어, 특정 렌더링 패스에서 CU 절반이 사용되지 않는 경우, 그 CU를 비동기 계산 작업에 활용할 수도 있습니다.
비동기 계산에는 몇 가지 제약이 있습니다.
UAV 카운터가 있는 버퍼는 지원되지 않습니다. 이는 XDK의 한계로, D3D 경고를 생성합니다.
비동기 계산 작업은 PIX GPU 캡처에 나타나지 않습니다(타이밍 캡처에 나타나기는 함). PIX는 그래픽 즉시 컨텍스트만 캡처하는데, 이는 플랫폼의 한계입니다.
자동 파이프라인 플러시는 드라이버에서 제공하지 않습니다. 한 디스패치가 기존 디스패치에 종속된 경우처럼 플러시가 필요하면 RHICSManualGpuFlush를 명시적으로 호출해 줘야 합니다.
API
RHIBeginAsyncComputeJob_DrawThread(EAsyncComputePriority Priority)
렌더링 스레드에서 비동기 계산 작업을 시작합니다. 우선순위를 사용하여 (ID3D11XComputeContext::SetLimits를 통해) 작업에 할당할 셰이더 리소스 수를 결정합니다. 현재 사용할 수 있는 우선순위는 AsyncComputePriority_High와 AsyncComputePriority_Default, 두 가지입니다.
RHIEndAsyncComputeJob_DrawThread
비동기 계산 작업을 종료합니다. 동기화에 사용할 수 있는 32비트 펜스 인덱스(Fence Index)를 반환하거나, 계산이 꺼져있거나 활성화된 계산 작업이 없는 경우 -1을 반환합니다.
RHIGraphicsWaitOnAsyncComputeJob
그래픽 즉시 컨텍스트에 n 명령을 삽입하여 비동기 작업이 완료될 때까지 블록합니다. -1을 전달하면 일찍 빠져나옵니다.
RHIBeginAsyncComputeJob_DrawThread와 RHIEndAsyncComputeJob_DrawThread 호출 사이에 RHI는 비동기 계산 상태가 됩니다. 이 기간에 비동기 계산 컨텍스트를 통해 지원되는 RHI 명령이 실행됩니다. 지원되지 않는 RHI의 경우에는 어서트가 발생합니다.
비활성화/활성화
비동기 계산은 컴파일 시에 #define USE_ASYNC_COMPUTE_CONTEXT로 활성화하거나 비활성화할 수 있습니다. 런타임에서는 r.rdg.asynccompute 콘솔 변수로 비활성화할 수 있습니다. 비동기 계산이 비활성화되면, 비동기 계산 블록 내 디스패치는 그래픽 명령 버퍼에서 동기식으로 실행됩니다. PC에서는 USE_ASYNC_COMPUTE_CONTEXT가 0으로 정의되어 있는데, 이는 D3D11.1에서 지원되지 않기 때문입니다.
PIX
비동기 계산 컨텍스트 작업은 GPU 캡처에 캡처되지 않으므로, 비동기 계산이 활성화된 경우 이러한 캡처로 인해 GPU 퍼포먼스를 잘못 파악하게 될 수 있습니다. 그래픽 디버깅이 목적이라면, 위의 CVar를 사용하여 비동기 계산을 비활성화해야 합니다. 비동기 계산은 PIX 타이밍 캡처에 의해 지원됩니다. 캡처는 타임라인에 다음과 같이 나타납니다.
크레딧
이 기능은 라이온헤드 스튜디오(Lionhead Studios)에서 구현했습니다. 이를 통합하여 XboxOne 렌더링을 최적화하는 툴로 활용할 계획입니다.