Browse code

Merge commit 'c45fcf30cfab687004ed1cdc06ebaa21f4262a0b'

* commit 'c45fcf30cfab687004ed1cdc06ebaa21f4262a0b':
DXV decoder

Merged-by: Hendrik Leppkes <h.leppkes@gmail.com>

Hendrik Leppkes authored on 2015/09/07 23:07:07
Showing 15 changed files
... ...
@@ -2,6 +2,7 @@ Entries are sorted chronologically from oldest to youngest within each release,
2 2
 releases are sorted from youngest to oldest.
3 3
 
4 4
 version <next>:
5
+- DXV decoding
5 6
 
6 7
 
7 8
 version 2.8:
... ...
@@ -2189,6 +2189,7 @@ dnxhd_encoder_select="aandcttables blockdsp fdctdsp idctdsp mpegvideoenc pixbloc
2189 2189
 dvvideo_decoder_select="dvprofile idctdsp"
2190 2190
 dvvideo_encoder_select="dvprofile fdctdsp me_cmp pixblockdsp"
2191 2191
 dxa_decoder_select="zlib"
2192
+dxv_decoder_select="lzf texturedsp"
2192 2193
 eac3_decoder_select="ac3_decoder"
2193 2194
 eac3_encoder_select="ac3_encoder"
2194 2195
 eamad_decoder_select="aandcttables blockdsp bswapdsp idctdsp mpegvideo"
... ...
@@ -463,6 +463,7 @@ library:
463 463
 @item Redirector                @tab   @tab X
464 464
 @item RedSpark                  @tab   @tab X
465 465
 @item Renderware TeXture Dictionary @tab   @tab X
466
+@item Resolume DXV              @tab   @tab X
466 467
 @item RL2                       @tab   @tab X
467 468
     @tab Audio and video format used in some games by Entertainment Software Partners.
468 469
 @item RPL/ARMovie               @tab   @tab X
... ...
@@ -242,6 +242,7 @@ OBJS-$(CONFIG_DVVIDEO_DECODER)         += dvdec.o dv.o dvdata.o
242 242
 OBJS-$(CONFIG_DVVIDEO_ENCODER)         += dvenc.o dv.o dvdata.o
243 243
 OBJS-$(CONFIG_DXA_DECODER)             += dxa.o
244 244
 OBJS-$(CONFIG_DXTORY_DECODER)          += dxtory.o
245
+OBJS-$(CONFIG_DXV_DECODER)             += dxv.o
245 246
 OBJS-$(CONFIG_EAC3_DECODER)            += eac3_data.o
246 247
 OBJS-$(CONFIG_EAC3_ENCODER)            += eac3enc.o eac3_data.o
247 248
 OBJS-$(CONFIG_EACMV_DECODER)           += eacmv.o
... ...
@@ -159,6 +159,7 @@ void avcodec_register_all(void)
159 159
     REGISTER_ENCDEC (DVVIDEO,           dvvideo);
160 160
     REGISTER_DECODER(DXA,               dxa);
161 161
     REGISTER_DECODER(DXTORY,            dxtory);
162
+    REGISTER_DECODER(DXV,               dxv);
162 163
     REGISTER_DECODER(EACMV,             eacmv);
163 164
     REGISTER_DECODER(EAMAD,             eamad);
164 165
     REGISTER_DECODER(EATGQ,             eatgq);
