From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from ffbox0-bg.mplayerhq.hu (ffbox0-bg.ffmpeg.org [79.124.17.100]) by master.gitmailbox.com (Postfix) with ESMTPS id AEEDD4C4EB for ; Sun, 9 Mar 2025 15:50:25 +0000 (UTC) Received: from [127.0.1.1] (localhost [127.0.0.1]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTP id 9FED968E628; Sun, 9 Mar 2025 17:50:23 +0200 (EET) Received: from SY8PR01CU002.outbound.protection.outlook.com (mail-australiaeastazolkn19010004.outbound.protection.outlook.com [52.103.72.4]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTPS id 23EC268E60C for ; Sun, 9 Mar 2025 17:50:17 +0200 (EET) ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=l5fTaO7tZfT/37Y96Kxlr5LbhHdUsJEpF8IRplHeoHOgnJV/j5/7qeG8jftxrFdHxJHCFHYazZsLFK+jO8ka0VGBrYJBjU1EWKuNIhkmQoi5NfmQnd9N6QpCzp8NFZhkC4504um/iwJCKf4t16yoOwN6oWMFGsL2U1UfhWBt/1vJlhQrKP5N6wqRfnwEkcDFC9OLx13u3DlS7kPFww3ERORzZpSRZ5b/ohBbhKd8+2cBK0IWQz9WwKL9nJ7HkDQfUa0uXvaDzxmqWxiTamSLPT1s09TC+U0+y9hqQPB5NSVvhIjqRLemoXeaJ/OOvKxdm4lOCgV2WfdfFFhyN3Gw2w== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector10001; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-AntiSpam-MessageData-ChunkCount:X-MS-Exchange-AntiSpam-MessageData-0:X-MS-Exchange-AntiSpam-MessageData-1; bh=fBHoohyXSOIrWZtxieBwBlMxwZlgAeJR9Sw9OsRjK4Y=; b=e89jb9pwSZkLL+oXNiAsVsQUiS5mPiHsh7z7PKHv1kO/Iaj/aAk6z7VU3i24UIDhqTFi7VYTJsdIYCdq03oJ/Pw+fZI1hxqMhRCkV98YIceote1oMhYIUiZMBUfPUPnGVuiqzlLSzn4DN20M5tF/AhH5qM9ntrm5QAK7FGZGb7slIEuI8QGRvBYM0FY+3B28aLpdm/Lu8pAY5mhg3E9K4iDimikUlptLKZHSWfOO5Uot5WFUtc6oeBN+pWmS3aEeA7VI5xa9qL/BA3RR3UQImemFVmvPG3/XcvPY5LvhAZlytdFNismc6PkxaeJWDW19Z/ordQ/f3LzCHyPX+xOqYQ== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=none; dmarc=none; dkim=none; arc=none DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=outlook.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=fBHoohyXSOIrWZtxieBwBlMxwZlgAeJR9Sw9OsRjK4Y=; b=Pc3gTn2QPzxQptg+JJ40hqRTQqv87Nlso4l6s/rKEUppfwNRYfqnzlS1FDAu12Q7AQOUZxy4kYZUf020pfdNSaz95wMHrp/hZ0J34xR0F4wRUKwON7e6lCQ7dIuu5bE2cOHcA+9q9MVaSAfkg5Ib5JZDs+LdcIagjbZwQ8zF8lhj/0XOvM4ajM5+W+H+3Q1Jlm+fTM8p4fPpWJwJXehuzM+afqEVct5uVnTJuAdU3zw/R+Cf1ivtMo3Ekk9JNpqvGKztaJvRgU2zxY9DfAF8BErGcBdBuxKpL1VHVlTiqdlt3fhFub8QzzMmUdnzlfEaPCDXFyhtf2BNv+REGjZg2w== Received: from SY7P300MB0845.AUSP300.PROD.OUTLOOK.COM (2603:10c6:10:288::12) by ME0P300MB1518.AUSP300.PROD.OUTLOOK.COM (2603:10c6:220:247::19) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.8511.26; Sun, 9 Mar 2025 15:50:12 +0000 Received: from SY7P300MB0845.AUSP300.PROD.OUTLOOK.COM ([fe80::eaec:d3ce:9584:3e10]) by SY7P300MB0845.AUSP300.PROD.OUTLOOK.COM ([fe80::eaec:d3ce:9584:3e10%2]) with mapi id 15.20.8511.025; Sun, 9 Mar 2025 15:50:12 +0000 From: Tong Wu To: FFmpeg development discussions and patches Thread-Topic: [FFmpeg-devel] [PATCH] avcodec/d3d12va_decode: enable reference-only decoder mode Thread-Index: AQHbhGzyBdG7ogElREeg8cxclihHQ7NrBYkA Date: Sun, 9 Mar 2025 15:50:11 +0000 Message-ID: References: <20250221142830.1839-1-Primeadvice@gmail.com> In-Reply-To: <20250221142830.1839-1-Primeadvice@gmail.com> Accept-Language: en-US, zh-CN Content-Language: en-US X-MS-Has-Attach: X-MS-TNEF-Correlator: x-ms-exchange-messagesentrepresentingtype: 1 x-ms-publictraffictype: Email x-ms-traffictypediagnostic: SY7P300MB0845:EE_|ME0P300MB1518:EE_ x-ms-office365-filtering-correlation-id: 72fa2a58-6d80-489e-30fd-08dd5f221395 x-microsoft-antispam: BCL:0; ARA:14566002|15080799006|8062599003|7092599003|19110799003|461199028|8060799006|12091999003|41001999003|56899033|3412199025|102099032|440099028; x-microsoft-antispam-message-info: =?us-ascii?Q?f2QdFXI45GEdimanYJUxkn5DNa2w+iyf+ULPy9HJycsintemcmStTyMea9TM?= =?us-ascii?Q?PNhNYEBlv/Hh8Fdm9nISi2YYIKzDVnScWOgujLQSYTZwrBpNgKtm/IBY56Xa?= =?us-ascii?Q?0KKGT6zVwO9qFWNgPNCwGPxWiB92x7puEOKccc7VRCpH1jPlo4VXlwV3SCjy?= =?us-ascii?Q?Ep4Hvi5K2c/sGQYpmvfmFaLW6qJcbg40A/0F65rYE7t0wIZb6PsCsWxfeQ1l?= =?us-ascii?Q?4IGW+TNdFlyx1R8hBwB/lJ7H26CUQC3FPKfww4fF5Hy2P14a2GAWt5V2Fltk?= =?us-ascii?Q?oaCWBN/vStREiSwY+tTpQ/S3ZsoNUm9tlwcQ9tpjUF3KX+YqqUZazwevcBTi?= =?us-ascii?Q?MqXWTCXNcDCmwquYyStRZ2vtuKjdwXnVdtlRuQjTfv1ESsQW4Jkeo4QBL5Tq?= =?us-ascii?Q?+cpN2EkPma69I0A4bAKVcsOeC+kmhfVeyGfSVEAJzXDhCh6JKKf+81/I7g8n?= =?us-ascii?Q?FmML/lzNj0V8hs14TSMr+IfwA8YdnZlwPyXK4hTfldYGSNWXo4BxM4rnVaTr?= =?us-ascii?Q?jTiWKlKlVs5PTO2vgKyeQiAUmbXV7JHzKA/k0pP3dEIWGwofdDz/3Mx8yFAA?= =?us-ascii?Q?cQtNO8AGsDUPfHe9d2+BVV2n8N/OT4EWlbGgvcF6J4Bbp5sst/3SFHDF165/?= =?us-ascii?Q?/BglKXdtWJP3kikiLyTn2RynVWPKH8XQcl2SlLayWqnlx7AOlInDNZSWinXt?= =?us-ascii?Q?YkKxc1eujZ9gogPYWCNu8Z232FBwSHADa8WsOV4LK6C+zSuXbj8LGw2hMul7?= =?us-ascii?Q?MLn20/XgGj/RUaEYfNVML4UG+o0SJ0oX1cq+uPdUVFMPKV+gr+Tne9CnF4lH?= =?us-ascii?Q?OTooXxY3zZ4zkgS/wxPLALXv7QIx96XseyaZYyebN8Mr6AwBLzKo7HbH0S5A?= =?us-ascii?Q?gwUsAlzWn5ex6kopgi+g5wUzRWnhF4LfIXW+6CK15+XcYsiACYHfI36VZfim?= =?us-ascii?Q?pDu8fEFtD1zJk/WSmH2e1dohKx7xoVqUdCmEiJ1fJYCwBGL2SykguxaddKYl?= =?us-ascii?Q?zlht5+5Y9K1Ns3Ek/KhS63UfDAynMwZkGh7XX1jPqMoyy+OGsfzbQs0LofgK?= =?us-ascii?Q?lWsIqsOA0RSjSThmOaZXC3BQL82JIwCSIQRUUBHcND3UQeHc95UIhYqgngLf?= =?us-ascii?Q?DgqFE/WDk1fhaQt63bx2fZLXt5GjrbVgnA=3D=3D?= x-ms-exchange-antispam-messagedata-chunkcount: 1 x-ms-exchange-antispam-messagedata-0: =?us-ascii?Q?GiGG/zDUUKKdFbb+QKLMsi45Gbg65hTU8wA6ka2a7ArIXw7CKiD74atMpvZh?= =?us-ascii?Q?poJo6hOcJ+rW/aWDsDT1cZ6z1gR2Wa850YW3WFpxneGkiGdPs3CtS2fRRDf7?= =?us-ascii?Q?+zKtJSjJ53aHmhPGh6xlXYcVpQiIOKxk+eLY/7ggzVXAxSbeJWR0S0lDbwPl?= =?us-ascii?Q?wY9IwJgrZ85r3TZHprygXFBfnU1fSxK661UplSEniPuwXFF6ZhYAYf4Bc4Qp?= =?us-ascii?Q?/TF/FrplRWa7fTc9uh0NcEnBk/5oZv2FQSusqL6tFOjc57ZetA8z+nuwESAw?= =?us-ascii?Q?fWKJxH5W/M70p+bzaAcWFizdxcxH34vwm95jFg9HxxmXyyqKy5s5TBEj1tn6?= =?us-ascii?Q?vwNHFAZb6bHBDwTdyUzQHY0NSFCTMM5mMDXUDXq3T6aiRmC67U9VDsE9PATB?= =?us-ascii?Q?PrHacWLJYw2Z58b3VY/2SPb90PGbMVmgZ2QgL2mCpqEQV2aKRhK6KZWRp/uf?= =?us-ascii?Q?HcRGWVsWXHpIo+9SBQgzeDfyYcOcKp/e/lMgp5YBw7pd+Lym+s92fkeAl90p?= =?us-ascii?Q?RYqf8fwSF6OZUWBdSyIgYZbaqJKUoBZK624BDWqn2vp+XYeDgcwoQlWT2xk0?= =?us-ascii?Q?ZCGb2hLuM6OjQ/mSDrZPRXtUEuAbvOdxtyydLt9ZVskvTTO2cjLucE6Xo04U?= =?us-ascii?Q?6I5gfYlq/6R/QHTdLc4aReEx1zjfY0Z7hkON+o4eJCez7poNXdNaOgRB5Kvt?= =?us-ascii?Q?wyxaC1eujmUw4ag1d3BppYZFkVL4TxPlSGzPzuByg0JA/pvJgHklpvUJ9UVR?= =?us-ascii?Q?eEWBFjSkbee3eTJg8raJkkjkXK6HYrmfrjcVglaAn+1DXmKtgernQt4mAiaq?= =?us-ascii?Q?BougVRoqmPnJnCjHrt3YifxQhQVxfvnCGI+KWIGMIcLl6djU/KM2VhBtDj5j?= =?us-ascii?Q?JbqVtMYWdbI4eZQsKZeeJ8Uz5Pp+OFg1tOR1oXH+AwuR1uY6fPDpI8S/eZVI?= =?us-ascii?Q?8IavQ3lT5Aagcs7WBIxh5GaCN5af5GM6bLbdoy2cQAkoxG5ZGlxQFqrsbdTL?= =?us-ascii?Q?4cYqawN0JPqODOm+HNjQVuXXn74pn1tD70gilyM6JqBtpAMJsQnjgoPYxcp1?= =?us-ascii?Q?J/14pkWPFtC+9rxvu/Dc08nOnFb8b89xfus9q4fiNKU1gb3jQNd+qpn4BIfk?= =?us-ascii?Q?kwdkuI/67pqNZne1Rzd9T8WlTjW0ysoV4VQsL2+qzoo+w3Qe5/GyEsIHl8z1?= =?us-ascii?Q?JRKFPlqYk2LRFwd7UcRYRcOPCJ/PM72bvV9bnXwwdZoibflAgeHLF1X4Y/w?= =?us-ascii?Q?=3D?= MIME-Version: 1.0 X-OriginatorOrg: outlook.com X-MS-Exchange-CrossTenant-AuthAs: Internal X-MS-Exchange-CrossTenant-AuthSource: SY7P300MB0845.AUSP300.PROD.OUTLOOK.COM X-MS-Exchange-CrossTenant-RMS-PersistedConsumerOrg: 00000000-0000-0000-0000-000000000000 X-MS-Exchange-CrossTenant-Network-Message-Id: 72fa2a58-6d80-489e-30fd-08dd5f221395 X-MS-Exchange-CrossTenant-originalarrivaltime: 09 Mar 2025 15:50:11.8320 (UTC) X-MS-Exchange-CrossTenant-fromentityheader: Hosted X-MS-Exchange-CrossTenant-id: 84df9e7f-e9f6-40af-b435-aaaaaaaaaaaa X-MS-Exchange-CrossTenant-rms-persistedconsumerorg: 00000000-0000-0000-0000-000000000000 X-MS-Exchange-Transport-CrossTenantHeadersStamped: ME0P300MB1518 Subject: Re: [FFmpeg-devel] [PATCH] avcodec/d3d12va_decode: enable reference-only decoder mode X-BeenThere: ffmpeg-devel@ffmpeg.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: FFmpeg development discussions and patches List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Reply-To: FFmpeg development discussions and patches Cc: Araz Iusubov Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Errors-To: ffmpeg-devel-bounces@ffmpeg.org Sender: "ffmpeg-devel" Archived-At: List-Archive: List-Post: Araz Iusubov: Hi there. Thanks for the patch. >Subject: [FFmpeg-devel] [PATCH] avcodec/d3d12va_decode: enable reference- >only decoder mode You should add this as PATCH v2 to better track it. > >The Reference-Only feature in DirectX 12 is a memory optimization technique >designed for video decoding scenarios. >This feature requires that reference resources must be allocated with the >D3D12_RESOURCE_FLAG_VIDEO_DECODE_REFERENCE_ONLY resource flag. >Reference textures must also be separated from output textures. >This feature is not supported in the current version of ffmpeg. >Since AMD GPU uses this feature in Direct 12 decoder, ffmpeg does not support >AMD GPU Direct 12 decoding. > >--- > libavcodec/d3d12va_decode.c | 176 +++++++++++++++++++++++++++++++++--- > libavcodec/d3d12va_decode.h | 13 +++ > 2 files changed, 176 insertions(+), 13 deletions(-) > >diff --git a/libavcodec/d3d12va_decode.c b/libavcodec/d3d12va_decode.c index >3b8978635e..c51234c256 100644 >--- a/libavcodec/d3d12va_decode.c >+++ b/libavcodec/d3d12va_decode.c >@@ -41,6 +41,111 @@ typedef struct HelperObjects { > uint64_t fence_value; > } HelperObjects; > >+typedef struct ReferenceFrame { >+ ID3D12Resource *resource; >+ int used; >+ ID3D12Resource *output_resource; >+} ReferenceFrame; >+ >+static ID3D12Resource *get_reference_only_resource(AVCodecContext >+*avctx, ID3D12Resource *output_resource) { >+ D3D12VADecodeContext *ctx = D3D12VA_DECODE_CONTEXT(avctx); >+ AVHWFramesContext *frames_ctx = D3D12VA_FRAMES_CONTEXT(avctx); >+ AVD3D12VADeviceContext *device_hwctx = ctx->device_ctx; >+ AVD3D12VAFramesContext *frames_hwctx = frames_ctx->hwctx; >+ int i; >+ ID3D12Resource *resource = NULL; >+ ReferenceFrame *reference_only_map = (ReferenceFrame *)(ctx- >>reference_only_map); >+ if(reference_only_map == NULL){ >+ av_log(avctx, AV_LOG_ERROR, "Reference frames are not allocated!\n"); >+ return NULL; >+ } >+ >+ // find unused resource >+ for (i = 0; i < ctx->max_num_ref; i++) { >+ if(!reference_only_map[i].used && reference_only_map[i].resource != >NULL) { >+ reference_only_map[i].used = 1; >+ resource = reference_only_map[i].resource; >+ reference_only_map[i].output_resource = output_resource; >+ break; A return missing? >+ } >+ } >+ if(resource == NULL){ You could remove this "if" after the return is added above. >+ // find space to allocate >+ for (i = 0; i < ctx->max_num_ref; i++) { >+ if(reference_only_map[i].resource == NULL) { >+ break; >+ } >+ } >+ } >+ if(i == ctx->max_num_ref){ >+ av_log(avctx, AV_LOG_ERROR, "No space for new Reference frame!\n"); I would prefer to return here and remove the following else. >+ }else{ >+ // allocate frame >+ D3D12_HEAP_PROPERTIES props = { .Type = >D3D12_HEAP_TYPE_DEFAULT }; >+ D3D12_RESOURCE_DESC desc = { >+ .Dimension = D3D12_RESOURCE_DIMENSION_TEXTURE2D, >+ .Alignment = 0, >+ .Width = avctx->coded_width, >+ .Height = avctx->coded_height, >+ .DepthOrArraySize = 1, >+ .MipLevels = 1, >+ .Format = frames_hwctx->format, >+ .SampleDesc = {.Count = 1, .Quality = 0 }, >+ .Layout = D3D12_TEXTURE_LAYOUT_UNKNOWN, >+ .Flags = >D3D12_RESOURCE_FLAG_VIDEO_DECODE_REFERENCE_ONLY | >D3D12_RESOURCE_FLAG_DENY_SHADER_RESOURCE, >+ }; >+ >+ if (FAILED(ID3D12Device_CreateCommittedResource(device_hwctx->device, >&props, D3D12_HEAP_FLAG_NONE, &desc, >+ D3D12_RESOURCE_STATE_COMMON, NULL, &IID_ID3D12Resource, (void >**)&reference_only_map[i].resource))) { >+ av_log(ctx, AV_LOG_ERROR, "Could not create the texture\n"); The log could be more specific >+ } >+ resource = reference_only_map[i].resource; >+ reference_only_map[i].used = 1; >+ reference_only_map[i].output_resource = output_resource; >+ } >+ // return it >+ return resource; >+} >+ >+static void free_reference_only_resources(AVCodecContext *avctx) { >+ D3D12VADecodeContext *ctx = D3D12VA_DECODE_CONTEXT(avctx); Please remove the extra spaces >+ int i; >+ ReferenceFrame *reference_only_map = (ReferenceFrame *)(ctx- >>reference_only_map); >+ if(reference_only_map != NULL){ >+ for (i = 0; i < ctx->max_num_ref; i++) { >+ if(reference_only_map[i].resource != NULL) { >+ D3D12_OBJECT_RELEASE(reference_only_map[i].resource); >+ } >+ } >+ av_freep(&ctx->reference_only_map); >+ av_freep(&ctx->ref_only_resources); >+ } >+} >+ >+static void prepare_reference_only_resources(AVCodecContext *avctx) { >+ D3D12VADecodeContext *ctx = D3D12VA_DECODE_CONTEXT(avctx); Same >+ int i, j; >+ ReferenceFrame *reference_only_map = (ReferenceFrame *)(ctx- >>reference_only_map); >+ if(reference_only_map == NULL){ >+ return; >+ } >+ memset(ctx->ref_only_resources, 0, ctx->max_num_ref * sizeof(*(ctx- >>ref_only_resources))); >+ for (j = 0; j < ctx->max_num_ref; j++) { >+ for (i = 0; i < ctx->max_num_ref; i++) { >+ if(reference_only_map[j].used && >reference_only_map[j].output_resource == ctx->ref_resources[i]) { >+ ctx->ref_only_resources[i] = reference_only_map[j].resource; >+ break; >+ } >+ } >+ if(i == ctx->max_num_ref){ >+ reference_only_map[j].used = 0; >+ } >+ } >+} >+ > int ff_d3d12va_get_suitable_max_bitstream_size(AVCodecContext *avctx) { > AVHWFramesContext *frames_ctx = D3D12VA_FRAMES_CONTEXT(avctx); @@ >-250,6 +355,18 @@ static int d3d12va_create_decoder(AVCodecContext *avctx) > return AVERROR_PATCHWELCOME; > } > >+ ctx->reference_only_map = NULL; >+ ctx->ref_only_resources = NULL; >+ if (feature.ConfigurationFlags & >D3D12_VIDEO_DECODE_CONFIGURATION_FLAG_REFERENCE_ONLY_ALLOCATI >ONS_REQUIRED) { >+ av_log(avctx, AV_LOG_VERBOSE, "Reference-Only Allocations are required >for this D3D12 decoder configuration.\n"); >+ ctx->reference_only_map = av_calloc(ctx->max_num_ref + 1, >sizeof(ReferenceFrame)); >+ if (!ctx->reference_only_map) >+ return AVERROR(ENOMEM); >+ ctx->ref_only_resources = av_calloc(ctx->max_num_ref, sizeof(*ctx- >>ref_only_resources)); >+ if (!ctx->ref_only_resources) >+ return AVERROR(ENOMEM); >+ } >+ > desc = (D3D12_VIDEO_DECODER_DESC) { > .NodeMask = 0, > .Configuration = ctx->cfg, >@@ -321,11 +438,11 @@ int ff_d3d12va_decode_init(AVCodecContext *avctx) > ctx->ref_resources = av_calloc(ctx->max_num_ref, sizeof(*ctx- >>ref_resources)); > if (!ctx->ref_resources) > return AVERROR(ENOMEM); >- >+ Avoid trailing whitespaces > ctx->ref_subresources = av_calloc(ctx->max_num_ref, sizeof(*ctx- >>ref_subresources)); > if (!ctx->ref_subresources) > return AVERROR(ENOMEM); >- >+ Same > ctx->objects_queue = av_fifo_alloc2(D3D12VA_VIDEO_DEC_ASYNC_DEPTH, > sizeof(HelperObjects), AV_FIFO_FLAG_AUTO_GROW); > if (!ctx->objects_queue) >@@ -394,6 +511,7 @@ int ff_d3d12va_decode_uninit(AVCodecContext *avctx) > > av_log(avctx, AV_LOG_VERBOSE, "Total number of command allocators >reused: %d\n", num_allocator); > } >+ free_reference_only_resources(avctx); > > av_fifo_freep2(&ctx->objects_queue); > >@@ -412,14 +530,15 @@ static inline int >d3d12va_update_reference_frames_state(AVCodecContext *avctx, D > ID3D12Resource *current_resource, int >state_before, int state_end) { > D3D12VADecodeContext *ctx = D3D12VA_DECODE_CONTEXT(avctx); >+ ID3D12Resource **ref_resources = ctx->ref_only_resources ? >+ ctx->ref_only_resources : ctx->ref_resources; > > int num_barrier = 0; > for (int i = 0; i < ctx->max_num_ref; i++) { >- if (((ctx->used_mask >> i) & 0x1) && ctx->ref_resources[i] && ctx- >>ref_resources[i] != current_resource) { >+ if (((ctx->used_mask >> i) & 0x1) && ref_resources[i] && >+ ref_resources[i] != current_resource) { > barriers[num_barrier].Type = >D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; > barriers[num_barrier].Flags = D3D12_RESOURCE_BARRIER_FLAG_NONE; > barriers[num_barrier].Transition = >(D3D12_RESOURCE_TRANSITION_BARRIER){ >- .pResource = ctx->ref_resources[i], >+ .pResource = ref_resources[i], > .Subresource = D3D12_RESOURCE_BARRIER_ALL_SUBRESOURCES, > .StateBefore = state_before, > .StateAfter = state_end, @@ -440,8 +559,9 @@ int >ff_d3d12va_common_end_frame(AVCodecContext *avctx, AVFrame *frame, > D3D12VADecodeContext *ctx = D3D12VA_DECODE_CONTEXT(avctx); > ID3D12Resource *buffer = NULL; > ID3D12CommandAllocator *command_allocator = NULL; >- AVD3D12VAFrame *f = (AVD3D12VAFrame *)frame->data[0]; >- ID3D12Resource *resource = (ID3D12Resource *)f->texture; >+ AVD3D12VAFrame *f = (AVD3D12VAFrame*)frame->data[0]; >+ ID3D12Resource *output_resource = (ID3D12Resource*)f->texture; >+ ID3D12Resource *ref_resource = NULL; > > ID3D12VideoDecodeCommandList *cmd_list = ctx->command_list; > D3D12_RESOURCE_BARRIER barriers[32] = { 0 }; @@ -466,25 +586,55 @@ int >ff_d3d12va_common_end_frame(AVCodecContext *avctx, AVFrame *frame, > D3D12_VIDEO_DECODE_OUTPUT_STREAM_ARGUMENTS output_args = { > .ConversionArguments = { 0 }, > .OutputSubresource = 0, >- .pOutputTexture2D = resource, >+ .pOutputTexture2D = output_resource, > }; > >+ memset(ctx->ref_subresources, 0, sizeof(UINT) * ctx->max_num_ref); >+ input_args.ReferenceFrames.NumTexture2Ds = ctx->max_num_ref; >+ input_args.ReferenceFrames.pSubresources = ctx->ref_subresources; >+ >+ if (ctx->reference_only_map) { >+ ref_resource = get_reference_only_resource(avctx, output_resource); >+ if(ref_resource == NULL){ >+ av_log(avctx, AV_LOG_ERROR, "Failed to get reference frame!\n"); >+ goto fail; >+ } >+ prepare_reference_only_resources(avctx); >+ >+ output_args.ConversionArguments.Enable = 1; >+ input_args.ReferenceFrames.ppTexture2Ds = ctx->ref_only_resources; >+ }else{ We better keep the same code style in a file, which needs to add space for "if else". Also, no need to add "{}" for one line condition. >+ ref_resource = output_resource; >+ input_args.ReferenceFrames.ppTexture2Ds = ctx->ref_resources; >+ } >+ output_args.ConversionArguments.pReferenceTexture2D = ref_resource; >+ output_args.ConversionArguments.ReferenceSubresource = 0; This looks strange, for non-reference-only case, you don't enable the ConversionArguments but give them the value. Should we keep them the way before? >+ > UINT num_barrier = 1; > barriers[0] = (D3D12_RESOURCE_BARRIER) { > .Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION, > .Flags = D3D12_RESOURCE_BARRIER_FLAG_NONE, > .Transition = { >- .pResource = resource, >+ .pResource = output_resource, > .Subresource = D3D12_RESOURCE_BARRIER_ALL_SUBRESOURCES, > .StateBefore = D3D12_RESOURCE_STATE_COMMON, > .StateAfter = D3D12_RESOURCE_STATE_VIDEO_DECODE_WRITE, > }, > }; > >- memset(ctx->ref_subresources, 0, sizeof(UINT) * ctx->max_num_ref); >- input_args.ReferenceFrames.NumTexture2Ds = ctx->max_num_ref; >- input_args.ReferenceFrames.ppTexture2Ds = ctx->ref_resources; >- input_args.ReferenceFrames.pSubresources = ctx->ref_subresources; >+ if (ctx->reference_only_map) { >+ barriers[1] = (D3D12_RESOURCE_BARRIER) { >+ .Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION, >+ .Flags = D3D12_RESOURCE_BARRIER_FLAG_NONE, >+ .Transition = { >+ .pResource = ref_resource, >+ .Subresource = D3D12_RESOURCE_BARRIER_ALL_SUBRESOURCES, >+ .StateBefore = D3D12_RESOURCE_STATE_COMMON, >+ .StateAfter = D3D12_RESOURCE_STATE_VIDEO_DECODE_WRITE, >+ }, >+ }; >+ num_barrier++; >+ } > > ret = d3d12va_fence_completion(&f->sync_ctx); > if (ret < 0) >@@ -505,7 +655,7 @@ int ff_d3d12va_common_end_frame(AVCodecContext >*avctx, AVFrame *frame, > > DX_CHECK(ID3D12VideoDecodeCommandList_Reset(cmd_list, >command_allocator)); > >- num_barrier += d3d12va_update_reference_frames_state(avctx, &barriers[1], >resource, D3D12_RESOURCE_STATE_COMMON, >D3D12_RESOURCE_STATE_VIDEO_DECODE_READ); >+ num_barrier += d3d12va_update_reference_frames_state(avctx, >+ &barriers[num_barrier], ref_resource, D3D12_RESOURCE_STATE_COMMON, >+ D3D12_RESOURCE_STATE_VIDEO_DECODE_READ); > > ID3D12VideoDecodeCommandList_ResourceBarrier(cmd_list, num_barrier, >barriers); > >diff --git a/libavcodec/d3d12va_decode.h b/libavcodec/d3d12va_decode.h index >b64994760a..74991fe853 100644 >--- a/libavcodec/d3d12va_decode.h >+++ b/libavcodec/d3d12va_decode.h >@@ -119,6 +119,19 @@ typedef struct D3D12VADecodeContext { > * Private to the FFmpeg AVHWAccel implementation > */ > unsigned report_id; >+ >+ /** >+ * The Reference-Only feature in DirectX 12 is a memory optimization >+ * technique designed for video decoding/encoding scenarios. >+ * This feature requires that reference resources must be allocated >+ * with the `D3D12_RESOURCE_FLAG_VIDEO_DECODE_REFERENCE_ONLY` >resource flag. >+ * Reference textures must also be separated from output textures. >+ * reference_only_map used as a storage for reference only frames >+ * ref_only_resources used as a shadow for ref_resources >+ */ >+ void *reference_only_map; >+ ID3D12Resource **ref_only_resources; >+ > } D3D12VADecodeContext; > > /** >-- >2.47.1.windows.1 > Thanks, Tong _______________________________________________ ffmpeg-devel mailing list ffmpeg-devel@ffmpeg.org https://ffmpeg.org/mailman/listinfo/ffmpeg-devel To unsubscribe, visit link above, or email ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".