Mercurial > libavcodec.hg
comparison h264.c @ 2898:95f469274a1d libavcodec
6% faster decode_cabac_residual
author | lorenm |
---|---|
date | Tue, 27 Sep 2005 05:12:13 +0000 |
parents | a5360f2a673e |
children | 71ca5ed04789 |
comparison
equal
deleted
inserted
replaced
2897:a5360f2a673e | 2898:95f469274a1d |
---|---|
5515 static const int significant_coeff_flag_field_offset[2] = { 105, 277 }; | 5515 static const int significant_coeff_flag_field_offset[2] = { 105, 277 }; |
5516 static const int last_significant_coeff_flag_field_offset[2] = { 166, 338 }; | 5516 static const int last_significant_coeff_flag_field_offset[2] = { 166, 338 }; |
5517 static const int significant_coeff_flag_offset[6] = { 0, 15, 29, 44, 47, 297 }; | 5517 static const int significant_coeff_flag_offset[6] = { 0, 15, 29, 44, 47, 297 }; |
5518 static const int last_significant_coeff_flag_offset[6] = { 0, 15, 29, 44, 47, 251 }; | 5518 static const int last_significant_coeff_flag_offset[6] = { 0, 15, 29, 44, 47, 251 }; |
5519 static const int coeff_abs_level_m1_offset[6] = { 227+0, 227+10, 227+20, 227+30, 227+39, 426 }; | 5519 static const int coeff_abs_level_m1_offset[6] = { 227+0, 227+10, 227+20, 227+30, 227+39, 426 }; |
5520 static const int identity[15] = { | |
5521 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14 | |
5522 }; | |
5523 static const int significant_coeff_flag_offset_8x8[63] = { | 5520 static const int significant_coeff_flag_offset_8x8[63] = { |
5524 0, 1, 2, 3, 4, 5, 5, 4, 4, 3, 3, 4, 4, 4, 5, 5, | 5521 0, 1, 2, 3, 4, 5, 5, 4, 4, 3, 3, 4, 4, 4, 5, 5, |
5525 4, 4, 4, 4, 3, 3, 6, 7, 7, 7, 8, 9,10, 9, 8, 7, | 5522 4, 4, 4, 4, 3, 3, 6, 7, 7, 7, 8, 9,10, 9, 8, 7, |
5526 7, 6,11,12,13,11, 6, 7, 8, 9,14,10, 9, 8, 6,11, | 5523 7, 6,11,12,13,11, 6, 7, 8, 9,14,10, 9, 8, 6,11, |
5527 12,13,11, 6, 9,14,10, 9,11,12,13,11,14,10,12 | 5524 12,13,11, 6, 9,14,10, 9,11,12,13,11,14,10,12 |
5539 int coeff_count = 0; | 5536 int coeff_count = 0; |
5540 | 5537 |
5541 int abslevel1 = 1; | 5538 int abslevel1 = 1; |
5542 int abslevelgt1 = 0; | 5539 int abslevelgt1 = 0; |
5543 | 5540 |
5544 const int* significant_coeff_ctx_offset; | 5541 uint8_t *significant_coeff_ctx_base; |
5545 const int* last_coeff_ctx_offset; | 5542 uint8_t *last_coeff_ctx_base; |
5546 const int significant_coeff_ctx_base = significant_coeff_flag_offset[cat] | 5543 uint8_t *abs_level_m1_ctx_base; |
5547 + significant_coeff_flag_field_offset[h->mb_field_decoding_flag]; | |
5548 const int last_coeff_ctx_base = last_significant_coeff_flag_offset[cat] | |
5549 + last_significant_coeff_flag_field_offset[h->mb_field_decoding_flag]; | |
5550 | 5544 |
5551 /* cat: 0-> DC 16x16 n = 0 | 5545 /* cat: 0-> DC 16x16 n = 0 |
5552 * 1-> AC 16x16 n = luma4x4idx | 5546 * 1-> AC 16x16 n = luma4x4idx |
5553 * 2-> Luma4x4 n = luma4x4idx | 5547 * 2-> Luma4x4 n = luma4x4idx |
5554 * 3-> DC Chroma n = iCbCr | 5548 * 3-> DC Chroma n = iCbCr |
5555 * 4-> AC Chroma n = 4 * iCbCr + chroma4x4idx | 5549 * 4-> AC Chroma n = 4 * iCbCr + chroma4x4idx |
5556 * 5-> Luma8x8 n = 4 * luma8x8idx | 5550 * 5-> Luma8x8 n = 4 * luma8x8idx |
5557 */ | 5551 */ |
5558 | 5552 |
5559 /* read coded block flag */ | 5553 /* read coded block flag */ |
5560 if( cat == 5 ) { | 5554 if( cat != 5 ) { |
5561 significant_coeff_ctx_offset = significant_coeff_flag_offset_8x8; | |
5562 last_coeff_ctx_offset = last_coeff_flag_offset_8x8; | |
5563 } else { | |
5564 if( get_cabac( &h->cabac, &h->cabac_state[85 + get_cabac_cbf_ctx( h, cat, n ) ] ) == 0 ) { | 5555 if( get_cabac( &h->cabac, &h->cabac_state[85 + get_cabac_cbf_ctx( h, cat, n ) ] ) == 0 ) { |
5565 if( cat == 1 || cat == 2 ) | 5556 if( cat == 1 || cat == 2 ) |
5566 h->non_zero_count_cache[scan8[n]] = 0; | 5557 h->non_zero_count_cache[scan8[n]] = 0; |
5567 else if( cat == 4 ) | 5558 else if( cat == 4 ) |
5568 h->non_zero_count_cache[scan8[16+n]] = 0; | 5559 h->non_zero_count_cache[scan8[16+n]] = 0; |
5569 | 5560 |
5570 return 0; | 5561 return 0; |
5571 } | 5562 } |
5572 | 5563 } |
5573 significant_coeff_ctx_offset = | 5564 |
5574 last_coeff_ctx_offset = identity; | 5565 significant_coeff_ctx_base = h->cabac_state |
5575 } | 5566 + significant_coeff_flag_offset[cat] |
5576 | 5567 + significant_coeff_flag_field_offset[h->mb_field_decoding_flag]; |
5577 for(last= 0; last < max_coeff - 1; last++) { | 5568 last_coeff_ctx_base = h->cabac_state |
5578 int sig_ctx = significant_coeff_ctx_base + significant_coeff_ctx_offset[last]; | 5569 + last_significant_coeff_flag_offset[cat] |
5579 if( get_cabac( &h->cabac, &h->cabac_state[sig_ctx] )) { | 5570 + last_significant_coeff_flag_field_offset[h->mb_field_decoding_flag]; |
5580 int last_ctx = last_coeff_ctx_base + last_coeff_ctx_offset[last]; | 5571 abs_level_m1_ctx_base = h->cabac_state |
5581 index[coeff_count++] = last; | 5572 + coeff_abs_level_m1_offset[cat]; |
5582 if( get_cabac( &h->cabac, &h->cabac_state[last_ctx] ) ) { | 5573 |
5583 last= max_coeff; | 5574 if( cat == 5 ) { |
5584 break; | 5575 #define DECODE_SIGNIFICANCE( coefs, sig_off, last_off ) \ |
5585 } | 5576 for(last= 0; last < coefs; last++) { \ |
5586 } | 5577 uint8_t *sig_ctx = significant_coeff_ctx_base + sig_off; \ |
5578 if( get_cabac( &h->cabac, sig_ctx )) { \ | |
5579 uint8_t *last_ctx = last_coeff_ctx_base + last_off; \ | |
5580 index[coeff_count++] = last; \ | |
5581 if( get_cabac( &h->cabac, last_ctx ) ) { \ | |
5582 last= max_coeff; \ | |
5583 break; \ | |
5584 } \ | |
5585 } \ | |
5586 } | |
5587 DECODE_SIGNIFICANCE( 63, significant_coeff_flag_offset_8x8[last], | |
5588 last_coeff_flag_offset_8x8[last] ); | |
5589 } else { | |
5590 DECODE_SIGNIFICANCE( max_coeff - 1, last, last ); | |
5587 } | 5591 } |
5588 if( last == max_coeff -1 ) { | 5592 if( last == max_coeff -1 ) { |
5589 index[coeff_count++] = last; | 5593 index[coeff_count++] = last; |
5590 } | 5594 } |
5591 assert(coeff_count > 0); | 5595 assert(coeff_count > 0); |
5602 assert( cat == 5 ); | 5606 assert( cat == 5 ); |
5603 fill_rectangle(&h->non_zero_count_cache[scan8[n]], 2, 2, 8, 1, 1); | 5607 fill_rectangle(&h->non_zero_count_cache[scan8[n]], 2, 2, 8, 1, 1); |
5604 } | 5608 } |
5605 | 5609 |
5606 for( i = coeff_count - 1; i >= 0; i-- ) { | 5610 for( i = coeff_count - 1; i >= 0; i-- ) { |
5607 int ctx = (abslevelgt1 != 0 ? 0 : FFMIN( 4, abslevel1 )) + coeff_abs_level_m1_offset[cat]; | 5611 uint8_t *ctx = (abslevelgt1 != 0 ? 0 : FFMIN( 4, abslevel1 )) + abs_level_m1_ctx_base; |
5608 int j= scantable[index[i]]; | 5612 int j= scantable[index[i]]; |
5609 | 5613 |
5610 if( get_cabac( &h->cabac, &h->cabac_state[ctx] ) == 0 ) { | 5614 if( get_cabac( &h->cabac, ctx ) == 0 ) { |
5611 if( cat == 0 || cat == 3 ) { | 5615 if( !qmul ) { |
5612 if( get_cabac_bypass( &h->cabac ) ) block[j] = -1; | 5616 if( get_cabac_bypass( &h->cabac ) ) block[j] = -1; |
5613 else block[j] = 1; | 5617 else block[j] = 1; |
5614 }else{ | 5618 }else{ |
5615 if( get_cabac_bypass( &h->cabac ) ) block[j] = -qmul[j]; | 5619 if( get_cabac_bypass( &h->cabac ) ) block[j] = -qmul[j]; |
5616 else block[j] = qmul[j]; | 5620 else block[j] = qmul[j]; |
5617 } | 5621 } |
5618 | 5622 |
5619 abslevel1++; | 5623 abslevel1++; |
5620 } else { | 5624 } else { |
5621 int coeff_abs = 2; | 5625 int coeff_abs = 2; |
5622 ctx = 5 + FFMIN( 4, abslevelgt1 ) + coeff_abs_level_m1_offset[cat]; | 5626 ctx = 5 + FFMIN( 4, abslevelgt1 ) + abs_level_m1_ctx_base; |
5623 while( coeff_abs < 15 && get_cabac( &h->cabac, &h->cabac_state[ctx] ) ) { | 5627 while( coeff_abs < 15 && get_cabac( &h->cabac, ctx ) ) { |
5624 coeff_abs++; | 5628 coeff_abs++; |
5625 } | 5629 } |
5626 | 5630 |
5627 if( coeff_abs >= 15 ) { | 5631 if( coeff_abs >= 15 ) { |
5628 int j = 0; | 5632 int j = 0; |
5635 if( get_cabac_bypass( &h->cabac ) ) | 5639 if( get_cabac_bypass( &h->cabac ) ) |
5636 coeff_abs += 1 << j ; | 5640 coeff_abs += 1 << j ; |
5637 } | 5641 } |
5638 } | 5642 } |
5639 | 5643 |
5640 if( cat == 0 || cat == 3 ) { | 5644 if( !qmul ) { |
5641 if( get_cabac_bypass( &h->cabac ) ) block[j] = -coeff_abs; | 5645 if( get_cabac_bypass( &h->cabac ) ) block[j] = -coeff_abs; |
5642 else block[j] = coeff_abs; | 5646 else block[j] = coeff_abs; |
5643 }else{ | 5647 }else{ |
5644 if( get_cabac_bypass( &h->cabac ) ) block[j] = -coeff_abs * qmul[j]; | 5648 if( get_cabac_bypass( &h->cabac ) ) block[j] = -coeff_abs * qmul[j]; |
5645 else block[j] = coeff_abs * qmul[j]; | 5649 else block[j] = coeff_abs * qmul[j]; |
6067 h->chroma_qp = get_chroma_qp(h->pps.chroma_qp_index_offset, s->qscale); | 6071 h->chroma_qp = get_chroma_qp(h->pps.chroma_qp_index_offset, s->qscale); |
6068 | 6072 |
6069 if( IS_INTRA16x16( mb_type ) ) { | 6073 if( IS_INTRA16x16( mb_type ) ) { |
6070 int i; | 6074 int i; |
6071 //av_log( s->avctx, AV_LOG_ERROR, "INTRA16x16 DC\n" ); | 6075 //av_log( s->avctx, AV_LOG_ERROR, "INTRA16x16 DC\n" ); |
6072 if( decode_cabac_residual( h, h->mb, 0, 0, dc_scan, h->dequant4_coeff[s->qscale], 16) < 0) | 6076 if( decode_cabac_residual( h, h->mb, 0, 0, dc_scan, NULL, 16) < 0) |
6073 return -1; | 6077 return -1; |
6074 if( cbp&15 ) { | 6078 if( cbp&15 ) { |
6075 for( i = 0; i < 16; i++ ) { | 6079 for( i = 0; i < 16; i++ ) { |
6076 //av_log( s->avctx, AV_LOG_ERROR, "INTRA16x16 AC:%d\n", i ); | 6080 //av_log( s->avctx, AV_LOG_ERROR, "INTRA16x16 AC:%d\n", i ); |
6077 if( decode_cabac_residual(h, h->mb + 16*i, 1, i, scan + 1, h->dequant4_coeff[s->qscale], 15) < 0 ) | 6081 if( decode_cabac_residual(h, h->mb + 16*i, 1, i, scan + 1, h->dequant4_coeff[s->qscale], 15) < 0 ) |
6109 | 6113 |
6110 if( cbp&0x30 ){ | 6114 if( cbp&0x30 ){ |
6111 int c; | 6115 int c; |
6112 for( c = 0; c < 2; c++ ) { | 6116 for( c = 0; c < 2; c++ ) { |
6113 //av_log( s->avctx, AV_LOG_ERROR, "INTRA C%d-DC\n",c ); | 6117 //av_log( s->avctx, AV_LOG_ERROR, "INTRA C%d-DC\n",c ); |
6114 if( decode_cabac_residual(h, h->mb + 256 + 16*4*c, 3, c, chroma_dc_scan, h->dequant4_coeff[h->chroma_qp], 4) < 0) | 6118 if( decode_cabac_residual(h, h->mb + 256 + 16*4*c, 3, c, chroma_dc_scan, NULL, 4) < 0) |
6115 return -1; | 6119 return -1; |
6116 } | 6120 } |
6117 } | 6121 } |
6118 | 6122 |
6119 if( cbp&0x20 ) { | 6123 if( cbp&0x20 ) { |