annotate bitstream.c @ 12530:63edd10ad4bc libavcodec tip

Try to fix crashes introduced by r25218 r25218 made assumptions about the existence of past reference frames that weren't necessarily true.
author darkshikari
date Tue, 28 Sep 2010 09:06:22 +0000
parents b9354f343d2d
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
1 /*
986e461dc072 Initial revision
glantau
parents:
diff changeset
2 * Common bit i/o utils
8629
04423b2f6e0b cosmetics: Remove pointless period after copyright statement non-sentences.
diego
parents: 8596
diff changeset
3 * Copyright (c) 2000, 2001 Fabrice Bellard
1739
07a484280a82 copyright year update of the files i touched and remembered, things look annoyingly unmaintained otherwise
michael
parents: 1660
diff changeset
4 * Copyright (c) 2002-2004 Michael Niedermayer <michaelni@gmx.at>
11547
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
5 * Copyright (c) 2010 Loren Merritt
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
6 *
5214
470601203f44 Group all copyright and author notices together.
diego
parents: 5206
diff changeset
7 * alternative bitstream reader & writer by Michael Niedermayer <michaelni@gmx.at>
470601203f44 Group all copyright and author notices together.
diego
parents: 5206
diff changeset
8 *
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3648
diff changeset
9 * This file is part of FFmpeg.
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3648
diff changeset
10 *
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3648
diff changeset
11 * FFmpeg is free software; you can redistribute it and/or
429
718a22dc121f license/copyright change
glantau
parents: 396
diff changeset
12 * modify it under the terms of the GNU Lesser General Public
718a22dc121f license/copyright change
glantau
parents: 396
diff changeset
13 * 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: 3648
diff changeset
14 * version 2.1 of the License, or (at your option) any later version.
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
15 *
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3648
diff changeset
16 * FFmpeg is distributed in the hope that it will be useful,
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
429
718a22dc121f license/copyright change
glantau
parents: 396
diff changeset
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
718a22dc121f license/copyright change
glantau
parents: 396
diff changeset
19 * Lesser General Public License for more details.
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
20 *
429
718a22dc121f license/copyright change
glantau
parents: 396
diff changeset
21 * 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: 3648
diff changeset
22 * License along with FFmpeg; if not, write to the Free Software
3036
0b546eab515d Update licensing information: The FSF changed postal address.
diego
parents: 2979
diff changeset
23 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
24 */
1106
1e39f273ecd6 per file doxy
michaelni
parents: 1083
diff changeset
25
1e39f273ecd6 per file doxy
michaelni
parents: 1083
diff changeset
26 /**
11644
7dd2a45249a9 Remove explicit filename from Doxygen @file commands.
diego
parents: 11548
diff changeset
27 * @file
2398
582e635cfa08 common.c -> bitstream.c (and the single non bitstream func -> utils.c)
michael
parents: 2370
diff changeset
28 * bitstream api.
1106
1e39f273ecd6 per file doxy
michaelni
parents: 1083
diff changeset
29 */
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2885
diff changeset
30
524
3e579fbef701 * declare av_free
kabi
parents: 520
diff changeset
31 #include "avcodec.h"
9428
0dce4fe6e6f3 Rename bitstream.h to get_bits.h.
stefano
parents: 9411
diff changeset
32 #include "get_bits.h"
9411
4cb7c65fc775 Split bitstream.h, put the bitstream writer stuff in the new file
stefano
parents: 9405
diff changeset
33 #include "put_bits.h"
1037
44a230c11d83 optimizing av_log2
michaelni
parents: 1031
diff changeset
34
7146
d3a1ac3e227b move ff_log2_run to bitstream.c and reuse in ffv1.c
stefang
parents: 6945
diff changeset
35 const uint8_t ff_log2_run[32]={
d3a1ac3e227b move ff_log2_run to bitstream.c and reuse in ffv1.c
stefang
parents: 6945
diff changeset
36 0, 0, 0, 0, 1, 1, 1, 1,
d3a1ac3e227b move ff_log2_run to bitstream.c and reuse in ffv1.c
stefang
parents: 6945
diff changeset
37 2, 2, 2, 2, 3, 3, 3, 3,
d3a1ac3e227b move ff_log2_run to bitstream.c and reuse in ffv1.c
stefang
parents: 6945
diff changeset
38 4, 4, 5, 5, 6, 6, 7, 7,
d3a1ac3e227b move ff_log2_run to bitstream.c and reuse in ffv1.c
stefang
parents: 6945
diff changeset
39 8, 9,10,11,12,13,14,15
d3a1ac3e227b move ff_log2_run to bitstream.c and reuse in ffv1.c
stefang
parents: 6945
diff changeset
40 };
d3a1ac3e227b move ff_log2_run to bitstream.c and reuse in ffv1.c
stefang
parents: 6945
diff changeset
41
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
42 void align_put_bits(PutBitContext *s)
986e461dc072 Initial revision
glantau
parents:
diff changeset
43 {
234
5fc0c3af3fe4 alternative bitstream writer (disabled by default, uncomment #define ALT_BISTREAM_WRITER in common.h if u want to try it)
michaelni
parents: 219
diff changeset
44 #ifdef ALT_BITSTREAM_WRITER
5fc0c3af3fe4 alternative bitstream writer (disabled by default, uncomment #define ALT_BISTREAM_WRITER in common.h if u want to try it)
michaelni
parents: 219
diff changeset
45 put_bits(s,( - s->index) & 7,0);
5fc0c3af3fe4 alternative bitstream writer (disabled by default, uncomment #define ALT_BISTREAM_WRITER in common.h if u want to try it)
michaelni
parents: 219
diff changeset
46 #else
238
99a9f903f0e3 optimized the normal bitstream writer, its faster than the alternative one on p3 now ... lets hope its at least not slower on p4 & k7
michaelni
parents: 234
diff changeset
47 put_bits(s,s->bit_left & 7,0);
234
5fc0c3af3fe4 alternative bitstream writer (disabled by default, uncomment #define ALT_BISTREAM_WRITER in common.h if u want to try it)
michaelni
parents: 219
diff changeset
48 #endif
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
49 }
986e461dc072 Initial revision
glantau
parents:
diff changeset
50
10599
f2a8cba717b0 Use more consistent / meaningful parameter names for the
stefano
parents: 10270
diff changeset
51 void ff_put_string(PutBitContext *pb, const char *string, int terminate_string)
358
2066dc543be4 move put_string() to common.{c,h}
michaelni
parents: 324
diff changeset
52 {
10599
f2a8cba717b0 Use more consistent / meaningful parameter names for the
stefano
parents: 10270
diff changeset
53 while(*string){
f2a8cba717b0 Use more consistent / meaningful parameter names for the
stefano
parents: 10270
diff changeset
54 put_bits(pb, 8, *string);
f2a8cba717b0 Use more consistent / meaningful parameter names for the
stefano
parents: 10270
diff changeset
55 string++;
358
2066dc543be4 move put_string() to common.{c,h}
michaelni
parents: 324
diff changeset
56 }
9405
9fc81340a5a8 Rename the 'put_zero' parameter of ff_put_string() to
stefano
parents: 9218
diff changeset
57 if(terminate_string)
10599
f2a8cba717b0 Use more consistent / meaningful parameter names for the
stefano
parents: 10270
diff changeset
58 put_bits(pb, 8, 0);
358
2066dc543be4 move put_string() to common.{c,h}
michaelni
parents: 324
diff changeset
59 }
2066dc543be4 move put_string() to common.{c,h}
michaelni
parents: 324
diff changeset
60
6325
michael
parents: 5409
diff changeset
61 void ff_copy_bits(PutBitContext *pb, const uint8_t *src, int length)
5229
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
62 {
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
63 int words= length>>4;
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
64 int bits= length&15;
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
65 int i;
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
66
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
67 if(length==0) return;
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
68
8596
68e959302527 replace all occurrence of ENABLE_ by the corresponding CONFIG_, HAVE_ or ARCH_
aurel
parents: 7146
diff changeset
69 if(CONFIG_SMALL || words < 16 || put_bits_count(pb)&7){
9905
f3ff182e9ecf Fix potentially unaligned accesses in ff_copy_bits()
mru
parents: 9431
diff changeset
70 for(i=0; i<words; i++) put_bits(pb, 16, AV_RB16(src + 2*i));
5229
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
71 }else{
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
72 for(i=0; put_bits_count(pb)&31; i++)
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
73 put_bits(pb, 8, src[i]);
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
74 flush_put_bits(pb);
9431
932543edc1d2 Rename pbBufPtr() to put_bits_ptr().
stefano
parents: 9428
diff changeset
75 memcpy(put_bits_ptr(pb), src+i, 2*words-i);
5229
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
76 skip_put_bytes(pb, 2*words-i);
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
77 }
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
78
9905
f3ff182e9ecf Fix potentially unaligned accesses in ff_copy_bits()
mru
parents: 9431
diff changeset
79 put_bits(pb, bits, AV_RB16(src + 2*words)>>(16-bits));
5229
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
80 }
604a09d6cf2e move ff_copy_bits to bitstream.c
aurel
parents: 5214
diff changeset
81
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
82 /* VLC decoding */
986e461dc072 Initial revision
glantau
parents:
diff changeset
83
986e461dc072 Initial revision
glantau
parents:
diff changeset
84 //#define DEBUG_VLC
986e461dc072 Initial revision
glantau
parents:
diff changeset
85
986e461dc072 Initial revision
glantau
parents:
diff changeset
86 #define GET_DATA(v, table, i, wrap, size) \
986e461dc072 Initial revision
glantau
parents:
diff changeset
87 {\
1064
b32afefe7d33 * UINTX -> uintx_t INTX -> intx_t
kabi
parents: 1057
diff changeset
88 const uint8_t *ptr = (const uint8_t *)table + i * wrap;\
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
89 switch(size) {\
986e461dc072 Initial revision
glantau
parents:
diff changeset
90 case 1:\
1064
b32afefe7d33 * UINTX -> uintx_t INTX -> intx_t
kabi
parents: 1057
diff changeset
91 v = *(const uint8_t *)ptr;\
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
92 break;\
986e461dc072 Initial revision
glantau
parents:
diff changeset
93 case 2:\
1064
b32afefe7d33 * UINTX -> uintx_t INTX -> intx_t
kabi
parents: 1057
diff changeset
94 v = *(const uint16_t *)ptr;\
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
95 break;\
986e461dc072 Initial revision
glantau
parents:
diff changeset
96 default:\
1064
b32afefe7d33 * UINTX -> uintx_t INTX -> intx_t
kabi
parents: 1057
diff changeset
97 v = *(const uint32_t *)ptr;\
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
98 break;\
986e461dc072 Initial revision
glantau
parents:
diff changeset
99 }\
986e461dc072 Initial revision
glantau
parents:
diff changeset
100 }
986e461dc072 Initial revision
glantau
parents:
diff changeset
101
986e461dc072 Initial revision
glantau
parents:
diff changeset
102
2370
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2281
diff changeset
103 static int alloc_table(VLC *vlc, int size, int use_static)
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
104 {
986e461dc072 Initial revision
glantau
parents:
diff changeset
105 int index;
986e461dc072 Initial revision
glantau
parents:
diff changeset
106 index = vlc->table_size;
986e461dc072 Initial revision
glantau
parents:
diff changeset
107 vlc->table_size += size;
986e461dc072 Initial revision
glantau
parents:
diff changeset
108 if (vlc->table_size > vlc->table_allocated) {
10268
05190dd593c9 Remove a piece of code left-over from the removed alloc'd static vlc table code.
reimar
parents: 10263
diff changeset
109 if(use_static)
6935
24e01f7cc819 Make init_vlc* support proper static tables instead of this broken beyond
michael
parents: 6519
diff changeset
110 abort(); //cant do anything, init_vlc() is used with too little memory
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
111 vlc->table_allocated += (1 << vlc->bits);
10269
74d5ddc5c0f6 Reindent.
reimar
parents: 10268
diff changeset
112 vlc->table = av_realloc(vlc->table,
74d5ddc5c0f6 Reindent.
reimar
parents: 10268
diff changeset
113 sizeof(VLC_TYPE) * 2 * vlc->table_allocated);
520
19a5e2a81e1a new bitstream reader API (old get_bits() based one is emulated and will still be supported in the future cuz its simpler)
michaelni
parents: 497
diff changeset
114 if (!vlc->table)
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
115 return -1;
986e461dc072 Initial revision
glantau
parents:
diff changeset
116 }
986e461dc072 Initial revision
glantau
parents:
diff changeset
117 return index;
986e461dc072 Initial revision
glantau
parents:
diff changeset
118 }
986e461dc072 Initial revision
glantau
parents:
diff changeset
119
11547
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
120 static av_always_inline uint32_t bitswap_32(uint32_t x) {
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
121 return av_reverse[x&0xFF]<<24
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
122 | av_reverse[(x>>8)&0xFF]<<16
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
123 | av_reverse[(x>>16)&0xFF]<<8
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
124 | av_reverse[x>>24];
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
125 }
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
126
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
127 typedef struct {
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
128 uint8_t bits;
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
129 uint16_t symbol;
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
130 /** codeword, with the first bit-to-be-read in the msb
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
131 * (even if intended for a little-endian bitstream reader) */
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
132 uint32_t code;
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
133 } VLCcode;
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
134
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
135 static int compare_vlcspec(const void *a, const void *b)
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
136 {
11547
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
137 const VLCcode *sa=a, *sb=b;
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
138 return (sa->code >> 1) - (sb->code >> 1);
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
139 }
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
140
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
141 /**
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
142 * Build VLC decoding tables suitable for use with get_vlc().
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
143 *
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
144 * @param vlc the context to be initted
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
145 *
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
146 * @param table_nb_bits max length of vlc codes to store directly in this table
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
147 * (Longer codes are delegated to subtables.)
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
148 *
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
149 * @param nb_codes number of elements in codes[]
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
150 *
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
151 * @param codes descriptions of the vlc codes
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
152 * These must be ordered such that codes going into the same subtable are contiguous.
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
153 * Sorting by VLCcode.code is sufficient, though not necessary.
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
154 */
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
155 static int build_table(VLC *vlc, int table_nb_bits, int nb_codes,
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
156 VLCcode *codes, int flags)
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
157 {
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
158 int table_size, table_index, index, code_prefix, symbol, subtable_bits;
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
159 int i, j, k, n, nb, inc;
1064
b32afefe7d33 * UINTX -> uintx_t INTX -> intx_t
kabi
parents: 1057
diff changeset
160 uint32_t code;
520
19a5e2a81e1a new bitstream reader API (old get_bits() based one is emulated and will still be supported in the future cuz its simpler)
michaelni
parents: 497
diff changeset
161 VLC_TYPE (*table)[2];
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
162
986e461dc072 Initial revision
glantau
parents:
diff changeset
163 table_size = 1 << table_nb_bits;
10263
fd9dfd5aa5e9 Completely remove INIT_VLC_USE_STATIC, it is deprecated since ages and
reimar
parents: 9905
diff changeset
164 table_index = alloc_table(vlc, table_size, flags & INIT_VLC_USE_NEW_STATIC);
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
165 #ifdef DEBUG_VLC
11547
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
166 av_log(NULL,AV_LOG_DEBUG,"new table index=%d size=%d\n",
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
167 table_index, table_size);
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
168 #endif
986e461dc072 Initial revision
glantau
parents:
diff changeset
169 if (table_index < 0)
986e461dc072 Initial revision
glantau
parents:
diff changeset
170 return -1;
520
19a5e2a81e1a new bitstream reader API (old get_bits() based one is emulated and will still be supported in the future cuz its simpler)
michaelni
parents: 497
diff changeset
171 table = &vlc->table[table_index];
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
172
11548
lorenm
parents: 11547
diff changeset
173 for (i = 0; i < table_size; i++) {
520
19a5e2a81e1a new bitstream reader API (old get_bits() based one is emulated and will still be supported in the future cuz its simpler)
michaelni
parents: 497
diff changeset
174 table[i][1] = 0; //bits
19a5e2a81e1a new bitstream reader API (old get_bits() based one is emulated and will still be supported in the future cuz its simpler)
michaelni
parents: 497
diff changeset
175 table[i][0] = -1; //codes
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
176 }
986e461dc072 Initial revision
glantau
parents:
diff changeset
177
986e461dc072 Initial revision
glantau
parents:
diff changeset
178 /* first pass: map codes and compute auxillary table sizes */
11548
lorenm
parents: 11547
diff changeset
179 for (i = 0; i < nb_codes; i++) {
11547
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
180 n = codes[i].bits;
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
181 code = codes[i].code;
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
182 symbol = codes[i].symbol;
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
183 #if defined(DEBUG_VLC) && 0
5013
c7904664624c printf --> av_log, patch by Denis Fortin, fortin nerim net
diego
parents: 4889
diff changeset
184 av_log(NULL,AV_LOG_DEBUG,"i=%d n=%d code=0x%x\n", i, n, code);
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
185 #endif
11548
lorenm
parents: 11547
diff changeset
186 if (n <= table_nb_bits) {
lorenm
parents: 11547
diff changeset
187 /* no need to add another table */
lorenm
parents: 11547
diff changeset
188 j = code >> (32 - table_nb_bits);
lorenm
parents: 11547
diff changeset
189 nb = 1 << (table_nb_bits - n);
lorenm
parents: 11547
diff changeset
190 inc = 1;
lorenm
parents: 11547
diff changeset
191 if (flags & INIT_VLC_LE) {
lorenm
parents: 11547
diff changeset
192 j = bitswap_32(code);
lorenm
parents: 11547
diff changeset
193 inc = 1 << n;
lorenm
parents: 11547
diff changeset
194 }
lorenm
parents: 11547
diff changeset
195 for (k = 0; k < nb; k++) {
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
196 #ifdef DEBUG_VLC
11548
lorenm
parents: 11547
diff changeset
197 av_log(NULL, AV_LOG_DEBUG, "%4x: code=%d n=%d\n",
lorenm
parents: 11547
diff changeset
198 j, i, n);
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
199 #endif
11548
lorenm
parents: 11547
diff changeset
200 if (table[j][1] /*bits*/ != 0) {
lorenm
parents: 11547
diff changeset
201 av_log(NULL, AV_LOG_ERROR, "incorrect codes\n");
lorenm
parents: 11547
diff changeset
202 return -1;
lorenm
parents: 11547
diff changeset
203 }
lorenm
parents: 11547
diff changeset
204 table[j][1] = n; //bits
lorenm
parents: 11547
diff changeset
205 table[j][0] = symbol;
lorenm
parents: 11547
diff changeset
206 j += inc;
lorenm
parents: 11547
diff changeset
207 }
lorenm
parents: 11547
diff changeset
208 } else {
lorenm
parents: 11547
diff changeset
209 /* fill auxiliary table recursively */
lorenm
parents: 11547
diff changeset
210 n -= table_nb_bits;
lorenm
parents: 11547
diff changeset
211 code_prefix = code >> (32 - table_nb_bits);
lorenm
parents: 11547
diff changeset
212 subtable_bits = n;
lorenm
parents: 11547
diff changeset
213 codes[i].bits = n;
lorenm
parents: 11547
diff changeset
214 codes[i].code = code << table_nb_bits;
lorenm
parents: 11547
diff changeset
215 for (k = i+1; k < nb_codes; k++) {
lorenm
parents: 11547
diff changeset
216 n = codes[k].bits - table_nb_bits;
lorenm
parents: 11547
diff changeset
217 if (n <= 0)
lorenm
parents: 11547
diff changeset
218 break;
lorenm
parents: 11547
diff changeset
219 code = codes[k].code;
lorenm
parents: 11547
diff changeset
220 if (code >> (32 - table_nb_bits) != code_prefix)
lorenm
parents: 11547
diff changeset
221 break;
lorenm
parents: 11547
diff changeset
222 codes[k].bits = n;
lorenm
parents: 11547
diff changeset
223 codes[k].code = code << table_nb_bits;
lorenm
parents: 11547
diff changeset
224 subtable_bits = FFMAX(subtable_bits, n);
lorenm
parents: 11547
diff changeset
225 }
lorenm
parents: 11547
diff changeset
226 subtable_bits = FFMIN(subtable_bits, table_nb_bits);
lorenm
parents: 11547
diff changeset
227 j = (flags & INIT_VLC_LE) ? bitswap_32(code_prefix) >> (32 - table_nb_bits) : code_prefix;
lorenm
parents: 11547
diff changeset
228 table[j][1] = -subtable_bits;
11233
mru
parents: 11232
diff changeset
229 #ifdef DEBUG_VLC
11548
lorenm
parents: 11547
diff changeset
230 av_log(NULL,AV_LOG_DEBUG,"%4x: n=%d (subtable)\n",
lorenm
parents: 11547
diff changeset
231 j, codes[i].bits + table_nb_bits);
11233
mru
parents: 11232
diff changeset
232 #endif
11548
lorenm
parents: 11547
diff changeset
233 index = build_table(vlc, subtable_bits, k-i, codes+i, flags);
lorenm
parents: 11547
diff changeset
234 if (index < 0)
lorenm
parents: 11547
diff changeset
235 return -1;
lorenm
parents: 11547
diff changeset
236 /* note: realloc has been done, so reload tables */
lorenm
parents: 11547
diff changeset
237 table = &vlc->table[table_index];
lorenm
parents: 11547
diff changeset
238 table[j][0] = index; //code
lorenm
parents: 11547
diff changeset
239 i = k-1;
lorenm
parents: 11547
diff changeset
240 }
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
241 }
986e461dc072 Initial revision
glantau
parents:
diff changeset
242 return table_index;
986e461dc072 Initial revision
glantau
parents:
diff changeset
243 }
986e461dc072 Initial revision
glantau
parents:
diff changeset
244
986e461dc072 Initial revision
glantau
parents:
diff changeset
245
24
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
246 /* Build VLC decoding tables suitable for use with get_vlc().
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
247
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
248 'nb_bits' set thee decoding table size (2^nb_bits) entries. The
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
249 bigger it is, the faster is the decoding. But it should not be too
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
250 big to save memory and L1 cache. '9' is a good compromise.
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2885
diff changeset
251
24
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
252 'nb_codes' : number of vlcs codes
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
253
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
254 'bits' : table which gives the size (in bits) of each vlc code.
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
255
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
256 'codes' : table which gives the bit pattern of of each vlc code.
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
257
5071
0d503c12092b add init_vlc_sparse(). faster than init_vlc() if there are lots of holes in the tables.
lorenm
parents: 5013
diff changeset
258 'symbols' : table which gives the values to be returned from get_vlc().
0d503c12092b add init_vlc_sparse(). faster than init_vlc() if there are lots of holes in the tables.
lorenm
parents: 5013
diff changeset
259
24
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
260 'xxx_wrap' : give the number of bytes between each entry of the
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
261 'bits' or 'codes' tables.
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
262
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
263 'xxx_size' : gives the number of bytes of each entry of the 'bits'
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
264 or 'codes' tables.
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
265
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
266 'wrap' and 'size' allows to use any memory configuration and types
5071
0d503c12092b add init_vlc_sparse(). faster than init_vlc() if there are lots of holes in the tables.
lorenm
parents: 5013
diff changeset
267 (byte/word/long) to store the 'bits', 'codes', and 'symbols' tables.
2370
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2281
diff changeset
268
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2281
diff changeset
269 'use_static' should be set to 1 for tables, which should be freed
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2281
diff changeset
270 with av_free_static(), 0 if free_vlc() will be used.
24
08265a63313e added MJPEG decoder + comments
glantau
parents: 20
diff changeset
271 */
5071
0d503c12092b add init_vlc_sparse(). faster than init_vlc() if there are lots of holes in the tables.
lorenm
parents: 5013
diff changeset
272 int init_vlc_sparse(VLC *vlc, int nb_bits, int nb_codes,
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
273 const void *bits, int bits_wrap, int bits_size,
2370
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2281
diff changeset
274 const void *codes, int codes_wrap, int codes_size,
5071
0d503c12092b add init_vlc_sparse(). faster than init_vlc() if there are lots of holes in the tables.
lorenm
parents: 5013
diff changeset
275 const void *symbols, int symbols_wrap, int symbols_size,
4685
2c8f88e7397a fix init_vlc() with nonzero flags
mru
parents: 4670
diff changeset
276 int flags)
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
277 {
11713
b9354f343d2d change a variable-length array to a malloc.
lorenm
parents: 11644
diff changeset
278 VLCcode *buf;
b9354f343d2d change a variable-length array to a malloc.
lorenm
parents: 11644
diff changeset
279 int i, j, ret;
11547
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
280
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
281 vlc->bits = nb_bits;
6935
24e01f7cc819 Make init_vlc* support proper static tables instead of this broken beyond
michael
parents: 6519
diff changeset
282 if(flags & INIT_VLC_USE_NEW_STATIC){
24e01f7cc819 Make init_vlc* support proper static tables instead of this broken beyond
michael
parents: 6519
diff changeset
283 if(vlc->table_size && vlc->table_size == vlc->table_allocated){
24e01f7cc819 Make init_vlc* support proper static tables instead of this broken beyond
michael
parents: 6519
diff changeset
284 return 0;
24e01f7cc819 Make init_vlc* support proper static tables instead of this broken beyond
michael
parents: 6519
diff changeset
285 }else if(vlc->table_size){
24e01f7cc819 Make init_vlc* support proper static tables instead of this broken beyond
michael
parents: 6519
diff changeset
286 abort(); // fatal error, we are called on a partially initialized table
24e01f7cc819 Make init_vlc* support proper static tables instead of this broken beyond
michael
parents: 6519
diff changeset
287 }
10263
fd9dfd5aa5e9 Completely remove INIT_VLC_USE_STATIC, it is deprecated since ages and
reimar
parents: 9905
diff changeset
288 }else {
2370
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2281
diff changeset
289 vlc->table = NULL;
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2281
diff changeset
290 vlc->table_allocated = 0;
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2281
diff changeset
291 vlc->table_size = 0;
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2281
diff changeset
292 }
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2281
diff changeset
293
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
294 #ifdef DEBUG_VLC
5013
c7904664624c printf --> av_log, patch by Denis Fortin, fortin nerim net
diego
parents: 4889
diff changeset
295 av_log(NULL,AV_LOG_DEBUG,"build table nb_codes=%d\n", nb_codes);
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
296 #endif
986e461dc072 Initial revision
glantau
parents:
diff changeset
297
11713
b9354f343d2d change a variable-length array to a malloc.
lorenm
parents: 11644
diff changeset
298 buf = av_malloc((nb_codes+1)*sizeof(VLCcode));
b9354f343d2d change a variable-length array to a malloc.
lorenm
parents: 11644
diff changeset
299
11547
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
300 assert(symbols_size <= 2 || !symbols);
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
301 j = 0;
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
302 #define COPY(condition)\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
303 for (i = 0; i < nb_codes; i++) {\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
304 GET_DATA(buf[j].bits, bits, i, bits_wrap, bits_size);\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
305 if (!(condition))\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
306 continue;\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
307 GET_DATA(buf[j].code, codes, i, codes_wrap, codes_size);\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
308 if (flags & INIT_VLC_LE)\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
309 buf[j].code = bitswap_32(buf[j].code);\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
310 else\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
311 buf[j].code <<= 32 - buf[j].bits;\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
312 if (symbols)\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
313 GET_DATA(buf[j].symbol, symbols, i, symbols_wrap, symbols_size)\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
314 else\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
315 buf[j].symbol = i;\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
316 j++;\
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
317 }
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
318 COPY(buf[j].bits > nb_bits);
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
319 // qsort is the slowest part of init_vlc, and could probably be improved or avoided
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
320 qsort(buf, j, sizeof(VLCcode), compare_vlcspec);
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
321 COPY(buf[j].bits && buf[j].bits <= nb_bits);
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
322 nb_codes = j;
aba20ba60384 optimize init_vlc().
lorenm
parents: 11233
diff changeset
323
11713
b9354f343d2d change a variable-length array to a malloc.
lorenm
parents: 11644
diff changeset
324 ret = build_table(vlc, nb_bits, nb_codes, buf, flags);
b9354f343d2d change a variable-length array to a malloc.
lorenm
parents: 11644
diff changeset
325
b9354f343d2d change a variable-length array to a malloc.
lorenm
parents: 11644
diff changeset
326 av_free(buf);
b9354f343d2d change a variable-length array to a malloc.
lorenm
parents: 11644
diff changeset
327 if (ret < 0) {
5206
02dd5e0d7e46 use av_freep() in free_vlc() and failed init_vlc()
mru
parents: 5071
diff changeset
328 av_freep(&vlc->table);
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
329 return -1;
986e461dc072 Initial revision
glantau
parents:
diff changeset
330 }
6935
24e01f7cc819 Make init_vlc* support proper static tables instead of this broken beyond
michael
parents: 6519
diff changeset
331 if((flags & INIT_VLC_USE_NEW_STATIC) && vlc->table_size != vlc->table_allocated)
24e01f7cc819 Make init_vlc* support proper static tables instead of this broken beyond
michael
parents: 6519
diff changeset
332 av_log(NULL, AV_LOG_ERROR, "needed %d had %d\n", vlc->table_size, vlc->table_allocated);
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
333 return 0;
986e461dc072 Initial revision
glantau
parents:
diff changeset
334 }
986e461dc072 Initial revision
glantau
parents:
diff changeset
335
986e461dc072 Initial revision
glantau
parents:
diff changeset
336
986e461dc072 Initial revision
glantau
parents:
diff changeset
337 void free_vlc(VLC *vlc)
986e461dc072 Initial revision
glantau
parents:
diff changeset
338 {
5206
02dd5e0d7e46 use av_freep() in free_vlc() and failed init_vlc()
mru
parents: 5071
diff changeset
339 av_freep(&vlc->table);
0
986e461dc072 Initial revision
glantau
parents:
diff changeset
340 }
986e461dc072 Initial revision
glantau
parents:
diff changeset
341