mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-05-04 22:49:13 +02:00
d3d12: Add support for AV1 Video Decode
Reviewed-by: Giancarlo Devich <gdevich@microsoft.com> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/18875>
This commit is contained in:
parent
f2fc9996d3
commit
af8f730d8d
9 changed files with 1099 additions and 0 deletions
|
|
@ -468,6 +468,7 @@ d3d12_convert_pipe_video_profile_to_dxgi_format(enum pipe_video_profile profile)
|
|||
case PIPE_VIDEO_PROFILE_MPEG4_AVC_EXTENDED:
|
||||
case PIPE_VIDEO_PROFILE_MPEG4_AVC_HIGH:
|
||||
case PIPE_VIDEO_PROFILE_HEVC_MAIN:
|
||||
case PIPE_VIDEO_PROFILE_AV1_MAIN:
|
||||
return DXGI_FORMAT_NV12;
|
||||
case PIPE_VIDEO_PROFILE_MPEG4_AVC_HIGH10:
|
||||
case PIPE_VIDEO_PROFILE_HEVC_MAIN_10:
|
||||
|
|
|
|||
|
|
@ -29,6 +29,7 @@
|
|||
#include "d3d12_video_dec.h"
|
||||
#include "d3d12_video_dec_h264.h"
|
||||
#include "d3d12_video_dec_hevc.h"
|
||||
#include "d3d12_video_dec_av1.h"
|
||||
#include "d3d12_video_buffer.h"
|
||||
#include "d3d12_residency.h"
|
||||
|
||||
|
|
@ -313,6 +314,12 @@ d3d12_video_decoder_store_upper_layer_references(struct d3d12_video_decoder *pD3
|
|||
pD3D12Dec->m_pCurrentReferenceTargets = pPicControlHevc->ref;
|
||||
} break;
|
||||
|
||||
case d3d12_video_decode_profile_type_av1:
|
||||
{
|
||||
pipe_av1_picture_desc *pPicControlAV1 = (pipe_av1_picture_desc *) picture;
|
||||
pD3D12Dec->m_pCurrentReferenceTargets = pPicControlAV1->ref;
|
||||
} break;
|
||||
|
||||
default:
|
||||
{
|
||||
unreachable("Unsupported d3d12_video_decode_profile_type");
|
||||
|
|
@ -1008,6 +1015,13 @@ d3d12_video_decoder_prepare_for_decode_frame(struct d3d12_video_decoder *pD3D12D
|
|||
currentFrameDPBEntrySubresource);
|
||||
} break;
|
||||
|
||||
case d3d12_video_decode_profile_type_av1:
|
||||
{
|
||||
d3d12_video_decoder_prepare_current_frame_references_av1(pD3D12Dec,
|
||||
pCurrentFrameDPBEntry,
|
||||
currentFrameDPBEntrySubresource);
|
||||
} break;
|
||||
|
||||
default:
|
||||
{
|
||||
unreachable("Unsupported d3d12_video_decode_profile_type");
|
||||
|
|
@ -1126,6 +1140,11 @@ d3d12_video_decoder_refresh_dpb_active_references(struct d3d12_video_decoder *pD
|
|||
d3d12_video_decoder_refresh_dpb_active_references_hevc(pD3D12Dec);
|
||||
} break;
|
||||
|
||||
case d3d12_video_decode_profile_type_av1:
|
||||
{
|
||||
d3d12_video_decoder_refresh_dpb_active_references_av1(pD3D12Dec);
|
||||
} break;
|
||||
|
||||
default:
|
||||
{
|
||||
unreachable("Unsupported d3d12_video_decode_profile_type");
|
||||
|
|
@ -1153,6 +1172,11 @@ d3d12_video_decoder_get_frame_info(
|
|||
d3d12_video_decoder_get_frame_info_hevc(pD3D12Dec, pWidth, pHeight, pMaxDPB, isInterlaced);
|
||||
} break;
|
||||
|
||||
case d3d12_video_decode_profile_type_av1:
|
||||
{
|
||||
d3d12_video_decoder_get_frame_info_av1(pD3D12Dec, pWidth, pHeight, pMaxDPB, isInterlaced);
|
||||
} break;
|
||||
|
||||
default:
|
||||
{
|
||||
unreachable("Unsupported d3d12_video_decode_profile_type");
|
||||
|
|
@ -1257,7 +1281,20 @@ d3d12_video_decoder_store_converted_dxva_picparams_from_pipe_input(
|
|||
pD3D12Dec->qp_matrix_frame_argument_enabled);
|
||||
d3d12_video_decoder_store_dxva_qmatrix_in_qmatrix_buffer(codec, &dxvaQmatrixHEVC, dxvaQMatrixBufferSize);
|
||||
} break;
|
||||
case d3d12_video_decode_profile_type_av1:
|
||||
{
|
||||
size_t dxvaPicParamsBufferSize = sizeof(DXVA_PicParams_AV1);
|
||||
pipe_av1_picture_desc *pPicControlAV1 = (pipe_av1_picture_desc *) picture;
|
||||
DXVA_PicParams_AV1 dxvaPicParamsAV1 =
|
||||
d3d12_video_decoder_dxva_picparams_from_pipe_picparams_av1(pD3D12Dec->m_fenceValue,
|
||||
codec->base.profile,
|
||||
pPicControlAV1);
|
||||
|
||||
d3d12_video_decoder_store_dxva_picparams_in_picparams_buffer(codec,
|
||||
&dxvaPicParamsAV1,
|
||||
dxvaPicParamsBufferSize);
|
||||
pD3D12Dec->qp_matrix_frame_argument_enabled = false;
|
||||
} break;
|
||||
default:
|
||||
{
|
||||
unreachable("Unsupported d3d12_video_decode_profile_type");
|
||||
|
|
@ -1283,6 +1320,11 @@ d3d12_video_decoder_prepare_dxva_slices_control(
|
|||
{
|
||||
d3d12_video_decoder_prepare_dxva_slices_control_hevc(pD3D12Dec, pD3D12Dec->m_SliceControlBuffer, (struct pipe_h265_picture_desc*) picture);
|
||||
} break;
|
||||
case d3d12_video_decode_profile_type_av1:
|
||||
{
|
||||
d3d12_video_decoder_prepare_dxva_slices_control_av1(pD3D12Dec, pD3D12Dec->m_SliceControlBuffer, (struct pipe_av1_picture_desc*) picture);
|
||||
} break;
|
||||
|
||||
default:
|
||||
{
|
||||
unreachable("Unsupported d3d12_video_decode_profile_type");
|
||||
|
|
@ -1324,6 +1366,7 @@ d3d12_video_decoder_supports_aot_dpb(D3D12_FEATURE_DATA_VIDEO_DECODE_SUPPORT dec
|
|||
switch (profileType) {
|
||||
case d3d12_video_decode_profile_type_h264:
|
||||
case d3d12_video_decode_profile_type_hevc:
|
||||
case d3d12_video_decode_profile_type_av1:
|
||||
supportedProfile = true;
|
||||
break;
|
||||
default:
|
||||
|
|
@ -1348,6 +1391,8 @@ d3d12_video_decoder_convert_pipe_video_profile_to_profile_type(enum pipe_video_p
|
|||
case PIPE_VIDEO_PROFILE_HEVC_MAIN:
|
||||
case PIPE_VIDEO_PROFILE_HEVC_MAIN_10:
|
||||
return d3d12_video_decode_profile_type_hevc;
|
||||
case PIPE_VIDEO_PROFILE_AV1_MAIN:
|
||||
return d3d12_video_decode_profile_type_av1;
|
||||
default:
|
||||
{
|
||||
unreachable("Unsupported pipe video profile");
|
||||
|
|
@ -1370,6 +1415,8 @@ d3d12_video_decoder_convert_pipe_video_profile_to_d3d12_profile(enum pipe_video_
|
|||
return D3D12_VIDEO_DECODE_PROFILE_HEVC_MAIN;
|
||||
case PIPE_VIDEO_PROFILE_HEVC_MAIN_10:
|
||||
return D3D12_VIDEO_DECODE_PROFILE_HEVC_MAIN10;
|
||||
case PIPE_VIDEO_PROFILE_AV1_MAIN:
|
||||
return D3D12_VIDEO_DECODE_PROFILE_AV1_PROFILE0;
|
||||
default:
|
||||
return {};
|
||||
}
|
||||
|
|
@ -1383,6 +1430,10 @@ d3d12_video_decoder_resolve_profile(d3d12_video_decode_profile_type profileType,
|
|||
return D3D12_VIDEO_DECODE_PROFILE_H264;
|
||||
case d3d12_video_decode_profile_type_hevc:
|
||||
return (decode_format == DXGI_FORMAT_NV12) ? D3D12_VIDEO_DECODE_PROFILE_HEVC_MAIN : D3D12_VIDEO_DECODE_PROFILE_HEVC_MAIN10;
|
||||
break;
|
||||
case d3d12_video_decode_profile_type_av1:
|
||||
return D3D12_VIDEO_DECODE_PROFILE_AV1_PROFILE0;
|
||||
break;
|
||||
default:
|
||||
{
|
||||
unreachable("Unsupported d3d12_video_decode_profile_type");
|
||||
|
|
|
|||
622
src/gallium/drivers/d3d12/d3d12_video_dec_av1.cpp
Normal file
622
src/gallium/drivers/d3d12/d3d12_video_dec_av1.cpp
Normal file
|
|
@ -0,0 +1,622 @@
|
|||
/*
|
||||
* Copyright © Microsoft Corporation
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
||||
* IN THE SOFTWARE.
|
||||
*/
|
||||
|
||||
#include "d3d12_video_dec.h"
|
||||
#include "d3d12_video_dec_av1.h"
|
||||
#include <cmath>
|
||||
|
||||
void
|
||||
d3d12_video_decoder_refresh_dpb_active_references_av1(struct d3d12_video_decoder *pD3D12Dec)
|
||||
{
|
||||
// Method overview
|
||||
// 1. Codec specific strategy in switch statement regarding reference frames eviction policy. Should only mark active
|
||||
// DPB references, leaving evicted ones as unused
|
||||
// 2. Call release_unused_references_texture_memory(); at the end of this method. Any references (and texture
|
||||
// allocations associated)
|
||||
// that were left not marked as used in m_spDPBManager by step (2) are lost.
|
||||
|
||||
// Assign DXVA original Index indices to current frame and references
|
||||
DXVA_PicParams_AV1 *pCurrPicParams = d3d12_video_decoder_get_current_dxva_picparams<DXVA_PicParams_AV1>(pD3D12Dec);
|
||||
|
||||
for (uint8_t i = 0; i < _countof(pCurrPicParams->RefFrameMapTextureIndex); i++) {
|
||||
if (pD3D12Dec->m_pCurrentReferenceTargets[i]) {
|
||||
pCurrPicParams->RefFrameMapTextureIndex[i] =
|
||||
pD3D12Dec->m_spDPBManager->get_index7bits(pD3D12Dec->m_pCurrentReferenceTargets[i]);
|
||||
}
|
||||
}
|
||||
|
||||
pD3D12Dec->m_spDPBManager->mark_all_references_as_unused();
|
||||
pD3D12Dec->m_spDPBManager->mark_references_in_use_av1(pCurrPicParams->RefFrameMapTextureIndex);
|
||||
|
||||
// Releases the underlying reference picture texture objects of all references that were not marked as used in this
|
||||
// method.
|
||||
pD3D12Dec->m_spDPBManager->release_unused_references_texture_memory();
|
||||
|
||||
pCurrPicParams->CurrPicTextureIndex = pD3D12Dec->m_spDPBManager->get_index7bits(pD3D12Dec->m_pCurrentDecodeTarget);
|
||||
}
|
||||
|
||||
void
|
||||
d3d12_video_decoder_get_frame_info_av1(
|
||||
struct d3d12_video_decoder *pD3D12Dec, uint32_t *pWidth, uint32_t *pHeight, uint16_t *pMaxDPB, bool &isInterlaced)
|
||||
{
|
||||
auto pPicParams = d3d12_video_decoder_get_current_dxva_picparams<DXVA_PicParams_AV1>(pD3D12Dec);
|
||||
/* width, height
|
||||
Specify the coded width and height of the current frame.
|
||||
These correspond to the syntax elements of: frame_width_minus_1 and frame_height_minus_1.
|
||||
If these values are derived for the frame (for example via the frame_size_override_flag),
|
||||
the host decoder will derive the appropriate values and store the result here.
|
||||
If superres is enabled these values represent the post-scaled frame resolution
|
||||
(referred to in the specification as UpscaledWidth). */
|
||||
*pWidth = pPicParams->width;
|
||||
*pHeight = pPicParams->height;
|
||||
|
||||
/*
|
||||
Note – The AV1 decoder maintains a pool (RefFrameMapTextureIndex[]) of 8 reference pictures at all times.
|
||||
Each frame may pick up to 7 reference frames (frame_refs[]) from the pool to use for inter prediction of the current frame.
|
||||
*/
|
||||
*pMaxDPB = 8 + 1 /*current picture*/;
|
||||
isInterlaced = false;
|
||||
}
|
||||
|
||||
void
|
||||
d3d12_video_decoder_prepare_current_frame_references_av1(struct d3d12_video_decoder *pD3D12Dec,
|
||||
ID3D12Resource *pTexture2D,
|
||||
uint32_t subresourceIndex)
|
||||
{
|
||||
DXVA_PicParams_AV1 *pPicParams = d3d12_video_decoder_get_current_dxva_picparams<DXVA_PicParams_AV1>(pD3D12Dec);
|
||||
pPicParams->CurrPicTextureIndex = pD3D12Dec->m_spDPBManager->store_future_reference(pPicParams->CurrPicTextureIndex,
|
||||
pD3D12Dec->m_spVideoDecoderHeap,
|
||||
pTexture2D,
|
||||
subresourceIndex);
|
||||
pD3D12Dec->m_spDPBManager->update_entries_av1(
|
||||
d3d12_video_decoder_get_current_dxva_picparams<DXVA_PicParams_AV1>(pD3D12Dec)->RefFrameMapTextureIndex,
|
||||
pD3D12Dec->m_transitionsStorage);
|
||||
|
||||
pD3D12Dec->m_spDecodeCommandList->ResourceBarrier(pD3D12Dec->m_transitionsStorage.size(), pD3D12Dec->m_transitionsStorage.data());
|
||||
|
||||
// Schedule reverse (back to common) transitions before command list closes for current frame
|
||||
for (auto BarrierDesc : pD3D12Dec->m_transitionsStorage) {
|
||||
std::swap(BarrierDesc.Transition.StateBefore, BarrierDesc.Transition.StateAfter);
|
||||
pD3D12Dec->m_transitionsBeforeCloseCmdList.push_back(BarrierDesc);
|
||||
}
|
||||
|
||||
debug_printf(
|
||||
"[d3d12_video_decoder_prepare_current_frame_references_av1] DXVA_PicParams_AV1 after index remapping)\n");
|
||||
d3d12_video_decoder_log_pic_params_av1(
|
||||
d3d12_video_decoder_get_current_dxva_picparams<DXVA_PicParams_AV1>(pD3D12Dec));
|
||||
}
|
||||
|
||||
void
|
||||
d3d12_video_decoder_log_pic_params_av1(DXVA_PicParams_AV1 *pPicParams)
|
||||
{
|
||||
|
||||
debug_printf("\n=============================================\n");
|
||||
debug_printf("width = %d\n", pPicParams->width);
|
||||
debug_printf("height = %d\n", pPicParams->height);
|
||||
|
||||
debug_printf("max_width = %d\n", pPicParams->max_width);
|
||||
debug_printf("max_height = %d\n", pPicParams->max_height);
|
||||
|
||||
debug_printf("CurrPicTextureIndex = %d\n", pPicParams->CurrPicTextureIndex);
|
||||
debug_printf("superres_denom = %d\n", pPicParams->superres_denom);
|
||||
debug_printf("bitdepth = %d\n", pPicParams->bitdepth);
|
||||
debug_printf("seq_profile = %d\n", pPicParams->seq_profile);
|
||||
|
||||
debug_printf("cols = %d\n", pPicParams->tiles.cols);
|
||||
debug_printf("rows = %d\n", pPicParams->tiles.rows);
|
||||
debug_printf("context_update_id = %d\n", pPicParams->tiles.context_update_id);
|
||||
for (uint32_t i = 0; i < pPicParams->tiles.cols; i++)
|
||||
debug_printf("widths[%d] = %d\n", i, pPicParams->tiles.widths[i]);
|
||||
for (uint32_t i = 0; i < pPicParams->tiles.rows; i++)
|
||||
debug_printf("heights[%d] = %d\n", i, pPicParams->tiles.heights[i]);
|
||||
|
||||
debug_printf("coding.use_128x128_superblock = %d\n", pPicParams->coding.use_128x128_superblock);
|
||||
debug_printf("coding.intra_edge_filter = %d\n", pPicParams->coding.intra_edge_filter);
|
||||
debug_printf("coding.interintra_compound = %d\n", pPicParams->coding.interintra_compound);
|
||||
debug_printf("coding.masked_compound = %d\n", pPicParams->coding.masked_compound);
|
||||
debug_printf("coding.warped_motion = %d\n", pPicParams->coding.warped_motion);
|
||||
debug_printf("coding.dual_filter = %d\n", pPicParams->coding.dual_filter);
|
||||
debug_printf("coding.jnt_comp = %d\n", pPicParams->coding.jnt_comp);
|
||||
debug_printf("coding.screen_content_tools = %d\n", pPicParams->coding.screen_content_tools);
|
||||
debug_printf("coding.integer_mv = %d\n", pPicParams->coding.integer_mv);
|
||||
debug_printf("coding.cdef = %d\n", pPicParams->coding.cdef);
|
||||
debug_printf("coding.restoration = %d\n", pPicParams->coding.restoration);
|
||||
debug_printf("coding.film_grain = %d\n", pPicParams->coding.film_grain);
|
||||
debug_printf("coding.intrabc = %d\n", pPicParams->coding.intrabc);
|
||||
debug_printf("coding.high_precision_mv = %d\n", pPicParams->coding.high_precision_mv);
|
||||
debug_printf("coding.switchable_motion_mode = %d\n", pPicParams->coding.switchable_motion_mode);
|
||||
debug_printf("coding.filter_intra = %d\n", pPicParams->coding.filter_intra);
|
||||
debug_printf("coding.disable_frame_end_update_cdf = %d\n", pPicParams->coding.disable_frame_end_update_cdf);
|
||||
debug_printf("coding.disable_cdf_update = %d\n", pPicParams->coding.disable_cdf_update);
|
||||
debug_printf("coding.reference_mode = %d\n", pPicParams->coding.reference_mode);
|
||||
debug_printf("coding.skip_mode = %d\n", pPicParams->coding.skip_mode);
|
||||
debug_printf("coding.reduced_tx_set = %d\n", pPicParams->coding.reduced_tx_set);
|
||||
debug_printf("coding.superres = %d\n", pPicParams->coding.superres);
|
||||
debug_printf("coding.tx_mode = %d\n", pPicParams->coding.tx_mode);
|
||||
debug_printf("coding.use_ref_frame_mvs = %d\n", pPicParams->coding.use_ref_frame_mvs);
|
||||
debug_printf("coding.enable_ref_frame_mvs = %d\n", pPicParams->coding.enable_ref_frame_mvs);
|
||||
debug_printf("coding.reference_frame_update = %d\n", pPicParams->coding.reference_frame_update);
|
||||
debug_printf("coding.Reserved = %d\n", pPicParams->coding.Reserved);
|
||||
debug_printf("coding.CodingParamToolFlags = %d\n", pPicParams->coding.CodingParamToolFlags);
|
||||
|
||||
debug_printf("format.frame_type = %d\n", pPicParams->format.frame_type);
|
||||
debug_printf("format.show_frame = %d\n", pPicParams->format.show_frame);
|
||||
debug_printf("format.showable_frame = %d\n", pPicParams->format.showable_frame);
|
||||
debug_printf("format.subsampling_x = %d\n", pPicParams->format.subsampling_x);
|
||||
debug_printf("format.subsampling_y = %d\n", pPicParams->format.subsampling_y);
|
||||
debug_printf("format.mono_chrome = %d\n", pPicParams->format.mono_chrome);
|
||||
debug_printf("format.Reserved = %d\n", pPicParams->format.Reserved);
|
||||
|
||||
debug_printf("primary_ref_frame = %d\n", pPicParams->primary_ref_frame);
|
||||
debug_printf("order_hint = %d\n", pPicParams->order_hint);
|
||||
debug_printf("order_hint_bits = %d\n", pPicParams->order_hint_bits);
|
||||
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->frame_refs); i++) {
|
||||
debug_printf("frame_refs[%d]\n", i);
|
||||
debug_printf("\twidth = %d\n", pPicParams->frame_refs[i].width);
|
||||
debug_printf("\theight = %d\n", pPicParams->frame_refs[i].height);
|
||||
|
||||
// Global motion parameters
|
||||
for (uint32_t j = 0; j < 6; j++)
|
||||
debug_printf("\t\twmmat[%d] = %d\n", j, pPicParams->frame_refs[i].wmmat[j]);
|
||||
debug_printf("\twminvalid = %d\n", pPicParams->frame_refs[i].wminvalid);
|
||||
debug_printf("\twmtype = %d\n", pPicParams->frame_refs[i].wmtype);
|
||||
debug_printf("\tGlobalMotionFlags = %d\n", pPicParams->frame_refs[i].GlobalMotionFlags);
|
||||
debug_printf("\tIndex = %d\n", pPicParams->frame_refs[i].Index);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->RefFrameMapTextureIndex); i++)
|
||||
debug_printf("RefFrameMapTextureIndex[%d] = %d\n", i, pPicParams->RefFrameMapTextureIndex[i]);
|
||||
|
||||
// Loop filter parameters
|
||||
debug_printf("filter_level[0] = %d\n", pPicParams->loop_filter.filter_level[0]);
|
||||
debug_printf("filter_level[1] = %d\n", pPicParams->loop_filter.filter_level[1]);
|
||||
debug_printf("filter_level_u = %d\n", pPicParams->loop_filter.filter_level_u);
|
||||
debug_printf("filter_level_v = %d\n", pPicParams->loop_filter.filter_level_v);
|
||||
debug_printf("sharpness_level = %d\n", pPicParams->loop_filter.sharpness_level);
|
||||
debug_printf("mode_ref_delta_enabled = %d\n", pPicParams->loop_filter.mode_ref_delta_enabled);
|
||||
debug_printf("mode_ref_delta_update = %d\n", pPicParams->loop_filter.mode_ref_delta_update);
|
||||
debug_printf("delta_lf_multi = %d\n", pPicParams->loop_filter.delta_lf_multi);
|
||||
debug_printf("delta_lf_present = %d\n", pPicParams->loop_filter.delta_lf_present);
|
||||
debug_printf("ControlFlags = %d\n", pPicParams->loop_filter.ControlFlags);
|
||||
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->loop_filter.ref_deltas); i++)
|
||||
debug_printf("loop_filter.ref_deltas[%d] = %d\n", i, pPicParams->loop_filter.ref_deltas[i]);
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->loop_filter.mode_deltas); i++)
|
||||
debug_printf("loop_filter.mode_deltas[%d] = %d\n", i, pPicParams->loop_filter.mode_deltas[i]);
|
||||
|
||||
debug_printf("delta_lf_res = %d\n", pPicParams->loop_filter.delta_lf_res);
|
||||
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->loop_filter.frame_restoration_type); i++)
|
||||
debug_printf("loop_filter.frame_restoration_type[%d] = %d\n", i, pPicParams->loop_filter.frame_restoration_type[i]);
|
||||
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->loop_filter.log2_restoration_unit_size); i++)
|
||||
debug_printf("loop_filter.log2_restoration_unit_size[%d] = %d\n", i, pPicParams->loop_filter.log2_restoration_unit_size[i]);
|
||||
|
||||
// Quantization
|
||||
debug_printf("delta_q_present = %d\n", pPicParams->quantization.delta_q_present);
|
||||
debug_printf("delta_q_res = %d\n", pPicParams->quantization.delta_q_res);
|
||||
debug_printf("ControlFlags = %d\n", pPicParams->quantization.ControlFlags);
|
||||
debug_printf("quantization.base_qindex = %d\n", pPicParams->quantization.base_qindex);
|
||||
debug_printf("quantization.y_dc_delta_q = %d\n", pPicParams->quantization.y_dc_delta_q);
|
||||
debug_printf("quantization.u_dc_delta_q = %d\n", pPicParams->quantization.u_dc_delta_q);
|
||||
debug_printf("quantization.v_dc_delta_q = %d\n", pPicParams->quantization.v_dc_delta_q);
|
||||
debug_printf("quantization.u_ac_delta_q = %d\n", pPicParams->quantization.u_ac_delta_q);
|
||||
debug_printf("quantization.v_ac_delta_q = %d\n", pPicParams->quantization.v_ac_delta_q);
|
||||
// using_qmatrix:
|
||||
debug_printf("quantization.qm_y = %d\n", pPicParams->quantization.qm_y);
|
||||
debug_printf("quantization.qm_u = %d\n", pPicParams->quantization.qm_u);
|
||||
debug_printf("quantization.qm_v = %d\n", pPicParams->quantization.qm_v);
|
||||
|
||||
// Cdef parameters
|
||||
debug_printf("cdef.damping = %d\n", pPicParams->cdef.damping);
|
||||
debug_printf("cdef.bits = %d\n", pPicParams->cdef.bits);
|
||||
debug_printf("cdef.Reserved = %d\n", pPicParams->cdef.Reserved);
|
||||
debug_printf("cdef.ControlFlags = %d\n", pPicParams->cdef.ControlFlags);
|
||||
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->cdef.y_strengths); i++) {
|
||||
debug_printf("cdef.primaryuv_strengthsy%d] = %d\n", i, pPicParams->cdef.y_strengths[i].primary);
|
||||
debug_printf("cdef.y_strengths.secondary[%d] = %d\n", i, pPicParams->cdef.y_strengths[i].secondary);
|
||||
debug_printf("cdef.y_strengths.combined[%d] = %d\n", i, pPicParams->cdef.y_strengths[i].combined);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->cdef.uv_strengths); i++) {
|
||||
debug_printf("cdef.uv_strengths.primary[%d] = %d\n", i, pPicParams->cdef.uv_strengths[i].primary);
|
||||
debug_printf("cdef.uv_strengths.secondary[%d] = %d\n", i, pPicParams->cdef.uv_strengths[i].secondary);
|
||||
debug_printf("cdef.uv_strengths.combined[%d] = %d\n", i, pPicParams->cdef.uv_strengths[i].combined);
|
||||
}
|
||||
|
||||
debug_printf("interp_filter = %d\n", pPicParams->interp_filter);
|
||||
|
||||
// Segmentation
|
||||
debug_printf("segmentation.enabled = %d\n", pPicParams->segmentation.enabled);
|
||||
debug_printf("segmentation.update_map = %d\n", pPicParams->segmentation.update_map);
|
||||
debug_printf("segmentation.update_data = %d\n", pPicParams->segmentation.update_data);
|
||||
debug_printf("segmentation.temporal_update = %d\n", pPicParams->segmentation.temporal_update);
|
||||
debug_printf("segmentation.Reserved = %d\n", pPicParams->segmentation.Reserved);
|
||||
debug_printf("segmentation.ControlFlags = %d\n", pPicParams->segmentation.ControlFlags);
|
||||
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->segmentation.feature_mask); i++) {
|
||||
debug_printf("segmentation.feature_mask[%d].alt_q = %d\n", i, pPicParams->segmentation.feature_mask[i].alt_q);
|
||||
debug_printf("segmentation.feature_mask[%d].alt_lf_y_v = %d\n", i, pPicParams->segmentation.feature_mask[i].alt_lf_y_v);
|
||||
debug_printf("segmentation.feature_mask[%d].alt_lf_y_h = %d\n", i, pPicParams->segmentation.feature_mask[i].alt_lf_y_h);
|
||||
debug_printf("segmentation.feature_mask[%d].alt_lf_u = %d\n", i, pPicParams->segmentation.feature_mask[i].alt_lf_u);
|
||||
debug_printf("segmentation.feature_mask[%d].alt_lf_v = %d\n", i, pPicParams->segmentation.feature_mask[i].alt_lf_v);
|
||||
debug_printf("segmentation.feature_mask[%d].ref_frame = %d\n", i, pPicParams->segmentation.feature_mask[i].ref_frame);
|
||||
debug_printf("segmentation.feature_mask[%d].skip = %d\n", i, pPicParams->segmentation.feature_mask[i].skip);
|
||||
debug_printf("segmentation.feature_mask[%d].globalmv = %d\n", i, pPicParams->segmentation.feature_mask[i].globalmv);
|
||||
debug_printf("segmentation.feature_mask[%d].mask = %d\n", i, pPicParams->segmentation.feature_mask[i].mask);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < 8; i++)
|
||||
for (uint32_t j = 0; j < 8; j++)
|
||||
debug_printf("segmentation.feature_data[%d][%d] = %d\n", i, j, pPicParams->segmentation.feature_data[i][j]);
|
||||
|
||||
debug_printf("film_grain.apply_grain = %d\n", pPicParams->film_grain.apply_grain);
|
||||
debug_printf("film_grain.scaling_shift_minus8 = %d\n", pPicParams->film_grain.scaling_shift_minus8);
|
||||
debug_printf("film_grain.chroma_scaling_from_luma = %d\n", pPicParams->film_grain.chroma_scaling_from_luma);
|
||||
debug_printf("film_grain.ar_coeff_lag = %d\n", pPicParams->film_grain.ar_coeff_lag);
|
||||
debug_printf("film_grain.ar_coeff_shift_minus6 = %d\n", pPicParams->film_grain.ar_coeff_shift_minus6);
|
||||
debug_printf("film_grain.grain_scale_shift = %d\n", pPicParams->film_grain.grain_scale_shift);
|
||||
debug_printf("film_grain.overlap_flag = %d\n", pPicParams->film_grain.overlap_flag);
|
||||
debug_printf("film_grain.clip_to_restricted_range = %d\n", pPicParams->film_grain.clip_to_restricted_range);
|
||||
debug_printf("film_grain.matrix_coeff_is_identity = %d\n", pPicParams->film_grain.matrix_coeff_is_identity);
|
||||
debug_printf("film_grain.Reserved = %d\n", pPicParams->film_grain.Reserved);
|
||||
debug_printf("film_grain.ControlFlags = %d\n", pPicParams->film_grain.ControlFlags);
|
||||
|
||||
debug_printf("film_grain.grain_seed = %d\n", pPicParams->film_grain.grain_seed);
|
||||
|
||||
for (uint32_t i = 0; i < 14; i++)
|
||||
for (uint32_t j = 0; j < 2; j++)
|
||||
debug_printf("film_grain.scaling_points_y[%d][%d] = %d\n", i, j, pPicParams->film_grain.scaling_points_y[i][j]);
|
||||
|
||||
debug_printf("film_grain.num_y_points = %d\n", pPicParams->film_grain.num_y_points);
|
||||
|
||||
for (uint32_t i = 0; i < 10; i++)
|
||||
for (uint32_t j = 0; j < 2; j++)
|
||||
debug_printf("film_grain.scaling_points_cb[%d][%d] = %d\n", i, j, pPicParams->film_grain.scaling_points_cb[i][j]);
|
||||
|
||||
debug_printf("film_grain.num_cb_points = %d\n", pPicParams->film_grain.num_cb_points);
|
||||
|
||||
for (uint32_t i = 0; i < 10; i++)
|
||||
for (uint32_t j = 0; j < 2; j++)
|
||||
debug_printf("film_grain.scaling_points_cr[%d][%d] = %d\n", i, j, pPicParams->film_grain.scaling_points_cr[i][j]);
|
||||
|
||||
debug_printf("film_grain.num_cr_points = %d\n", pPicParams->film_grain.num_cr_points);
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->film_grain.ar_coeffs_y); i++)
|
||||
debug_printf("film_grain.ar_coeffs_y[%d] = %d\n", i, pPicParams->film_grain.ar_coeffs_y[i]);
|
||||
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->film_grain.ar_coeffs_cb); i++)
|
||||
debug_printf("film_grain.ar_coeffs_cb[%d] = %d\n", i, pPicParams->film_grain.ar_coeffs_cb[i]);
|
||||
|
||||
for (uint32_t i = 0; i < _countof(pPicParams->film_grain.ar_coeffs_cr); i++)
|
||||
debug_printf("film_grain.ar_coeffs_cr[%d] = %d\n", i, pPicParams->film_grain.ar_coeffs_cr[i]);
|
||||
|
||||
debug_printf("film_grain.cb_mult = %d\n", pPicParams->film_grain.cb_mult);
|
||||
debug_printf("film_grain.cb_luma_mult = %d\n", pPicParams->film_grain.cb_luma_mult);
|
||||
debug_printf("film_grain.cr_mult = %d\n", pPicParams->film_grain.cr_mult);
|
||||
debug_printf("film_grain.cr_luma_mult = %d\n", pPicParams->film_grain.cr_luma_mult);
|
||||
debug_printf("film_grain.Reserved8Bits = %d\n", pPicParams->film_grain.Reserved8Bits);
|
||||
debug_printf("film_grain.cb_offset = %d\n", pPicParams->film_grain.cb_offset);
|
||||
debug_printf("film_grain.cr_offset = %d\n", pPicParams->film_grain.cr_offset);
|
||||
|
||||
debug_printf("Reserved32Bits = %d\n", pPicParams->Reserved32Bits);
|
||||
debug_printf("StatusReportFeedbackNumber = %d\n", pPicParams->StatusReportFeedbackNumber);
|
||||
}
|
||||
|
||||
void
|
||||
d3d12_video_decoder_prepare_dxva_slices_control_av1(struct d3d12_video_decoder *pD3D12Dec,
|
||||
std::vector<uint8_t> &vecOutSliceControlBuffers,
|
||||
struct pipe_av1_picture_desc *picture_av1)
|
||||
{
|
||||
uint32_t tile_count = picture_av1->picture_parameter.tile_cols * picture_av1->picture_parameter.tile_rows;
|
||||
debug_printf("[d3d12_video_decoder_av1] Upper layer reported %d tiles for this frame, parsing them below...\n",
|
||||
tile_count);
|
||||
|
||||
uint64_t TotalSlicesDXVAArrayByteSize = tile_count * sizeof(DXVA_Tile_AV1);
|
||||
pD3D12Dec->m_SliceControlBuffer.resize(TotalSlicesDXVAArrayByteSize);
|
||||
|
||||
uint8_t* pData = vecOutSliceControlBuffers.data();
|
||||
for (uint32_t tileIdx = 0; tileIdx < tile_count; tileIdx++)
|
||||
{
|
||||
DXVA_Tile_AV1 currentTileEntry = {};
|
||||
currentTileEntry.DataOffset = picture_av1->slice_parameter.slice_data_offset[tileIdx];
|
||||
currentTileEntry.DataSize = picture_av1->slice_parameter.slice_data_size[tileIdx];
|
||||
currentTileEntry.row = picture_av1->slice_parameter.slice_data_row[tileIdx];
|
||||
currentTileEntry.column = picture_av1->slice_parameter.slice_data_col[tileIdx];
|
||||
currentTileEntry.anchor_frame = picture_av1->slice_parameter.slice_data_anchor_frame_idx[tileIdx];
|
||||
|
||||
debug_printf("[d3d12_video_decoder_av1] Detected tile index %" PRIu32
|
||||
" with DataOffset %" PRIu32
|
||||
" - DataSize %" PRIu32
|
||||
" - row: %" PRIu16
|
||||
" - col: %" PRIu16
|
||||
" - anchor_frame_idx: %" PRIu8
|
||||
" for frame with "
|
||||
"fenceValue: %d\n",
|
||||
tileIdx,
|
||||
currentTileEntry.DataOffset,
|
||||
currentTileEntry.DataSize,
|
||||
currentTileEntry.row,
|
||||
currentTileEntry.column,
|
||||
currentTileEntry.anchor_frame,
|
||||
pD3D12Dec->m_fenceValue);
|
||||
|
||||
memcpy(pData, ¤tTileEntry, sizeof(DXVA_Tile_AV1));
|
||||
pData += sizeof(DXVA_Tile_AV1);
|
||||
}
|
||||
assert(vecOutSliceControlBuffers.size() == TotalSlicesDXVAArrayByteSize);
|
||||
}
|
||||
|
||||
DXVA_PicParams_AV1
|
||||
d3d12_video_decoder_dxva_picparams_from_pipe_picparams_av1(
|
||||
uint32_t frameNum,
|
||||
pipe_video_profile profile,
|
||||
pipe_av1_picture_desc *pipe_av1)
|
||||
{
|
||||
DXVA_PicParams_AV1 dxvaStructure;
|
||||
memset(&dxvaStructure, 0, sizeof(dxvaStructure));
|
||||
|
||||
dxvaStructure.width = pipe_av1->picture_parameter.frame_width;
|
||||
dxvaStructure.height = pipe_av1->picture_parameter.frame_height;
|
||||
|
||||
dxvaStructure.max_width = pipe_av1->picture_parameter.max_width;
|
||||
dxvaStructure.max_height = pipe_av1->picture_parameter.max_height;
|
||||
|
||||
uint8_t bit_depths[] = { 8, 10, 12 };
|
||||
|
||||
// dxvaStructure.CurrPicTextureIndex = is set by d3d12_video_decoder_refresh_dpb_active_references_av1
|
||||
dxvaStructure.superres_denom = pipe_av1->picture_parameter.superres_scale_denominator;
|
||||
dxvaStructure.bitdepth = bit_depths[pipe_av1->picture_parameter.bit_depth_idx];
|
||||
dxvaStructure.seq_profile = pipe_av1->picture_parameter.profile;
|
||||
|
||||
/* Tiling info */
|
||||
dxvaStructure.tiles.cols = pipe_av1->picture_parameter.tile_cols;
|
||||
dxvaStructure.tiles.rows = pipe_av1->picture_parameter.tile_rows;
|
||||
dxvaStructure.tiles.context_update_id = pipe_av1->picture_parameter.context_update_tile_id;
|
||||
|
||||
for (uint32_t i = 0; i < dxvaStructure.tiles.cols; i++)
|
||||
dxvaStructure.tiles.widths[i] = pipe_av1->picture_parameter.width_in_sbs[i];
|
||||
|
||||
for (uint32_t i = 0; i < dxvaStructure.tiles.rows; i++)
|
||||
dxvaStructure.tiles.heights[i] = pipe_av1->picture_parameter.height_in_sbs[i];
|
||||
|
||||
// Fix the last tile rounding when uniform_tile_spacing_flag
|
||||
if (pipe_av1->picture_parameter.pic_info_fields.uniform_tile_spacing_flag) {
|
||||
uint32_t sbPixSize = pipe_av1->picture_parameter.seq_info_fields.use_128x128_superblock ? 128 : 64;
|
||||
if (dxvaStructure.tiles.cols > 1) {
|
||||
uint32_t acumSbWMinusLast = 0;
|
||||
for (uint32_t i = 0; i < dxvaStructure.tiles.cols - 1u; i++)
|
||||
acumSbWMinusLast += dxvaStructure.tiles.widths[i];
|
||||
|
||||
dxvaStructure.tiles.widths[dxvaStructure.tiles.cols-1] =
|
||||
std::ceil(pipe_av1->picture_parameter.frame_width / (float)sbPixSize) - acumSbWMinusLast;
|
||||
}
|
||||
|
||||
if (dxvaStructure.tiles.rows > 1) {
|
||||
uint32_t acumSbHMinusLast = 0;
|
||||
for (uint32_t i = 0; i < dxvaStructure.tiles.rows - 1u; i++)
|
||||
acumSbHMinusLast += dxvaStructure.tiles.heights[i];
|
||||
|
||||
dxvaStructure.tiles.heights[dxvaStructure.tiles.rows-1] =
|
||||
std::ceil(pipe_av1->picture_parameter.frame_width / (float)sbPixSize) - acumSbHMinusLast;
|
||||
}
|
||||
}
|
||||
|
||||
/* Coding tools */
|
||||
dxvaStructure.coding.use_128x128_superblock = pipe_av1->picture_parameter.seq_info_fields.use_128x128_superblock;
|
||||
dxvaStructure.coding.intra_edge_filter = pipe_av1->picture_parameter.seq_info_fields.enable_intra_edge_filter;
|
||||
dxvaStructure.coding.interintra_compound = pipe_av1->picture_parameter.seq_info_fields.enable_interintra_compound;
|
||||
dxvaStructure.coding.masked_compound = pipe_av1->picture_parameter.seq_info_fields.enable_masked_compound;
|
||||
dxvaStructure.coding.warped_motion = pipe_av1->picture_parameter.pic_info_fields.allow_warped_motion;
|
||||
dxvaStructure.coding.dual_filter = pipe_av1->picture_parameter.seq_info_fields.enable_dual_filter;
|
||||
dxvaStructure.coding.jnt_comp = pipe_av1->picture_parameter.seq_info_fields.enable_jnt_comp;
|
||||
dxvaStructure.coding.screen_content_tools = pipe_av1->picture_parameter.pic_info_fields.allow_screen_content_tools;
|
||||
dxvaStructure.coding.integer_mv = pipe_av1->picture_parameter.pic_info_fields.force_integer_mv || !(pipe_av1->picture_parameter.pic_info_fields.frame_type & 1);
|
||||
dxvaStructure.coding.cdef = pipe_av1->picture_parameter.seq_info_fields.enable_cdef;
|
||||
dxvaStructure.coding.restoration = 1; // This indicates the feature MAY be enabled in the sequence
|
||||
dxvaStructure.coding.film_grain = pipe_av1->picture_parameter.seq_info_fields.film_grain_params_present;
|
||||
dxvaStructure.coding.intrabc = pipe_av1->picture_parameter.pic_info_fields.allow_intrabc;
|
||||
dxvaStructure.coding.high_precision_mv = pipe_av1->picture_parameter.pic_info_fields.allow_high_precision_mv;
|
||||
dxvaStructure.coding.switchable_motion_mode = pipe_av1->picture_parameter.pic_info_fields.is_motion_mode_switchable;
|
||||
dxvaStructure.coding.filter_intra = pipe_av1->picture_parameter.seq_info_fields.enable_filter_intra;
|
||||
dxvaStructure.coding.disable_frame_end_update_cdf = pipe_av1->picture_parameter.pic_info_fields.disable_frame_end_update_cdf;
|
||||
dxvaStructure.coding.disable_cdf_update = pipe_av1->picture_parameter.pic_info_fields.disable_cdf_update;
|
||||
dxvaStructure.coding.reference_mode = pipe_av1->picture_parameter.mode_control_fields.reference_select;
|
||||
dxvaStructure.coding.skip_mode = pipe_av1->picture_parameter.mode_control_fields.skip_mode_present;
|
||||
dxvaStructure.coding.reduced_tx_set = pipe_av1->picture_parameter.mode_control_fields.reduced_tx_set_used;
|
||||
dxvaStructure.coding.superres = pipe_av1->picture_parameter.pic_info_fields.use_superres;
|
||||
dxvaStructure.coding.tx_mode = pipe_av1->picture_parameter.mode_control_fields.tx_mode;
|
||||
dxvaStructure.coding.use_ref_frame_mvs = pipe_av1->picture_parameter.pic_info_fields.use_ref_frame_mvs;
|
||||
dxvaStructure.coding.enable_ref_frame_mvs = pipe_av1->picture_parameter.seq_info_fields.ref_frame_mvs;
|
||||
dxvaStructure.coding.reference_frame_update = 1;
|
||||
|
||||
/* Format & Picture Info flags */
|
||||
dxvaStructure.format.frame_type = pipe_av1->picture_parameter.pic_info_fields.frame_type;
|
||||
dxvaStructure.format.show_frame = pipe_av1->picture_parameter.pic_info_fields.show_frame;
|
||||
dxvaStructure.format.showable_frame = pipe_av1->picture_parameter.pic_info_fields.showable_frame;
|
||||
dxvaStructure.format.subsampling_x = 1; // D3D12 Only Supports 4:2:0 (ie. Profile0)
|
||||
dxvaStructure.format.subsampling_y = 1; // D3D12 Only Supports 4:2:0 (ie. Profile0)
|
||||
dxvaStructure.format.mono_chrome = pipe_av1->picture_parameter.seq_info_fields.mono_chrome;
|
||||
|
||||
/* References */
|
||||
dxvaStructure.primary_ref_frame = pipe_av1->picture_parameter.primary_ref_frame;
|
||||
dxvaStructure.order_hint = pipe_av1->picture_parameter.order_hint;
|
||||
dxvaStructure.order_hint_bits = pipe_av1->picture_parameter.seq_info_fields.enable_order_hint ? pipe_av1->picture_parameter.order_hint_bits_minus_1 + 1 : 0;
|
||||
|
||||
// d3d12_video_decoder_refresh_dpb_active_references_av1 will assign the correct Index for
|
||||
// RefFrameMapTextureIndex entries where pipe_av1->ref[i] has a surface
|
||||
memset(dxvaStructure.RefFrameMapTextureIndex, DXVA_AV1_INVALID_PICTURE_INDEX, sizeof(dxvaStructure.RefFrameMapTextureIndex));
|
||||
memset(&dxvaStructure.frame_refs[0], 0, sizeof(dxvaStructure.frame_refs));
|
||||
for (uint32_t i = 0; i < _countof(dxvaStructure.frame_refs); i++) {
|
||||
debug_printf("libva ref[%d] = %p\n", i, pipe_av1->ref[i]);
|
||||
debug_printf("libva ref_frame_idx[%d] = %d\n", i, pipe_av1->picture_parameter.ref_frame_idx[i]);
|
||||
|
||||
uint8_t ref_idx = pipe_av1->picture_parameter.ref_frame_idx[i];
|
||||
struct pipe_video_buffer *ref_frame = (ref_idx <= _countof(pipe_av1->ref)) ? pipe_av1->ref[ref_idx] : NULL;
|
||||
if(ref_frame) {
|
||||
dxvaStructure.frame_refs[i].width = ref_frame->width;
|
||||
dxvaStructure.frame_refs[i].height = ref_frame->height;
|
||||
dxvaStructure.frame_refs[i].Index = ref_idx;
|
||||
|
||||
/* Global Motion */
|
||||
dxvaStructure.frame_refs[i].wminvalid = pipe_av1->picture_parameter.wm[i].invalid;
|
||||
dxvaStructure.frame_refs[i].wmtype = pipe_av1->picture_parameter.wm[i].wmtype;
|
||||
for (uint32_t j = 0; j < 6; ++j) {
|
||||
dxvaStructure.frame_refs[i].wmmat[j] = pipe_av1->picture_parameter.wm[i].wmmat[j];
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
dxvaStructure.frame_refs[i].Index = DXVA_AV1_INVALID_PICTURE_INDEX;
|
||||
}
|
||||
}
|
||||
|
||||
/* Loop filter parameters */
|
||||
dxvaStructure.loop_filter.filter_level[0] = pipe_av1->picture_parameter.filter_level[0];
|
||||
dxvaStructure.loop_filter.filter_level[1] = pipe_av1->picture_parameter.filter_level[1];
|
||||
dxvaStructure.loop_filter.filter_level_u = pipe_av1->picture_parameter.filter_level_u;
|
||||
dxvaStructure.loop_filter.filter_level_v = pipe_av1->picture_parameter.filter_level_v;
|
||||
dxvaStructure.loop_filter.sharpness_level = pipe_av1->picture_parameter.loop_filter_info_fields.sharpness_level;
|
||||
dxvaStructure.loop_filter.mode_ref_delta_enabled = pipe_av1->picture_parameter.loop_filter_info_fields.mode_ref_delta_enabled;
|
||||
dxvaStructure.loop_filter.mode_ref_delta_update = pipe_av1->picture_parameter.loop_filter_info_fields.mode_ref_delta_update;
|
||||
dxvaStructure.loop_filter.delta_lf_multi = pipe_av1->picture_parameter.mode_control_fields.delta_lf_multi;
|
||||
dxvaStructure.loop_filter.delta_lf_present = pipe_av1->picture_parameter.mode_control_fields.delta_lf_present_flag;
|
||||
if (dxvaStructure.loop_filter.delta_lf_present)
|
||||
dxvaStructure.loop_filter.delta_lf_res = pipe_av1->picture_parameter.mode_control_fields.log2_delta_lf_res; /* no need to convert log2 here */
|
||||
|
||||
for (uint32_t i = 0; i < 8; i++) {
|
||||
dxvaStructure.loop_filter.ref_deltas[i] = pipe_av1->picture_parameter.ref_deltas[i];
|
||||
}
|
||||
|
||||
dxvaStructure.loop_filter.mode_deltas[0] = pipe_av1->picture_parameter.mode_deltas[0];
|
||||
dxvaStructure.loop_filter.mode_deltas[1] = pipe_av1->picture_parameter.mode_deltas[1];
|
||||
|
||||
/* VAAPI already receives *frame_restoration_type after the remap_lr_type conversion */
|
||||
dxvaStructure.loop_filter.frame_restoration_type[0] = pipe_av1->picture_parameter.loop_restoration_fields.yframe_restoration_type;
|
||||
dxvaStructure.loop_filter.frame_restoration_type[1] = pipe_av1->picture_parameter.loop_restoration_fields.cbframe_restoration_type;
|
||||
dxvaStructure.loop_filter.frame_restoration_type[2] = pipe_av1->picture_parameter.loop_restoration_fields.crframe_restoration_type;
|
||||
|
||||
bool lr_enabled = dxvaStructure.loop_filter.frame_restoration_type[0] || dxvaStructure.loop_filter.frame_restoration_type[1] || dxvaStructure.loop_filter.frame_restoration_type[2];
|
||||
dxvaStructure.loop_filter.log2_restoration_unit_size[0] = lr_enabled ? (6 + pipe_av1->picture_parameter.loop_restoration_fields.lr_unit_shift) : 8;
|
||||
dxvaStructure.loop_filter.log2_restoration_unit_size[1] = lr_enabled ? (6 + pipe_av1->picture_parameter.loop_restoration_fields.lr_unit_shift - pipe_av1->picture_parameter.loop_restoration_fields.lr_uv_shift) : 8;
|
||||
dxvaStructure.loop_filter.log2_restoration_unit_size[2] = lr_enabled ? (6 + pipe_av1->picture_parameter.loop_restoration_fields.lr_unit_shift - pipe_av1->picture_parameter.loop_restoration_fields.lr_uv_shift) : 8;
|
||||
|
||||
/* Quantization */
|
||||
dxvaStructure.quantization.delta_q_present = pipe_av1->picture_parameter.mode_control_fields.delta_q_present_flag;
|
||||
if(dxvaStructure.quantization.delta_q_present)
|
||||
dxvaStructure.quantization.delta_q_res = pipe_av1->picture_parameter.mode_control_fields.log2_delta_q_res; /* no need to convert log2 here */
|
||||
dxvaStructure.quantization.base_qindex = pipe_av1->picture_parameter.base_qindex;
|
||||
dxvaStructure.quantization.y_dc_delta_q = pipe_av1->picture_parameter.y_dc_delta_q;
|
||||
dxvaStructure.quantization.u_dc_delta_q = pipe_av1->picture_parameter.u_dc_delta_q;
|
||||
dxvaStructure.quantization.v_dc_delta_q = pipe_av1->picture_parameter.v_dc_delta_q;
|
||||
dxvaStructure.quantization.u_ac_delta_q = pipe_av1->picture_parameter.u_ac_delta_q;
|
||||
dxvaStructure.quantization.v_ac_delta_q = pipe_av1->picture_parameter.v_ac_delta_q;
|
||||
|
||||
if(pipe_av1->picture_parameter.qmatrix_fields.using_qmatrix)
|
||||
{
|
||||
dxvaStructure.quantization.qm_y = pipe_av1->picture_parameter.qmatrix_fields.qm_y;
|
||||
dxvaStructure.quantization.qm_u = pipe_av1->picture_parameter.qmatrix_fields.qm_u;
|
||||
dxvaStructure.quantization.qm_v = pipe_av1->picture_parameter.qmatrix_fields.qm_v;
|
||||
} else {
|
||||
dxvaStructure.quantization.qm_y = 0xFF;
|
||||
dxvaStructure.quantization.qm_u = 0xFF;
|
||||
dxvaStructure.quantization.qm_v = 0xFF;
|
||||
}
|
||||
|
||||
/* Cdef parameters */
|
||||
dxvaStructure.cdef.damping = pipe_av1->picture_parameter.cdef_damping_minus_3;
|
||||
dxvaStructure.cdef.bits = pipe_av1->picture_parameter.cdef_bits;
|
||||
for (uint32_t i = 0; i < 8; i++) {
|
||||
dxvaStructure.cdef.y_strengths[i].primary = (pipe_av1->picture_parameter.cdef_y_strengths[i] >> 2);
|
||||
dxvaStructure.cdef.y_strengths[i].secondary = (pipe_av1->picture_parameter.cdef_y_strengths[i] & 0x03);
|
||||
dxvaStructure.cdef.uv_strengths[i].primary = (pipe_av1->picture_parameter.cdef_uv_strengths[i] >> 2);
|
||||
dxvaStructure.cdef.uv_strengths[i].secondary = (pipe_av1->picture_parameter.cdef_uv_strengths[i] & 0x03);
|
||||
}
|
||||
|
||||
/* Misc flags */
|
||||
dxvaStructure.interp_filter = pipe_av1->picture_parameter.interp_filter;
|
||||
|
||||
/* Segmentation */
|
||||
dxvaStructure.segmentation.enabled = pipe_av1->picture_parameter.seg_info.segment_info_fields.enabled;
|
||||
dxvaStructure.segmentation.update_map = pipe_av1->picture_parameter.seg_info.segment_info_fields.update_map;
|
||||
dxvaStructure.segmentation.update_data = pipe_av1->picture_parameter.seg_info.segment_info_fields.update_data;
|
||||
dxvaStructure.segmentation.temporal_update = pipe_av1->picture_parameter.seg_info.segment_info_fields.temporal_update;
|
||||
for (uint32_t i = 0; i < 8; i++) {
|
||||
dxvaStructure.segmentation.feature_mask[i].mask |= pipe_av1->picture_parameter.seg_info.feature_mask[i];
|
||||
for (uint32_t j = 0; j < 8; j++) {
|
||||
dxvaStructure.segmentation.feature_data[i][j] = pipe_av1->picture_parameter.seg_info.feature_data[i][j];
|
||||
}
|
||||
}
|
||||
|
||||
/* Film grain */
|
||||
if (pipe_av1->picture_parameter.film_grain_info.film_grain_info_fields.apply_grain) {
|
||||
dxvaStructure.film_grain.apply_grain = 1;
|
||||
dxvaStructure.film_grain.scaling_shift_minus8 = pipe_av1->picture_parameter.film_grain_info.film_grain_info_fields.grain_scaling_minus_8;
|
||||
dxvaStructure.film_grain.chroma_scaling_from_luma = pipe_av1->picture_parameter.film_grain_info.film_grain_info_fields.chroma_scaling_from_luma;
|
||||
dxvaStructure.film_grain.ar_coeff_lag = pipe_av1->picture_parameter.film_grain_info.film_grain_info_fields.ar_coeff_lag;
|
||||
dxvaStructure.film_grain.ar_coeff_shift_minus6 = pipe_av1->picture_parameter.film_grain_info.film_grain_info_fields.ar_coeff_shift_minus_6;
|
||||
dxvaStructure.film_grain.grain_scale_shift = pipe_av1->picture_parameter.film_grain_info.film_grain_info_fields.grain_scale_shift;
|
||||
dxvaStructure.film_grain.overlap_flag = pipe_av1->picture_parameter.film_grain_info.film_grain_info_fields.overlap_flag;
|
||||
dxvaStructure.film_grain.clip_to_restricted_range = pipe_av1->picture_parameter.film_grain_info.film_grain_info_fields.clip_to_restricted_range;
|
||||
|
||||
/* order of coefficients is actually GBR, also IEC 61966-2-1 (sRGB) */
|
||||
constexpr uint8_t AVCOL_SPC_RGB = 0;
|
||||
dxvaStructure.film_grain.matrix_coeff_is_identity = (pipe_av1->picture_parameter.matrix_coefficients == AVCOL_SPC_RGB);
|
||||
|
||||
dxvaStructure.film_grain.grain_seed = pipe_av1->picture_parameter.film_grain_info.grain_seed;
|
||||
dxvaStructure.film_grain.num_y_points = pipe_av1->picture_parameter.film_grain_info.num_y_points;
|
||||
for (uint32_t i = 0; i < pipe_av1->picture_parameter.film_grain_info.num_y_points; i++) {
|
||||
dxvaStructure.film_grain.scaling_points_y[i][0] = pipe_av1->picture_parameter.film_grain_info.point_y_value[i];
|
||||
dxvaStructure.film_grain.scaling_points_y[i][1] = pipe_av1->picture_parameter.film_grain_info.point_y_scaling[i];
|
||||
}
|
||||
dxvaStructure.film_grain.num_cb_points = pipe_av1->picture_parameter.film_grain_info.num_cb_points;
|
||||
for (uint32_t i = 0; i < pipe_av1->picture_parameter.film_grain_info.num_cb_points; i++) {
|
||||
dxvaStructure.film_grain.scaling_points_cb[i][0] = pipe_av1->picture_parameter.film_grain_info.point_cb_value[i];
|
||||
dxvaStructure.film_grain.scaling_points_cb[i][1] = pipe_av1->picture_parameter.film_grain_info.point_cb_scaling[i];
|
||||
}
|
||||
dxvaStructure.film_grain.num_cr_points = pipe_av1->picture_parameter.film_grain_info.num_cr_points;
|
||||
for (uint32_t i = 0; i < pipe_av1->picture_parameter.film_grain_info.num_cr_points; i++) {
|
||||
dxvaStructure.film_grain.scaling_points_cr[i][0] = pipe_av1->picture_parameter.film_grain_info.point_cr_value[i];
|
||||
dxvaStructure.film_grain.scaling_points_cr[i][1] = pipe_av1->picture_parameter.film_grain_info.point_cr_scaling[i];
|
||||
}
|
||||
for (uint32_t i = 0; i < 24; i++) {
|
||||
dxvaStructure.film_grain.ar_coeffs_y[i] = pipe_av1->picture_parameter.film_grain_info.ar_coeffs_y[i];
|
||||
}
|
||||
for (uint32_t i = 0; i < 25; i++) {
|
||||
dxvaStructure.film_grain.ar_coeffs_cb[i] = pipe_av1->picture_parameter.film_grain_info.ar_coeffs_cb[i];
|
||||
dxvaStructure.film_grain.ar_coeffs_cr[i] = pipe_av1->picture_parameter.film_grain_info.ar_coeffs_cr[i];
|
||||
}
|
||||
dxvaStructure.film_grain.cb_mult = pipe_av1->picture_parameter.film_grain_info.cb_mult;
|
||||
dxvaStructure.film_grain.cb_luma_mult = pipe_av1->picture_parameter.film_grain_info.cb_luma_mult;
|
||||
dxvaStructure.film_grain.cr_mult = pipe_av1->picture_parameter.film_grain_info.cr_mult;
|
||||
dxvaStructure.film_grain.cr_luma_mult = pipe_av1->picture_parameter.film_grain_info.cr_luma_mult;
|
||||
dxvaStructure.film_grain.cb_offset = pipe_av1->picture_parameter.film_grain_info.cb_offset;
|
||||
dxvaStructure.film_grain.cr_offset = pipe_av1->picture_parameter.film_grain_info.cr_offset;
|
||||
dxvaStructure.film_grain.cr_offset = pipe_av1->picture_parameter.film_grain_info.cr_offset;
|
||||
}
|
||||
|
||||
dxvaStructure.StatusReportFeedbackNumber = frameNum;
|
||||
assert(dxvaStructure.StatusReportFeedbackNumber > 0);
|
||||
return dxvaStructure;
|
||||
}
|
||||
353
src/gallium/drivers/d3d12/d3d12_video_dec_av1.h
Normal file
353
src/gallium/drivers/d3d12/d3d12_video_dec_av1.h
Normal file
|
|
@ -0,0 +1,353 @@
|
|||
|
||||
/*
|
||||
* Copyright © Microsoft Corporation
|
||||
*
|
||||
* Permission is hereby granted, free of uint8_tge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
||||
* IN THE SOFTWARE.
|
||||
*/
|
||||
|
||||
#ifndef D3D12_VIDEO_DEC_AV1_H
|
||||
#define D3D12_VIDEO_DEC_AV1_H
|
||||
|
||||
#include "d3d12_video_types.h"
|
||||
|
||||
// From DXVA AV1 spec
|
||||
// Entries that will not be used for decoding the current picture,
|
||||
// or any subsequent pictures, are indicated by setting this value to 0xFF.
|
||||
// Also, When DXVA_PicEntry_AV1. Index does not contain an index to a valid
|
||||
// reference, the value shall be set to 255, to indicate that the index is invalid.
|
||||
constexpr uint16_t DXVA_AV1_INVALID_PICTURE_INDEX = 0xFF;
|
||||
|
||||
// Frame Restoration types (section 6.10.15)
|
||||
enum {
|
||||
AV1_RESTORE_NONE = 0,
|
||||
AV1_RESTORE_WIENER = 1,
|
||||
AV1_RESTORE_SGRPROJ = 2,
|
||||
AV1_RESTORE_SWITCHABLE = 3,
|
||||
};
|
||||
|
||||
#pragma pack(push, BeforeDXVApacking, 1)
|
||||
|
||||
#ifndef _DIRECTX_AV1_VA_
|
||||
#define _DIRECTX_AV1_VA_
|
||||
|
||||
/* AV1 picture entry data structure */
|
||||
typedef struct _DXVA_PicEntry_AV1 {
|
||||
|
||||
uint32_t width;
|
||||
uint32_t height;
|
||||
|
||||
// Global motion parameters
|
||||
int32_t wmmat[6];
|
||||
union {
|
||||
struct {
|
||||
uint8_t wminvalid : 1;
|
||||
uint8_t wmtype : 2;
|
||||
uint8_t Reserved : 5;
|
||||
};
|
||||
uint8_t GlobalMotionFlags;
|
||||
};
|
||||
|
||||
uint8_t Index;
|
||||
uint16_t Reserved16Bits;
|
||||
|
||||
} DXVA_PicEntry_AV1, *LPDXVA_PicEntry_AV1;
|
||||
|
||||
/* AV1 picture parameters structure */
|
||||
typedef struct _DXVA_PicParams_AV1 {
|
||||
uint32_t width;
|
||||
uint32_t height;
|
||||
|
||||
uint32_t max_width;
|
||||
uint32_t max_height;
|
||||
|
||||
uint8_t CurrPicTextureIndex;
|
||||
uint8_t superres_denom;
|
||||
uint8_t bitdepth;
|
||||
uint8_t seq_profile;
|
||||
|
||||
// Tiles:
|
||||
struct {
|
||||
uint8_t cols;
|
||||
uint8_t rows;
|
||||
uint16_t context_update_id;
|
||||
uint16_t widths[64];
|
||||
uint16_t heights[64];
|
||||
} tiles;
|
||||
|
||||
// Coding Tools
|
||||
union {
|
||||
struct {
|
||||
uint32_t use_128x128_superblock : 1;
|
||||
uint32_t intra_edge_filter : 1;
|
||||
uint32_t interintra_compound : 1;
|
||||
uint32_t masked_compound : 1;
|
||||
uint32_t warped_motion : 1;
|
||||
uint32_t dual_filter : 1;
|
||||
uint32_t jnt_comp : 1;
|
||||
uint32_t screen_content_tools : 1;
|
||||
uint32_t integer_mv : 1;
|
||||
uint32_t cdef : 1;
|
||||
uint32_t restoration : 1;
|
||||
uint32_t film_grain : 1;
|
||||
uint32_t intrabc : 1;
|
||||
uint32_t high_precision_mv : 1;
|
||||
uint32_t switchable_motion_mode : 1;
|
||||
uint32_t filter_intra : 1;
|
||||
uint32_t disable_frame_end_update_cdf : 1;
|
||||
uint32_t disable_cdf_update : 1;
|
||||
uint32_t reference_mode : 1;
|
||||
uint32_t skip_mode : 1;
|
||||
uint32_t reduced_tx_set : 1;
|
||||
uint32_t superres : 1;
|
||||
uint32_t tx_mode : 2;
|
||||
uint32_t use_ref_frame_mvs : 1;
|
||||
uint32_t enable_ref_frame_mvs : 1;
|
||||
uint32_t reference_frame_update : 1;
|
||||
uint32_t Reserved : 5;
|
||||
};
|
||||
uint32_t CodingParamToolFlags;
|
||||
} coding;
|
||||
|
||||
// Format & Picture Info flags
|
||||
union {
|
||||
struct {
|
||||
uint8_t frame_type : 2;
|
||||
uint8_t show_frame : 1;
|
||||
uint8_t showable_frame : 1;
|
||||
uint8_t subsampling_x : 1;
|
||||
uint8_t subsampling_y : 1;
|
||||
uint8_t mono_chrome : 1;
|
||||
uint8_t Reserved : 1;
|
||||
};
|
||||
uint8_t FormatAndPictureInfoFlags;
|
||||
} format;
|
||||
|
||||
// References
|
||||
uint8_t primary_ref_frame;
|
||||
uint8_t order_hint;
|
||||
uint8_t order_hint_bits;
|
||||
|
||||
DXVA_PicEntry_AV1 frame_refs[7];
|
||||
uint8_t RefFrameMapTextureIndex[8];
|
||||
|
||||
// Loop filter parameters
|
||||
struct {
|
||||
uint8_t filter_level[2];
|
||||
uint8_t filter_level_u;
|
||||
uint8_t filter_level_v;
|
||||
|
||||
uint8_t sharpness_level;
|
||||
union {
|
||||
struct {
|
||||
uint8_t mode_ref_delta_enabled : 1;
|
||||
uint8_t mode_ref_delta_update : 1;
|
||||
uint8_t delta_lf_multi : 1;
|
||||
uint8_t delta_lf_present : 1;
|
||||
uint8_t Reserved : 4;
|
||||
};
|
||||
uint8_t ControlFlags;
|
||||
};
|
||||
char ref_deltas[8];
|
||||
char mode_deltas[2];
|
||||
uint8_t delta_lf_res;
|
||||
uint8_t frame_restoration_type[3];
|
||||
uint16_t log2_restoration_unit_size[3];
|
||||
uint16_t Reserved16Bits;
|
||||
} loop_filter;
|
||||
|
||||
// Quantization
|
||||
struct {
|
||||
union {
|
||||
struct {
|
||||
uint8_t delta_q_present : 1;
|
||||
uint8_t delta_q_res : 2;
|
||||
uint8_t Reserved : 5;
|
||||
};
|
||||
uint8_t ControlFlags;
|
||||
};
|
||||
|
||||
uint8_t base_qindex;
|
||||
char y_dc_delta_q;
|
||||
char u_dc_delta_q;
|
||||
char v_dc_delta_q;
|
||||
char u_ac_delta_q;
|
||||
char v_ac_delta_q;
|
||||
// using_qmatrix:
|
||||
uint8_t qm_y;
|
||||
uint8_t qm_u;
|
||||
uint8_t qm_v;
|
||||
uint16_t Reserved16Bits;
|
||||
} quantization;
|
||||
|
||||
// Cdef parameters
|
||||
struct {
|
||||
union {
|
||||
struct {
|
||||
uint8_t damping : 2;
|
||||
uint8_t bits : 2;
|
||||
uint8_t Reserved : 4;
|
||||
};
|
||||
uint8_t ControlFlags;
|
||||
};
|
||||
|
||||
union {
|
||||
struct {
|
||||
uint8_t primary : 6;
|
||||
uint8_t secondary : 2;
|
||||
};
|
||||
uint8_t combined;
|
||||
} y_strengths[8];
|
||||
|
||||
union {
|
||||
struct {
|
||||
uint8_t primary : 6;
|
||||
uint8_t secondary : 2;
|
||||
};
|
||||
uint8_t combined;
|
||||
} uv_strengths[8];
|
||||
|
||||
} cdef;
|
||||
|
||||
uint8_t interp_filter;
|
||||
|
||||
// Segmentation
|
||||
struct {
|
||||
union {
|
||||
struct {
|
||||
uint8_t enabled : 1;
|
||||
uint8_t update_map : 1;
|
||||
uint8_t update_data : 1;
|
||||
uint8_t temporal_update : 1;
|
||||
uint8_t Reserved : 4;
|
||||
};
|
||||
uint8_t ControlFlags;
|
||||
};
|
||||
uint8_t Reserved24Bits[3];
|
||||
|
||||
union {
|
||||
struct {
|
||||
uint8_t alt_q : 1;
|
||||
uint8_t alt_lf_y_v : 1;
|
||||
uint8_t alt_lf_y_h : 1;
|
||||
uint8_t alt_lf_u : 1;
|
||||
uint8_t alt_lf_v : 1;
|
||||
uint8_t ref_frame : 1;
|
||||
uint8_t skip : 1;
|
||||
uint8_t globalmv : 1;
|
||||
};
|
||||
uint8_t mask;
|
||||
} feature_mask[8];
|
||||
|
||||
int16_t feature_data[8][8];
|
||||
|
||||
} segmentation;
|
||||
|
||||
struct {
|
||||
union {
|
||||
struct {
|
||||
uint16_t apply_grain : 1;
|
||||
uint16_t scaling_shift_minus8 : 2;
|
||||
uint16_t chroma_scaling_from_luma : 1;
|
||||
uint16_t ar_coeff_lag : 2;
|
||||
uint16_t ar_coeff_shift_minus6 : 2;
|
||||
uint16_t grain_scale_shift : 2;
|
||||
uint16_t overlap_flag : 1;
|
||||
uint16_t clip_to_restricted_range : 1;
|
||||
uint16_t matrix_coeff_is_identity : 1;
|
||||
uint16_t Reserved : 3;
|
||||
};
|
||||
uint16_t ControlFlags;
|
||||
};
|
||||
|
||||
uint16_t grain_seed;
|
||||
uint8_t scaling_points_y[14][2];
|
||||
uint8_t num_y_points;
|
||||
uint8_t scaling_points_cb[10][2];
|
||||
uint8_t num_cb_points;
|
||||
uint8_t scaling_points_cr[10][2];
|
||||
uint8_t num_cr_points;
|
||||
uint8_t ar_coeffs_y[24];
|
||||
uint8_t ar_coeffs_cb[25];
|
||||
uint8_t ar_coeffs_cr[25];
|
||||
uint8_t cb_mult;
|
||||
uint8_t cb_luma_mult;
|
||||
uint8_t cr_mult;
|
||||
uint8_t cr_luma_mult;
|
||||
uint8_t Reserved8Bits;
|
||||
int16_t cb_offset;
|
||||
int16_t cr_offset;
|
||||
} film_grain;
|
||||
|
||||
uint32_t Reserved32Bits;
|
||||
uint32_t StatusReportFeedbackNumber;
|
||||
} DXVA_PicParams_AV1, *LPDXVA_PicParams_AV1;
|
||||
|
||||
/* AV1 tile structure */
|
||||
typedef struct _DXVA_Tile_AV1 {
|
||||
uint32_t DataOffset;
|
||||
uint32_t DataSize;
|
||||
uint16_t row;
|
||||
uint16_t column;
|
||||
uint16_t Reserved16Bits;
|
||||
uint8_t anchor_frame;
|
||||
uint8_t Reserved8Bits;
|
||||
} DXVA_Tile_AV1, *LPDXVA_Tile_AV1;
|
||||
|
||||
/* AV1 status reporting data structure */
|
||||
typedef struct _DXVA_Status_AV1 {
|
||||
uint32_t StatusReportFeedbackNumber;
|
||||
DXVA_PicEntry_AV1 CurrPic;
|
||||
uint8_t BufType;
|
||||
uint8_t Status;
|
||||
uint8_t Reserved8Bits;
|
||||
uint16_t NumMbsAffected;
|
||||
} DXVA_Status_AV1, *LPDXVA_Status_AV1;
|
||||
|
||||
#endif // _DIRECTX_AV1_VA_
|
||||
|
||||
#pragma pack(pop, BeforeDXVApacking)
|
||||
|
||||
void
|
||||
d3d12_video_decoder_prepare_current_frame_references_av1(struct d3d12_video_decoder *pD3D12Dec,
|
||||
ID3D12Resource *pTexture2D,
|
||||
uint32_t subresourceIndex);
|
||||
|
||||
void
|
||||
d3d12_video_decoder_refresh_dpb_active_references_av1(struct d3d12_video_decoder *pD3D12Dec);
|
||||
|
||||
void
|
||||
d3d12_video_decoder_get_frame_info_av1(
|
||||
struct d3d12_video_decoder *pD3D12Dec, uint32_t *pWidth, uint32_t *pHeight, uint16_t *pMaxDPB, bool &isInterlaced);
|
||||
|
||||
DXVA_PicParams_AV1
|
||||
d3d12_video_decoder_dxva_picparams_from_pipe_picparams_av1(
|
||||
uint32_t frameNum,
|
||||
pipe_video_profile profile,
|
||||
pipe_av1_picture_desc *pPipeDesc);
|
||||
|
||||
void
|
||||
d3d12_video_decoder_log_pic_params_av1(DXVA_PicParams_AV1 *pPicParams);
|
||||
|
||||
void
|
||||
d3d12_video_decoder_prepare_dxva_slices_control_av1(struct d3d12_video_decoder *pD3D12Dec,
|
||||
std::vector<uint8_t> &vecOutSliceControlBuffers,
|
||||
struct pipe_av1_picture_desc *picture_av1);
|
||||
|
||||
#endif
|
||||
|
|
@ -24,6 +24,7 @@
|
|||
#include "d3d12_video_dec_references_mgr.h"
|
||||
#include "d3d12_video_dec_h264.h"
|
||||
#include "d3d12_video_dec_hevc.h"
|
||||
#include "d3d12_video_dec_av1.h"
|
||||
#include "d3d12_video_texture_array_dpb_manager.h"
|
||||
#include "d3d12_video_array_of_textures_dpb_manager.h"
|
||||
#include "d3d12_screen.h"
|
||||
|
|
@ -43,6 +44,8 @@ GetInvalidReferenceIndex(d3d12_video_decode_profile_type DecodeProfileType)
|
|||
return DXVA_H264_INVALID_PICTURE_INDEX;
|
||||
case d3d12_video_decode_profile_type_hevc:
|
||||
return DXVA_HEVC_INVALID_PICTURE_INDEX;
|
||||
case d3d12_video_decode_profile_type_av1:
|
||||
return DXVA_AV1_INVALID_PICTURE_INDEX;
|
||||
default:
|
||||
return 0;
|
||||
};
|
||||
|
|
|
|||
|
|
@ -56,6 +56,8 @@ struct d3d12_video_decoder_references_manager
|
|||
|
||||
template <typename T, size_t size>
|
||||
void mark_references_in_use(const T (&picEntries)[size]);
|
||||
template <typename T, size_t size>
|
||||
void mark_references_in_use_av1(const T (&picEntries)[size]);
|
||||
void mark_reference_in_use(uint16_t index);
|
||||
|
||||
uint16_t store_future_reference(uint16_t index,
|
||||
|
|
@ -68,6 +70,9 @@ struct d3d12_video_decoder_references_manager
|
|||
template <typename T, size_t size>
|
||||
void update_entries(T (&picEntries)[size], std::vector<D3D12_RESOURCE_BARRIER> &outNeededTransitions);
|
||||
|
||||
template <typename T, size_t size>
|
||||
void update_entries_av1(T (&picEntries)[size], std::vector<D3D12_RESOURCE_BARRIER> &outNeededTransitions);
|
||||
|
||||
void get_reference_only_output(
|
||||
struct pipe_video_buffer * pCurrentDecodeTarget,
|
||||
ID3D12Resource **ppOutputReference, // out -> new reference slot assigned or nullptr
|
||||
|
|
@ -217,4 +222,65 @@ d3d12_video_decoder_references_manager::mark_references_in_use(const T (&picEntr
|
|||
}
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------------------------------------------------------------
|
||||
template <typename T, size_t size>
|
||||
void
|
||||
d3d12_video_decoder_references_manager::update_entries_av1(T (&picEntries)[size],
|
||||
std::vector<D3D12_RESOURCE_BARRIER> &outNeededTransitions)
|
||||
{
|
||||
outNeededTransitions.clear();
|
||||
|
||||
for (auto &picEntry : picEntries) {
|
||||
// uint16_t update_entry(
|
||||
// uint16_t index, // in
|
||||
// ID3D12Resource*& pOutputReference, // out -> new reference slot assigned or nullptr
|
||||
// uint32_t& OutputSubresource, // out -> new reference slot assigned or 0
|
||||
// bool& outNeedsTransitionToDecodeRead // out -> indicates if output resource argument has to be transitioned
|
||||
// to D3D12_RESOURCE_STATE_VIDEO_DECODE_READ by the caller
|
||||
// );
|
||||
|
||||
ID3D12Resource *pOutputReference = {};
|
||||
uint32_t OutputSubresource = 0u;
|
||||
bool outNeedsTransitionToDecodeRead = false;
|
||||
|
||||
picEntry =
|
||||
update_entry(picEntry, pOutputReference, OutputSubresource, outNeedsTransitionToDecodeRead);
|
||||
|
||||
if (outNeedsTransitionToDecodeRead) {
|
||||
///
|
||||
/// The subresource indexing in D3D12 Video within the DPB doesn't take into account the Y, UV planes (ie.
|
||||
/// subresource 0, 1, 2, 3..., N are different full NV12 references in the DPB) but when using the subresources
|
||||
/// in other areas of D3D12 we need to convert it to the D3D12CalcSubresource format, explained in
|
||||
/// https://docs.microsoft.com/en-us/windows/win32/direct3d12/subresources
|
||||
///
|
||||
CD3DX12_RESOURCE_DESC refDesc(GetDesc(pOutputReference));
|
||||
uint32_t MipLevel, PlaneSlice, ArraySlice;
|
||||
D3D12DecomposeSubresource(OutputSubresource,
|
||||
refDesc.MipLevels,
|
||||
refDesc.ArraySize(),
|
||||
MipLevel,
|
||||
ArraySlice,
|
||||
PlaneSlice);
|
||||
|
||||
for (PlaneSlice = 0; PlaneSlice < m_formatInfo.PlaneCount; PlaneSlice++) {
|
||||
uint planeOutputSubresource = refDesc.CalcSubresource(MipLevel, ArraySlice, PlaneSlice);
|
||||
outNeededTransitions.push_back(CD3DX12_RESOURCE_BARRIER::Transition(pOutputReference,
|
||||
D3D12_RESOURCE_STATE_COMMON,
|
||||
D3D12_RESOURCE_STATE_VIDEO_DECODE_READ,
|
||||
planeOutputSubresource));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------------------------------------------------------------
|
||||
template <typename T, size_t size>
|
||||
void
|
||||
d3d12_video_decoder_references_manager::mark_references_in_use_av1(const T (&picEntries)[size])
|
||||
{
|
||||
for (auto &picEntry : picEntries) {
|
||||
mark_reference_in_use(picEntry);
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -153,6 +153,7 @@ d3d12_has_video_decode_support(struct pipe_screen *pscreen, enum pipe_video_prof
|
|||
case PIPE_VIDEO_PROFILE_MPEG4_AVC_HIGH10:
|
||||
case PIPE_VIDEO_PROFILE_HEVC_MAIN:
|
||||
case PIPE_VIDEO_PROFILE_HEVC_MAIN_10:
|
||||
case PIPE_VIDEO_PROFILE_AV1_MAIN:
|
||||
{
|
||||
supportsProfile = true;
|
||||
} break;
|
||||
|
|
|
|||
|
|
@ -109,6 +109,7 @@ enum d3d12_video_decode_profile_type
|
|||
d3d12_video_decode_profile_type_none,
|
||||
d3d12_video_decode_profile_type_h264,
|
||||
d3d12_video_decode_profile_type_hevc,
|
||||
d3d12_video_decode_profile_type_av1,
|
||||
d3d12_video_decode_profile_type_max_valid
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -68,6 +68,7 @@ if with_gallium_d3d12_video
|
|||
'd3d12_video_encoder_bitstream_builder_hevc.cpp',
|
||||
'd3d12_video_encoder_nalu_writer_hevc.cpp',
|
||||
'd3d12_video_encoder_references_manager_hevc.cpp',
|
||||
'd3d12_video_dec_av1.cpp',
|
||||
]
|
||||
endif
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue