annotate smacker.c @ 3995:b00c06477dff libavcodec

write cabac low and range variables as early as possible to prevent stalls from reading them before they where written, the P4 is said to disslike that alot, on P3 its 2% faster (START/STOP_TIMER over decode_residual)
author michael
date Wed, 11 Oct 2006 16:11:41 +0000
parents c8c591fe26f8
children d6f83e2f8804
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
1 /*
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
2 * Smacker decoder
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
3 * Copyright (c) 2006 Konstantin Shishkov
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
4 *
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3800
diff changeset
5 * This file is part of FFmpeg.
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3800
diff changeset
6 *
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3800
diff changeset
7 * FFmpeg is free software; you can redistribute it and/or
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
8 * modify it under the terms of the GNU Lesser General Public
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
9 * License as published by the Free Software Foundation; either
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3800
diff changeset
10 * version 2.1 of the License, or (at your option) any later version.
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
11 *
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3800
diff changeset
12 * FFmpeg is distributed in the hope that it will be useful,
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
15 * Lesser General Public License for more details.
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
16 *
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
17 * You should have received a copy of the GNU Lesser General Public
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3800
diff changeset
18 * License along with FFmpeg; if not, write to the Free Software
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
20 *
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
21 */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
22
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
23 /**
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
24 * @file smacker.c
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
25 * Smacker decoder
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
26 */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
27
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
28 /*
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
29 * Based on http://wiki.multimedia.cx/index.php?title=Smacker
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
30 */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
31
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
32 #include <stdio.h>
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
33 #include <stdlib.h>
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
34
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
35 #include "common.h"
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
36 #include "avcodec.h"
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
37
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
38 #define ALT_BITSTREAM_READER_LE
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
39 #include "bitstream.h"
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
40
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
41 #define SMKTREE_BITS 9
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
42 #define SMK_NODE 0x80000000
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
43
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
44 /*
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
45 * Decoder context
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
46 */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
47 typedef struct SmackVContext {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
48 AVCodecContext *avctx;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
49 AVFrame pic;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
50
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
51 int *mmap_tbl, *mclr_tbl, *full_tbl, *type_tbl;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
52 int mmap_last[3], mclr_last[3], full_last[3], type_last[3];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
53 } SmackVContext;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
54
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
55 /**
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
56 * Context used for code reconstructing
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
57 */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
58 typedef struct HuffContext {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
59 int length;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
60 int maxlength;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
61 int current;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
62 uint32_t *bits;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
63 int *lengths;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
64 int *values;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
65 } HuffContext;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
66
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
67 /* common parameters used for decode_bigtree */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
68 typedef struct DBCtx {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
69 VLC *v1, *v2;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
70 int *recode1, *recode2;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
71 int escapes[3];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
72 int *last;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
73 int lcur;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
74 } DBCtx;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
75
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
76 /* possible runs of blocks */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
77 static const int block_runs[64] = {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
78 1, 2, 3, 4, 5, 6, 7, 8,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
79 9, 10, 11, 12, 13, 14, 15, 16,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
80 17, 18, 19, 20, 21, 22, 23, 24,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
81 25, 26, 27, 28, 29, 30, 31, 32,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
82 33, 34, 35, 36, 37, 38, 39, 40,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
83 41, 42, 43, 44, 45, 46, 47, 48,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
84 49, 50, 51, 52, 53, 54, 55, 56,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
85 57, 58, 59, 128, 256, 512, 1024, 2048 };
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
86
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
87 enum SmkBlockTypes {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
88 SMK_BLK_MONO = 0,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
89 SMK_BLK_FULL = 1,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
90 SMK_BLK_SKIP = 2,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
91 SMK_BLK_FILL = 3 };
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
92
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
93 /**
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
94 * Decode local frame tree
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
95 */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
96 static int smacker_decode_tree(GetBitContext *gb, HuffContext *hc, uint32_t prefix, int length)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
97 {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
98 if(!get_bits1(gb)){ //Leaf
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
99 if(hc->current >= 256){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
100 av_log(NULL, AV_LOG_ERROR, "Tree size exceeded!\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
101 return -1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
102 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
103 if(length){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
104 hc->bits[hc->current] = prefix;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
105 hc->lengths[hc->current] = length;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
106 } else {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
107 hc->bits[hc->current] = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
108 hc->lengths[hc->current] = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
109 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
110 hc->values[hc->current] = get_bits(gb, 8);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
111 hc->current++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
112 if(hc->maxlength < length)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
113 hc->maxlength = length;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
114 return 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
115 } else { //Node
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
116 int r;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
117 length++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
118 r = smacker_decode_tree(gb, hc, prefix, length);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
119 if(r)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
120 return r;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
121 return smacker_decode_tree(gb, hc, prefix | (1 << (length - 1)), length);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
122 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
123 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
124
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
125 /**
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
126 * Decode header tree
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
127 */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
128 static int smacker_decode_bigtree(GetBitContext *gb, HuffContext *hc, DBCtx *ctx)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
129 {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
130 if(!get_bits1(gb)){ //Leaf
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
131 int val, i1, i2, b1, b2;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
132 if(hc->current >= hc->length){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
133 av_log(NULL, AV_LOG_ERROR, "Tree size exceeded!\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
134 return -1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
135 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
136 b1 = get_bits_count(gb);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
137 i1 = get_vlc2(gb, ctx->v1->table, SMKTREE_BITS, 3);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
138 b1 = get_bits_count(gb) - b1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
139 b2 = get_bits_count(gb);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
140 i2 = get_vlc2(gb, ctx->v2->table, SMKTREE_BITS, 3);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
141 b2 = get_bits_count(gb) - b2;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
142 val = ctx->recode1[i1] | (ctx->recode2[i2] << 8);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
143 if(val == ctx->escapes[0]) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
144 ctx->last[0] = hc->current;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
145 val = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
146 } else if(val == ctx->escapes[1]) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
147 ctx->last[1] = hc->current;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
148 val = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
149 } else if(val == ctx->escapes[2]) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
150 ctx->last[2] = hc->current;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
151 val = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
152 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
153
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
154 hc->values[hc->current++] = val;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
155 return 1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
156 } else { //Node
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
157 int r = 0, t;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
158
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
159 t = hc->current++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
160 r = smacker_decode_bigtree(gb, hc, ctx);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
161 if(r < 0)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
162 return r;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
163 hc->values[t] = SMK_NODE | r;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
164 r++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
165 r += smacker_decode_bigtree(gb, hc, ctx);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
166 return r;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
167 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
168 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
169
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
170 /**
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
171 * Store large tree as FFmpeg's vlc codes
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
172 */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
173 static int smacker_decode_header_tree(SmackVContext *smk, GetBitContext *gb, int **recodes, int *last, int size)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
174 {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
175 int res;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
176 HuffContext huff;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
177 HuffContext tmp1, tmp2;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
178 VLC vlc[2];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
179 int escapes[3];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
180 DBCtx ctx;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
181
3303
68721b62a528 sanity checks, some might have been exploitable ...
michael
parents: 3220
diff changeset
182 if(size >= UINT_MAX>>4){ // (((size + 3) >> 2) + 3) << 2 must not overflow
68721b62a528 sanity checks, some might have been exploitable ...
michael
parents: 3220
diff changeset
183 av_log(smk->avctx, AV_LOG_ERROR, "size too large\n");
68721b62a528 sanity checks, some might have been exploitable ...
michael
parents: 3220
diff changeset
184 return -1;
68721b62a528 sanity checks, some might have been exploitable ...
michael
parents: 3220
diff changeset
185 }
68721b62a528 sanity checks, some might have been exploitable ...
michael
parents: 3220
diff changeset
186
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
187 tmp1.length = 256;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
188 tmp1.maxlength = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
189 tmp1.current = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
190 tmp1.bits = av_mallocz(256 * 4);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
191 tmp1.lengths = av_mallocz(256 * sizeof(int));
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
192 tmp1.values = av_mallocz(256 * sizeof(int));
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
193
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
194 tmp2.length = 256;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
195 tmp2.maxlength = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
196 tmp2.current = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
197 tmp2.bits = av_mallocz(256 * 4);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
198 tmp2.lengths = av_mallocz(256 * sizeof(int));
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
199 tmp2.values = av_mallocz(256 * sizeof(int));
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
200
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
201 memset(&vlc[0], 0, sizeof(VLC));
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
202 memset(&vlc[1], 0, sizeof(VLC));
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
203
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
204 if(get_bits1(gb)) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
205 smacker_decode_tree(gb, &tmp1, 0, 0);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
206 get_bits1(gb);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
207 res = init_vlc(&vlc[0], SMKTREE_BITS, tmp1.length,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
208 tmp1.lengths, sizeof(int), sizeof(int),
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
209 tmp1.bits, sizeof(uint32_t), sizeof(uint32_t), INIT_VLC_LE);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
210 if(res < 0) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
211 av_log(smk->avctx, AV_LOG_ERROR, "Cannot build VLC table\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
212 return -1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
213 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
214 } else {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
215 av_log(smk->avctx, AV_LOG_ERROR, "Skipping low bytes tree\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
216 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
217 if(get_bits1(gb)){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
218 smacker_decode_tree(gb, &tmp2, 0, 0);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
219 get_bits1(gb);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
220 res = init_vlc(&vlc[1], SMKTREE_BITS, tmp2.length,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
221 tmp2.lengths, sizeof(int), sizeof(int),
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
222 tmp2.bits, sizeof(uint32_t), sizeof(uint32_t), INIT_VLC_LE);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
223 if(res < 0) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
224 av_log(smk->avctx, AV_LOG_ERROR, "Cannot build VLC table\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
225 return -1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
226 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
227 } else {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
228 av_log(smk->avctx, AV_LOG_ERROR, "Skipping high bytes tree\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
229 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
230
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
231 escapes[0] = get_bits(gb, 8);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
232 escapes[0] |= get_bits(gb, 8) << 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
233 escapes[1] = get_bits(gb, 8);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
234 escapes[1] |= get_bits(gb, 8) << 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
235 escapes[2] = get_bits(gb, 8);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
236 escapes[2] |= get_bits(gb, 8) << 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
237
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
238 last[0] = last[1] = last[2] = -1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
239
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
240 ctx.escapes[0] = escapes[0];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
241 ctx.escapes[1] = escapes[1];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
242 ctx.escapes[2] = escapes[2];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
243 ctx.v1 = &vlc[0];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
244 ctx.v2 = &vlc[1];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
245 ctx.recode1 = tmp1.values;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
246 ctx.recode2 = tmp2.values;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
247 ctx.last = last;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
248
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
249 huff.length = ((size + 3) >> 2) + 3;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
250 huff.maxlength = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
251 huff.current = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
252 huff.values = av_mallocz(huff.length * sizeof(int));
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
253
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
254 smacker_decode_bigtree(gb, &huff, &ctx);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
255 get_bits1(gb);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
256 if(ctx.last[0] == -1) ctx.last[0] = huff.current++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
257 if(ctx.last[1] == -1) ctx.last[1] = huff.current++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
258 if(ctx.last[2] == -1) ctx.last[2] = huff.current++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
259
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
260 *recodes = huff.values;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
261
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
262 if(vlc[0].table)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
263 free_vlc(&vlc[0]);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
264 if(vlc[1].table)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
265 free_vlc(&vlc[1]);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
266 av_free(tmp1.bits);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
267 av_free(tmp1.lengths);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
268 av_free(tmp1.values);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
269 av_free(tmp2.bits);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
270 av_free(tmp2.lengths);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
271 av_free(tmp2.values);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
272
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
273 return 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
274 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
275
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
276 static int decode_header_trees(SmackVContext *smk) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
277 GetBitContext gb;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
278 int mmap_size, mclr_size, full_size, type_size;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
279
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
280 mmap_size = LE_32(smk->avctx->extradata);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
281 mclr_size = LE_32(smk->avctx->extradata + 4);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
282 full_size = LE_32(smk->avctx->extradata + 8);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
283 type_size = LE_32(smk->avctx->extradata + 12);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
284
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
285 init_get_bits(&gb, smk->avctx->extradata + 16, (smk->avctx->extradata_size - 16) * 8);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
286
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
287 if(!get_bits1(&gb)) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
288 av_log(smk->avctx, AV_LOG_INFO, "Skipping MMAP tree\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
289 smk->mmap_tbl = av_malloc(sizeof(int) * 2);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
290 smk->mmap_tbl[0] = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
291 smk->mmap_last[0] = smk->mmap_last[1] = smk->mmap_last[2] = 1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
292 } else {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
293 smacker_decode_header_tree(smk, &gb, &smk->mmap_tbl, smk->mmap_last, mmap_size);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
294 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
295 if(!get_bits(&gb, 1)) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
296 av_log(smk->avctx, AV_LOG_INFO, "Skipping MCLR tree\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
297 smk->mclr_tbl = av_malloc(sizeof(int) * 2);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
298 smk->mclr_tbl[0] = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
299 smk->mclr_last[0] = smk->mclr_last[1] = smk->mclr_last[2] = 1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
300 } else {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
301 smacker_decode_header_tree(smk, &gb, &smk->mclr_tbl, smk->mclr_last, mclr_size);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
302 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
303 if(!get_bits(&gb, 1)) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
304 av_log(smk->avctx, AV_LOG_INFO, "Skipping FULL tree\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
305 smk->full_tbl = av_malloc(sizeof(int) * 2);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
306 smk->full_tbl[0] = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
307 smk->full_last[0] = smk->full_last[1] = smk->full_last[2] = 1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
308 } else {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
309 smacker_decode_header_tree(smk, &gb, &smk->full_tbl, smk->full_last, full_size);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
310 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
311 if(!get_bits(&gb, 1)) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
312 av_log(smk->avctx, AV_LOG_INFO, "Skipping TYPE tree\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
313 smk->type_tbl = av_malloc(sizeof(int) * 2);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
314 smk->type_tbl[0] = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
315 smk->type_last[0] = smk->type_last[1] = smk->type_last[2] = 1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
316 } else {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
317 smacker_decode_header_tree(smk, &gb, &smk->type_tbl, smk->type_last, type_size);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
318 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
319
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
320 return 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
321 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
322
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
323 static always_inline void last_reset(int *recode, int *last) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
324 recode[last[0]] = recode[last[1]] = recode[last[2]] = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
325 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
326
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
327 /* get code and update history */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
328 static always_inline int smk_get_code(GetBitContext *gb, int *recode, int *last) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
329 register int *table = recode;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
330 int v, b;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
331
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
332 b = get_bits_count(gb);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
333 while(*table & SMK_NODE) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
334 if(get_bits1(gb))
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
335 table += (*table) & (~SMK_NODE);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
336 table++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
337 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
338 v = *table;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
339 b = get_bits_count(gb) - b;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
340
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
341 if(v != recode[last[0]]) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
342 recode[last[2]] = recode[last[1]];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
343 recode[last[1]] = recode[last[0]];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
344 recode[last[0]] = v;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
345 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
346 return v;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
347 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
348
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
349 static int decode_frame(AVCodecContext *avctx, void *data, int *data_size, uint8_t *buf, int buf_size)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
350 {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
351 SmackVContext * const smk = (SmackVContext *)avctx->priv_data;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
352 uint8_t *out;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
353 uint32_t *pal;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
354 GetBitContext gb;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
355 int blocks, blk, bw, bh;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
356 int i;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
357 int stride;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
358
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
359 if(buf_size == 769)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
360 return 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
361 if(smk->pic.data[0])
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
362 avctx->release_buffer(avctx, &smk->pic);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
363
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
364 smk->pic.reference = 1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
365 smk->pic.buffer_hints = FF_BUFFER_HINTS_VALID | FF_BUFFER_HINTS_PRESERVE | FF_BUFFER_HINTS_REUSABLE;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
366 if(avctx->reget_buffer(avctx, &smk->pic) < 0){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
367 av_log(avctx, AV_LOG_ERROR, "get_buffer() failed\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
368 return -1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
369 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
370
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
371 /* make the palette available on the way out */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
372 out = buf + 1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
373 pal = (uint32_t*)smk->pic.data[1];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
374 smk->pic.palette_has_changed = buf[0] & 1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
375 smk->pic.key_frame = !!(buf[0] & 2);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
376 if(smk->pic.key_frame)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
377 smk->pic.pict_type = FF_I_TYPE;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
378 else
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
379 smk->pic.pict_type = FF_P_TYPE;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
380
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
381 for(i = 0; i < 256; i++) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
382 int r, g, b;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
383 r = *out++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
384 g = *out++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
385 b = *out++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
386 *pal++ = (r << 16) | (g << 8) | b;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
387 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
388
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
389 last_reset(smk->mmap_tbl, smk->mmap_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
390 last_reset(smk->mclr_tbl, smk->mclr_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
391 last_reset(smk->full_tbl, smk->full_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
392 last_reset(smk->type_tbl, smk->type_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
393 init_get_bits(&gb, buf + 769, (buf_size - 769) * 8);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
394
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
395 blk = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
396 bw = avctx->width >> 2;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
397 bh = avctx->height >> 2;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
398 blocks = bw * bh;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
399 out = smk->pic.data[0];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
400 stride = smk->pic.linesize[0];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
401 while(blk < blocks) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
402 int type, run, mode;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
403 uint16_t pix;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
404
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
405 type = smk_get_code(&gb, smk->type_tbl, smk->type_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
406 run = block_runs[(type >> 2) & 0x3F];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
407 switch(type & 3){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
408 case SMK_BLK_MONO:
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
409 while(run-- && blk < blocks){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
410 int clr, map;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
411 int hi, lo;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
412 clr = smk_get_code(&gb, smk->mclr_tbl, smk->mclr_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
413 map = smk_get_code(&gb, smk->mmap_tbl, smk->mmap_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
414 out = smk->pic.data[0] + (blk / bw) * (stride * 4) + (blk % bw) * 4;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
415 hi = clr >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
416 lo = clr & 0xFF;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
417 for(i = 0; i < 4; i++) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
418 if(map & 1) out[0] = hi; else out[0] = lo;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
419 if(map & 2) out[1] = hi; else out[1] = lo;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
420 if(map & 4) out[2] = hi; else out[2] = lo;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
421 if(map & 8) out[3] = hi; else out[3] = lo;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
422 map >>= 4;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
423 out += stride;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
424 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
425 blk++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
426 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
427 break;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
428 case SMK_BLK_FULL:
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
429 mode = 0;
3310
48fc664f7348 Now MPlayer should understand Smacker audio and video codecs.
kostya
parents: 3303
diff changeset
430 if(avctx->codec_tag == MKTAG('S', 'M', 'K', '4')) { // In case of Smacker v4 we have three modes
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
431 if(get_bits1(&gb)) mode = 1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
432 else if(get_bits1(&gb)) mode = 2;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
433 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
434 while(run-- && blk < blocks){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
435 out = smk->pic.data[0] + (blk / bw) * (stride * 4) + (blk % bw) * 4;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
436 switch(mode){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
437 case 0:
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
438 for(i = 0; i < 4; i++) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
439 pix = smk_get_code(&gb, smk->full_tbl, smk->full_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
440 out[2] = pix & 0xFF;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
441 out[3] = pix >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
442 pix = smk_get_code(&gb, smk->full_tbl, smk->full_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
443 out[0] = pix & 0xFF;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
444 out[1] = pix >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
445 out += stride;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
446 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
447 break;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
448 case 1:
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
449 pix = smk_get_code(&gb, smk->full_tbl, smk->full_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
450 out[0] = out[1] = pix & 0xFF;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
451 out[2] = out[3] = pix >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
452 out += stride;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
453 out[0] = out[1] = pix & 0xFF;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
454 out[2] = out[3] = pix >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
455 out += stride;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
456 pix = smk_get_code(&gb, smk->full_tbl, smk->full_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
457 out[0] = out[1] = pix & 0xFF;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
458 out[2] = out[3] = pix >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
459 out += stride;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
460 out[0] = out[1] = pix & 0xFF;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
461 out[2] = out[3] = pix >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
462 out += stride;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
463 break;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
464 case 2:
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
465 for(i = 0; i < 2; i++) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
466 uint16_t pix1, pix2;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
467 pix1 = smk_get_code(&gb, smk->full_tbl, smk->full_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
468 pix2 = smk_get_code(&gb, smk->full_tbl, smk->full_last);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
469 out[0] = pix1 & 0xFF; out[1] = pix1 >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
470 out[2] = pix2 & 0xFF; out[3] = pix2 >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
471 out += stride;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
472 out[0] = pix1 & 0xFF; out[1] = pix1 >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
473 out[2] = pix2 & 0xFF; out[3] = pix2 >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
474 out += stride;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
475 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
476 break;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
477 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
478 blk++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
479 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
480 break;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
481 case SMK_BLK_SKIP:
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
482 while(run-- && blk < blocks)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
483 blk++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
484 break;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
485 case SMK_BLK_FILL:
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
486 mode = type >> 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
487 while(run-- && blk < blocks){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
488 uint32_t col;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
489 out = smk->pic.data[0] + (blk / bw) * (stride * 4) + (blk % bw) * 4;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
490 col = mode * 0x01010101;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
491 for(i = 0; i < 4; i++) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
492 *((uint32_t*)out) = col;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
493 out += stride;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
494 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
495 blk++;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
496 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
497 break;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
498 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
499
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
500 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
501
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
502 *data_size = sizeof(AVFrame);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
503 *(AVFrame*)data = smk->pic;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
504
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
505 /* always report that the buffer was completely consumed */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
506 return buf_size;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
507 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
508
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
509
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
510
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
511 /*
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
512 *
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
513 * Init smacker decoder
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
514 *
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
515 */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
516 static int decode_init(AVCodecContext *avctx)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
517 {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
518 SmackVContext * const c = (SmackVContext *)avctx->priv_data;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
519
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
520 c->avctx = avctx;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
521 avctx->has_b_frames = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
522
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
523 c->pic.data[0] = NULL;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
524
3800
9b75ab171fa9 1l: correct argument order in avcodec_check_dimensions
kostya
parents: 3694
diff changeset
525 if (avcodec_check_dimensions(avctx, avctx->width, avctx->height) < 0) {
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
526 return 1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
527 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
528
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
529 avctx->pix_fmt = PIX_FMT_PAL8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
530
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
531
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
532 /* decode huffman trees from extradata */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
533 if(avctx->extradata_size < 16){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
534 av_log(avctx, AV_LOG_ERROR, "Extradata missing!\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
535 return -1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
536 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
537
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
538 decode_header_trees(c);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
539
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
540
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
541 return 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
542 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
543
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
544
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
545
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
546 /*
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
547 *
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
548 * Uninit smacker decoder
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
549 *
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
550 */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
551 static int decode_end(AVCodecContext *avctx)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
552 {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
553 SmackVContext * const smk = (SmackVContext *)avctx->priv_data;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
554
3694
8765ee4eaa45 Drop unneeded checks before av_free() and change to av_freep() where it's more suitable.
kostya
parents: 3310
diff changeset
555 av_freep(&smk->mmap_tbl);
8765ee4eaa45 Drop unneeded checks before av_free() and change to av_freep() where it's more suitable.
kostya
parents: 3310
diff changeset
556 av_freep(&smk->mclr_tbl);
8765ee4eaa45 Drop unneeded checks before av_free() and change to av_freep() where it's more suitable.
kostya
parents: 3310
diff changeset
557 av_freep(&smk->full_tbl);
8765ee4eaa45 Drop unneeded checks before av_free() and change to av_freep() where it's more suitable.
kostya
parents: 3310
diff changeset
558 av_freep(&smk->type_tbl);
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
559
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
560 if (smk->pic.data[0])
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
561 avctx->release_buffer(avctx, &smk->pic);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
562
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
563 return 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
564 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
565
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
566
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
567 static int smka_decode_init(AVCodecContext *avctx)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
568 {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
569 return 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
570 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
571
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
572 /**
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
573 * Decode Smacker audio data
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
574 */
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
575 static int smka_decode_frame(AVCodecContext *avctx, void *data, int *data_size, uint8_t *buf, int buf_size)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
576 {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
577 GetBitContext gb;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
578 HuffContext h[4];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
579 VLC vlc[4];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
580 int16_t *samples = data;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
581 int val;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
582 int i, res;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
583 int unp_size;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
584 int bits, stereo;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
585 int pred[2] = {0, 0};
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
586
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
587 unp_size = LE_32(buf);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
588
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
589 init_get_bits(&gb, buf + 4, (buf_size - 4) * 8);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
590
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
591 if(!get_bits1(&gb)){
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
592 av_log(avctx, AV_LOG_INFO, "Sound: no data\n");
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
593 *data_size = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
594 return 1;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
595 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
596 stereo = get_bits1(&gb);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
597 bits = get_bits1(&gb);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
598
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
599 memset(vlc, 0, sizeof(VLC) * 4);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
600 memset(h, 0, sizeof(HuffContext) * 4);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
601 // Initialize
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
602 for(i = 0; i < (1 << (bits + stereo)); i++) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
603 h[i].length = 256;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
604 h[i].maxlength = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
605 h[i].current = 0;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
606 h[i].bits = av_mallocz(256 * 4);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
607 h[i].lengths = av_mallocz(256 * sizeof(int));
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
608 h[i].values = av_mallocz(256 * sizeof(int));
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
609 get_bits1(&gb);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
610 smacker_decode_tree(&gb, &h[i], 0, 0);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
611 get_bits1(&gb);
3220
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
612 if(h[i].current > 1) {
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
613 res = init_vlc(&vlc[i], SMKTREE_BITS, h[i].length,
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
614 h[i].lengths, sizeof(int), sizeof(int),
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
615 h[i].bits, sizeof(uint32_t), sizeof(uint32_t), INIT_VLC_LE);
3220
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
616 if(res < 0) {
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
617 av_log(avctx, AV_LOG_ERROR, "Cannot build VLC table\n");
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
618 return -1;
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
619 }
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
620 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
621 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
622 if(bits) { //decode 16-bit data
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
623 pred[0] = get_bits(&gb, 8);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
624 pred[0] |= get_bits(&gb, 8);
3220
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
625 *samples++ = pred[0];
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
626 if(stereo) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
627 pred[1] = get_bits(&gb, 8);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
628 pred[1] |= get_bits(&gb, 8);
3220
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
629 *samples++ = pred[1];
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
630 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
631 for(i = 0; i < unp_size / 2; i++) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
632 if(i & stereo) {
3220
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
633 if(vlc[2].table)
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
634 res = get_vlc2(&gb, vlc[2].table, SMKTREE_BITS, 3);
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
635 else
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
636 res = 0;
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
637 val = h[2].values[res];
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
638 if(vlc[3].table)
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
639 res = get_vlc2(&gb, vlc[3].table, SMKTREE_BITS, 3);
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
640 else
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
641 res = 0;
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
642 val |= h[3].values[res] << 8;
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
643 pred[1] += (int16_t)val;
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
644 *samples++ = pred[1];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
645 } else {
3220
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
646 if(vlc[0].table)
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
647 res = get_vlc2(&gb, vlc[0].table, SMKTREE_BITS, 3);
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
648 else
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
649 res = 0;
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
650 val = h[0].values[res];
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
651 if(vlc[1].table)
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
652 res = get_vlc2(&gb, vlc[1].table, SMKTREE_BITS, 3);
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
653 else
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
654 res = 0;
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
655 val |= h[1].values[res] << 8;
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
656 pred[0] += val;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
657 *samples++ = pred[0];
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
658 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
659 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
660 } else { //8-bit data
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
661 pred[0] = get_bits(&gb, 8);
3220
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
662 *samples++ = (pred[0] - 0x80) << 8;
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
663 if(stereo) {
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
664 pred[1] = get_bits(&gb, 8);
3220
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
665 *samples++ = (pred[1] - 0x80) << 8;
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
666 }
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
667 for(i = 0; i < unp_size; i++) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
668 if(i & stereo){
3220
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
669 if(vlc[1].table)
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
670 res = get_vlc2(&gb, vlc[1].table, SMKTREE_BITS, 3);
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
671 else
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
672 res = 0;
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
673 pred[1] += (int8_t)h[1].values[res];
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
674 *samples++ = (pred[1] - 0x80) << 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
675 } else {
3220
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
676 if(vlc[0].table)
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
677 res = get_vlc2(&gb, vlc[0].table, SMKTREE_BITS, 3);
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
678 else
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
679 res = 0;
a931984ec6ab Don't use get_vlc2() when tree is one symbol. This fixes audio decoding
kostya
parents: 3209
diff changeset
680 pred[0] += (int8_t)h[0].values[res];
3209
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
681 *samples++ = (pred[0] - 0x80) << 8;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
682 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
683 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
684 unp_size *= 2;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
685 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
686
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
687 for(i = 0; i < 4; i++) {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
688 if(vlc[i].table)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
689 free_vlc(&vlc[i]);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
690 if(h[i].bits)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
691 av_free(h[i].bits);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
692 if(h[i].lengths)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
693 av_free(h[i].lengths);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
694 if(h[i].values)
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
695 av_free(h[i].values);
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
696 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
697
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
698 *data_size = unp_size;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
699 return buf_size;
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
700 }
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
701
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
702 AVCodec smacker_decoder = {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
703 "smackvid",
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
704 CODEC_TYPE_VIDEO,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
705 CODEC_ID_SMACKVIDEO,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
706 sizeof(SmackVContext),
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
707 decode_init,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
708 NULL,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
709 decode_end,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
710 decode_frame
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
711 };
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
712
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
713 AVCodec smackaud_decoder = {
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
714 "smackaud",
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
715 CODEC_TYPE_AUDIO,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
716 CODEC_ID_SMACKAUDIO,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
717 0,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
718 smka_decode_init,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
719 NULL,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
720 NULL,
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
721 smka_decode_frame
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
722 };
cc86ebc32143 Smacker demuxer and decoder.
kostya
parents:
diff changeset
723