Bitstream parsing moves from the GPU process to the WebProcess
Component: WebCore WebRTC codecs | 4ae8b7a
Source/WebCore/platform/video-codecs/cocoa/GPUVideoDecoderVTB.mm
WebRTC와 WebCodecs의 video decoding은 GPU process에서 수행됩니다. LibWebRTCCodecsProxy가 IPC로 encoded frame을 수신하고, 이를 VideoToolbox(VTB)에 전달하는 구조입니다. 이때 VTB에는 codec configuration(SPS/PPS/VPS, avcC/hvcC)으로 구성한 format description이 필요합니다. 또한 VTB는 length-prefixed NAL unit을 입력으로 기대합니다. 반면 WebRTC는 AnnexB start-code stream 형태로 데이터를 전달합니다.
이번 commit으로 H.264/HEVC(AnnexB, avcC/hvcC)와 VP9 bitstream parsing이 WebProcess(LibWebRTCCodecs)로 이동되었습니다. 먼저 WebProcess가 AnnexB frame을 length-prefixed 형태로 변환합니다. 동시에 parsing된 reorderQueueMaxSize를 포함하는 VideoInfo를 생성합니다. 이 VideoInfo는 setDecoderFormatDescription을 통해 GPU process로 전달되며, 선택적으로 각 decodeFrame 호출과 함께 전달되기도 합니다. 아울러 codec별로 나뉘어 있던 네 개의 VTB subclass는 하나의 final 클래스인 GPUVideoDecoderVTB로 통합되었습니다.
Significance
그동안 버그가 잦았던 bitstream parsing이 더 높은 권한의 GPU process 밖으로 이동했습니다. 대신 GPU process는 이제 IPC로 전달된 VideoInfo를 신뢰해 VideoToolbox를 구성하고 reorder queue 크기를 결정합니다.
Audit directions
이번 변경으로 신뢰 방향이 뒤집혔습니다. Compromised renderer threat model을 가정하면, GPU process는 이제 attacker가 전적으로 제어하는 VideoInfo를 수신하게 됩니다. 해당 타입의 serialization은 WebCoreArgumentCoders.serialization.in에서 변경되었습니다.
먼저 GPUVideoDecoderVTB가 extensionAtoms와 colorspace/codec config를 이용해 format description을 구성하는 방식을 확인해야 합니다. 제거된 parser와 함께 validation도 사라졌는지 살펴볼 필요가 있습니다. 다음으로 sender가 지정하는 uint8_t 타입의 reorderQueueMaxSize를 점검해야 합니다. 이 값으로 frame이 제한 없이 보관될 수 있는지, 그리고 flush/drain과 어떻게 상호작용하는지가 관건입니다.
Stream 도중 VideoInfo가 도착하는 경우도 확인 대상입니다. 구체적으로는 format이 설정되기 전에 도착한 frame, 반복적인 format 변경, 업데이트 중 decoder가 destroy되는 경우가 있습니다. 처리 중인 frame이 남아 있는 상태에서 기존 session이 정리되는 경우도 포함됩니다. 한편 잘못된 NAL length나 실제 frame 내용과 일치하지 않는 format 선언은 이제 그대로 VideoToolbox에 전달됩니다.
마지막으로 클래스 통합 과정에서 VP9/AV1 특례 처리가 유지되었는지 확인해야 합니다. 여기에는 삭제된 shouldOverrideColorSpaceAttachments와 createVideoInfoFromVP9Stream의 BT.709 기본값이 포함됩니다.