annotate cabac.h @ 2497:69adfbbdcdeb libavcodec

- samples from mplayer ftp in the "adv" profile seem to have profile=2, which isn't the advanced one; and indeed, using adv. profile parser fails. Using normal parser works, and that's what is done - attempt at taking care of stride for NORM2 bitplane decoding - duplication of much code from msmpeg4.c; this code isn't yet used, but goes down as far as the block layer (mainly Transform Type stuff, the remains are wild editing without checking). Unusable yet, and lacks the AC decoding (but a step further in bitstream parsing) patch by anonymous
author michael
date Fri, 04 Feb 2005 02:20:38 +0000
parents 1c39d9786efd
children e25782262d7d
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
1287
michaelni
parents:
diff changeset
1 /*
michaelni
parents:
diff changeset
2 * H.26L/H.264/AVC/JVT/14496-10/... encoder/decoder
michaelni
parents:
diff changeset
3 * Copyright (c) 2003 Michael Niedermayer <michaelni@gmx.at>
michaelni
parents:
diff changeset
4 *
michaelni
parents:
diff changeset
5 * This library is free software; you can redistribute it and/or
michaelni
parents:
diff changeset
6 * modify it under the terms of the GNU Lesser General Public
michaelni
parents:
diff changeset
7 * License as published by the Free Software Foundation; either
michaelni
parents:
diff changeset
8 * version 2 of the License, or (at your option) any later version.
michaelni
parents:
diff changeset
9 *
michaelni
parents:
diff changeset
10 * This library is distributed in the hope that it will be useful,
michaelni
parents:
diff changeset
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
michaelni
parents:
diff changeset
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
michaelni
parents:
diff changeset
13 * Lesser General Public License for more details.
michaelni
parents:
diff changeset
14 *
michaelni
parents:
diff changeset
15 * You should have received a copy of the GNU Lesser General Public
michaelni
parents:
diff changeset
16 * License along with this library; if not, write to the Free Software
michaelni
parents:
diff changeset
17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
michaelni
parents:
diff changeset
18 *
michaelni
parents:
diff changeset
19 */
michaelni
parents:
diff changeset
20
michaelni
parents:
diff changeset
21 /**
michaelni
parents:
diff changeset
22 * @file cabac.h
michaelni
parents:
diff changeset
23 * Context Adaptive Binary Arithmetic Coder.
michaelni
parents:
diff changeset
24 */
michaelni
parents:
diff changeset
25
michaelni
parents:
diff changeset
26
michaelni
parents:
diff changeset
27 #undef NDEBUG
michaelni
parents:
diff changeset
28 #include <assert.h>
michaelni
parents:
diff changeset
29
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
30 #define CABAC_BITS 8
1c39d9786efd optimization
michael
parents: 2116
diff changeset
31 #define CABAC_MASK ((1<<CABAC_BITS)-1)
1c39d9786efd optimization
michael
parents: 2116
diff changeset
32
1287
michaelni
parents:
diff changeset
33 typedef struct CABACContext{
michaelni
parents:
diff changeset
34 int low;
michaelni
parents:
diff changeset
35 int range;
michaelni
parents:
diff changeset
36 int outstanding_count;
michaelni
parents:
diff changeset
37 #ifdef STRICT_LIMITS
michaelni
parents:
diff changeset
38 int symCount;
michaelni
parents:
diff changeset
39 #endif
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
40 uint8_t lps_range[2*65][4]; ///< rangeTabLPS
1287
michaelni
parents:
diff changeset
41 uint8_t lps_state[2*64]; ///< transIdxLPS
michaelni
parents:
diff changeset
42 uint8_t mps_state[2*64]; ///< transIdxMPS
2024
f65d87bfdd5a some of the warning fixes by (Michael Roitzsch <mroi at users dot sourceforge dot net>)
michael
parents: 1787
diff changeset
43 const uint8_t *bytestream_start;
f65d87bfdd5a some of the warning fixes by (Michael Roitzsch <mroi at users dot sourceforge dot net>)
michael
parents: 1787
diff changeset
44 const uint8_t *bytestream;
2116
48d9f86fb047 overread fix
michael
parents: 2024
diff changeset
45 const uint8_t *bytestream_end;
1287
michaelni
parents:
diff changeset
46 PutBitContext pb;
michaelni
parents:
diff changeset
47 }CABACContext;
michaelni
parents:
diff changeset
48
1301
michaelni
parents: 1300
diff changeset
49 extern const uint8_t ff_h264_lps_range[64][4];
michaelni
parents: 1300
diff changeset
50 extern const uint8_t ff_h264_mps_state[64];
michaelni
parents: 1300
diff changeset
51 extern const uint8_t ff_h264_lps_state[64];
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
52 extern const uint8_t ff_h264_norm_shift[256];
1c39d9786efd optimization
michael
parents: 2116
diff changeset
53
1287
michaelni
parents:
diff changeset
54
michaelni
parents:
diff changeset
55 void ff_init_cabac_encoder(CABACContext *c, uint8_t *buf, int buf_size);
2024
f65d87bfdd5a some of the warning fixes by (Michael Roitzsch <mroi at users dot sourceforge dot net>)
michael
parents: 1787
diff changeset
56 void ff_init_cabac_decoder(CABACContext *c, const uint8_t *buf, int buf_size);
1287
michaelni
parents:
diff changeset
57 void ff_init_cabac_states(CABACContext *c, uint8_t const (*lps_range)[4],
michaelni
parents:
diff changeset
58 uint8_t const *mps_state, uint8_t const *lps_state, int state_count);
michaelni
parents:
diff changeset
59
michaelni
parents:
diff changeset
60
michaelni
parents:
diff changeset
61 static inline void put_cabac_bit(CABACContext *c, int b){
michaelni
parents:
diff changeset
62 put_bits(&c->pb, 1, b);
michaelni
parents:
diff changeset
63 for(;c->outstanding_count; c->outstanding_count--){
michaelni
parents:
diff changeset
64 put_bits(&c->pb, 1, 1-b);
michaelni
parents:
diff changeset
65 }
michaelni
parents:
diff changeset
66 }
michaelni
parents:
diff changeset
67
michaelni
parents:
diff changeset
68 static inline void renorm_cabac_encoder(CABACContext *c){
michaelni
parents:
diff changeset
69 while(c->range < 0x100){
michaelni
parents:
diff changeset
70 //FIXME optimize
michaelni
parents:
diff changeset
71 if(c->low<0x100){
michaelni
parents:
diff changeset
72 put_cabac_bit(c, 0);
michaelni
parents:
diff changeset
73 }else if(c->low<0x200){
michaelni
parents:
diff changeset
74 c->outstanding_count++;
michaelni
parents:
diff changeset
75 c->low -= 0x100;
michaelni
parents:
diff changeset
76 }else{
michaelni
parents:
diff changeset
77 put_cabac_bit(c, 1);
michaelni
parents:
diff changeset
78 c->low -= 0x200;
michaelni
parents:
diff changeset
79 }
michaelni
parents:
diff changeset
80
michaelni
parents:
diff changeset
81 c->range+= c->range;
michaelni
parents:
diff changeset
82 c->low += c->low;
michaelni
parents:
diff changeset
83 }
michaelni
parents:
diff changeset
84 }
michaelni
parents:
diff changeset
85
michaelni
parents:
diff changeset
86 static inline void put_cabac(CABACContext *c, uint8_t * const state, int bit){
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
87 int RangeLPS= c->lps_range[*state][c->range>>6];
1287
michaelni
parents:
diff changeset
88
michaelni
parents:
diff changeset
89 if(bit == ((*state)&1)){
michaelni
parents:
diff changeset
90 c->range -= RangeLPS;
michaelni
parents:
diff changeset
91 *state= c->mps_state[*state];
michaelni
parents:
diff changeset
92 }else{
michaelni
parents:
diff changeset
93 c->low += c->range - RangeLPS;
michaelni
parents:
diff changeset
94 c->range = RangeLPS;
michaelni
parents:
diff changeset
95 *state= c->lps_state[*state];
michaelni
parents:
diff changeset
96 }
michaelni
parents:
diff changeset
97
michaelni
parents:
diff changeset
98 renorm_cabac_encoder(c);
michaelni
parents:
diff changeset
99
michaelni
parents:
diff changeset
100 #ifdef STRICT_LIMITS
michaelni
parents:
diff changeset
101 c->symCount++;
michaelni
parents:
diff changeset
102 #endif
michaelni
parents:
diff changeset
103 }
michaelni
parents:
diff changeset
104
michaelni
parents:
diff changeset
105 static inline void put_cabac_static(CABACContext *c, int RangeLPS, int bit){
michaelni
parents:
diff changeset
106 assert(c->range > RangeLPS);
michaelni
parents:
diff changeset
107
michaelni
parents:
diff changeset
108 if(!bit){
michaelni
parents:
diff changeset
109 c->range -= RangeLPS;
michaelni
parents:
diff changeset
110 }else{
michaelni
parents:
diff changeset
111 c->low += c->range - RangeLPS;
michaelni
parents:
diff changeset
112 c->range = RangeLPS;
michaelni
parents:
diff changeset
113 }
michaelni
parents:
diff changeset
114
michaelni
parents:
diff changeset
115 renorm_cabac_encoder(c);
michaelni
parents:
diff changeset
116
michaelni
parents:
diff changeset
117 #ifdef STRICT_LIMITS
michaelni
parents:
diff changeset
118 c->symCount++;
michaelni
parents:
diff changeset
119 #endif
michaelni
parents:
diff changeset
120 }
michaelni
parents:
diff changeset
121
1290
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
122 /**
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
123 * @param bit 0 -> write zero bit, !=0 write one bit
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
124 */
1287
michaelni
parents:
diff changeset
125 static inline void put_cabac_bypass(CABACContext *c, int bit){
michaelni
parents:
diff changeset
126 c->low += c->low;
michaelni
parents:
diff changeset
127
michaelni
parents:
diff changeset
128 if(bit){
michaelni
parents:
diff changeset
129 c->low += c->range;
michaelni
parents:
diff changeset
130 }
michaelni
parents:
diff changeset
131 //FIXME optimize
michaelni
parents:
diff changeset
132 if(c->low<0x200){
michaelni
parents:
diff changeset
133 put_cabac_bit(c, 0);
michaelni
parents:
diff changeset
134 }else if(c->low<0x400){
michaelni
parents:
diff changeset
135 c->outstanding_count++;
michaelni
parents:
diff changeset
136 c->low -= 0x200;
michaelni
parents:
diff changeset
137 }else{
michaelni
parents:
diff changeset
138 put_cabac_bit(c, 1);
michaelni
parents:
diff changeset
139 c->low -= 0x400;
michaelni
parents:
diff changeset
140 }
michaelni
parents:
diff changeset
141
michaelni
parents:
diff changeset
142 #ifdef STRICT_LIMITS
michaelni
parents:
diff changeset
143 c->symCount++;
michaelni
parents:
diff changeset
144 #endif
michaelni
parents:
diff changeset
145 }
michaelni
parents:
diff changeset
146
1300
e18667d1e94d FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents: 1298
diff changeset
147 /**
e18667d1e94d FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents: 1298
diff changeset
148 *
e18667d1e94d FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents: 1298
diff changeset
149 * @return the number of bytes written
e18667d1e94d FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents: 1298
diff changeset
150 */
e18667d1e94d FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents: 1298
diff changeset
151 static inline int put_cabac_terminate(CABACContext *c, int bit){
1287
michaelni
parents:
diff changeset
152 c->range -= 2;
michaelni
parents:
diff changeset
153
michaelni
parents:
diff changeset
154 if(!bit){
michaelni
parents:
diff changeset
155 renorm_cabac_encoder(c);
michaelni
parents:
diff changeset
156 }else{
michaelni
parents:
diff changeset
157 c->low += c->range;
michaelni
parents:
diff changeset
158 c->range= 2;
michaelni
parents:
diff changeset
159
michaelni
parents:
diff changeset
160 renorm_cabac_encoder(c);
michaelni
parents:
diff changeset
161
michaelni
parents:
diff changeset
162 assert(c->low <= 0x1FF);
michaelni
parents:
diff changeset
163 put_cabac_bit(c, c->low>>9);
michaelni
parents:
diff changeset
164 put_bits(&c->pb, 2, ((c->low>>7)&3)|1);
michaelni
parents:
diff changeset
165
michaelni
parents:
diff changeset
166 flush_put_bits(&c->pb); //FIXME FIXME FIXME XXX wrong
michaelni
parents:
diff changeset
167 }
michaelni
parents:
diff changeset
168
michaelni
parents:
diff changeset
169 #ifdef STRICT_LIMITS
michaelni
parents:
diff changeset
170 c->symCount++;
michaelni
parents:
diff changeset
171 #endif
1300
e18667d1e94d FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents: 1298
diff changeset
172
1787
752b51a3c8ed get_bit_count -> put_bits_count
alex
parents: 1301
diff changeset
173 return (put_bits_count(&c->pb)+7)>>3;
1287
michaelni
parents:
diff changeset
174 }
michaelni
parents:
diff changeset
175
1290
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
176 /**
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
177 * put (truncated) unary binarization.
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
178 */
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
179 static inline void put_cabac_u(CABACContext *c, uint8_t * state, int v, int max, int max_index, int truncated){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
180 int i;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
181
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
182 assert(v <= max);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
183
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
184 #if 1
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
185 for(i=0; i<v; i++){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
186 put_cabac(c, state, 1);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
187 if(i < max_index) state++;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
188 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
189 if(truncated==0 || v<max)
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
190 put_cabac(c, state, 0);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
191 #else
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
192 if(v <= max_index){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
193 for(i=0; i<v; i++){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
194 put_cabac(c, state+i, 1);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
195 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
196 if(truncated==0 || v<max)
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
197 put_cabac(c, state+i, 0);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
198 }else{
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
199 for(i=0; i<=max_index; i++){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
200 put_cabac(c, state+i, 1);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
201 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
202 for(; i<v; i++){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
203 put_cabac(c, state+max_index, 1);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
204 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
205 if(truncated==0 || v<max)
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
206 put_cabac(c, state+max_index, 0);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
207 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
208 #endif
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
209 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
210
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
211 /**
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
212 * put unary exp golomb k-th order binarization.
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
213 */
1298
5bc3184810dc cleanup
michaelni
parents: 1290
diff changeset
214 static inline void put_cabac_ueg(CABACContext *c, uint8_t * state, int v, int max, int is_signed, int k, int max_index){
1290
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
215 int i;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
216
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
217 if(v==0)
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
218 put_cabac(c, state, 0);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
219 else{
1298
5bc3184810dc cleanup
michaelni
parents: 1290
diff changeset
220 const int sign= v < 0;
5bc3184810dc cleanup
michaelni
parents: 1290
diff changeset
221
5bc3184810dc cleanup
michaelni
parents: 1290
diff changeset
222 if(is_signed) v= ABS(v);
5bc3184810dc cleanup
michaelni
parents: 1290
diff changeset
223
1290
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
224 if(v<max){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
225 for(i=0; i<v; i++){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
226 put_cabac(c, state, 1);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
227 if(i < max_index) state++;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
228 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
229
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
230 put_cabac(c, state, 0);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
231 }else{
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
232 int m= 1<<k;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
233
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
234 for(i=0; i<max; i++){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
235 put_cabac(c, state, 1);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
236 if(i < max_index) state++;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
237 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
238
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
239 v -= max;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
240 while(v >= m){ //FIXME optimize
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
241 put_cabac_bypass(c, 1);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
242 v-= m;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
243 m+= m;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
244 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
245 put_cabac_bypass(c, 0);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
246 while(m>>=1){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
247 put_cabac_bypass(c, v&m);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
248 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
249 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
250
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
251 if(is_signed)
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
252 put_cabac_bypass(c, sign);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
253 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
254 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
255
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
256 static void refill(CABACContext *c){
1c39d9786efd optimization
michael
parents: 2116
diff changeset
257 if(c->bytestream < c->bytestream_end)
1c39d9786efd optimization
michael
parents: 2116
diff changeset
258 #if CABAC_BITS == 16
1c39d9786efd optimization
michael
parents: 2116
diff changeset
259 c->low+= ((c->bytestream[0]<<9) + (c->bytestream[1])<<1);
1c39d9786efd optimization
michael
parents: 2116
diff changeset
260 #else
1c39d9786efd optimization
michael
parents: 2116
diff changeset
261 c->low+= c->bytestream[0]<<1;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
262 #endif
1c39d9786efd optimization
michael
parents: 2116
diff changeset
263 c->low -= CABAC_MASK;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
264 c->bytestream+= CABAC_BITS/8;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
265 }
1c39d9786efd optimization
michael
parents: 2116
diff changeset
266
1c39d9786efd optimization
michael
parents: 2116
diff changeset
267 static void refill2(CABACContext *c){
1c39d9786efd optimization
michael
parents: 2116
diff changeset
268 int i, x;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
269
1c39d9786efd optimization
michael
parents: 2116
diff changeset
270 x= c->low ^ (c->low-1);
1c39d9786efd optimization
michael
parents: 2116
diff changeset
271 i= 8 - ff_h264_norm_shift[x>>(CABAC_BITS+1)];
1c39d9786efd optimization
michael
parents: 2116
diff changeset
272
1c39d9786efd optimization
michael
parents: 2116
diff changeset
273 x= -CABAC_MASK;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
274
1c39d9786efd optimization
michael
parents: 2116
diff changeset
275 if(c->bytestream < c->bytestream_end)
1c39d9786efd optimization
michael
parents: 2116
diff changeset
276 #if CABAC_BITS == 16
1c39d9786efd optimization
michael
parents: 2116
diff changeset
277 x+= (c->bytestream[0]<<9) + (c->bytestream[1]<<1);
1c39d9786efd optimization
michael
parents: 2116
diff changeset
278 #else
1c39d9786efd optimization
michael
parents: 2116
diff changeset
279 x+= c->bytestream[0]<<1;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
280 #endif
1c39d9786efd optimization
michael
parents: 2116
diff changeset
281
1c39d9786efd optimization
michael
parents: 2116
diff changeset
282 c->low += x<<i;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
283 c->bytestream+= CABAC_BITS/8;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
284 }
1c39d9786efd optimization
michael
parents: 2116
diff changeset
285
1c39d9786efd optimization
michael
parents: 2116
diff changeset
286
1287
michaelni
parents:
diff changeset
287 static inline void renorm_cabac_decoder(CABACContext *c){
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
288 while(c->range < (0x200 << CABAC_BITS)){
1287
michaelni
parents:
diff changeset
289 c->range+= c->range;
michaelni
parents:
diff changeset
290 c->low+= c->low;
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
291 if(!(c->low & CABAC_MASK))
1c39d9786efd optimization
michael
parents: 2116
diff changeset
292 refill(c);
1287
michaelni
parents:
diff changeset
293 }
michaelni
parents:
diff changeset
294 }
michaelni
parents:
diff changeset
295
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
296 static inline void renorm_cabac_decoder_once(CABACContext *c){
1c39d9786efd optimization
michael
parents: 2116
diff changeset
297 int mask= (c->range - (0x200 << CABAC_BITS))>>31;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
298 c->range+= c->range&mask;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
299 c->low += c->low &mask;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
300 if(!(c->low & CABAC_MASK))
1c39d9786efd optimization
michael
parents: 2116
diff changeset
301 refill(c);
1c39d9786efd optimization
michael
parents: 2116
diff changeset
302 }
1c39d9786efd optimization
michael
parents: 2116
diff changeset
303
1287
michaelni
parents:
diff changeset
304 static inline int get_cabac(CABACContext *c, uint8_t * const state){
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
305 int RangeLPS= c->lps_range[*state][c->range>>(CABAC_BITS+7)]<<(CABAC_BITS+1);
1c39d9786efd optimization
michael
parents: 2116
diff changeset
306 int bit, lps_mask;
1287
michaelni
parents:
diff changeset
307
michaelni
parents:
diff changeset
308 c->range -= RangeLPS;
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
309 #if 1
1287
michaelni
parents:
diff changeset
310 if(c->low < c->range){
michaelni
parents:
diff changeset
311 bit= (*state)&1;
michaelni
parents:
diff changeset
312 *state= c->mps_state[*state];
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
313 renorm_cabac_decoder_once(c);
1287
michaelni
parents:
diff changeset
314 }else{
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
315 // int shift= ff_h264_norm_shift[RangeLPS>>17];
1287
michaelni
parents:
diff changeset
316 bit= ((*state)&1)^1;
michaelni
parents:
diff changeset
317 c->low -= c->range;
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
318 *state= c->lps_state[*state];
1287
michaelni
parents:
diff changeset
319 c->range = RangeLPS;
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
320 renorm_cabac_decoder(c);
1c39d9786efd optimization
michael
parents: 2116
diff changeset
321 /* c->range = RangeLPS<<shift;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
322 c->low <<= shift;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
323 if(!(c->low & 0xFFFF)){
1c39d9786efd optimization
michael
parents: 2116
diff changeset
324 refill2(c);
1c39d9786efd optimization
michael
parents: 2116
diff changeset
325 }*/
1287
michaelni
parents:
diff changeset
326 }
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
327 #else
1c39d9786efd optimization
michael
parents: 2116
diff changeset
328 lps_mask= (c->range - c->low)>>31;
1287
michaelni
parents:
diff changeset
329
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
330 c->low -= c->range & lps_mask;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
331 c->range += (RangeLPS - c->range) & lps_mask;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
332
1c39d9786efd optimization
michael
parents: 2116
diff changeset
333 bit= ((*state)^lps_mask)&1;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
334 *state= c->mps_state[(*state) - (128&lps_mask)];
1287
michaelni
parents:
diff changeset
335
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
336 lps_mask= ff_h264_norm_shift[c->range>>(CABAC_BITS+2)];
1c39d9786efd optimization
michael
parents: 2116
diff changeset
337 c->range<<= lps_mask;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
338 c->low <<= lps_mask;
1c39d9786efd optimization
michael
parents: 2116
diff changeset
339 if(!(c->low & CABAC_MASK))
1c39d9786efd optimization
michael
parents: 2116
diff changeset
340 refill2(c);
1c39d9786efd optimization
michael
parents: 2116
diff changeset
341 #endif
1c39d9786efd optimization
michael
parents: 2116
diff changeset
342
1287
michaelni
parents:
diff changeset
343 return bit;
michaelni
parents:
diff changeset
344 }
michaelni
parents:
diff changeset
345
michaelni
parents:
diff changeset
346 static inline int get_cabac_bypass(CABACContext *c){
michaelni
parents:
diff changeset
347 c->low += c->low;
michaelni
parents:
diff changeset
348
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
349 if(!(c->low & CABAC_MASK))
1c39d9786efd optimization
michael
parents: 2116
diff changeset
350 refill(c);
1287
michaelni
parents:
diff changeset
351
michaelni
parents:
diff changeset
352 if(c->low < c->range){
michaelni
parents:
diff changeset
353 return 0;
michaelni
parents:
diff changeset
354 }else{
michaelni
parents:
diff changeset
355 c->low -= c->range;
michaelni
parents:
diff changeset
356 return 1;
michaelni
parents:
diff changeset
357 }
michaelni
parents:
diff changeset
358 }
michaelni
parents:
diff changeset
359
1300
e18667d1e94d FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents: 1298
diff changeset
360 /**
e18667d1e94d FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents: 1298
diff changeset
361 *
e18667d1e94d FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents: 1298
diff changeset
362 * @return the number of bytes read or 0 if no end
e18667d1e94d FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents: 1298
diff changeset
363 */
1287
michaelni
parents:
diff changeset
364 static inline int get_cabac_terminate(CABACContext *c){
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
365 c->range -= 4<<CABAC_BITS;
1287
michaelni
parents:
diff changeset
366 if(c->low < c->range){
2323
1c39d9786efd optimization
michael
parents: 2116
diff changeset
367 renorm_cabac_decoder_once(c);
1287
michaelni
parents:
diff changeset
368 return 0;
michaelni
parents:
diff changeset
369 }else{
1300
e18667d1e94d FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents: 1298
diff changeset
370 return c->bytestream - c->bytestream_start;
1287
michaelni
parents:
diff changeset
371 }
michaelni
parents:
diff changeset
372 }
michaelni
parents:
diff changeset
373
1290
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
374 /**
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
375 * get (truncated) unnary binarization.
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
376 */
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
377 static inline int get_cabac_u(CABACContext *c, uint8_t * state, int max, int max_index, int truncated){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
378 int i;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
379
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
380 for(i=0; i<max; i++){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
381 if(get_cabac(c, state)==0)
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
382 return i;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
383
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
384 if(i< max_index) state++;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
385 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
386
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
387 return truncated ? max : -1;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
388 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
389
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
390 /**
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
391 * get unary exp golomb k-th order binarization.
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
392 */
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
393 static inline int get_cabac_ueg(CABACContext *c, uint8_t * state, int max, int is_signed, int k, int max_index){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
394 int i, v;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
395 int m= 1<<k;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
396
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
397 if(get_cabac(c, state)==0)
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
398 return 0;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
399
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
400 if(0 < max_index) state++;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
401
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
402 for(i=1; i<max; i++){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
403 if(get_cabac(c, state)==0){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
404 if(is_signed && get_cabac_bypass(c)){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
405 return -i;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
406 }else
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
407 return i;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
408 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
409
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
410 if(i < max_index) state++;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
411 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
412
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
413 while(get_cabac_bypass(c)){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
414 i+= m;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
415 m+= m;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
416 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
417
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
418 v=0;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
419 while(m>>=1){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
420 v+= v + get_cabac_bypass(c);
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
421 }
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
422 i += v;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
423
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
424 if(is_signed && get_cabac_bypass(c)){
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
425 return -i;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
426 }else
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
427 return i;
dae280b939ca (truncated) unary binerization
michaelni
parents: 1287
diff changeset
428 }