1 /******************************************************************************
2 *
3 * Copyright (C) 2015 The Android Open Source Project
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 *****************************************************************************
18 * Originally developed and contributed by Ittiam Systems Pvt. Ltd, Bangalore
19 */
20
21 /**
22 *******************************************************************************
23 * @file
24 * ih264e_cavlc.c
25 *
26 * @brief
27 * Contains all the routines to code syntax elements and residuals when entropy
28 * coding chosen is CAVLC
29 *
30 * @author
31 * ittiam
32 *
33 * @par List of Functions:
34 * - ih264e_compute_zeroruns_and_trailingones()
35 * - ih264e_write_coeff4x4_cavlc()
36 * - ih264e_write_coeff8x8_cavlc()
37 * - ih264e_encode_residue()
38 * - ih264e_write_islice_mb_cavlc()
39 * - ih264e_write_pslice_mb_cavlc()
40 *
41 * @remarks
42 * None
43 *
44 *******************************************************************************
45 */
46
47 /*****************************************************************************/
48 /* File Includes */
49 /*****************************************************************************/
50
51 /* System include files */
52 #include <stdio.h>
53 #include <assert.h>
54 #include <limits.h>
55
56 /* User include files */
57 #include "ih264e_config.h"
58 #include "ih264_typedefs.h"
59 #include "iv2.h"
60 #include "ive2.h"
61 #include "ih264_debug.h"
62 #include "ih264_macros.h"
63 #include "ih264_defs.h"
64 #include "ih264e_defs.h"
65 #include "ih264e_error.h"
66 #include "ih264e_bitstream.h"
67 #include "ime_distortion_metrics.h"
68 #include "ime_defs.h"
69 #include "ime_structs.h"
70 #include "ih264_error.h"
71 #include "ih264_structs.h"
72 #include "ih264_trans_quant_itrans_iquant.h"
73 #include "ih264_inter_pred_filters.h"
74 #include "ih264_mem_fns.h"
75 #include "ih264_padding.h"
76 #include "ih264_intra_pred_filters.h"
77 #include "ih264_deblk_edge_filters.h"
78 #include "ih264_cabac_tables.h"
79 #include "irc_cntrl_param.h"
80 #include "irc_frame_info_collector.h"
81 #include "ih264e_rate_control.h"
82 #include "ih264e_cabac_structs.h"
83 #include "ih264e_structs.h"
84 #include "ih264e_encode_header.h"
85 #include "ih264_cavlc_tables.h"
86 #include "ih264e_cavlc.h"
87 #include "ih264e_statistics.h"
88 #include "ih264e_trace.h"
89
90 /*****************************************************************************/
91 /* Function Definitions */
92 /*****************************************************************************/
93
94 /**
95 *******************************************************************************
96 *
97 * @brief
98 * This function computes run of zero, number of trailing ones and sign of
99 * trailing ones basing on the significant coeff map, residual block and
100 * total nnz.
101 *
102 * @param[in] pi2_res_block
103 * Pointer to residual block containing levels in scan order
104 *
105 * @param[in] u4_total_coeff
106 * Total non-zero coefficients in that sub block
107 *
108 * @param[in] pu1_zero_run
109 * Pointer to array to store run of zeros
110 *
111 * @param[in] u4_sig_coeff_map
112 * significant coefficient map
113 *
114 * @returns u4_totzero_sign_trailone
115 * Bits 0-8 contains number of trailing ones.
116 * Bits 8-16 contains bitwise sign information of trailing one
117 * Bits 16-24 contains total number of zeros.
118 *
119 * @remarks
120 * None
121 *
122 *******************************************************************************
123 */
ih264e_compute_zeroruns_and_trailingones(WORD16 * pi2_res_block,UWORD32 u4_total_coeff,UWORD8 * pu1_zero_run,UWORD32 u4_sig_coeff_map)124 static UWORD32 ih264e_compute_zeroruns_and_trailingones(WORD16 *pi2_res_block,
125 UWORD32 u4_total_coeff,
126 UWORD8 *pu1_zero_run,
127 UWORD32 u4_sig_coeff_map)
128 {
129 UWORD32 i = 0;
130 UWORD32 u4_nnz_coeff = 0;
131 WORD32 i4_run = -1;
132 UWORD32 u4_sign = 0;
133 UWORD32 u4_tot_zero = 0;
134 UWORD32 u4_trailing1 = 0;
135 WORD32 i4_val;
136 UWORD32 u4_totzero_sign_trailone;
137 UWORD32 *pu4_zero_run;
138
139 pu4_zero_run = (void *)pu1_zero_run;
140 pu4_zero_run[0] = 0;
141 pu4_zero_run[1] = 0;
142 pu4_zero_run[2] = 0;
143 pu4_zero_run[3] = 0;
144
145 /* Compute Runs of zeros for all nnz coefficients except the last 3 */
146 if (u4_total_coeff > 3)
147 {
148 for (i = 0; u4_nnz_coeff < (u4_total_coeff-3); i++)
149 {
150 i4_run++;
151
152 i4_val = (u4_sig_coeff_map & 0x1);
153 u4_sig_coeff_map >>= 1;
154
155 if (i4_val != 0)
156 {
157 pu1_zero_run[u4_nnz_coeff++] = i4_run;
158 i4_run = -1;
159 }
160 }
161 }
162
163 /* Compute T1's, Signof(T1's) and Runs of zeros for the last 3 */
164 while (u4_nnz_coeff != u4_total_coeff)
165 {
166 i4_run++;
167
168 i4_val = (u4_sig_coeff_map & 0x1);
169 u4_sig_coeff_map >>= 1;
170
171 if (i4_val != 0)
172 {
173 if (pi2_res_block[u4_nnz_coeff] == 1)
174 {
175 pu1_zero_run[u4_nnz_coeff] = i4_run;
176 u4_trailing1++;
177 }
178 else
179 {
180 if (pi2_res_block[u4_nnz_coeff] == -1)
181 {
182 pu1_zero_run[u4_nnz_coeff] = i4_run;
183 u4_sign |= 1 << u4_trailing1;
184 u4_trailing1++;
185 }
186 else
187 {
188 pu1_zero_run[u4_nnz_coeff] = i4_run;
189 u4_trailing1 = 0;
190 u4_sign = 0;
191 }
192 }
193 i4_run = -1;
194 u4_nnz_coeff++;
195 }
196 i++;
197 }
198
199 u4_tot_zero = i - u4_total_coeff;
200 u4_totzero_sign_trailone = (u4_tot_zero << 16)|(u4_sign << 8)|u4_trailing1;
201
202 return (u4_totzero_sign_trailone);
203 }
204
205 /**
206 *******************************************************************************
207 *
208 * @brief
209 * This function generates CAVLC coded bit stream for the given residual block
210 *
211 * @param[in] pi2_res_block
212 * Pointer to residual block containing levels in scan order
213 *
214 * @param[in] u4_total_coeff
215 * Total non-zero coefficients in the sub block
216 *
217 * @param[in] u4_block_type
218 * block type
219 *
220 * @param[in] pu1_zero_run
221 * Pointer to array to store run of zeros
222 *
223 * @param[in] u4_nc
224 * average of non zero coeff from top and left blocks (when available)
225 *
226 * @param[in, out] ps_bit_stream
227 * structure pointing to a buffer holding output bit stream
228 *
229 * @param[in] u4_sig_coeff_map
230 * significant coefficient map of the residual block
231 *
232 * @returns
233 * error code
234 *
235 * @remarks
236 * If the block type is CAVLC_CHROMA_4x4_DC, then u4_nc is non-significant
237 *
238 *******************************************************************************
239 */
ih264e_write_coeff4x4_cavlc(WORD16 * pi2_res_block,UWORD32 u4_total_coeff,ENTROPY_BLK_TYPE u4_block_type,UWORD8 * pu1_zero_run,UWORD32 u4_nc,bitstrm_t * ps_bit_stream,UWORD32 u4_sig_coeff_map)240 static IH264E_ERROR_T ih264e_write_coeff4x4_cavlc(WORD16 *pi2_res_block,
241 UWORD32 u4_total_coeff,
242 ENTROPY_BLK_TYPE u4_block_type,
243 UWORD8 *pu1_zero_run,
244 UWORD32 u4_nc,
245 bitstrm_t *ps_bit_stream,
246 UWORD32 u4_sig_coeff_map)
247 {
248 IH264E_ERROR_T error_status = IH264E_SUCCESS;
249 UWORD32 u4_totzero_sign_trailone = 0;
250 UWORD32 u4_trailing_ones = 0;
251 UWORD32 u4_tot_zeros = 0;
252 UWORD32 u4_remaining_coeff = 0;
253 UWORD32 u4_sign1 = 0;
254 UWORD32 u4_max_num_coeff = 0;
255 const UWORD32 au4_max_num_nnz_coeff[] = {16, 15, 16, 4, 15};
256
257 /* validate inputs */
258 ASSERT(u4_block_type <= CAVLC_CHROMA_4x4_AC);
259
260 u4_max_num_coeff = au4_max_num_nnz_coeff[u4_block_type];
261
262 ASSERT(u4_total_coeff <= u4_max_num_coeff);
263
264 if (!u4_total_coeff)
265 {
266 UWORD32 u4_codeword = 15;
267 UWORD32 u4_codesize = 1;
268 if (u4_block_type == CAVLC_CHROMA_4x4_DC)
269 {
270 u4_codeword = 1;
271 u4_codesize = 2;
272 DEBUG("\n[%d numcoeff, %d numtrailing ones]",u4_total_coeff, 0);
273 ENTROPY_TRACE("\tnumber of non zero coeffs ",u4_total_coeff);
274 ENTROPY_TRACE("\tnumber of trailing ones ",0);
275 }
276 else
277 {
278 UWORD32 u4_vlcnum = u4_nc >> 1;
279
280 /* write coeff_token */
281 if (u4_vlcnum > 3)
282 {
283 /* Num-FLC */
284 u4_codeword = 3;
285 u4_codesize = 6;
286 }
287 else
288 {
289 /* Num-VLC 0, 1, 2 */
290 if (u4_vlcnum > 1)
291 {
292 u4_vlcnum = 2;
293 }
294 u4_codesize <<= u4_vlcnum;
295 u4_codeword >>= (4 - u4_codesize);
296 }
297
298 DEBUG("\n[%d numcoeff, %d numtrailing ones, %d nnz]",u4_total_coeff, 0, u4_nc);
299 ENTROPY_TRACE("\tnumber of non zero coeffs ",u4_total_coeff);
300 ENTROPY_TRACE("\tnC ",u4_nc);
301 }
302
303
304 DEBUG("\nCOEFF TOKEN 0: %d u4_codeword, %d u4_codesize",u4_codeword, u4_codesize);
305 ENTROPY_TRACE("\tcodeword ",u4_codeword);
306 ENTROPY_TRACE("\tcodesize ",u4_codesize);
307
308 error_status = ih264e_put_bits(ps_bit_stream, u4_codeword, u4_codesize);
309
310 return error_status;
311 }
312 else
313 {
314 /* Compute zero run, number of trailing ones and their sign. */
315 u4_totzero_sign_trailone =
316 ih264e_compute_zeroruns_and_trailingones(pi2_res_block,
317 u4_total_coeff,
318 pu1_zero_run,
319 u4_sig_coeff_map);
320 u4_trailing_ones = u4_totzero_sign_trailone & 0xFF;
321 u4_sign1 = (u4_totzero_sign_trailone >> 8)& 0xFF;
322 u4_tot_zeros = (u4_totzero_sign_trailone >> 16) & 0xFF;
323 u4_remaining_coeff = u4_total_coeff - u4_trailing_ones;
324
325 /* write coeff_token */
326 {
327 UWORD32 u4_codeword;
328 UWORD32 u4_codesize;
329 if (u4_block_type == CAVLC_CHROMA_4x4_DC)
330 {
331 u4_codeword = gu1_code_coeff_token_table_chroma[u4_trailing_ones][u4_total_coeff-1];
332 u4_codesize = gu1_size_coeff_token_table_chroma[u4_trailing_ones][u4_total_coeff-1];
333
334 DEBUG("\n[%d numcoeff, %d numtrailing ones]",u4_total_coeff, u4_trailing_ones);
335 ENTROPY_TRACE("\tnumber of non zero coeffs ",u4_total_coeff);
336 ENTROPY_TRACE("\tnumber of trailing ones ",u4_trailing_ones);
337 }
338 else
339 {
340 UWORD32 u4_vlcnum = u4_nc >> 1;
341
342 if (u4_vlcnum > 3)
343 {
344 /* Num-FLC */
345 u4_codeword = ((u4_total_coeff-1) << 2 ) + u4_trailing_ones;
346 u4_codesize = 6;
347 }
348 else
349 {
350 /* Num-VLC 0, 1, 2 */
351 if (u4_vlcnum > 1)
352 {
353 u4_vlcnum = 2;
354 }
355 u4_codeword = gu1_code_coeff_token_table[u4_vlcnum][u4_trailing_ones][u4_total_coeff-1];
356 u4_codesize = gu1_size_coeff_token_table[u4_vlcnum][u4_trailing_ones][u4_total_coeff-1];
357 }
358
359 DEBUG("\n[%d numcoeff, %d numtrailing ones, %d nnz]",u4_total_coeff, u4_trailing_ones, u4_nc);
360 ENTROPY_TRACE("\tnumber of non zero coeffs ",u4_total_coeff);
361 ENTROPY_TRACE("\tnumber of trailing ones ",u4_trailing_ones);
362 ENTROPY_TRACE("\tnC ",u4_nc);
363 }
364
365 DEBUG("\nCOEFF TOKEN 0: %d u4_codeword, %d u4_codesize",u4_codeword, u4_codesize);
366 ENTROPY_TRACE("\tcodeword ",u4_codeword);
367 ENTROPY_TRACE("\tcodesize ",u4_codesize);
368
369 error_status = ih264e_put_bits(ps_bit_stream, u4_codeword, u4_codesize);
370 }
371
372 /* write sign of trailing ones */
373 if (u4_trailing_ones)
374 {
375 DEBUG("\nT1's: %d u4_codeword, %d u4_codesize",u4_sign1, u4_trailing_ones);
376 error_status = ih264e_put_bits(ps_bit_stream, u4_sign1, u4_trailing_ones);
377 ENTROPY_TRACE("\tnumber of trailing ones ",u4_trailing_ones);
378 ENTROPY_TRACE("\tsign of trailing ones ",u4_sign1);
379 }
380
381 /* write level codes */
382 if (u4_remaining_coeff)
383 {
384 WORD32 i4_level = pi2_res_block[u4_remaining_coeff-1];
385 UWORD32 u4_escape;
386 UWORD32 u4_suffix_length = 0; // Level-VLC[N]
387 UWORD32 u4_abs_level, u4_abs_level_actual = 0;
388 WORD32 i4_sign;
389 const UWORD32 u4_rndfactor[] = {0, 0, 1, 3, 7, 15, 31};
390
391 DEBUG("\n \t%d coeff,",i4_level);
392 ENTROPY_TRACE("\tcoeff ",i4_level);
393
394 if (u4_trailing_ones < 3)
395 {
396 /* If there are less than 3 T1s, then the first non-T1 level is incremented if negative (decremented if positive)*/
397 if (i4_level < 0)
398 {
399 i4_level += 1;
400 }
401 else
402 {
403 i4_level -= 1;
404 }
405
406 u4_abs_level_actual = 1;
407
408 /* Initialize VLC table (Suffix Length) to encode the level */
409 if (u4_total_coeff > 10)
410 {
411 u4_suffix_length = 1;
412 }
413 }
414
415 i4_sign = (i4_level >> (sizeof(WORD32) * CHAR_BIT - 1));
416 u4_abs_level = ((i4_level + i4_sign) ^ i4_sign);
417
418 u4_abs_level_actual += u4_abs_level;
419
420 u4_escape = (u4_abs_level + u4_rndfactor[u4_suffix_length]) >> u4_suffix_length;
421
422 while (1)
423 {
424 UWORD32 u4_codesize;
425 UWORD32 u4_codeword;
426 UWORD32 u4_codeval;
427
428 u4_remaining_coeff--;
429
430 GATHER_CAVLC_STATS1();
431
432 {
433 u4_codeval = u4_abs_level << 1;
434 u4_codeval = u4_codeval - 2 - i4_sign;
435
436 if ((!u4_suffix_length) && (u4_escape > 7) && (u4_abs_level < 16))
437 {
438 u4_codeword = (1 << 4) + (u4_codeval - 14);
439 u4_codesize = 19;
440 }
441 else if (u4_escape > 7)
442 {
443 u4_codeword = (1 << 12) + (u4_codeval - (15 << u4_suffix_length));
444 u4_codesize = 28;
445 if (!u4_suffix_length)
446 {
447 u4_codeword -= 15;
448 }
449 }
450 else
451 {
452 u4_codeword = (1 << u4_suffix_length) + (u4_codeval & ((1 << u4_suffix_length)-1));
453 u4_codesize = (u4_codeval >> u4_suffix_length) + 1 + u4_suffix_length;
454 }
455 }
456
457 /*put the level code in bitstream*/
458 DEBUG("\nLEVEL: %d u4_codeword, %d u4_codesize",u4_codeword, u4_codesize);
459 ENTROPY_TRACE("\tcodeword ",u4_codeword);
460 ENTROPY_TRACE("\tcodesize ",u4_codesize);
461 error_status = ih264e_put_bits(ps_bit_stream, u4_codeword, u4_codesize);
462
463 if (u4_remaining_coeff == 0) break;
464
465 /*update suffix length for next level*/
466 if (u4_suffix_length == 0)
467 {
468 u4_suffix_length++;
469 }
470 if (u4_suffix_length < 6)
471 {
472 if (u4_abs_level_actual > gu1_threshold_vlc_level[u4_suffix_length])
473 {
474 u4_suffix_length++;
475 }
476 }
477
478 /* next level */
479 i4_level = pi2_res_block[u4_remaining_coeff-1];
480
481 DEBUG("\n \t%d coeff,",i4_level);
482 ENTROPY_TRACE("\tcoeff ",i4_level);
483
484 i4_sign = (i4_level >> (sizeof(WORD32) * CHAR_BIT - 1));
485 u4_abs_level = ((i4_level + i4_sign) ^ i4_sign);
486
487 u4_abs_level_actual = u4_abs_level;
488
489 u4_escape = (u4_abs_level + u4_rndfactor[u4_suffix_length]) >> u4_suffix_length;
490 }
491 }
492
493 DEBUG("\n \t %d totalzeros",u4_tot_zeros);
494 ENTROPY_TRACE("\ttotal zeros ",u4_tot_zeros);
495
496 /* Write Total Zeros */
497 if (u4_total_coeff < u4_max_num_coeff)
498 {
499 WORD32 index;
500 UWORD32 u4_codeword;
501 UWORD32 u4_codesize;
502
503 if (u4_block_type == CAVLC_CHROMA_4x4_DC)
504 {
505 UWORD8 gu1_index_zero_table_chroma[] = {0, 4, 7};
506 index = gu1_index_zero_table_chroma[u4_total_coeff-1] + u4_tot_zeros;
507 u4_codesize = gu1_size_zero_table_chroma[index];
508 u4_codeword = gu1_code_zero_table_chroma[index];
509 }
510 else
511 {
512 index = gu1_index_zero_table[u4_total_coeff-1] + u4_tot_zeros;
513 u4_codesize = gu1_size_zero_table[index];
514 u4_codeword = gu1_code_zero_table[index];
515 }
516
517 DEBUG("\nTOTAL ZEROS: %d u4_codeword, %d u4_codesize",u4_codeword, u4_codesize);
518 ENTROPY_TRACE("\tcodeword ",u4_codeword);
519 ENTROPY_TRACE("\tcodesize ",u4_codesize);
520 error_status = ih264e_put_bits(ps_bit_stream, u4_codeword, u4_codesize);
521 }
522
523 /* Write Run Before */
524 if (u4_tot_zeros)
525 {
526 UWORD32 u4_max_num_coef = u4_total_coeff-1;
527 UWORD32 u4_codeword;
528 UWORD32 u4_codesize;
529 UWORD32 u4_zeros_left = u4_tot_zeros;
530
531 while (u4_max_num_coef)
532 {
533 UWORD32 u4_run_before = pu1_zero_run[u4_max_num_coef];
534 UWORD32 u4_index;
535
536 if (u4_zeros_left > MAX_ZERO_LEFT)
537 {
538 u4_index = gu1_index_run_table[MAX_ZERO_LEFT];
539 }
540 else
541 {
542 u4_index = gu1_index_run_table[u4_zeros_left - 1];
543 }
544
545 u4_codesize = gu1_size_run_table[u4_index + u4_run_before];
546 u4_codeword = gu1_code_run_table[u4_index + u4_run_before];
547
548 DEBUG("\nRUN BEFORE ZEROS: %d u4_codeword, %d u4_codesize",u4_codeword, u4_codesize);
549 ENTROPY_TRACE("\tcodeword ",u4_codeword);
550 ENTROPY_TRACE("\tcodesize ",u4_codesize);
551 error_status = ih264e_put_bits(ps_bit_stream, u4_codeword, u4_codesize);
552
553 u4_zeros_left -= u4_run_before;
554 if (!u4_zeros_left)
555 {
556 break;
557 }
558 u4_max_num_coef--;
559 }
560 }
561 }
562
563 return error_status;
564 }
565
566 /**
567 *******************************************************************************
568 *
569 * @brief
570 * This function generates CAVLC coded bit stream for the given subblock
571 *
572 * @param[in] ps_ent_ctxt
573 * Pointer to entropy context
574 *
575 * @param[in] pi2_res_block
576 * Pointers to residual blocks of all the partitions for the current subblk
577 * (containing levels in scan order)
578 *
579 * @param[in] pu1_nnz
580 * Total non-zero coefficients of all the partitions for the current subblk
581 *
582 * @param[in] pu2_sig_coeff_map
583 * Significant coefficient map of all the partitions for the current subblk
584 *
585 * @param[in] u4_block_type
586 * entropy coding block type
587 *
588 * @param[in] u4_ngbr_avbl
589 * top and left availability of all the partitions for the current subblk
590 * (packed)
591 *
592 * @param[in] pu1_top_nnz
593 * pointer to the buffer containing nnz of all the subblks to the top
594 *
595 * @param[in] pu1_left_nnz
596 * pointer to the buffer containing nnz of all the subblks to the left
597 *
598 * @returns error status
599 *
600 * @remarks none
601 *
602 *******************************************************************************
603 */
ih264e_write_coeff8x8_cavlc(entropy_ctxt_t * ps_ent_ctxt,WORD16 ** pi2_res_block,UWORD8 * pu1_nnz,UWORD16 * pu2_sig_coeff_map,ENTROPY_BLK_TYPE u4_block_type,UWORD32 u4_ngbr_avlb,UWORD8 * pu1_top_nnz,UWORD8 * pu1_left_nnz)604 static IH264E_ERROR_T ih264e_write_coeff8x8_cavlc(entropy_ctxt_t *ps_ent_ctxt,
605 WORD16 **pi2_res_block,
606 UWORD8 *pu1_nnz,
607 UWORD16 *pu2_sig_coeff_map,
608 ENTROPY_BLK_TYPE u4_block_type,
609 UWORD32 u4_ngbr_avlb,
610 UWORD8 *pu1_top_nnz,
611 UWORD8 *pu1_left_nnz)
612 {
613 IH264E_ERROR_T error_status = IH264E_SUCCESS;
614 bitstrm_t *ps_bitstream = ps_ent_ctxt->ps_bitstrm;
615 UWORD8 *pu1_zero_run = ps_ent_ctxt->au1_zero_run, *pu1_ngbr_avbl;
616 UWORD32 u4_nC;
617 UWORD8 u1_mb_a, u1_mb_b;
618
619 pu1_ngbr_avbl = (void *)(&u4_ngbr_avlb);
620
621 /* encode ac block index 4x4 = 0*/
622 u1_mb_a = pu1_ngbr_avbl[0] & 0x0F;
623 u1_mb_b = pu1_ngbr_avbl[0] & 0xF0;
624 u4_nC = 0;
625 if (u1_mb_a)
626 u4_nC += pu1_left_nnz[0];
627 if (u1_mb_b)
628 u4_nC += pu1_top_nnz[0];
629 if (u1_mb_a && u1_mb_b)
630 u4_nC = (u4_nC + 1) >> 1;
631 pu1_left_nnz[0] = pu1_top_nnz[0] = pu1_nnz[0];
632 error_status = ih264e_write_coeff4x4_cavlc(pi2_res_block[0], pu1_nnz[0], u4_block_type, pu1_zero_run, u4_nC, ps_bitstream, pu2_sig_coeff_map[0]);
633
634 /* encode ac block index 4x4 = 1*/
635 u1_mb_a = pu1_ngbr_avbl[1] & 0x0F;
636 u1_mb_b = pu1_ngbr_avbl[1] & 0xF0;
637 u4_nC = 0;
638 if (u1_mb_a)
639 u4_nC += pu1_left_nnz[0];
640 if (u1_mb_b)
641 u4_nC += pu1_top_nnz[1];
642 if (u1_mb_a && u1_mb_b)
643 u4_nC = (u4_nC + 1) >> 1;
644 pu1_left_nnz[0] = pu1_top_nnz[1] = pu1_nnz[1];
645 error_status = ih264e_write_coeff4x4_cavlc(pi2_res_block[1], pu1_nnz[1], u4_block_type, pu1_zero_run, u4_nC, ps_bitstream, pu2_sig_coeff_map[1]);
646
647 /* encode ac block index 4x4 = 2*/
648 u1_mb_a = pu1_ngbr_avbl[2] & 0x0F;
649 u1_mb_b = pu1_ngbr_avbl[2] & 0xF0;
650 u4_nC = 0;
651 if (u1_mb_a)
652 u4_nC += pu1_left_nnz[1];
653 if (u1_mb_b)
654 u4_nC += pu1_top_nnz[0];
655 if (u1_mb_a && u1_mb_b)
656 u4_nC = (u4_nC + 1) >> 1;
657 pu1_left_nnz[1] = pu1_top_nnz[0] = pu1_nnz[2];
658 error_status = ih264e_write_coeff4x4_cavlc(pi2_res_block[2], pu1_nnz[2], u4_block_type, pu1_zero_run, u4_nC, ps_bitstream, pu2_sig_coeff_map[2]);
659
660 /* encode ac block index 4x4 = 0*/
661 u1_mb_a = pu1_ngbr_avbl[3] & 0x0F;
662 u1_mb_b = pu1_ngbr_avbl[3] & 0xF0;
663 u4_nC = 0;
664 if (u1_mb_a)
665 u4_nC += pu1_left_nnz[1];
666 if (u1_mb_b)
667 u4_nC += pu1_top_nnz[1];
668 if (u1_mb_a && u1_mb_b)
669 u4_nC = (u4_nC + 1) >> 1;
670 pu1_left_nnz[1] = pu1_top_nnz[1] = pu1_nnz[3];
671 error_status = ih264e_write_coeff4x4_cavlc(pi2_res_block[3], pu1_nnz[3], u4_block_type, pu1_zero_run, u4_nC, ps_bitstream, pu2_sig_coeff_map[3]);
672
673 return error_status;
674 }
675
676 /**
677 *******************************************************************************
678 *
679 * @brief
680 * This function encodes luma and chroma residues of a macro block when
681 * the entropy coding mode chosen is cavlc.
682 *
683 * @param[in] ps_ent_ctxt
684 * Pointer to entropy context
685 *
686 * @param[in] u4_mb_type
687 * current mb type
688 *
689 * @param[in] u4_cbp
690 * coded block pattern for the current mb
691 *
692 * @returns error code
693 *
694 * @remarks none
695 *
696 *******************************************************************************
697 */
ih264e_encode_residue(entropy_ctxt_t * ps_ent_ctxt,UWORD32 u4_mb_type,UWORD32 u4_cbp)698 static IH264E_ERROR_T ih264e_encode_residue(entropy_ctxt_t *ps_ent_ctxt,
699 UWORD32 u4_mb_type,
700 UWORD32 u4_cbp)
701 {
702 /* error status */
703 IH264E_ERROR_T error_status = IH264E_SUCCESS;
704
705 /* packed residue */
706 void *pv_mb_coeff_data = ps_ent_ctxt->pv_mb_coeff_data;
707
708 /* bit stream buffer */
709 bitstrm_t *ps_bitstream = ps_ent_ctxt->ps_bitstrm;
710
711 /* zero run */
712 UWORD8 *pu1_zero_run = ps_ent_ctxt->au1_zero_run;
713
714 /* temp var */
715 UWORD32 u4_nC, u4_ngbr_avlb;
716 UWORD8 au1_nnz[4], *pu1_ngbr_avlb, *pu1_top_nnz, *pu1_left_nnz;
717 UWORD16 au2_sig_coeff_map[4] = {0};
718 WORD16 *pi2_res_block[4] = {NULL};
719 UWORD8 *pu1_slice_idx = ps_ent_ctxt->pu1_slice_idx;
720 tu_sblk_coeff_data_t *ps_mb_coeff_data;
721 ENTROPY_BLK_TYPE e_entropy_blk_type = CAVLC_LUMA_4x4;
722
723 /* ngbr availability */
724 UWORD8 u1_mb_a, u1_mb_b;
725
726 /* cbp */
727 UWORD32 u4_cbp_luma = u4_cbp & 0xF, u4_cbp_chroma = u4_cbp >> 4;
728
729 /* mb indices */
730 WORD32 i4_mb_x, i4_mb_y;
731
732 /* derive neighbor availability */
733 i4_mb_x = ps_ent_ctxt->i4_mb_x;
734 i4_mb_y = ps_ent_ctxt->i4_mb_y;
735 pu1_slice_idx += (i4_mb_y * ps_ent_ctxt->i4_wd_mbs);
736 /* left macroblock availability */
737 u1_mb_a = (i4_mb_x == 0 ||
738 (pu1_slice_idx[i4_mb_x - 1 ] != pu1_slice_idx[i4_mb_x]))? 0 : 1;
739 /* top macroblock availability */
740 u1_mb_b = (i4_mb_y == 0 ||
741 (pu1_slice_idx[i4_mb_x-ps_ent_ctxt->i4_wd_mbs] != pu1_slice_idx[i4_mb_x]))? 0 : 1;
742
743 pu1_ngbr_avlb = (void *)(&u4_ngbr_avlb);
744 pu1_top_nnz = ps_ent_ctxt->pu1_top_nnz_luma[ps_ent_ctxt->i4_mb_x];
745 pu1_left_nnz = (UWORD8 *)&ps_ent_ctxt->u4_left_nnz_luma;
746
747 /* encode luma residue */
748
749 /* mb type intra 16x16 */
750 if (u4_mb_type == I16x16)
751 {
752 /* parse packed coeff data structure for residual data */
753 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[0], au2_sig_coeff_map[0], pi2_res_block[0]);
754 /* estimate nnz for the current mb */
755 u4_nC = 0;
756 if (u1_mb_a)
757 u4_nC += pu1_left_nnz[0];
758 if (u1_mb_b)
759 u4_nC += pu1_top_nnz[0];
760 if (u1_mb_a && u1_mb_b)
761 u4_nC = (u4_nC + 1) >> 1;
762
763 /* encode dc block */
764 ENTROPY_TRACE("Luma DC blk idx %d",0);
765 error_status = ih264e_write_coeff4x4_cavlc(pi2_res_block[0], au1_nnz[0], CAVLC_LUMA_4x4_DC, pu1_zero_run, u4_nC, ps_bitstream, au2_sig_coeff_map[0]);
766
767 e_entropy_blk_type = CAVLC_LUMA_4x4_AC;
768 }
769
770 if (u4_cbp_luma & 1)
771 {
772 /* encode ac block index 8x8 = 0*/
773 /* parse packed coeff data structure for residual data */
774 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[0], au2_sig_coeff_map[0], pi2_res_block[0]);
775 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[1], au2_sig_coeff_map[1], pi2_res_block[1]);
776 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[2], au2_sig_coeff_map[2], pi2_res_block[2]);
777 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[3], au2_sig_coeff_map[3], pi2_res_block[3]);
778 /* derive sub block neighbor availability */
779
780 pu1_ngbr_avlb[0] = (u1_mb_b << 4) | (u1_mb_a);
781 pu1_ngbr_avlb[1] = (u1_mb_b << 4) | 1;
782 pu1_ngbr_avlb[2] = (1 << 4) | (u1_mb_a);
783 pu1_ngbr_avlb[3] = 0x11;
784 /* encode sub blk */
785 ENTROPY_TRACE("Luma blk idx %d",0);
786 error_status = ih264e_write_coeff8x8_cavlc(ps_ent_ctxt, pi2_res_block, au1_nnz, au2_sig_coeff_map, e_entropy_blk_type, u4_ngbr_avlb, pu1_top_nnz, pu1_left_nnz);
787 }
788 else
789 {
790 pu1_top_nnz[0] = pu1_top_nnz[1] = 0;
791 pu1_left_nnz[0] = pu1_left_nnz[1] = 0;
792 }
793
794 if (u4_cbp_luma & 2)
795 {
796 /* encode ac block index 8x8 = 1*/
797 /* parse packed coeff data structure for residual data */
798 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[0], au2_sig_coeff_map[0], pi2_res_block[0]);
799 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[1], au2_sig_coeff_map[1], pi2_res_block[1]);
800 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[2], au2_sig_coeff_map[2], pi2_res_block[2]);
801 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[3], au2_sig_coeff_map[3], pi2_res_block[3]);
802
803 /* derive sub block neighbor availability */
804 pu1_ngbr_avlb[1] = pu1_ngbr_avlb[0] = (u1_mb_b << 4) | 1;
805 pu1_ngbr_avlb[3] = pu1_ngbr_avlb[2] = 0x11;
806 /* encode sub blk */
807 ENTROPY_TRACE("Luma blk idx %d",1);
808 error_status = ih264e_write_coeff8x8_cavlc(ps_ent_ctxt, pi2_res_block, au1_nnz, au2_sig_coeff_map, e_entropy_blk_type, u4_ngbr_avlb, pu1_top_nnz+2, pu1_left_nnz);
809 }
810 else
811 {
812 (pu1_top_nnz + 2)[0] = (pu1_top_nnz + 2)[1] = 0;
813 pu1_left_nnz[0] = pu1_left_nnz[1] = 0;
814 }
815
816 if (u4_cbp_luma & 0x4)
817 {
818 /* encode ac block index 8x8 = 2*/
819 /* parse packed coeff data structure for residual data */
820 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[0], au2_sig_coeff_map[0], pi2_res_block[0]);
821 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[1], au2_sig_coeff_map[1], pi2_res_block[1]);
822 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[2], au2_sig_coeff_map[2], pi2_res_block[2]);
823 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[3], au2_sig_coeff_map[3], pi2_res_block[3]);
824
825 /* derive sub block neighbor availability */
826 pu1_ngbr_avlb[2] = pu1_ngbr_avlb[0] = (1 << 4) | u1_mb_a;
827 pu1_ngbr_avlb[1] = pu1_ngbr_avlb[3] = 0x11;
828 /* encode sub blk */
829 ENTROPY_TRACE("Luma blk idx %d",2);
830 error_status = ih264e_write_coeff8x8_cavlc(ps_ent_ctxt, pi2_res_block, au1_nnz, au2_sig_coeff_map, e_entropy_blk_type, u4_ngbr_avlb, pu1_top_nnz, (pu1_left_nnz+2));
831 }
832 else
833 {
834 pu1_top_nnz[0] = pu1_top_nnz[1] = 0;
835 (pu1_left_nnz + 2)[0] = (pu1_left_nnz + 2)[1] = 0;
836 }
837
838 if (u4_cbp_luma & 0x8)
839 {
840 /* encode ac block index 8x8 = 3*/
841 /* parse packed coeff data structure for residual data */
842 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[0], au2_sig_coeff_map[0], pi2_res_block[0]);
843 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[1], au2_sig_coeff_map[1], pi2_res_block[1]);
844 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[2], au2_sig_coeff_map[2], pi2_res_block[2]);
845 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[3], au2_sig_coeff_map[3], pi2_res_block[3]);
846
847 /* derive sub block neighbor availability */
848 u4_ngbr_avlb = 0x11111111;
849 /* encode sub blk */
850 ENTROPY_TRACE("Luma blk idx %d",3);
851 error_status = ih264e_write_coeff8x8_cavlc(ps_ent_ctxt, pi2_res_block, au1_nnz, au2_sig_coeff_map, e_entropy_blk_type, u4_ngbr_avlb, pu1_top_nnz+2, pu1_left_nnz+2);
852 }
853 else
854 {
855 (pu1_top_nnz + 2)[0] = (pu1_top_nnz + 2)[1] = 0;
856 (pu1_left_nnz + 2)[0] = (pu1_left_nnz + 2)[1] = 0;
857 }
858
859 /* encode chroma residue */
860 if (u4_cbp_chroma & 3)
861 {
862 /* parse packed coeff data structure for residual data */
863 /* cb, cr */
864 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[0], au2_sig_coeff_map[0], pi2_res_block[0]);
865 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[1], au2_sig_coeff_map[1], pi2_res_block[1]);
866
867 /* encode dc block */
868 /* cb, cr */
869 ENTROPY_TRACE("Chroma DC blk idx %d",0);
870 error_status = ih264e_write_coeff4x4_cavlc(pi2_res_block[0], au1_nnz[0], CAVLC_CHROMA_4x4_DC, pu1_zero_run, 0, ps_bitstream, au2_sig_coeff_map[0]);
871 ENTROPY_TRACE("Chroma DC blk idx %d",1);
872 error_status = ih264e_write_coeff4x4_cavlc(pi2_res_block[1], au1_nnz[1], CAVLC_CHROMA_4x4_DC, pu1_zero_run, 0, ps_bitstream, au2_sig_coeff_map[1]);
873 }
874
875 pu1_top_nnz = ps_ent_ctxt->pu1_top_nnz_cbcr[ps_ent_ctxt->i4_mb_x];
876 pu1_left_nnz = (UWORD8 *) &ps_ent_ctxt->u4_left_nnz_cbcr;
877
878 /* encode sub blk */
879 if (u4_cbp_chroma & 0x2)
880 {
881 /* encode ac block index 8x8 = 0*/
882 /* derive sub block neighbor availability */
883 pu1_ngbr_avlb[0] = (u1_mb_b << 4) | (u1_mb_a);
884 pu1_ngbr_avlb[1] = (u1_mb_b << 4) | 1;
885 pu1_ngbr_avlb[2] = (1 << 4) | (u1_mb_a);
886 pu1_ngbr_avlb[3] = 0x11;
887
888 /* parse packed coeff data structure for residual data */
889 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[0], au2_sig_coeff_map[0], pi2_res_block[0]);
890 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[1], au2_sig_coeff_map[1], pi2_res_block[1]);
891 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[2], au2_sig_coeff_map[2], pi2_res_block[2]);
892 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[3], au2_sig_coeff_map[3], pi2_res_block[3]);
893
894 ENTROPY_TRACE("Chroma AC blk idx %d",0);
895 error_status = ih264e_write_coeff8x8_cavlc(ps_ent_ctxt, pi2_res_block, au1_nnz, au2_sig_coeff_map, CAVLC_CHROMA_4x4_AC, u4_ngbr_avlb, pu1_top_nnz, pu1_left_nnz);
896 }
897 else
898 {
899 pu1_top_nnz[0] = pu1_top_nnz[1] = 0;
900 pu1_left_nnz[0] = pu1_left_nnz[1] = 0;
901 }
902
903 pu1_top_nnz += 2;
904 pu1_left_nnz += 2;
905
906 /* encode sub blk */
907 if (u4_cbp_chroma & 0x2)
908 {
909 /* parse packed coeff data structure for residual data */
910 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[0], au2_sig_coeff_map[0], pi2_res_block[0]);
911 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[1], au2_sig_coeff_map[1], pi2_res_block[1]);
912 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[2], au2_sig_coeff_map[2], pi2_res_block[2]);
913 PARSE_COEFF_DATA_BLOCK_4x4(pv_mb_coeff_data, ps_mb_coeff_data, au1_nnz[3], au2_sig_coeff_map[3], pi2_res_block[3]);
914
915 ENTROPY_TRACE("Chroma AC blk idx %d",1);
916 error_status = ih264e_write_coeff8x8_cavlc(ps_ent_ctxt, pi2_res_block, au1_nnz, au2_sig_coeff_map, CAVLC_CHROMA_4x4_AC, u4_ngbr_avlb, pu1_top_nnz, pu1_left_nnz);
917 }
918 else
919 {
920 pu1_top_nnz[0] = pu1_top_nnz[1] = 0;
921 pu1_left_nnz[0] = pu1_left_nnz[1] = 0;
922 }
923
924 /* store the index of the next mb coeff data */
925 ps_ent_ctxt->pv_mb_coeff_data = pv_mb_coeff_data;
926
927 return error_status;
928 }
929
930
931 /**
932 *******************************************************************************
933 *
934 * @brief
935 * This function generates CAVLC coded bit stream for an Intra Slice.
936 *
937 * @description
938 * The mb syntax layer for intra slices constitutes luma mb mode, luma sub modes
939 * (if present), mb qp delta, coded block pattern, chroma mb mode and
940 * luma/chroma residue. These syntax elements are written as directed by table
941 * 7.3.5 of h264 specification.
942 *
943 * @param[in] ps_ent_ctxt
944 * pointer to entropy context
945 *
946 * @returns error code
947 *
948 * @remarks none
949 *
950 *******************************************************************************
951 */
ih264e_write_islice_mb_cavlc(entropy_ctxt_t * ps_ent_ctxt)952 IH264E_ERROR_T ih264e_write_islice_mb_cavlc(entropy_ctxt_t *ps_ent_ctxt)
953 {
954 /* error status */
955 IH264E_ERROR_T error_status = IH264E_SUCCESS;
956
957 /* bit stream ptr */
958 bitstrm_t *ps_bitstream = ps_ent_ctxt->ps_bitstrm;
959
960 /* packed header data */
961 UWORD8 *pu1_byte = ps_ent_ctxt->pv_mb_header_data;
962
963 /* mb header info */
964 /*
965 * mb_tpm : mb type plus mode
966 * mb_type : luma mb type and chroma mb type are packed
967 * cbp : coded block pattern
968 * mb_qp_delta : mb qp delta
969 * chroma_intra_mode : chroma intra mode
970 * luma_intra_mode : luma intra mode
971 */
972 WORD32 mb_tpm, mb_type, cbp, chroma_intra_mode, luma_intra_mode;
973 WORD8 mb_qp_delta;
974
975 /* temp var */
976 WORD32 i, mb_type_stream;
977
978 WORD32 bitstream_start_offset, bitstream_end_offset;
979
980 /* Starting bitstream offset for header in bits */
981 bitstream_start_offset = GET_NUM_BITS(ps_bitstream);
982
983
984 /********************************************************************/
985 /* BEGIN HEADER GENERATION */
986 /********************************************************************/
987
988 /* mb header info */
989 mb_tpm = *pu1_byte++;
990 cbp = *pu1_byte++;
991 mb_qp_delta = *pu1_byte++;
992
993 /* mb type */
994 mb_type = mb_tpm & 0xF;
995 /* is intra ? */
996 if (mb_type == I16x16)
997 {
998 UWORD32 u4_cbp_l, u4_cbp_c;
999
1000 u4_cbp_c = (cbp >> 4);
1001 u4_cbp_l = (cbp & 0xF);
1002 luma_intra_mode = (mb_tpm >> 4) & 3;
1003 chroma_intra_mode = (mb_tpm >> 6);
1004
1005 mb_type_stream = luma_intra_mode + 1 + (u4_cbp_c << 2) + (u4_cbp_l == 15) * 12;
1006
1007 /* write mb type */
1008 PUT_BITS_UEV(ps_bitstream, mb_type_stream, error_status, "mb type");
1009
1010 /* intra_chroma_pred_mode */
1011 PUT_BITS_UEV(ps_bitstream, chroma_intra_mode, error_status, "intra_chroma_pred_mode");
1012 }
1013 else if (mb_type == I4x4)
1014 {
1015 /* mb sub blk modes */
1016 WORD32 intra_pred_mode_flag, rem_intra_mode;
1017 WORD32 byte;
1018
1019 chroma_intra_mode = (mb_tpm >> 6);
1020
1021 /* write mb type */
1022 PUT_BITS_UEV(ps_bitstream, 0, error_status, "mb type");
1023
1024 for (i = 0; i < 16; i += 2)
1025 {
1026 /* sub blk idx 1 */
1027 byte = *pu1_byte++;
1028
1029 intra_pred_mode_flag = byte & 0x1;
1030
1031 /* prev_intra4x4_pred_mode_flag */
1032 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1033
1034 /* rem_intra4x4_pred_mode */
1035 if (!intra_pred_mode_flag)
1036 {
1037 rem_intra_mode = (byte & 0xF) >> 1;
1038 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1039 }
1040
1041 /* sub blk idx 2 */
1042 byte >>= 4;
1043
1044 intra_pred_mode_flag = byte & 0x1;
1045
1046 /* prev_intra4x4_pred_mode_flag */
1047 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1048
1049 /* rem_intra4x4_pred_mode */
1050 if (!intra_pred_mode_flag)
1051 {
1052 rem_intra_mode = (byte & 0xF) >> 1;
1053 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1054 }
1055 }
1056
1057 /* intra_chroma_pred_mode */
1058 PUT_BITS_UEV(ps_bitstream, chroma_intra_mode, error_status, "intra_chroma_pred_mode");
1059 }
1060 else if (mb_type == I8x8)
1061 {
1062 /* transform 8x8 flag */
1063 UWORD32 u4_transform_size_8x8_flag = ps_ent_ctxt->i1_transform_8x8_mode_flag;
1064
1065 /* mb sub blk modes */
1066 WORD32 intra_pred_mode_flag, rem_intra_mode;
1067 WORD32 byte;
1068
1069 chroma_intra_mode = (mb_tpm >> 6);
1070
1071 ASSERT(0);
1072
1073 /* write mb type */
1074 PUT_BITS_UEV(ps_bitstream, 0, error_status, "mb type");
1075
1076 /* u4_transform_size_8x8_flag */
1077 PUT_BITS(ps_bitstream, u4_transform_size_8x8_flag, 1, error_status, "u4_transform_size_8x8_flag");
1078
1079 /* write sub block modes */
1080 for (i = 0; i < 4; i++)
1081 {
1082 /* sub blk idx 1 */
1083 byte = *pu1_byte++;
1084
1085 intra_pred_mode_flag = byte & 0x1;
1086
1087 /* prev_intra4x4_pred_mode_flag */
1088 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1089
1090 /* rem_intra4x4_pred_mode */
1091 if (!intra_pred_mode_flag)
1092 {
1093 rem_intra_mode = (byte & 0xF) >> 1;
1094 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1095 }
1096
1097 /* sub blk idx 2 */
1098 byte >>= 4;
1099
1100 intra_pred_mode_flag = byte & 0x1;
1101
1102 /* prev_intra4x4_pred_mode_flag */
1103 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1104
1105 /* rem_intra4x4_pred_mode */
1106 if (!intra_pred_mode_flag)
1107 {
1108 rem_intra_mode = (byte & 0xF) >> 1;
1109 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1110 }
1111 }
1112
1113 /* intra_chroma_pred_mode */
1114 PUT_BITS_UEV(ps_bitstream, chroma_intra_mode, error_status, "intra_chroma_pred_mode");
1115 }
1116 else
1117 {
1118 }
1119
1120 /* coded_block_pattern */
1121 if (mb_type != I16x16)
1122 {
1123 PUT_BITS_UEV(ps_bitstream, gu1_cbp_map_tables[cbp][0], error_status, "coded_block_pattern");
1124 }
1125
1126 if (cbp || mb_type == I16x16)
1127 {
1128 /* mb_qp_delta */
1129 PUT_BITS_SEV(ps_bitstream, mb_qp_delta, error_status, "mb_qp_delta");
1130 }
1131
1132 /* Ending bitstream offset for header in bits */
1133 bitstream_end_offset = GET_NUM_BITS(ps_bitstream);
1134
1135 ps_ent_ctxt->u4_header_bits[0] += bitstream_end_offset - bitstream_start_offset;
1136
1137 /* Starting bitstream offset for residue */
1138 bitstream_start_offset = bitstream_end_offset;
1139
1140 /* residual */
1141 error_status = ih264e_encode_residue(ps_ent_ctxt, mb_type, cbp);
1142
1143 /* Ending bitstream offset for reside in bits */
1144 bitstream_end_offset = GET_NUM_BITS(ps_bitstream);
1145 ps_ent_ctxt->u4_residue_bits[0] += bitstream_end_offset - bitstream_start_offset;
1146
1147 /* store the index of the next mb syntax layer */
1148 ps_ent_ctxt->pv_mb_header_data = pu1_byte;
1149
1150 return error_status;
1151 }
1152
1153 /**
1154 *******************************************************************************
1155 *
1156 * @brief
1157 * This function generates CAVLC coded bit stream for Inter slices
1158 *
1159 * @description
1160 * The mb syntax layer for inter slices constitutes luma mb mode, luma sub modes
1161 * (if present), mb qp delta, coded block pattern, chroma mb mode and
1162 * luma/chroma residue. These syntax elements are written as directed by table
1163 * 7.3.5 of h264 specification
1164 *
1165 * @param[in] ps_ent_ctxt
1166 * pointer to entropy context
1167 *
1168 * @returns error code
1169 *
1170 * @remarks none
1171 *
1172 *******************************************************************************
1173 */
ih264e_write_pslice_mb_cavlc(entropy_ctxt_t * ps_ent_ctxt)1174 IH264E_ERROR_T ih264e_write_pslice_mb_cavlc(entropy_ctxt_t *ps_ent_ctxt)
1175 {
1176 /* error status */
1177 IH264E_ERROR_T error_status = IH264E_SUCCESS;
1178
1179 /* bit stream ptr */
1180 bitstrm_t *ps_bitstream = ps_ent_ctxt->ps_bitstrm;
1181
1182 /* packed header data */
1183 UWORD8 *pu1_byte = ps_ent_ctxt->pv_mb_header_data;
1184
1185 /* mb header info */
1186 /*
1187 * mb_tpm : mb type plus mode
1188 * mb_type : luma mb type and chroma mb type are packed
1189 * cbp : coded block pattern
1190 * mb_qp_delta : mb qp delta
1191 * chroma_intra_mode : chroma intra mode
1192 * luma_intra_mode : luma intra mode
1193 * ps_pu : Pointer to the array of structures having motion vectors, size
1194 * and position of sub partitions
1195 */
1196 WORD32 mb_tpm, mb_type, cbp, chroma_intra_mode, luma_intra_mode;
1197 WORD8 mb_qp_delta;
1198
1199 /* temp var */
1200 WORD32 i, mb_type_stream, cbptable = 1;
1201
1202 WORD32 is_inter = 0;
1203
1204 WORD32 bitstream_start_offset, bitstream_end_offset;
1205
1206 /* Starting bitstream offset for header in bits */
1207 bitstream_start_offset = GET_NUM_BITS(ps_bitstream);
1208
1209 /********************************************************************/
1210 /* BEGIN HEADER GENERATION */
1211 /********************************************************************/
1212
1213 /* mb header info */
1214 mb_tpm = *pu1_byte++;
1215
1216 /* mb type */
1217 mb_type = mb_tpm & 0xF;
1218
1219 /* check for skip */
1220 if (mb_type == PSKIP)
1221 {
1222 UWORD32 *nnz;
1223
1224 is_inter = 1;
1225
1226 /* increment skip counter */
1227 (*ps_ent_ctxt->pi4_mb_skip_run)++;
1228
1229 /* store the index of the next mb syntax layer */
1230 ps_ent_ctxt->pv_mb_header_data = pu1_byte;
1231
1232 /* set nnz to zero */
1233 ps_ent_ctxt->u4_left_nnz_luma = 0;
1234 nnz = (UWORD32 *)ps_ent_ctxt->pu1_top_nnz_luma[ps_ent_ctxt->i4_mb_x];
1235 *nnz = 0;
1236 ps_ent_ctxt->u4_left_nnz_cbcr = 0;
1237 nnz = (UWORD32 *)ps_ent_ctxt->pu1_top_nnz_cbcr[ps_ent_ctxt->i4_mb_x];
1238 *nnz = 0;
1239
1240 /* residual */
1241 error_status = ih264e_encode_residue(ps_ent_ctxt, P16x16, 0);
1242
1243 bitstream_end_offset = GET_NUM_BITS(ps_bitstream);
1244
1245 ps_ent_ctxt->u4_header_bits[is_inter] += bitstream_end_offset - bitstream_start_offset;
1246
1247 return error_status;
1248 }
1249
1250 /* remaining mb header info */
1251 cbp = *pu1_byte++;
1252 mb_qp_delta = *pu1_byte++;
1253
1254 /* mb skip run */
1255 PUT_BITS_UEV(ps_bitstream, *ps_ent_ctxt->pi4_mb_skip_run, error_status, "mb skip run");
1256
1257 /* reset skip counter */
1258 *ps_ent_ctxt->pi4_mb_skip_run = 0;
1259
1260 /* is intra ? */
1261 if (mb_type == I16x16)
1262 {
1263 UWORD32 u4_cbp_l, u4_cbp_c;
1264
1265 is_inter = 0;
1266
1267 u4_cbp_c = (cbp >> 4);
1268 u4_cbp_l = (cbp & 0xF);
1269 luma_intra_mode = (mb_tpm >> 4) & 3;
1270 chroma_intra_mode = (mb_tpm >> 6);
1271
1272 mb_type_stream = luma_intra_mode + 1 + (u4_cbp_c << 2) + (u4_cbp_l == 15) * 12;
1273
1274 mb_type_stream += 5;
1275
1276 /* write mb type */
1277 PUT_BITS_UEV(ps_bitstream, mb_type_stream, error_status, "mb type");
1278
1279 /* intra_chroma_pred_mode */
1280 PUT_BITS_UEV(ps_bitstream, chroma_intra_mode, error_status, "intra_chroma_pred_mode");
1281 }
1282 else if (mb_type == I4x4)
1283 {
1284 /* mb sub blk modes */
1285 WORD32 intra_pred_mode_flag, rem_intra_mode;
1286 WORD32 byte;
1287
1288 is_inter = 0;
1289
1290 chroma_intra_mode = (mb_tpm >> 6);
1291 cbptable = 0;
1292
1293 /* write mb type */
1294 PUT_BITS_UEV(ps_bitstream, 5, error_status, "mb type");
1295
1296 for (i = 0; i < 16; i += 2)
1297 {
1298 /* sub blk idx 1 */
1299 byte = *pu1_byte++;
1300
1301 intra_pred_mode_flag = byte & 0x1;
1302
1303 /* prev_intra4x4_pred_mode_flag */
1304 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1305
1306 /* rem_intra4x4_pred_mode */
1307 if (!intra_pred_mode_flag)
1308 {
1309 rem_intra_mode = (byte & 0xF) >> 1;
1310 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1311 }
1312
1313 /* sub blk idx 2 */
1314 byte >>= 4;
1315
1316 intra_pred_mode_flag = byte & 0x1;
1317
1318 /* prev_intra4x4_pred_mode_flag */
1319 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1320
1321 /* rem_intra4x4_pred_mode */
1322 if (!intra_pred_mode_flag)
1323 {
1324 rem_intra_mode = (byte & 0xF) >> 1;
1325 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1326 }
1327 }
1328
1329 /* intra_chroma_pred_mode */
1330 PUT_BITS_UEV(ps_bitstream, chroma_intra_mode, error_status, "intra_chroma_pred_mode");
1331 }
1332 else if (mb_type == I8x8)
1333 {
1334 /* transform 8x8 flag */
1335 UWORD32 u4_transform_size_8x8_flag = ps_ent_ctxt->i1_transform_8x8_mode_flag;
1336
1337 /* mb sub blk modes */
1338 WORD32 intra_pred_mode_flag, rem_intra_mode;
1339 WORD32 byte;
1340
1341 is_inter = 0;
1342
1343 chroma_intra_mode = (mb_tpm >> 6);
1344 cbptable = 0;
1345
1346 ASSERT(0);
1347
1348 /* write mb type */
1349 PUT_BITS_UEV(ps_bitstream, 5, error_status, "mb type");
1350
1351 /* u4_transform_size_8x8_flag */
1352 PUT_BITS(ps_bitstream, u4_transform_size_8x8_flag, 1, error_status, "u4_transform_size_8x8_flag");
1353
1354 /* write sub block modes */
1355 for (i = 0; i < 4; i++)
1356 {
1357 /* sub blk idx 1 */
1358 byte = *pu1_byte++;
1359
1360 intra_pred_mode_flag = byte & 0x1;
1361
1362 /* prev_intra4x4_pred_mode_flag */
1363 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1364
1365 /* rem_intra4x4_pred_mode */
1366 if (!intra_pred_mode_flag)
1367 {
1368 rem_intra_mode = (byte & 0xF) >> 1;
1369 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1370 }
1371
1372 /* sub blk idx 2 */
1373 byte >>= 4;
1374
1375 intra_pred_mode_flag = byte & 0x1;
1376
1377 /* prev_intra4x4_pred_mode_flag */
1378 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1379
1380 /* rem_intra4x4_pred_mode */
1381 if (!intra_pred_mode_flag)
1382 {
1383 rem_intra_mode = (byte & 0xF) >> 1;
1384 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1385 }
1386 }
1387
1388 /* intra_chroma_pred_mode */
1389 PUT_BITS_UEV(ps_bitstream, chroma_intra_mode, error_status, "intra_chroma_pred_mode");
1390 }
1391 else
1392 {
1393 /* inter macro block partition cnt */
1394 const UWORD8 au1_part_cnt[] = { 1, 2, 2, 4 };
1395
1396 /* mv ptr */
1397 WORD16 *pi2_mv_ptr = (WORD16 *)pu1_byte;
1398
1399 /* number of partitions for the current mb */
1400 UWORD32 u4_part_cnt = au1_part_cnt[mb_type - 3];
1401
1402 is_inter = 1;
1403
1404 /* write mb type */
1405 PUT_BITS_UEV(ps_bitstream, mb_type - 3, error_status, "mb type");
1406
1407 for (i = 0; i < (WORD32)u4_part_cnt; i++)
1408 {
1409 PUT_BITS_SEV(ps_bitstream, *pi2_mv_ptr++, error_status, "mv x");
1410 PUT_BITS_SEV(ps_bitstream, *pi2_mv_ptr++, error_status, "mv y");
1411 }
1412
1413 pu1_byte = (UWORD8 *)pi2_mv_ptr;
1414 }
1415
1416 /* coded_block_pattern */
1417 if (mb_type != I16x16)
1418 {
1419 PUT_BITS_UEV(ps_bitstream, gu1_cbp_map_tables[cbp][cbptable], error_status, "coded_block_pattern");
1420 }
1421
1422 if (cbp || mb_type == I16x16)
1423 {
1424 /* mb_qp_delta */
1425 PUT_BITS_SEV(ps_bitstream, mb_qp_delta, error_status, "mb_qp_delta");
1426 }
1427
1428 /* Ending bitstream offset for header in bits */
1429 bitstream_end_offset = GET_NUM_BITS(ps_bitstream);
1430
1431 ps_ent_ctxt->u4_header_bits[is_inter] += bitstream_end_offset - bitstream_start_offset;
1432
1433 /* start bitstream offset for residue in bits */
1434 bitstream_start_offset = bitstream_end_offset;
1435
1436 /* residual */
1437 error_status = ih264e_encode_residue(ps_ent_ctxt, mb_type, cbp);
1438
1439 /* Ending bitstream offset for residue in bits */
1440 bitstream_end_offset = GET_NUM_BITS(ps_bitstream);
1441
1442 ps_ent_ctxt->u4_residue_bits[is_inter] += bitstream_end_offset - bitstream_start_offset;
1443
1444 /* store the index of the next mb syntax layer */
1445 ps_ent_ctxt->pv_mb_header_data = pu1_byte;
1446
1447 return error_status;
1448 }
1449
1450
1451 /**
1452 *******************************************************************************
1453 *
1454 * @brief
1455 * This function generates CAVLC coded bit stream for B slices
1456 *
1457 * @description
1458 * The mb syntax layer for inter slices constitutes luma mb mode, luma sub modes
1459 * (if present), mb qp delta, coded block pattern, chroma mb mode and
1460 * luma/chroma residue. These syntax elements are written as directed by table
1461 * 7.3.5 of h264 specification
1462 *
1463 * @param[in] ps_ent_ctxt
1464 * pointer to entropy context
1465 *
1466 * @returns error code
1467 *
1468 * @remarks none
1469 *
1470 *******************************************************************************
1471 */
ih264e_write_bslice_mb_cavlc(entropy_ctxt_t * ps_ent_ctxt)1472 IH264E_ERROR_T ih264e_write_bslice_mb_cavlc(entropy_ctxt_t *ps_ent_ctxt)
1473 {
1474 /* error status */
1475 IH264E_ERROR_T error_status = IH264E_SUCCESS;
1476
1477 /* bit stream ptr */
1478 bitstrm_t *ps_bitstream = ps_ent_ctxt->ps_bitstrm;
1479
1480 /* packed header data */
1481 UWORD8 *pu1_byte = ps_ent_ctxt->pv_mb_header_data;
1482
1483 /* mb header info */
1484 /*
1485 * mb_tpm : mb type plus mode
1486 * mb_type : luma mb type and chroma mb type are packed
1487 * cbp : coded block pattern
1488 * mb_qp_delta : mb qp delta
1489 * chroma_intra_mode : chroma intra mode
1490 * luma_intra_mode : luma intra mode
1491 * ps_pu : Pointer to the array of structures having motion vectors, size
1492 * and position of sub partitions
1493 */
1494 WORD32 mb_tpm, mb_type, cbp, chroma_intra_mode, luma_intra_mode;
1495 WORD8 mb_qp_delta;
1496
1497 /* temp var */
1498 WORD32 i, mb_type_stream, cbptable = 1;
1499
1500 WORD32 is_inter = 0;
1501
1502 WORD32 bitstream_start_offset, bitstream_end_offset;
1503
1504 /* Starting bitstream offset for header in bits */
1505 bitstream_start_offset = GET_NUM_BITS(ps_bitstream);
1506
1507 /********************************************************************/
1508 /* BEGIN HEADER GENERATION */
1509 /********************************************************************/
1510
1511 mb_tpm = *pu1_byte++;
1512
1513 /* mb type */
1514 mb_type = mb_tpm & 0xF;
1515
1516 /* check for skip */
1517 if (mb_type == BSKIP)
1518 {
1519 UWORD32 *nnz;
1520
1521 is_inter = 1;
1522
1523 /* increment skip counter */
1524 (*ps_ent_ctxt->pi4_mb_skip_run)++;
1525
1526 /* store the index of the next mb syntax layer */
1527 ps_ent_ctxt->pv_mb_header_data = pu1_byte;
1528
1529 /* set nnz to zero */
1530 ps_ent_ctxt->u4_left_nnz_luma = 0;
1531 nnz = (UWORD32 *)ps_ent_ctxt->pu1_top_nnz_luma[ps_ent_ctxt->i4_mb_x];
1532 *nnz = 0;
1533 ps_ent_ctxt->u4_left_nnz_cbcr = 0;
1534 nnz = (UWORD32 *)ps_ent_ctxt->pu1_top_nnz_cbcr[ps_ent_ctxt->i4_mb_x];
1535 *nnz = 0;
1536
1537 /* residual */
1538 error_status = ih264e_encode_residue(ps_ent_ctxt, B16x16, 0);
1539
1540 bitstream_end_offset = GET_NUM_BITS(ps_bitstream);
1541
1542 ps_ent_ctxt->u4_header_bits[is_inter] += bitstream_end_offset
1543 - bitstream_start_offset;
1544
1545 return error_status;
1546 }
1547
1548
1549 /* remaining mb header info */
1550 cbp = *pu1_byte++;
1551 mb_qp_delta = *pu1_byte++;
1552
1553 /* mb skip run */
1554 PUT_BITS_UEV(ps_bitstream, *ps_ent_ctxt->pi4_mb_skip_run, error_status, "mb skip run");
1555
1556 /* reset skip counter */
1557 *ps_ent_ctxt->pi4_mb_skip_run = 0;
1558
1559 /* is intra ? */
1560 if (mb_type == I16x16)
1561 {
1562 UWORD32 u4_cbp_l, u4_cbp_c;
1563
1564 is_inter = 0;
1565
1566 u4_cbp_c = (cbp >> 4);
1567 u4_cbp_l = (cbp & 0xF);
1568 luma_intra_mode = (mb_tpm >> 4) & 3;
1569 chroma_intra_mode = (mb_tpm >> 6);
1570
1571 mb_type_stream = luma_intra_mode + 1 + (u4_cbp_c << 2) + (u4_cbp_l == 15) * 12;
1572
1573 mb_type_stream += 23;
1574
1575 /* write mb type */
1576 PUT_BITS_UEV(ps_bitstream, mb_type_stream, error_status, "mb type");
1577
1578 /* intra_chroma_pred_mode */
1579 PUT_BITS_UEV(ps_bitstream, chroma_intra_mode, error_status, "intra_chroma_pred_mode");
1580 }
1581 else if (mb_type == I4x4)
1582 {
1583 /* mb sub blk modes */
1584 WORD32 intra_pred_mode_flag, rem_intra_mode;
1585 WORD32 byte;
1586
1587 is_inter = 0;
1588
1589 chroma_intra_mode = (mb_tpm >> 6);
1590 cbptable = 0;
1591
1592 /* write mb type */
1593 PUT_BITS_UEV(ps_bitstream, 23, error_status, "mb type");
1594
1595 for (i = 0; i < 16; i += 2)
1596 {
1597 /* sub blk idx 1 */
1598 byte = *pu1_byte++;
1599
1600 intra_pred_mode_flag = byte & 0x1;
1601
1602 /* prev_intra4x4_pred_mode_flag */
1603 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1604
1605 /* rem_intra4x4_pred_mode */
1606 if (!intra_pred_mode_flag)
1607 {
1608 rem_intra_mode = (byte & 0xF) >> 1;
1609 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1610 }
1611
1612 /* sub blk idx 2 */
1613 byte >>= 4;
1614
1615 intra_pred_mode_flag = byte & 0x1;
1616
1617 /* prev_intra4x4_pred_mode_flag */
1618 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1619
1620 /* rem_intra4x4_pred_mode */
1621 if (!intra_pred_mode_flag)
1622 {
1623 rem_intra_mode = (byte & 0xF) >> 1;
1624 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1625 }
1626 }
1627
1628 /* intra_chroma_pred_mode */
1629 PUT_BITS_UEV(ps_bitstream, chroma_intra_mode, error_status, "intra_chroma_pred_mode");
1630 }
1631 else if (mb_type == I8x8)
1632 {
1633 /* transform 8x8 flag */
1634 UWORD32 u4_transform_size_8x8_flag = ps_ent_ctxt->i1_transform_8x8_mode_flag;
1635
1636 /* mb sub blk modes */
1637 WORD32 intra_pred_mode_flag, rem_intra_mode;
1638 WORD32 byte;
1639
1640 is_inter = 0;
1641
1642 chroma_intra_mode = (mb_tpm >> 6);
1643 cbptable = 0;
1644
1645 ASSERT(0);
1646
1647 /* write mb type */
1648 PUT_BITS_UEV(ps_bitstream, 23, error_status, "mb type");
1649
1650 /* u4_transform_size_8x8_flag */
1651 PUT_BITS(ps_bitstream, u4_transform_size_8x8_flag, 1, error_status, "u4_transform_size_8x8_flag");
1652
1653 /* write sub block modes */
1654 for (i = 0; i < 4; i++)
1655 {
1656 /* sub blk idx 1 */
1657 byte = *pu1_byte++;
1658
1659 intra_pred_mode_flag = byte & 0x1;
1660
1661 /* prev_intra4x4_pred_mode_flag */
1662 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1663
1664 /* rem_intra4x4_pred_mode */
1665 if (!intra_pred_mode_flag)
1666 {
1667 rem_intra_mode = (byte & 0xF) >> 1;
1668 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1669 }
1670
1671 /* sub blk idx 2 */
1672 byte >>= 4;
1673
1674 intra_pred_mode_flag = byte & 0x1;
1675
1676 /* prev_intra4x4_pred_mode_flag */
1677 PUT_BITS(ps_bitstream, intra_pred_mode_flag, 1, error_status, "prev_intra4x4_pred_mode_flag");
1678
1679 /* rem_intra4x4_pred_mode */
1680 if (!intra_pred_mode_flag)
1681 {
1682 rem_intra_mode = (byte & 0xF) >> 1;
1683 PUT_BITS(ps_bitstream, rem_intra_mode, 3, error_status, "rem_intra4x4_pred_mode");
1684 }
1685 }
1686
1687 /* intra_chroma_pred_mode */
1688 PUT_BITS_UEV(ps_bitstream, chroma_intra_mode, error_status, "intra_chroma_pred_mode");
1689 }
1690 else if(mb_type == BDIRECT)
1691 {
1692 is_inter = 1;
1693 /* write mb type */
1694 PUT_BITS_UEV(ps_bitstream, B_DIRECT_16x16, error_status, "mb type");
1695 }
1696 else /* if mb_type == B16x16 */
1697 {
1698 /* inter macro block partition cnt for 16x16 16x8 8x16 8x8 */
1699 const UWORD8 au1_part_cnt[] = { 1, 2, 2, 4 };
1700
1701 /* mv ptr */
1702 WORD16 *pi2_mvd_ptr = (WORD16 *)pu1_byte;
1703
1704 /* number of partitions for the current mb */
1705 UWORD32 u4_part_cnt = au1_part_cnt[mb_type - B16x16];
1706
1707 /* Get the pred modes */
1708 WORD32 i4_mb_part_pred_mode = (mb_tpm >> 4);
1709
1710 is_inter = 1;
1711
1712 mb_type_stream = mb_type - B16x16 + B_L0_16x16 + i4_mb_part_pred_mode;
1713
1714 /* write mb type */
1715 PUT_BITS_UEV(ps_bitstream, mb_type_stream, error_status, "mb type");
1716
1717 for (i = 0; i < (WORD32)u4_part_cnt; i++)
1718 {
1719 if (i4_mb_part_pred_mode != PRED_L1)/* || PRED_BI */
1720 {
1721 PUT_BITS_SEV(ps_bitstream, *pi2_mvd_ptr, error_status, "mv l0 x");
1722 pi2_mvd_ptr++;
1723 PUT_BITS_SEV(ps_bitstream, *pi2_mvd_ptr, error_status, "mv l0 y");
1724 pi2_mvd_ptr++;
1725 }
1726 if (i4_mb_part_pred_mode != PRED_L0)/* || PRED_BI */
1727 {
1728 PUT_BITS_SEV(ps_bitstream, *pi2_mvd_ptr, error_status, "mv l1 x");
1729 pi2_mvd_ptr++;
1730 PUT_BITS_SEV(ps_bitstream, *pi2_mvd_ptr, error_status, "mv l1 y");
1731 pi2_mvd_ptr++;
1732 }
1733 }
1734
1735 pu1_byte = (UWORD8 *)pi2_mvd_ptr;
1736 }
1737
1738 /* coded_block_pattern */
1739 if (mb_type != I16x16)
1740 {
1741 PUT_BITS_UEV(ps_bitstream, gu1_cbp_map_tables[cbp][cbptable], error_status, "coded_block_pattern");
1742 }
1743
1744 if (cbp || mb_type == I16x16)
1745 {
1746 /* mb_qp_delta */
1747 PUT_BITS_SEV(ps_bitstream, mb_qp_delta, error_status, "mb_qp_delta");
1748 }
1749
1750 /* Ending bitstream offset for header in bits */
1751 bitstream_end_offset = GET_NUM_BITS(ps_bitstream);
1752
1753 ps_ent_ctxt->u4_header_bits[is_inter] += bitstream_end_offset - bitstream_start_offset;
1754
1755 /* start bitstream offset for residue in bits */
1756 bitstream_start_offset = bitstream_end_offset;
1757
1758 /* residual */
1759 error_status = ih264e_encode_residue(ps_ent_ctxt, mb_type, cbp);
1760
1761 /* Ending bitstream offset for residue in bits */
1762 bitstream_end_offset = GET_NUM_BITS(ps_bitstream);
1763
1764 ps_ent_ctxt->u4_residue_bits[is_inter] += bitstream_end_offset - bitstream_start_offset;
1765
1766 /* store the index of the next mb syntax layer */
1767 ps_ent_ctxt->pv_mb_header_data = pu1_byte;
1768
1769 return error_status;
1770 }
1771