... ...
@@ -295,6 +295,7 @@ enum AVCodecID {
295 295
     AV_CODEC_ID_HQ_HQA,
296 296
     AV_CODEC_ID_HAP,
297 297
     AV_CODEC_ID_DDS,
298
+    AV_CODEC_ID_DXV,
298 299
 
299 300
     AV_CODEC_ID_BRENDER_PIX= MKBETAG('B','P','I','X'),
300 301
     AV_CODEC_ID_Y41P       = MKBETAG('Y','4','1','P'),
301 302
new file mode 100644
... ...
@@ -0,0 +1,461 @@
0
+/*
1
+ * Resolume DXV decoder
2
+ * Copyright (C) 2015 Vittorio Giovara <vittorio.giovara@gmail.com>
3
+ *
4
+ * This file is part of FFmpeg.
5
+ *
6
+ * FFmpeg is free software; you can redistribute it and/or
7
+ * modify it under the terms of the GNU Lesser General Public
8
+ * License as published by the Free Software Foundation; either
9
+ * version 2.1 of the License, or (at your option) any later version.
10
+ *
11
+ * FFmpeg is distributed in the hope that it will be useful,
12
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14
+ * Lesser General Public License for more details.
15
+ *
16
+ * You should have received a copy of the GNU Lesser General Public
17
+ * License along with FFmpeg; if not, write to the Free Software
18
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19
+ */
20
+
21
+#include <stdint.h>
22
+
23
+#include "libavutil/imgutils.h"
24
+
25
+#include "avcodec.h"
26
+#include "bytestream.h"
27
+#include "internal.h"
28
+#include "lzf.h"
29
+#include "texturedsp.h"
30
+#include "thread.h"
31
+
32
+typedef struct DXVContext {
33
+    TextureDSPContext texdsp;
34
+    GetByteContext gbc;
35
+
36
+    uint8_t *tex_data;  // Compressed texture
37
+    int tex_rat;        // Compression ratio
38
+    int tex_step;       // Distance between blocks
39
+    int64_t tex_size;   // Texture size
40
+
41
+    /* Optimal number of slices for parallel decoding */
42
+    int slice_count;
43
+
44
+    /* Pointer to the selected decompression function */
45
+    int (*tex_funct)(uint8_t *dst, ptrdiff_t stride, const uint8_t *block);
46
+} DXVContext;
47
+
48
+static int decompress_texture_thread(AVCodecContext *avctx, void *arg,
49
+                                     int slice, int thread_nb)
50
+{
51
+    DXVContext *ctx = avctx->priv_data;
52
+    AVFrame *frame = arg;
53
+    const uint8_t *d = ctx->tex_data;
54
+    int w_block = avctx->coded_width / TEXTURE_BLOCK_W;
55
+    int h_block = avctx->coded_height / TEXTURE_BLOCK_H;
56
+    int x, y;
57
+    int start_slice, end_slice;
58
+    int base_blocks_per_slice = h_block / ctx->slice_count;
59
+    int remainder_blocks = h_block % ctx->slice_count;
60
+
61
+    /* When the frame height (in blocks) doesn't divide evenly between the
62
+     * number of slices, spread the remaining blocks evenly between the first
63
+     * operations */
64
+    start_slice = slice * base_blocks_per_slice;
65
+    /* Add any extra blocks (one per slice) that have been added
66
+     * before this slice */
67
+    start_slice += FFMIN(slice, remainder_blocks);
68
+
69
+    end_slice = start_slice + base_blocks_per_slice;
70
+    /* Add an extra block if there are remainder blocks to be accounted for */
71
+    if (slice < remainder_blocks)
72
+        end_slice++;
73
+
74
+    for (y = start_slice; y < end_slice; y++) {
75
+        uint8_t *p = frame->data[0] + y * frame->linesize[0] * TEXTURE_BLOCK_H;
76
+        int off  = y * w_block;
77
+        for (x = 0; x < w_block; x++) {
78
+            ctx->tex_funct(p + x * 16, frame->linesize[0],
79
+                           d + (off + x) * ctx->tex_step);
80
+        }
81
+    }
82
+
83
+    return 0;
84
+}
85
+
86
+/* This scheme addresses already decoded elements depending on 2-bit status:
87
+ *   0 -> copy new element
88
+ *   1 -> copy one element from position -x
89
+ *   2 -> copy one element from position -(get_byte() + 2) * x
90
+ *   3 -> copy one element from position -(get_16le() + 0x102) * x
91
+ * x is always 2 for dxt1 and 4 for dxt5. */
92
+#define CHECKPOINT(x)                                                         \
93
+    do {                                                                      \
94
+        if (state == 0) {                                                     \
95
+            value = bytestream2_get_le32(gbc);                                \
96
+            state = 16;                                                       \
97
+        }                                                                     \
98
+        op = value & 0x3;                                                     \
99
+        value >>= 2;                                                          \
100
+        state--;                                                              \
101
+        switch (op) {                                                         \
102
+        case 1:                                                               \
103
+            idx = x;                                                          \
104
+            break;                                                            \
105
+        case 2:                                                               \
106
+            idx = (bytestream2_get_byte(gbc) + 2) * x;                        \
107
+            break;                                                            \
108
+        case 3:                                                               \
109
+            idx = (bytestream2_get_le16(gbc) + 0x102) * x;                    \
110
+            break;                                                            \
111
+        }                                                                     \
112
+    } while(0)
113
+
114
+static int dxv_decompress_dxt1(AVCodecContext *avctx)
115
+{
116
+    DXVContext *ctx = avctx->priv_data;
117
+    GetByteContext *gbc = &ctx->gbc;
118
+    uint32_t value, prev, op;
119
+    int idx = 0, state = 0;
120
+    int pos = 2;
121
+
122
+    /* Copy the first two elements */
123
+    AV_WL32(ctx->tex_data, bytestream2_get_le32(gbc));
124
+    AV_WL32(ctx->tex_data + 4, bytestream2_get_le32(gbc));
125
+
126
+    /* Process input until the whole texture has been filled */
127
+    while (pos < ctx->tex_size / 4) {
128
+        CHECKPOINT(2);
129
+
130
+        /* Copy two elements from a previous offset or from the input buffer */
131
+        if (op) {
132
+            prev = AV_RL32(ctx->tex_data + 4 * (pos - idx));
133
+            AV_WL32(ctx->tex_data + 4 * pos, prev);
134
+            pos++;
135
+
136
+            prev = AV_RL32(ctx->tex_data + 4 * (pos - idx));
137
+            AV_WL32(ctx->tex_data + 4 * pos, prev);
138
+            pos++;
139
+        } else {
140
+            CHECKPOINT(2);
141
+
142
+            if (op)
143
+                prev = AV_RL32(ctx->tex_data + 4 * (pos - idx));
144
+            else
145
+                prev = bytestream2_get_le32(gbc);
146
+            AV_WL32(ctx->tex_data + 4 * pos, prev);
147
+            pos++;
148
+
149
+            CHECKPOINT(2);
150
+
151
+            if (op)
152
+                prev = AV_RL32(ctx->tex_data + 4 * (pos - idx));
153
+            else
154
+                prev = bytestream2_get_le32(gbc);
155
+            AV_WL32(ctx->tex_data + 4 * pos, prev);
156
+            pos++;
157
+        }
158
+    }
159
+
160
+    return 0;
161
+}
162
+
163
+static int dxv_decompress_dxt5(AVCodecContext *avctx)
164
+{
165
+    DXVContext *ctx = avctx->priv_data;
166
+    GetByteContext *gbc = &ctx->gbc;
167
+    uint32_t value, op;
168
+    int idx, prev, state = 0;
169
+    int pos = 4;
170
+    int run = 0;
171
+    int probe, check;
172
+
173
+    /* Copy the first four elements */
174
+    AV_WL32(ctx->tex_data +  0, bytestream2_get_le32(gbc));
175
+    AV_WL32(ctx->tex_data +  4, bytestream2_get_le32(gbc));
176
+    AV_WL32(ctx->tex_data +  8, bytestream2_get_le32(gbc));
177
+    AV_WL32(ctx->tex_data + 12, bytestream2_get_le32(gbc));
178
+
179
+    /* Process input until the whole texture has been filled */
180
+    while (pos < ctx->tex_size / 4) {
181
+        if (run) {
182
+            run--;
183
+
184
+            prev = AV_RL32(ctx->tex_data + 4 * (pos - 4));
185
+            AV_WL32(ctx->tex_data + 4 * pos, prev);
186
+            pos++;
187
+            prev = AV_RL32(ctx->tex_data + 4 * (pos - 4));
188
+            AV_WL32(ctx->tex_data + 4 * pos, prev);
189
+            pos++;
190
+        } else {
191
+            if (state == 0) {
192
+                value = bytestream2_get_le32(gbc);
193
+                state = 16;
194
+            }
195
+            op = value & 0x3;
196
+            value >>= 2;
197
+            state--;
198
+
199
+            switch (op) {
200
+            case 0:
201
+                /* Long copy */
202
+                check = bytestream2_get_byte(gbc) + 1;
203
+                if (check == 256) {
204
+                    do {
205
+                        probe = bytestream2_get_le16(gbc);
206
+                        check += probe;
207
+                    } while (probe == 0xFFFF);
208
+                }
209
+                while (check && pos < ctx->tex_size / 4) {
210
+                    prev = AV_RL32(ctx->tex_data + 4 * (pos - 4));
211
+                    AV_WL32(ctx->tex_data + 4 * pos, prev);
212
+                    pos++;
213
+
214
+                    prev = AV_RL32(ctx->tex_data + 4 * (pos - 4));
215
+                    AV_WL32(ctx->tex_data + 4 * pos, prev);
216
+                    pos++;
217
+
218
+                    prev = AV_RL32(ctx->tex_data + 4 * (pos - 4));
219
+                    AV_WL32(ctx->tex_data + 4 * pos, prev);
220
+                    pos++;
221
+
222
+                    prev = AV_RL32(ctx->tex_data + 4 * (pos - 4));
223
+                    AV_WL32(ctx->tex_data + 4 * pos, prev);
224
+                    pos++;
225
+
226
+                    check--;
227
+                }
228
+
229
+                /* Restart (or exit) the loop */
230
+                continue;
231
+                break;
232
+            case 1:
233
+                /* Load new run value */
234
+                run = bytestream2_get_byte(gbc);
235
+                if (run == 255) {
236
+                    do {
237
+                        probe = bytestream2_get_le16(gbc);
238
+                        run += probe;
239
+                    } while (probe == 0xFFFF);
240
+                }
241
+
242
+                /* Copy two dwords from previous data */
243
+                prev = AV_RL32(ctx->tex_data + 4 * (pos - 4));
244
+                AV_WL32(ctx->tex_data + 4 * pos, prev);
245
+                pos++;
246
+
247
+                prev = AV_RL32(ctx->tex_data + 4 * (pos - 4));
248
+                AV_WL32(ctx->tex_data + 4 * pos, prev);
249
+                pos++;
250
+                break;
251
+            case 2:
252
+                /* Copy two dwords from a previous index */
253
+                idx = 8 + bytestream2_get_le16(gbc);
254
+                prev = AV_RL32(ctx->tex_data + 4 * (pos - idx));
255
+                AV_WL32(ctx->tex_data + 4 * pos, prev);
256
+                pos++;
257
+
258
+                prev = AV_RL32(ctx->tex_data + 4 * (pos - idx));
259
+                AV_WL32(ctx->tex_data + 4 * pos, prev);
260
+                pos++;
261
+                break;
262
+            case 3:
263
+                /* Copy two dwords from input */
264
+                prev = bytestream2_get_le32(gbc);
265
+                AV_WL32(ctx->tex_data + 4 * pos, prev);
266
+                pos++;
267
+
268
+                prev = bytestream2_get_le32(gbc);
269
+                AV_WL32(ctx->tex_data + 4 * pos, prev);
270
+                pos++;
271
+                break;
272
+            }
273
+        }
274
+
275
+        CHECKPOINT(4);
276
+
277
+        /* Copy two elements from a previous offset or from the input buffer */
278
+        if (op) {
279
+            prev = AV_RL32(ctx->tex_data + 4 * (pos - idx));
280
+            AV_WL32(ctx->tex_data + 4 * pos, prev);
281
+            pos++;
282
+
283
+            prev = AV_RL32(ctx->tex_data + 4 * (pos - idx));
284
+            AV_WL32(ctx->tex_data + 4 * pos, prev);
285
+            pos++;
286
+        } else {
287
+            CHECKPOINT(4);
288
+
289
+            if (op)
290
+                prev = AV_RL32(ctx->tex_data + 4 * (pos - idx));
291
+            else
292
+                prev = bytestream2_get_le32(gbc);
293
+            AV_WL32(ctx->tex_data + 4 * pos, prev);
294
+            pos++;
295
+
296
+            CHECKPOINT(4);
297
+
298
+            if (op)
299
+                prev = AV_RL32(ctx->tex_data + 4 * (pos - idx));
300
+            else
301
+                prev = bytestream2_get_le32(gbc);
302
+            AV_WL32(ctx->tex_data + 4 * pos, prev);
303
+            pos++;
304
+        }
305
+    }
306
+
307
+    return 0;
308
+}
309
+
310
+static int dxv_decompress_lzf(AVCodecContext *avctx)
311
+{
312
+    DXVContext *ctx = avctx->priv_data;
313
+    return ff_lzf_uncompress(&ctx->gbc, &ctx->tex_data, &ctx->tex_size);
314
+}
315
+
316
+static int dxv_decode(AVCodecContext *avctx, void *data,
317
+                      int *got_frame, AVPacket *avpkt)
318
+{
319
+    DXVContext *ctx = avctx->priv_data;
320
+    ThreadFrame tframe;
321
+    GetByteContext *gbc = &ctx->gbc;
322
+    int (*decompress_tex)(AVCodecContext *avctx);
323
+    uint32_t tag;
324
+    int channels, size = 0, old_type = 0;
325
+    int ret;
326
+
327
+    bytestream2_init(gbc, avpkt->data, avpkt->size);
328
+
329
+    tag = bytestream2_get_le32(gbc);
330
+    switch (tag) {
331
+    case MKBETAG('D', 'X', 'T', '1'):
332
+        decompress_tex = dxv_decompress_dxt1;
333
+        ctx->tex_funct = ctx->texdsp.dxt1_block;
334
+        ctx->tex_rat   = 8;
335
+        ctx->tex_step  = 8;
336
+        av_log(avctx, AV_LOG_DEBUG, "DXTR1 compression and DXT1 texture ");
337
+        break;
338
+    case MKBETAG('D', 'X', 'T', '5'):
339
+        decompress_tex = dxv_decompress_dxt5;
340
+        ctx->tex_funct = ctx->texdsp.dxt5_block;
341
+        ctx->tex_rat   = 4;
342
+        ctx->tex_step  = 16;
343
+        av_log(avctx, AV_LOG_DEBUG, "DXTR5 compression and DXT5 texture ");
344
+        break;
345
+    case MKBETAG('Y', 'C', 'G', '6'):
346
+    case MKBETAG('Y', 'G', '1', '0'):
347
+        avpriv_report_missing_feature(avctx, "Tag 0x%08X", tag);
348
+        return AVERROR_PATCHWELCOME;
349
+    default:
350
+        /* Old version does not have a real header, just size and type. */
351
+        size = tag & 0x00FFFFFF;
352
+        old_type = tag >> 24;
353
+        channels = old_type & 0x0F;
354
+        if (old_type & 0x40) {
355
+            av_log(avctx, AV_LOG_DEBUG, "LZF compression and DXT5 texture ");
356
+            ctx->tex_funct = ctx->texdsp.dxt5_block;
357
+            ctx->tex_step  = 16;
358
+        } else if (old_type & 0x20) {
359
+            av_log(avctx, AV_LOG_DEBUG, "LZF compression and DXT1 texture ");
360
+            ctx->tex_funct = ctx->texdsp.dxt1_block;
361
+            ctx->tex_step  = 8;
362
+        } else {
363
+            av_log(avctx, AV_LOG_ERROR, "Unsupported header (0x%08X)\n.", tag);
364
+            return AVERROR_INVALIDDATA;
365
+        }
366
+        decompress_tex = dxv_decompress_lzf;
367
+        ctx->tex_rat = 1;
368
+        break;
369
+    }
370
+
371
+    /* New header is 12 bytes long. */
372
+    if (!old_type) {
373
+        channels = bytestream2_get_byte(gbc);
374
+        bytestream2_skip(gbc, 3); // unknown
375
+        size = bytestream2_get_le32(gbc);
376
+    }
377
+    av_log(avctx, AV_LOG_DEBUG, "(%d channels)\n", channels);
378
+
379
+    if (size != bytestream2_get_bytes_left(gbc)) {
380
+        av_log(avctx, AV_LOG_ERROR, "Incomplete or invalid file (%u > %u)\n.",
381
+               size, bytestream2_get_bytes_left(gbc));
382
+        return AVERROR_INVALIDDATA;
383
+    }
384
+
385
+    ctx->tex_size = avctx->coded_width * avctx->coded_height * 4 / ctx->tex_rat;
386
+    ret = av_reallocp(&ctx->tex_data, ctx->tex_size);
387
+    if (ret < 0)
388
+        return ret;
389
+
390
+    /* Decompress texture out of the intermediate compression. */
391
+    ret = decompress_tex(avctx);
392
+    if (ret < 0)
393
+        return ret;
394
+
395
+    tframe.f = data;
396
+    ret = ff_thread_get_buffer(avctx, &tframe, 0);
397
+    if (ret < 0)
398
+        return ret;
399
+    ff_thread_finish_setup(avctx);
400
+
401
+    /* Now decompress the texture with the standard functions. */
402
+    avctx->execute2(avctx, decompress_texture_thread,
403
+                    tframe.f, NULL, ctx->slice_count);
404
+
405
+    /* Frame is ready to be output. */
406
+    tframe.f->pict_type = AV_PICTURE_TYPE_I;
407
+    tframe.f->key_frame = 1;
408
+    *got_frame = 1;
409
+
410
+    return avpkt->size;
411
+}
412
+
413
+static int dxv_init(AVCodecContext *avctx)
414
+{
415
+    DXVContext *ctx = avctx->priv_data;
416
+    int ret = av_image_check_size(avctx->width, avctx->height, 0, avctx);
417
+
418
+    if (ret < 0) {
419
+        av_log(avctx, AV_LOG_ERROR, "Invalid image size %dx%d.\n",
420
+               avctx->width, avctx->height);
421
+        return ret;
422
+    }
423
+
424
+    /* Codec requires 16x16 alignment. */
425
+    avctx->coded_width  = FFALIGN(avctx->width,  16);
426
+    avctx->coded_height = FFALIGN(avctx->height, 16);
427
+
428
+    ff_texturedsp_init(&ctx->texdsp);
429
+    avctx->pix_fmt = AV_PIX_FMT_RGBA;
430
+
431
+    ctx->slice_count = av_clip(avctx->thread_count, 1,
432
+                               avctx->coded_height / TEXTURE_BLOCK_H);
433
+
434
+    return 0;
435
+}
436
+
437
+static int dxv_close(AVCodecContext *avctx)
438
+{
439
+    DXVContext *ctx = avctx->priv_data;
440
+
441
+    av_freep(&ctx->tex_data);
442
+
443
+    return 0;
444
+}
445
+
446
+AVCodec ff_dxv_decoder = {
447
+    .name           = "dxv",
448
+    .long_name      = NULL_IF_CONFIG_SMALL("Resolume DXV"),
449
+    .type           = AVMEDIA_TYPE_VIDEO,
450
+    .id             = AV_CODEC_ID_DXV,
451
+    .init           = dxv_init,
452
+    .decode         = dxv_decode,
453
+    .close          = dxv_close,
454
+    .priv_data_size = sizeof(DXVContext),
455
+    .capabilities   = AV_CODEC_CAP_DR1 |
456
+                      AV_CODEC_CAP_SLICE_THREADS |
457
+                      AV_CODEC_CAP_FRAME_THREADS,
458
+    .caps_internal  = FF_CODEC_CAP_INIT_THREADSAFE |
459
+                      FF_CODEC_CAP_INIT_CLEANUP,
460
+};
... ...
@@ -1227,9 +1227,9 @@ int attribute_align_arg avcodec_open2(AVCodecContext *avctx, const AVCodec *code
1227 1227
         goto free_and_end;
1228 1228
     }
1229 1229
 
1230
-    // only call ff_set_dimensions() for non H.264/VP6F codecs so as not to overwrite previously setup dimensions
1230
+    // only call ff_set_dimensions() for non H.264/VP6F/DXV codecs so as not to overwrite previously setup dimensions
1231 1231
     if (!(avctx->coded_width && avctx->coded_height && avctx->width && avctx->height &&
1232
-          (avctx->codec_id == AV_CODEC_ID_H264 || avctx->codec_id == AV_CODEC_ID_VP6F))) {
1232
+          (avctx->codec_id == AV_CODEC_ID_H264 || avctx->codec_id == AV_CODEC_ID_VP6F || avctx->codec_id == AV_CODEC_ID_DXV))) {
1233 1233
     if (avctx->coded_width && avctx->coded_height)
1234 1234
         ret = ff_set_dimensions(avctx, avctx->coded_width, avctx->coded_height);
1235 1235
     else if (avctx->width && avctx->height)
... ...
@@ -29,7 +29,7 @@
29 29
 #include "libavutil/version.h"
30 30
 
31 31
 #define LIBAVCODEC_VERSION_MAJOR  57
32
-#define LIBAVCODEC_VERSION_MINOR   0
32
+#define LIBAVCODEC_VERSION_MINOR   1
33 33
 #define LIBAVCODEC_VERSION_MICRO 100
34 34
 
35 35
 #define LIBAVCODEC_VERSION_INT  AV_VERSION_INT(LIBAVCODEC_VERSION_MAJOR, \
... ...
@@ -262,6 +262,9 @@ const AVCodecTag ff_codec_movvideo_tags[] = {
262 262
     { AV_CODEC_ID_HAP, MKTAG('H', 'a', 'p', '5') },
263 263
     { AV_CODEC_ID_HAP, MKTAG('H', 'a', 'p', 'Y') },
264 264
 
265
+    { AV_CODEC_ID_DXV, MKTAG('D', 'X', 'D', '3') },
266
+    { AV_CODEC_ID_DXV, MKTAG('D', 'X', 'D', 'I') },
267
+
265 268
     { AV_CODEC_ID_NONE, 0 },
266 269
 };
267 270
 
... ...
@@ -144,6 +144,21 @@ fate-dxa-scummvm: CMD = framecrc -i $(TARGET_SAMPLES)/dxa/scummvm.dxa -pix_fmt r
144 144
 FATE_VIDEO-$(call DEMDEC, DXA, DXA) += $(FATE_DXA)
145 145
 fate-dxa: $(FATE_DXA)
146 146
 
147
+FATE_DXV += fate-dxv-dxt1
148
+fate-dxv-dxt1: CMD = framecrc -i $(TARGET_SAMPLES)/dxv/dxv-na.mov
149
+
150
+FATE_DXV += fate-dxv-dxt5
151
+fate-dxv-dxt5: CMD = framecrc -i $(TARGET_SAMPLES)/dxv/dxv-wa.mov
152
+
153
+FATE_DXV += fate-dxv3-dxt1
154
+fate-dxv3-dxt1: CMD = framecrc -i $(TARGET_SAMPLES)/dxv/dxv3-nqna.mov
155
+
156
+FATE_DXV += fate-dxv3-dxt5
157
+fate-dxv3-dxt5: CMD = framecrc -i $(TARGET_SAMPLES)/dxv/dxv3-nqwa.mov
158
+
159
+FATE_VIDEO-$(call DEMDEC, MOV, DXV) += $(FATE_DXV)
160
+fate-dxv: $(FATE_DXV)
161
+
147 162
 FATE_VIDEO-$(call DEMDEC, SEGAFILM, CINEPAK) += fate-film-cvid
148 163
 fate-film-cvid: CMD = framecrc -i $(TARGET_SAMPLES)/film/logo-capcom.cpk -an
149 164
 
150 165
new file mode 100644
... ...
@@ -0,0 +1,2 @@
0
+#tb 0: 1001/30000
1
+0,          0,          0,        1,  8294400, 0x0797cd53
0 2
new file mode 100644
... ...
@@ -0,0 +1,2 @@
0
+#tb 0: 1001/30000
1
+0,          0,          0,        1,  8294400, 0x0797cd53
0 2
new file mode 100644
... ...
@@ -0,0 +1,2 @@
0
+#tb 0: 1001/30000
1
+0,          0,          0,        1,  8294400, 0x98bbcc85
0 2
new file mode 100644
... ...
@@ -0,0 +1,2 @@
0
+#tb 0: 1001/30000
1
+0,          0,          0,        1,  8294400, 0x0797cd53