X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=libavcodec%2Fdxva2_h264.c;h=ea51958c62252e5eb2233c10fe9c7c034d80b660;hb=24adf7832b8370f3c1febbef6c686f574d360d32;hp=8de4c51082b08a37462f9286f8eb540c8bf4c055;hpb=975a1447f76e8d30fc01e6ea5466c84faf3d76e4;p=ffmpeg diff --git a/libavcodec/dxva2_h264.c b/libavcodec/dxva2_h264.c index 8de4c51082b..ea51958c622 100644 --- a/libavcodec/dxva2_h264.c +++ b/libavcodec/dxva2_h264.c @@ -70,15 +70,15 @@ static void fill_picture_parameters(struct dxva_context *ctx, const H264Context ff_dxva2_get_surface_index(ctx, r), r->long_ref != 0); - if ((r->reference & PICT_TOP_FIELD) && r->field_poc[0] != INT_MAX) + if ((r->f.reference & PICT_TOP_FIELD) && r->field_poc[0] != INT_MAX) pp->FieldOrderCntList[i][0] = r->field_poc[0]; - if ((r->reference & PICT_BOTTOM_FIELD) && r->field_poc[1] != INT_MAX) + if ((r->f.reference & PICT_BOTTOM_FIELD) && r->field_poc[1] != INT_MAX) pp->FieldOrderCntList[i][1] = r->field_poc[1]; pp->FrameNumList[i] = r->long_ref ? r->pic_id : r->frame_num; - if (r->reference & PICT_TOP_FIELD) + if (r->f.reference & PICT_TOP_FIELD) pp->UsedForReferenceFlags |= 1 << (2*i + 0); - if (r->reference & PICT_BOTTOM_FIELD) + if (r->f.reference & PICT_BOTTOM_FIELD) pp->UsedForReferenceFlags |= 1 << (2*i + 1); } else { pp->RefFrameList[i].bPicEntry = 0xff; @@ -113,7 +113,10 @@ static void fill_picture_parameters(struct dxva_context *ctx, const H264Context pp->bit_depth_luma_minus8 = h->sps.bit_depth_luma - 8; pp->bit_depth_chroma_minus8 = h->sps.bit_depth_chroma - 8; - pp->Reserved16Bits = 3; /* FIXME is there a way to detect the right mode ? */ + if (ctx->workaround & FF_DXVA2_WORKAROUND_SCALING_LIST_ZIGZAG) + pp->Reserved16Bits = 0; + else + pp->Reserved16Bits = 3; /* FIXME is there a way to detect the right mode ? */ pp->StatusReportFeedbackNumber = 1 + ctx->report_id++; pp->CurrFieldOrderCnt[0] = 0; if ((s->picture_structure & PICT_TOP_FIELD) && @@ -150,17 +153,29 @@ static void fill_picture_parameters(struct dxva_context *ctx, const H264Context //pp->SliceGroupMap[810]; /* XXX not implemented by Libav */ } -static void fill_scaling_lists(const H264Context *h, DXVA_Qmatrix_H264 *qm) +static void fill_scaling_lists(struct dxva_context *ctx, const H264Context *h, DXVA_Qmatrix_H264 *qm) { unsigned i, j; memset(qm, 0, sizeof(*qm)); - for (i = 0; i < 6; i++) - for (j = 0; j < 16; j++) - qm->bScalingLists4x4[i][j] = h->pps.scaling_matrix4[i][zigzag_scan[j]]; + if (ctx->workaround & FF_DXVA2_WORKAROUND_SCALING_LIST_ZIGZAG) { + for (i = 0; i < 6; i++) + for (j = 0; j < 16; j++) + qm->bScalingLists4x4[i][j] = h->pps.scaling_matrix4[i][j]; + + for (i = 0; i < 64; i++) { + qm->bScalingLists8x8[0][i] = h->pps.scaling_matrix8[0][i]; + qm->bScalingLists8x8[1][i] = h->pps.scaling_matrix8[3][i]; + } + } else { + for (i = 0; i < 6; i++) + for (j = 0; j < 16; j++) + qm->bScalingLists4x4[i][j] = h->pps.scaling_matrix4[i][zigzag_scan[j]]; - for (i = 0; i < 2; i++) - for (j = 0; j < 64; j++) - qm->bScalingLists8x8[i][j] = h->pps.scaling_matrix8[i][ff_zigzag_direct[j]]; + for (i = 0; i < 64; i++) { + qm->bScalingLists8x8[0][i] = h->pps.scaling_matrix8[0][ff_zigzag_direct[i]]; + qm->bScalingLists8x8[1][i] = h->pps.scaling_matrix8[3][ff_zigzag_direct[i]]; + } + } } static int is_slice_short(struct dxva_context *ctx) @@ -216,7 +231,7 @@ static void fill_slice_long(AVCodecContext *avctx, DXVA_Slice_H264_Long *slice, unsigned plane; fill_picture_entry(&slice->RefPicList[list][i], ff_dxva2_get_surface_index(ctx, r), - r->reference == PICT_BOTTOM_FIELD); + r->f.reference == PICT_BOTTOM_FIELD); for (plane = 0; plane < 3; plane++) { int w, o; if (plane == 0 && h->luma_weight_flag[list]) { @@ -265,7 +280,7 @@ static int commit_bitstream_and_slice_buffer(AVCodecContext *avctx, const unsigned mb_count = s->mb_width * s->mb_height; struct dxva_context *ctx = avctx->hwaccel_context; const Picture *current_picture = h->s.current_picture_ptr; - struct dxva2_picture_context *ctx_pic = current_picture->hwaccel_picture_private; + struct dxva2_picture_context *ctx_pic = current_picture->f.hwaccel_picture_private; DXVA_Slice_H264_Short *slice = NULL; uint8_t *dxva_data, *current, *end; unsigned dxva_size; @@ -360,7 +375,7 @@ static int start_frame(AVCodecContext *avctx, { const H264Context *h = avctx->priv_data; struct dxva_context *ctx = avctx->hwaccel_context; - struct dxva2_picture_context *ctx_pic = h->s.current_picture_ptr->hwaccel_picture_private; + struct dxva2_picture_context *ctx_pic = h->s.current_picture_ptr->f.hwaccel_picture_private; if (!ctx->decoder || !ctx->cfg || ctx->surface_count <= 0) return -1; @@ -370,7 +385,7 @@ static int start_frame(AVCodecContext *avctx, fill_picture_parameters(ctx, h, &ctx_pic->pp); /* Fill up DXVA_Qmatrix_H264 */ - fill_scaling_lists(h, &ctx_pic->qm); + fill_scaling_lists(ctx, h, &ctx_pic->qm); ctx_pic->slice_count = 0; ctx_pic->bitstream_size = 0; @@ -384,7 +399,7 @@ static int decode_slice(AVCodecContext *avctx, const H264Context *h = avctx->priv_data; struct dxva_context *ctx = avctx->hwaccel_context; const Picture *current_picture = h->s.current_picture_ptr; - struct dxva2_picture_context *ctx_pic = current_picture->hwaccel_picture_private; + struct dxva2_picture_context *ctx_pic = current_picture->f.hwaccel_picture_private; unsigned position; if (ctx_pic->slice_count >= MAX_SLICES) @@ -413,7 +428,7 @@ static int end_frame(AVCodecContext *avctx) H264Context *h = avctx->priv_data; MpegEncContext *s = &h->s; struct dxva2_picture_context *ctx_pic = - h->s.current_picture_ptr->hwaccel_picture_private; + h->s.current_picture_ptr->f.hwaccel_picture_private; if (ctx_pic->slice_count <= 0 || ctx_pic->bitstream_size <= 0) return -1;