Browse code

d3d11va: WindowsPhone requires a mutex around ID3D11VideoContext

Steve Lhomme authored on 2015/09/16 20:27:42
Showing 6 changed files
... ...
@@ -13,6 +13,10 @@ libavutil:     2015-08-28
13 13
 
14 14
 API changes, most recent first:
15 15
 
16
+2015-xx-xx - xxxxxxx - lavc 57.2.0 - d3d11va.h
17
+  Add av_d3d11va_alloc_context(). This function must from now on be used for
18
+  allocating AVD3D11VAContext.
19
+
16 20
 2015-xx-xx - lavu 55.0.0
17 21
   xxxxxxx - Change type of AVPixFmtDescriptor.flags from uint8_t to uint64_t.
18 22
   xxxxxxx - Change type of AVComponentDescriptor fields from uint16_t to int
... ...
@@ -581,7 +581,7 @@ OBJS-$(CONFIG_ADPCM_YAMAHA_DECODER)       += adpcm.o adpcm_data.o
581 581
 OBJS-$(CONFIG_ADPCM_YAMAHA_ENCODER)       += adpcmenc.o adpcm_data.o
582 582
 
583 583
 # hardware accelerators
584
-OBJS-$(CONFIG_D3D11VA)                    += dxva2.o
584
+OBJS-$(CONFIG_D3D11VA)                    += d3d11va.o dxva2.o
585 585
 OBJS-$(CONFIG_DXVA2)                      += dxva2.o
586 586
 OBJS-$(CONFIG_VAAPI)                      += vaapi.o
587 587
 OBJS-$(CONFIG_VDA)                        += vda.o
588 588
new file mode 100644
... ...
@@ -0,0 +1,33 @@
0
+/*
1
+ * Direct3D11 HW acceleration
2
+ *
3
+ * copyright (c) 2015 Steve Lhomme
4
+ *
5
+ * This file is part of Libav.
6
+ *
7
+ * Libav is free software; you can redistribute it and/or
8
+ * modify it under the terms of the GNU Lesser General Public
9
+ * License as published by the Free Software Foundation; either
10
+ * version 2.1 of the License, or (at your option) any later version.
11
+ *
12
+ * Libav is distributed in the hope that it will be useful,
13
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15
+ * Lesser General Public License for more details.
16
+ *
17
+ * You should have received a copy of the GNU Lesser General Public
18
+ * License along with Libav; if not, write to the Free Software
19
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20
+ */
21
+
22
+#include "config.h"
23
+#include "libavutil/mem.h"
24
+
25
+#include "d3d11va.h"
26
+
27
+AVD3D11VAContext *av_d3d11va_alloc_context(void)
28
+{
29
+    AVD3D11VAContext* res = av_mallocz(sizeof(AVD3D11VAContext));
30
+    res->context_mutex = INVALID_HANDLE_VALUE;
31
+    return res;
32
+}
... ...
@@ -53,8 +53,10 @@
53 53
  * to the Direct3D11 Libav HWAccel implementation.
54 54
  *
55 55
  * The application must make it available as AVCodecContext.hwaccel_context.
56
+ *
57
+ * Use av_d3d11va_alloc_context() exclusively to allocate an AVD3D11VAContext.
56 58
  */
57
-struct AVD3D11VAContext {
59
+typedef struct AVD3D11VAContext {
58 60
     /**
59 61
      * D3D11 decoder object
60 62
      */
... ...
@@ -89,7 +91,19 @@ struct AVD3D11VAContext {
89 89
      * Private to the Libav AVHWAccel implementation
90 90
      */
91 91
     unsigned report_id;
92
-};
92
+
93
+    /**
94
+      * Mutex to access video_context
95
+      */
96
+    HANDLE  context_mutex;
97
+} AVD3D11VAContext;
98
+
99
+/**
100
+ * Allocate an AVD3D11VAContext.
101
+ *
102
+ * @return Newly-allocated AVD3D11VAContext or NULL on failure.
103
+ */
104
+AVD3D11VAContext *av_d3d11va_alloc_context(void);
93 105
 
94 106
 /**
95 107
  * @}
... ...
@@ -144,10 +144,13 @@ int ff_dxva2_common_end_frame(AVCodecContext *avctx, AVFrame *frame,
144 144
 
145 145
     do {
146 146
 #if CONFIG_D3D11VA
147
-        if (avctx->pix_fmt == AV_PIX_FMT_D3D11VA_VLD)
147
+        if (avctx->pix_fmt == AV_PIX_FMT_D3D11VA_VLD) {
148
+            if (D3D11VA_CONTEXT(ctx)->context_mutex != INVALID_HANDLE_VALUE)
149
+                WaitForSingleObjectEx(D3D11VA_CONTEXT(ctx)->context_mutex, INFINITE, FALSE);
148 150
             hr = ID3D11VideoContext_DecoderBeginFrame(D3D11VA_CONTEXT(ctx)->video_context, D3D11VA_CONTEXT(ctx)->decoder,
149 151
                                                       ff_dxva2_get_surface(frame),
150 152
                                                       0, NULL);
153
+        }
151 154
 #endif
152 155
 #if CONFIG_DXVA2
153 156
         if (avctx->pix_fmt == AV_PIX_FMT_DXVA2_VLD)
... ...
@@ -161,6 +164,11 @@ int ff_dxva2_common_end_frame(AVCodecContext *avctx, AVFrame *frame,
161 161
 
162 162
     if (FAILED(hr)) {
163 163
         av_log(avctx, AV_LOG_ERROR, "Failed to begin frame: 0x%lx\n", hr);
164
+#if CONFIG_D3D11VA
165
+        if (avctx->pix_fmt == AV_PIX_FMT_D3D11VA_VLD)
166
+            if (D3D11VA_CONTEXT(ctx)->context_mutex != INVALID_HANDLE_VALUE)
167
+                ReleaseMutex(D3D11VA_CONTEXT(ctx)->context_mutex);
168
+#endif
164 169
         return -1;
165 170
     }
166 171
 
... ...
@@ -260,8 +268,11 @@ int ff_dxva2_common_end_frame(AVCodecContext *avctx, AVFrame *frame,
260 260
 
261 261
 end:
262 262
 #if CONFIG_D3D11VA
263
-    if (avctx->pix_fmt == AV_PIX_FMT_D3D11VA_VLD)
263
+    if (avctx->pix_fmt == AV_PIX_FMT_D3D11VA_VLD) {
264 264
         hr = ID3D11VideoContext_DecoderEndFrame(D3D11VA_CONTEXT(ctx)->video_context, D3D11VA_CONTEXT(ctx)->decoder);
265
+        if (D3D11VA_CONTEXT(ctx)->context_mutex != INVALID_HANDLE_VALUE)
266
+            ReleaseMutex(D3D11VA_CONTEXT(ctx)->context_mutex);
267
+    }
265 268
 #endif
266 269
 #if CONFIG_DXVA2
267 270
     if (avctx->pix_fmt == AV_PIX_FMT_DXVA2_VLD)
... ...
@@ -29,7 +29,7 @@
29 29
 #include "libavutil/version.h"
30 30
 
31 31
 #define LIBAVCODEC_VERSION_MAJOR 57
32
-#define LIBAVCODEC_VERSION_MINOR  1
32
+#define LIBAVCODEC_VERSION_MINOR  2
33 33
 #define LIBAVCODEC_VERSION_MICRO  0
34 34
 
35 35
 #define LIBAVCODEC_VERSION_INT  AV_VERSION_INT(LIBAVCODEC_VERSION_MAJOR, \