129a84457aed4c45bc900998b5e11c03023264208James Dong/* ------------------------------------------------------------------ 229a84457aed4c45bc900998b5e11c03023264208James Dong * Copyright (C) 1998-2009 PacketVideo 329a84457aed4c45bc900998b5e11c03023264208James Dong * 429a84457aed4c45bc900998b5e11c03023264208James Dong * Licensed under the Apache License, Version 2.0 (the "License"); 529a84457aed4c45bc900998b5e11c03023264208James Dong * you may not use this file except in compliance with the License. 629a84457aed4c45bc900998b5e11c03023264208James Dong * You may obtain a copy of the License at 729a84457aed4c45bc900998b5e11c03023264208James Dong * 829a84457aed4c45bc900998b5e11c03023264208James Dong * http://www.apache.org/licenses/LICENSE-2.0 929a84457aed4c45bc900998b5e11c03023264208James Dong * 1029a84457aed4c45bc900998b5e11c03023264208James Dong * Unless required by applicable law or agreed to in writing, software 1129a84457aed4c45bc900998b5e11c03023264208James Dong * distributed under the License is distributed on an "AS IS" BASIS, 1229a84457aed4c45bc900998b5e11c03023264208James Dong * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either 1329a84457aed4c45bc900998b5e11c03023264208James Dong * express or implied. 1429a84457aed4c45bc900998b5e11c03023264208James Dong * See the License for the specific language governing permissions 1529a84457aed4c45bc900998b5e11c03023264208James Dong * and limitations under the License. 1629a84457aed4c45bc900998b5e11c03023264208James Dong * ------------------------------------------------------------------- 1729a84457aed4c45bc900998b5e11c03023264208James Dong */ 1829a84457aed4c45bc900998b5e11c03023264208James Dong#include "avcenc_lib.h" 1929a84457aed4c45bc900998b5e11c03023264208James Dong#include "avcenc_api.h" 2029a84457aed4c45bc900998b5e11c03023264208James Dong 2129a84457aed4c45bc900998b5e11c03023264208James Dong/** see subclause 7.4.2.1 */ 2229a84457aed4c45bc900998b5e11c03023264208James Dong/* no need for checking the valid range , already done in SetEncodeParam(), 2329a84457aed4c45bc900998b5e11c03023264208James Dongif we have to send another SPS, the ranges should be verified first before 2429a84457aed4c45bc900998b5e11c03023264208James Dongusers call PVAVCEncodeSPS() */ 2529a84457aed4c45bc900998b5e11c03023264208James DongAVCEnc_Status EncodeSPS(AVCEncObject *encvid, AVCEncBitstream *stream) 2629a84457aed4c45bc900998b5e11c03023264208James Dong{ 2729a84457aed4c45bc900998b5e11c03023264208James Dong AVCCommonObj *video = encvid->common; 2829a84457aed4c45bc900998b5e11c03023264208James Dong AVCSeqParamSet *seqParam = video->currSeqParams; 2929a84457aed4c45bc900998b5e11c03023264208James Dong AVCVUIParams *vui = &(seqParam->vui_parameters); 3029a84457aed4c45bc900998b5e11c03023264208James Dong int i; 3129a84457aed4c45bc900998b5e11c03023264208James Dong AVCEnc_Status status = AVCENC_SUCCESS; 3229a84457aed4c45bc900998b5e11c03023264208James Dong 3329a84457aed4c45bc900998b5e11c03023264208James Dong //DEBUG_LOG(userData,AVC_LOGTYPE_INFO,"EncodeSPS",-1,-1); 3429a84457aed4c45bc900998b5e11c03023264208James Dong 3529a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWriteBits(stream, 8, seqParam->profile_idc); 3629a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, seqParam->constrained_set0_flag); 3729a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, seqParam->constrained_set1_flag); 3829a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, seqParam->constrained_set2_flag); 3929a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, seqParam->constrained_set3_flag); 4029a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWriteBits(stream, 4, 0); /* forbidden zero bits */ 4129a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) /* we can check after each write also */ 4229a84457aed4c45bc900998b5e11c03023264208James Dong { 4329a84457aed4c45bc900998b5e11c03023264208James Dong return status; 4429a84457aed4c45bc900998b5e11c03023264208James Dong } 4529a84457aed4c45bc900998b5e11c03023264208James Dong 4629a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWriteBits(stream, 8, seqParam->level_idc); 4729a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->seq_parameter_set_id); 4829a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->log2_max_frame_num_minus4); 4929a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->pic_order_cnt_type); 5029a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 5129a84457aed4c45bc900998b5e11c03023264208James Dong { 5229a84457aed4c45bc900998b5e11c03023264208James Dong return status; 5329a84457aed4c45bc900998b5e11c03023264208James Dong } 5429a84457aed4c45bc900998b5e11c03023264208James Dong 5529a84457aed4c45bc900998b5e11c03023264208James Dong if (seqParam->pic_order_cnt_type == 0) 5629a84457aed4c45bc900998b5e11c03023264208James Dong { 5729a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->log2_max_pic_order_cnt_lsb_minus4); 5829a84457aed4c45bc900998b5e11c03023264208James Dong } 5929a84457aed4c45bc900998b5e11c03023264208James Dong else if (seqParam->pic_order_cnt_type == 1) 6029a84457aed4c45bc900998b5e11c03023264208James Dong { 6129a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, seqParam->delta_pic_order_always_zero_flag); 6229a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, seqParam->offset_for_non_ref_pic); /* upto 32 bits */ 6329a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, seqParam->offset_for_top_to_bottom_field); /* upto 32 bits */ 6429a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->num_ref_frames_in_pic_order_cnt_cycle); 6529a84457aed4c45bc900998b5e11c03023264208James Dong 6629a84457aed4c45bc900998b5e11c03023264208James Dong for (i = 0; i < (int)(seqParam->num_ref_frames_in_pic_order_cnt_cycle); i++) 6729a84457aed4c45bc900998b5e11c03023264208James Dong { 6829a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, seqParam->offset_for_ref_frame[i]); /* upto 32 bits */ 6929a84457aed4c45bc900998b5e11c03023264208James Dong } 7029a84457aed4c45bc900998b5e11c03023264208James Dong } 7129a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 7229a84457aed4c45bc900998b5e11c03023264208James Dong { 7329a84457aed4c45bc900998b5e11c03023264208James Dong return status; 7429a84457aed4c45bc900998b5e11c03023264208James Dong } 7529a84457aed4c45bc900998b5e11c03023264208James Dong 7629a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->num_ref_frames); 7729a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, seqParam->gaps_in_frame_num_value_allowed_flag); 7829a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->pic_width_in_mbs_minus1); 7929a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->pic_height_in_map_units_minus1); 8029a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, seqParam->frame_mbs_only_flag); 8129a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 8229a84457aed4c45bc900998b5e11c03023264208James Dong { 8329a84457aed4c45bc900998b5e11c03023264208James Dong return status; 8429a84457aed4c45bc900998b5e11c03023264208James Dong } 8529a84457aed4c45bc900998b5e11c03023264208James Dong /* if frame_mbs_only_flag is 0, then write, mb_adaptive_frame_field_frame here */ 8629a84457aed4c45bc900998b5e11c03023264208James Dong 8729a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, seqParam->direct_8x8_inference_flag); 8829a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, seqParam->frame_cropping_flag); 8929a84457aed4c45bc900998b5e11c03023264208James Dong if (seqParam->frame_cropping_flag) 9029a84457aed4c45bc900998b5e11c03023264208James Dong { 9129a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->frame_crop_left_offset); 9229a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->frame_crop_right_offset); 9329a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->frame_crop_top_offset); 9429a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, seqParam->frame_crop_bottom_offset); 9529a84457aed4c45bc900998b5e11c03023264208James Dong } 9629a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 9729a84457aed4c45bc900998b5e11c03023264208James Dong { 9829a84457aed4c45bc900998b5e11c03023264208James Dong return status; 9929a84457aed4c45bc900998b5e11c03023264208James Dong } 10029a84457aed4c45bc900998b5e11c03023264208James Dong 10129a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, seqParam->vui_parameters_present_flag); 10229a84457aed4c45bc900998b5e11c03023264208James Dong if (seqParam->vui_parameters_present_flag) 10329a84457aed4c45bc900998b5e11c03023264208James Dong { 10429a84457aed4c45bc900998b5e11c03023264208James Dong /* not supported */ 10529a84457aed4c45bc900998b5e11c03023264208James Dong //return AVCENC_SPS_FAIL; 10629a84457aed4c45bc900998b5e11c03023264208James Dong EncodeVUI(stream, vui); 10729a84457aed4c45bc900998b5e11c03023264208James Dong } 10829a84457aed4c45bc900998b5e11c03023264208James Dong 10929a84457aed4c45bc900998b5e11c03023264208James Dong return status; 11029a84457aed4c45bc900998b5e11c03023264208James Dong} 11129a84457aed4c45bc900998b5e11c03023264208James Dong 11229a84457aed4c45bc900998b5e11c03023264208James Dong 11329a84457aed4c45bc900998b5e11c03023264208James Dongvoid EncodeVUI(AVCEncBitstream* stream, AVCVUIParams* vui) 11429a84457aed4c45bc900998b5e11c03023264208James Dong{ 11529a84457aed4c45bc900998b5e11c03023264208James Dong int temp; 11629a84457aed4c45bc900998b5e11c03023264208James Dong 11729a84457aed4c45bc900998b5e11c03023264208James Dong temp = vui->aspect_ratio_info_present_flag; 11829a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, temp); 11929a84457aed4c45bc900998b5e11c03023264208James Dong if (temp) 12029a84457aed4c45bc900998b5e11c03023264208James Dong { 12129a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 8, vui->aspect_ratio_idc); 12229a84457aed4c45bc900998b5e11c03023264208James Dong if (vui->aspect_ratio_idc == 255) 12329a84457aed4c45bc900998b5e11c03023264208James Dong { 12429a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 16, vui->sar_width); 12529a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 16, vui->sar_height); 12629a84457aed4c45bc900998b5e11c03023264208James Dong } 12729a84457aed4c45bc900998b5e11c03023264208James Dong } 12829a84457aed4c45bc900998b5e11c03023264208James Dong temp = vui->overscan_info_present_flag; 12929a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, temp); 13029a84457aed4c45bc900998b5e11c03023264208James Dong if (temp) 13129a84457aed4c45bc900998b5e11c03023264208James Dong { 13229a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, vui->overscan_appropriate_flag); 13329a84457aed4c45bc900998b5e11c03023264208James Dong } 13429a84457aed4c45bc900998b5e11c03023264208James Dong temp = vui->video_signal_type_present_flag; 13529a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, temp); 13629a84457aed4c45bc900998b5e11c03023264208James Dong if (temp) 13729a84457aed4c45bc900998b5e11c03023264208James Dong { 13829a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 3, vui->video_format); 13929a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, vui->video_full_range_flag); 14029a84457aed4c45bc900998b5e11c03023264208James Dong temp = vui->colour_description_present_flag; 14129a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, temp); 14229a84457aed4c45bc900998b5e11c03023264208James Dong if (temp) 14329a84457aed4c45bc900998b5e11c03023264208James Dong { 14429a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 8, vui->colour_primaries); 14529a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 8, vui->transfer_characteristics); 14629a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 8, vui->matrix_coefficients); 14729a84457aed4c45bc900998b5e11c03023264208James Dong } 14829a84457aed4c45bc900998b5e11c03023264208James Dong } 14929a84457aed4c45bc900998b5e11c03023264208James Dong temp = vui->chroma_location_info_present_flag; 15029a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, temp); 15129a84457aed4c45bc900998b5e11c03023264208James Dong if (temp) 15229a84457aed4c45bc900998b5e11c03023264208James Dong { 15329a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, vui->chroma_sample_loc_type_top_field); 15429a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, vui->chroma_sample_loc_type_bottom_field); 15529a84457aed4c45bc900998b5e11c03023264208James Dong } 15629a84457aed4c45bc900998b5e11c03023264208James Dong 15729a84457aed4c45bc900998b5e11c03023264208James Dong temp = vui->timing_info_present_flag; 15829a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, temp); 15929a84457aed4c45bc900998b5e11c03023264208James Dong if (temp) 16029a84457aed4c45bc900998b5e11c03023264208James Dong { 16129a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 32, vui->num_units_in_tick); 16229a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 32, vui->time_scale); 16329a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, vui->fixed_frame_rate_flag); 16429a84457aed4c45bc900998b5e11c03023264208James Dong } 16529a84457aed4c45bc900998b5e11c03023264208James Dong 16629a84457aed4c45bc900998b5e11c03023264208James Dong temp = vui->nal_hrd_parameters_present_flag; 16729a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, temp); 16829a84457aed4c45bc900998b5e11c03023264208James Dong if (temp) 16929a84457aed4c45bc900998b5e11c03023264208James Dong { 17029a84457aed4c45bc900998b5e11c03023264208James Dong EncodeHRD(stream, &(vui->nal_hrd_parameters)); 17129a84457aed4c45bc900998b5e11c03023264208James Dong } 17229a84457aed4c45bc900998b5e11c03023264208James Dong temp = vui->vcl_hrd_parameters_present_flag; 17329a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, temp); 17429a84457aed4c45bc900998b5e11c03023264208James Dong if (temp) 17529a84457aed4c45bc900998b5e11c03023264208James Dong { 17629a84457aed4c45bc900998b5e11c03023264208James Dong EncodeHRD(stream, &(vui->vcl_hrd_parameters)); 17729a84457aed4c45bc900998b5e11c03023264208James Dong } 17829a84457aed4c45bc900998b5e11c03023264208James Dong if (vui->nal_hrd_parameters_present_flag || vui->vcl_hrd_parameters_present_flag) 17929a84457aed4c45bc900998b5e11c03023264208James Dong { 18029a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, vui->low_delay_hrd_flag); 18129a84457aed4c45bc900998b5e11c03023264208James Dong } 18229a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, vui->pic_struct_present_flag); 18329a84457aed4c45bc900998b5e11c03023264208James Dong temp = vui->bitstream_restriction_flag; 18429a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, temp); 18529a84457aed4c45bc900998b5e11c03023264208James Dong if (temp) 18629a84457aed4c45bc900998b5e11c03023264208James Dong { 18729a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWrite1Bit(stream, vui->motion_vectors_over_pic_boundaries_flag); 18829a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, vui->max_bytes_per_pic_denom); 18929a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, vui->max_bits_per_mb_denom); 19029a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, vui->log2_max_mv_length_horizontal); 19129a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, vui->log2_max_mv_length_vertical); 19229a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, vui->max_dec_frame_reordering); 19329a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, vui->max_dec_frame_buffering); 19429a84457aed4c45bc900998b5e11c03023264208James Dong } 19529a84457aed4c45bc900998b5e11c03023264208James Dong 19629a84457aed4c45bc900998b5e11c03023264208James Dong return ; 19729a84457aed4c45bc900998b5e11c03023264208James Dong} 19829a84457aed4c45bc900998b5e11c03023264208James Dong 19929a84457aed4c45bc900998b5e11c03023264208James Dong 20029a84457aed4c45bc900998b5e11c03023264208James Dongvoid EncodeHRD(AVCEncBitstream* stream, AVCHRDParams* hrd) 20129a84457aed4c45bc900998b5e11c03023264208James Dong{ 20229a84457aed4c45bc900998b5e11c03023264208James Dong int i; 20329a84457aed4c45bc900998b5e11c03023264208James Dong 20429a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, hrd->cpb_cnt_minus1); 20529a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 4, hrd->bit_rate_scale); 20629a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 4, hrd->cpb_size_scale); 20729a84457aed4c45bc900998b5e11c03023264208James Dong for (i = 0; i <= (int)hrd->cpb_cnt_minus1; i++) 20829a84457aed4c45bc900998b5e11c03023264208James Dong { 20929a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, hrd->bit_rate_value_minus1[i]); 21029a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, hrd->cpb_size_value_minus1[i]); 21129a84457aed4c45bc900998b5e11c03023264208James Dong ue_v(stream, hrd->cbr_flag[i]); 21229a84457aed4c45bc900998b5e11c03023264208James Dong } 21329a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 5, hrd->initial_cpb_removal_delay_length_minus1); 21429a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 5, hrd->cpb_removal_delay_length_minus1); 21529a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 5, hrd->dpb_output_delay_length_minus1); 21629a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, 5, hrd->time_offset_length); 21729a84457aed4c45bc900998b5e11c03023264208James Dong 21829a84457aed4c45bc900998b5e11c03023264208James Dong return ; 21929a84457aed4c45bc900998b5e11c03023264208James Dong} 22029a84457aed4c45bc900998b5e11c03023264208James Dong 22129a84457aed4c45bc900998b5e11c03023264208James Dong 22229a84457aed4c45bc900998b5e11c03023264208James Dong 22329a84457aed4c45bc900998b5e11c03023264208James Dong/** see subclause 7.4.2.2 */ 22429a84457aed4c45bc900998b5e11c03023264208James Dong/* no need for checking the valid range , already done in SetEncodeParam(). 22529a84457aed4c45bc900998b5e11c03023264208James DongIf we have to send another SPS, the ranges should be verified first before 22629a84457aed4c45bc900998b5e11c03023264208James Dongusers call PVAVCEncodeSPS()*/ 22729a84457aed4c45bc900998b5e11c03023264208James DongAVCEnc_Status EncodePPS(AVCEncObject *encvid, AVCEncBitstream *stream) 22829a84457aed4c45bc900998b5e11c03023264208James Dong{ 22929a84457aed4c45bc900998b5e11c03023264208James Dong AVCCommonObj *video = encvid->common; 23029a84457aed4c45bc900998b5e11c03023264208James Dong AVCEnc_Status status = AVCENC_SUCCESS; 23129a84457aed4c45bc900998b5e11c03023264208James Dong AVCPicParamSet *picParam = video->currPicParams; 23229a84457aed4c45bc900998b5e11c03023264208James Dong int i, iGroup, numBits; 23329a84457aed4c45bc900998b5e11c03023264208James Dong uint temp; 23429a84457aed4c45bc900998b5e11c03023264208James Dong 23529a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, picParam->pic_parameter_set_id); 23629a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, picParam->seq_parameter_set_id); 23729a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, picParam->entropy_coding_mode_flag); 23829a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, picParam->pic_order_present_flag); 23929a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 24029a84457aed4c45bc900998b5e11c03023264208James Dong { 24129a84457aed4c45bc900998b5e11c03023264208James Dong return status; 24229a84457aed4c45bc900998b5e11c03023264208James Dong } 24329a84457aed4c45bc900998b5e11c03023264208James Dong 24429a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, picParam->num_slice_groups_minus1); 24529a84457aed4c45bc900998b5e11c03023264208James Dong if (picParam->num_slice_groups_minus1 > 0) 24629a84457aed4c45bc900998b5e11c03023264208James Dong { 24729a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, picParam->slice_group_map_type); 24829a84457aed4c45bc900998b5e11c03023264208James Dong if (picParam->slice_group_map_type == 0) 24929a84457aed4c45bc900998b5e11c03023264208James Dong { 25029a84457aed4c45bc900998b5e11c03023264208James Dong for (iGroup = 0; iGroup <= (int)picParam->num_slice_groups_minus1; iGroup++) 25129a84457aed4c45bc900998b5e11c03023264208James Dong { 25229a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, picParam->run_length_minus1[iGroup]); 25329a84457aed4c45bc900998b5e11c03023264208James Dong } 25429a84457aed4c45bc900998b5e11c03023264208James Dong } 25529a84457aed4c45bc900998b5e11c03023264208James Dong else if (picParam->slice_group_map_type == 2) 25629a84457aed4c45bc900998b5e11c03023264208James Dong { 25729a84457aed4c45bc900998b5e11c03023264208James Dong for (iGroup = 0; iGroup < (int)picParam->num_slice_groups_minus1; iGroup++) 25829a84457aed4c45bc900998b5e11c03023264208James Dong { 25929a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, picParam->top_left[iGroup]); 26029a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, picParam->bottom_right[iGroup]); 26129a84457aed4c45bc900998b5e11c03023264208James Dong } 26229a84457aed4c45bc900998b5e11c03023264208James Dong } 26329a84457aed4c45bc900998b5e11c03023264208James Dong else if (picParam->slice_group_map_type == 3 || 26429a84457aed4c45bc900998b5e11c03023264208James Dong picParam->slice_group_map_type == 4 || 26529a84457aed4c45bc900998b5e11c03023264208James Dong picParam->slice_group_map_type == 5) 26629a84457aed4c45bc900998b5e11c03023264208James Dong { 26729a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, picParam->slice_group_change_direction_flag); 26829a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, picParam->slice_group_change_rate_minus1); 26929a84457aed4c45bc900998b5e11c03023264208James Dong } 27029a84457aed4c45bc900998b5e11c03023264208James Dong else /*if(picParam->slice_group_map_type == 6)*/ 27129a84457aed4c45bc900998b5e11c03023264208James Dong { 27229a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, picParam->pic_size_in_map_units_minus1); 27329a84457aed4c45bc900998b5e11c03023264208James Dong 27429a84457aed4c45bc900998b5e11c03023264208James Dong numBits = 0;/* ceil(log2(num_slice_groups_minus1+1)) bits */ 27529a84457aed4c45bc900998b5e11c03023264208James Dong i = picParam->num_slice_groups_minus1; 27629a84457aed4c45bc900998b5e11c03023264208James Dong while (i > 0) 27729a84457aed4c45bc900998b5e11c03023264208James Dong { 27829a84457aed4c45bc900998b5e11c03023264208James Dong numBits++; 27929a84457aed4c45bc900998b5e11c03023264208James Dong i >>= 1; 28029a84457aed4c45bc900998b5e11c03023264208James Dong } 28129a84457aed4c45bc900998b5e11c03023264208James Dong 28229a84457aed4c45bc900998b5e11c03023264208James Dong for (i = 0; i <= (int)picParam->pic_size_in_map_units_minus1; i++) 28329a84457aed4c45bc900998b5e11c03023264208James Dong { 28429a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWriteBits(stream, numBits, picParam->slice_group_id[i]); 28529a84457aed4c45bc900998b5e11c03023264208James Dong } 28629a84457aed4c45bc900998b5e11c03023264208James Dong } 28729a84457aed4c45bc900998b5e11c03023264208James Dong } 28829a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 28929a84457aed4c45bc900998b5e11c03023264208James Dong { 29029a84457aed4c45bc900998b5e11c03023264208James Dong return status; 29129a84457aed4c45bc900998b5e11c03023264208James Dong } 29229a84457aed4c45bc900998b5e11c03023264208James Dong 29329a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, picParam->num_ref_idx_l0_active_minus1); 29429a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, picParam->num_ref_idx_l1_active_minus1); 29529a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, picParam->weighted_pred_flag); 29629a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWriteBits(stream, 2, picParam->weighted_bipred_idc); 29729a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 29829a84457aed4c45bc900998b5e11c03023264208James Dong { 29929a84457aed4c45bc900998b5e11c03023264208James Dong return status; 30029a84457aed4c45bc900998b5e11c03023264208James Dong } 30129a84457aed4c45bc900998b5e11c03023264208James Dong 30229a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, picParam->pic_init_qp_minus26); 30329a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, picParam->pic_init_qs_minus26); 30429a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, picParam->chroma_qp_index_offset); 30529a84457aed4c45bc900998b5e11c03023264208James Dong 30629a84457aed4c45bc900998b5e11c03023264208James Dong temp = picParam->deblocking_filter_control_present_flag << 2; 30729a84457aed4c45bc900998b5e11c03023264208James Dong temp |= (picParam->constrained_intra_pred_flag << 1); 30829a84457aed4c45bc900998b5e11c03023264208James Dong temp |= picParam->redundant_pic_cnt_present_flag; 30929a84457aed4c45bc900998b5e11c03023264208James Dong 31029a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWriteBits(stream, 3, temp); 31129a84457aed4c45bc900998b5e11c03023264208James Dong 31229a84457aed4c45bc900998b5e11c03023264208James Dong return status; 31329a84457aed4c45bc900998b5e11c03023264208James Dong} 31429a84457aed4c45bc900998b5e11c03023264208James Dong 31529a84457aed4c45bc900998b5e11c03023264208James Dong/** see subclause 7.4.3 */ 31629a84457aed4c45bc900998b5e11c03023264208James DongAVCEnc_Status EncodeSliceHeader(AVCEncObject *encvid, AVCEncBitstream *stream) 31729a84457aed4c45bc900998b5e11c03023264208James Dong{ 31829a84457aed4c45bc900998b5e11c03023264208James Dong AVCCommonObj *video = encvid->common; 31929a84457aed4c45bc900998b5e11c03023264208James Dong AVCSliceHeader *sliceHdr = video->sliceHdr; 32029a84457aed4c45bc900998b5e11c03023264208James Dong AVCPicParamSet *currPPS = video->currPicParams; 32129a84457aed4c45bc900998b5e11c03023264208James Dong AVCSeqParamSet *currSPS = video->currSeqParams; 32229a84457aed4c45bc900998b5e11c03023264208James Dong AVCEnc_Status status = AVCENC_SUCCESS; 32329a84457aed4c45bc900998b5e11c03023264208James Dong int slice_type, temp, i; 32429a84457aed4c45bc900998b5e11c03023264208James Dong int num_bits; 32529a84457aed4c45bc900998b5e11c03023264208James Dong 32629a84457aed4c45bc900998b5e11c03023264208James Dong num_bits = (stream->write_pos << 3) - stream->bit_left; 32729a84457aed4c45bc900998b5e11c03023264208James Dong 32829a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->first_mb_in_slice); 32929a84457aed4c45bc900998b5e11c03023264208James Dong 33029a84457aed4c45bc900998b5e11c03023264208James Dong slice_type = video->slice_type; 33129a84457aed4c45bc900998b5e11c03023264208James Dong 33229a84457aed4c45bc900998b5e11c03023264208James Dong if (video->mbNum == 0) /* first mb in frame */ 33329a84457aed4c45bc900998b5e11c03023264208James Dong { 33429a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->slice_type); 33529a84457aed4c45bc900998b5e11c03023264208James Dong } 33629a84457aed4c45bc900998b5e11c03023264208James Dong else 33729a84457aed4c45bc900998b5e11c03023264208James Dong { 33829a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, slice_type); 33929a84457aed4c45bc900998b5e11c03023264208James Dong } 34029a84457aed4c45bc900998b5e11c03023264208James Dong 34129a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->pic_parameter_set_id); 34229a84457aed4c45bc900998b5e11c03023264208James Dong 34329a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWriteBits(stream, currSPS->log2_max_frame_num_minus4 + 4, sliceHdr->frame_num); 34429a84457aed4c45bc900998b5e11c03023264208James Dong 34529a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 34629a84457aed4c45bc900998b5e11c03023264208James Dong { 34729a84457aed4c45bc900998b5e11c03023264208James Dong return status; 34829a84457aed4c45bc900998b5e11c03023264208James Dong } 34929a84457aed4c45bc900998b5e11c03023264208James Dong /* if frame_mbs_only_flag is 0, encode field_pic_flag, bottom_field_flag here */ 35029a84457aed4c45bc900998b5e11c03023264208James Dong 35129a84457aed4c45bc900998b5e11c03023264208James Dong if (video->nal_unit_type == AVC_NALTYPE_IDR) 35229a84457aed4c45bc900998b5e11c03023264208James Dong { 35329a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->idr_pic_id); 35429a84457aed4c45bc900998b5e11c03023264208James Dong } 35529a84457aed4c45bc900998b5e11c03023264208James Dong 35629a84457aed4c45bc900998b5e11c03023264208James Dong if (currSPS->pic_order_cnt_type == 0) 35729a84457aed4c45bc900998b5e11c03023264208James Dong { 35829a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWriteBits(stream, currSPS->log2_max_pic_order_cnt_lsb_minus4 + 4, 35929a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->pic_order_cnt_lsb); 36029a84457aed4c45bc900998b5e11c03023264208James Dong 36129a84457aed4c45bc900998b5e11c03023264208James Dong if (currPPS->pic_order_present_flag && !sliceHdr->field_pic_flag) 36229a84457aed4c45bc900998b5e11c03023264208James Dong { 36329a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, sliceHdr->delta_pic_order_cnt_bottom); /* 32 bits */ 36429a84457aed4c45bc900998b5e11c03023264208James Dong } 36529a84457aed4c45bc900998b5e11c03023264208James Dong } 36629a84457aed4c45bc900998b5e11c03023264208James Dong if (currSPS->pic_order_cnt_type == 1 && !currSPS->delta_pic_order_always_zero_flag) 36729a84457aed4c45bc900998b5e11c03023264208James Dong { 36829a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, sliceHdr->delta_pic_order_cnt[0]); /* 32 bits */ 36929a84457aed4c45bc900998b5e11c03023264208James Dong if (currPPS->pic_order_present_flag && !sliceHdr->field_pic_flag) 37029a84457aed4c45bc900998b5e11c03023264208James Dong { 37129a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, sliceHdr->delta_pic_order_cnt[1]); /* 32 bits */ 37229a84457aed4c45bc900998b5e11c03023264208James Dong } 37329a84457aed4c45bc900998b5e11c03023264208James Dong } 37429a84457aed4c45bc900998b5e11c03023264208James Dong 37529a84457aed4c45bc900998b5e11c03023264208James Dong if (currPPS->redundant_pic_cnt_present_flag) 37629a84457aed4c45bc900998b5e11c03023264208James Dong { 37729a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->redundant_pic_cnt); 37829a84457aed4c45bc900998b5e11c03023264208James Dong } 37929a84457aed4c45bc900998b5e11c03023264208James Dong 38029a84457aed4c45bc900998b5e11c03023264208James Dong if (slice_type == AVC_B_SLICE) 38129a84457aed4c45bc900998b5e11c03023264208James Dong { 38229a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, sliceHdr->direct_spatial_mv_pred_flag); 38329a84457aed4c45bc900998b5e11c03023264208James Dong } 38429a84457aed4c45bc900998b5e11c03023264208James Dong 38529a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 38629a84457aed4c45bc900998b5e11c03023264208James Dong { 38729a84457aed4c45bc900998b5e11c03023264208James Dong return status; 38829a84457aed4c45bc900998b5e11c03023264208James Dong } 38929a84457aed4c45bc900998b5e11c03023264208James Dong 39029a84457aed4c45bc900998b5e11c03023264208James Dong if (slice_type == AVC_P_SLICE || slice_type == AVC_SP_SLICE || slice_type == AVC_B_SLICE) 39129a84457aed4c45bc900998b5e11c03023264208James Dong { 39229a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, sliceHdr->num_ref_idx_active_override_flag); 39329a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->num_ref_idx_active_override_flag) 39429a84457aed4c45bc900998b5e11c03023264208James Dong { 39529a84457aed4c45bc900998b5e11c03023264208James Dong /* we shouldn't enter this part at all */ 39629a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->num_ref_idx_l0_active_minus1); 39729a84457aed4c45bc900998b5e11c03023264208James Dong if (slice_type == AVC_B_SLICE) 39829a84457aed4c45bc900998b5e11c03023264208James Dong { 39929a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->num_ref_idx_l1_active_minus1); 40029a84457aed4c45bc900998b5e11c03023264208James Dong } 40129a84457aed4c45bc900998b5e11c03023264208James Dong } 40229a84457aed4c45bc900998b5e11c03023264208James Dong } 40329a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 40429a84457aed4c45bc900998b5e11c03023264208James Dong { 40529a84457aed4c45bc900998b5e11c03023264208James Dong return status; 40629a84457aed4c45bc900998b5e11c03023264208James Dong } 40729a84457aed4c45bc900998b5e11c03023264208James Dong 40829a84457aed4c45bc900998b5e11c03023264208James Dong /* ref_pic_list_reordering() */ 40929a84457aed4c45bc900998b5e11c03023264208James Dong status = ref_pic_list_reordering(video, stream, sliceHdr, slice_type); 41029a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 41129a84457aed4c45bc900998b5e11c03023264208James Dong { 41229a84457aed4c45bc900998b5e11c03023264208James Dong return status; 41329a84457aed4c45bc900998b5e11c03023264208James Dong } 41429a84457aed4c45bc900998b5e11c03023264208James Dong 41529a84457aed4c45bc900998b5e11c03023264208James Dong if ((currPPS->weighted_pred_flag && (slice_type == AVC_P_SLICE || slice_type == AVC_SP_SLICE)) || 41629a84457aed4c45bc900998b5e11c03023264208James Dong (currPPS->weighted_bipred_idc == 1 && slice_type == AVC_B_SLICE)) 41729a84457aed4c45bc900998b5e11c03023264208James Dong { 41829a84457aed4c45bc900998b5e11c03023264208James Dong // pred_weight_table(); // not supported !! 41929a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_PRED_WEIGHT_TAB_FAIL; 42029a84457aed4c45bc900998b5e11c03023264208James Dong } 42129a84457aed4c45bc900998b5e11c03023264208James Dong 42229a84457aed4c45bc900998b5e11c03023264208James Dong if (video->nal_ref_idc != 0) 42329a84457aed4c45bc900998b5e11c03023264208James Dong { 42429a84457aed4c45bc900998b5e11c03023264208James Dong status = dec_ref_pic_marking(video, stream, sliceHdr); 42529a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 42629a84457aed4c45bc900998b5e11c03023264208James Dong { 42729a84457aed4c45bc900998b5e11c03023264208James Dong return status; 42829a84457aed4c45bc900998b5e11c03023264208James Dong } 42929a84457aed4c45bc900998b5e11c03023264208James Dong } 43029a84457aed4c45bc900998b5e11c03023264208James Dong 43129a84457aed4c45bc900998b5e11c03023264208James Dong if (currPPS->entropy_coding_mode_flag && slice_type != AVC_I_SLICE && slice_type != AVC_SI_SLICE) 43229a84457aed4c45bc900998b5e11c03023264208James Dong { 43329a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_CABAC_FAIL; 43429a84457aed4c45bc900998b5e11c03023264208James Dong /* ue_v(stream,&(sliceHdr->cabac_init_idc)); 43529a84457aed4c45bc900998b5e11c03023264208James Dong if(sliceHdr->cabac_init_idc > 2){ 43629a84457aed4c45bc900998b5e11c03023264208James Dong // not supported !!!! 43729a84457aed4c45bc900998b5e11c03023264208James Dong }*/ 43829a84457aed4c45bc900998b5e11c03023264208James Dong } 43929a84457aed4c45bc900998b5e11c03023264208James Dong 44029a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, sliceHdr->slice_qp_delta); 44129a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 44229a84457aed4c45bc900998b5e11c03023264208James Dong { 44329a84457aed4c45bc900998b5e11c03023264208James Dong return status; 44429a84457aed4c45bc900998b5e11c03023264208James Dong } 44529a84457aed4c45bc900998b5e11c03023264208James Dong 44629a84457aed4c45bc900998b5e11c03023264208James Dong if (slice_type == AVC_SP_SLICE || slice_type == AVC_SI_SLICE) 44729a84457aed4c45bc900998b5e11c03023264208James Dong { 44829a84457aed4c45bc900998b5e11c03023264208James Dong if (slice_type == AVC_SP_SLICE) 44929a84457aed4c45bc900998b5e11c03023264208James Dong { 45029a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, sliceHdr->sp_for_switch_flag); 45129a84457aed4c45bc900998b5e11c03023264208James Dong /* if sp_for_switch_flag is 0, P macroblocks in SP slice is decoded using 45229a84457aed4c45bc900998b5e11c03023264208James Dong SP decoding process for non-switching pictures in 8.6.1 */ 45329a84457aed4c45bc900998b5e11c03023264208James Dong /* else, P macroblocks in SP slice is decoded using SP and SI decoding 45429a84457aed4c45bc900998b5e11c03023264208James Dong process for switching picture in 8.6.2 */ 45529a84457aed4c45bc900998b5e11c03023264208James Dong } 45629a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, sliceHdr->slice_qs_delta); 45729a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 45829a84457aed4c45bc900998b5e11c03023264208James Dong { 45929a84457aed4c45bc900998b5e11c03023264208James Dong return status; 46029a84457aed4c45bc900998b5e11c03023264208James Dong } 46129a84457aed4c45bc900998b5e11c03023264208James Dong } 46229a84457aed4c45bc900998b5e11c03023264208James Dong 46329a84457aed4c45bc900998b5e11c03023264208James Dong if (currPPS->deblocking_filter_control_present_flag) 46429a84457aed4c45bc900998b5e11c03023264208James Dong { 46529a84457aed4c45bc900998b5e11c03023264208James Dong 46629a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->disable_deblocking_filter_idc); 46729a84457aed4c45bc900998b5e11c03023264208James Dong 46829a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->disable_deblocking_filter_idc != 1) 46929a84457aed4c45bc900998b5e11c03023264208James Dong { 47029a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, sliceHdr->slice_alpha_c0_offset_div2); 47129a84457aed4c45bc900998b5e11c03023264208James Dong 47229a84457aed4c45bc900998b5e11c03023264208James Dong status = se_v(stream, sliceHdr->slice_beta_offset_div_2); 47329a84457aed4c45bc900998b5e11c03023264208James Dong } 47429a84457aed4c45bc900998b5e11c03023264208James Dong if (status != AVCENC_SUCCESS) 47529a84457aed4c45bc900998b5e11c03023264208James Dong { 47629a84457aed4c45bc900998b5e11c03023264208James Dong return status; 47729a84457aed4c45bc900998b5e11c03023264208James Dong } 47829a84457aed4c45bc900998b5e11c03023264208James Dong } 47929a84457aed4c45bc900998b5e11c03023264208James Dong 48029a84457aed4c45bc900998b5e11c03023264208James Dong if (currPPS->num_slice_groups_minus1 > 0 && currPPS->slice_group_map_type >= 3 48129a84457aed4c45bc900998b5e11c03023264208James Dong && currPPS->slice_group_map_type <= 5) 48229a84457aed4c45bc900998b5e11c03023264208James Dong { 48329a84457aed4c45bc900998b5e11c03023264208James Dong /* Ceil(Log2(PicSizeInMapUnits/(float)SliceGroupChangeRate + 1)) */ 48429a84457aed4c45bc900998b5e11c03023264208James Dong temp = video->PicSizeInMapUnits / video->SliceGroupChangeRate; 48529a84457aed4c45bc900998b5e11c03023264208James Dong if (video->PicSizeInMapUnits % video->SliceGroupChangeRate) 48629a84457aed4c45bc900998b5e11c03023264208James Dong { 48729a84457aed4c45bc900998b5e11c03023264208James Dong temp++; 48829a84457aed4c45bc900998b5e11c03023264208James Dong } 48929a84457aed4c45bc900998b5e11c03023264208James Dong i = 0; 49029a84457aed4c45bc900998b5e11c03023264208James Dong while (temp > 1) 49129a84457aed4c45bc900998b5e11c03023264208James Dong { 49229a84457aed4c45bc900998b5e11c03023264208James Dong temp >>= 1; 49329a84457aed4c45bc900998b5e11c03023264208James Dong i++; 49429a84457aed4c45bc900998b5e11c03023264208James Dong } 49529a84457aed4c45bc900998b5e11c03023264208James Dong 49629a84457aed4c45bc900998b5e11c03023264208James Dong BitstreamWriteBits(stream, i, sliceHdr->slice_group_change_cycle); 49729a84457aed4c45bc900998b5e11c03023264208James Dong } 49829a84457aed4c45bc900998b5e11c03023264208James Dong 49929a84457aed4c45bc900998b5e11c03023264208James Dong 50029a84457aed4c45bc900998b5e11c03023264208James Dong encvid->rateCtrl->NumberofHeaderBits += (stream->write_pos << 3) - stream->bit_left - num_bits; 50129a84457aed4c45bc900998b5e11c03023264208James Dong 50229a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_SUCCESS; 50329a84457aed4c45bc900998b5e11c03023264208James Dong} 50429a84457aed4c45bc900998b5e11c03023264208James Dong 50529a84457aed4c45bc900998b5e11c03023264208James Dong/** see subclause 7.4.3.1 */ 50629a84457aed4c45bc900998b5e11c03023264208James DongAVCEnc_Status ref_pic_list_reordering(AVCCommonObj *video, AVCEncBitstream *stream, AVCSliceHeader *sliceHdr, int slice_type) 50729a84457aed4c45bc900998b5e11c03023264208James Dong{ 50829a84457aed4c45bc900998b5e11c03023264208James Dong (void)(video); 50929a84457aed4c45bc900998b5e11c03023264208James Dong int i; 51029a84457aed4c45bc900998b5e11c03023264208James Dong AVCEnc_Status status = AVCENC_SUCCESS; 51129a84457aed4c45bc900998b5e11c03023264208James Dong 51229a84457aed4c45bc900998b5e11c03023264208James Dong if (slice_type != AVC_I_SLICE && slice_type != AVC_SI_SLICE) 51329a84457aed4c45bc900998b5e11c03023264208James Dong { 51429a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, sliceHdr->ref_pic_list_reordering_flag_l0); 51529a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->ref_pic_list_reordering_flag_l0) 51629a84457aed4c45bc900998b5e11c03023264208James Dong { 51729a84457aed4c45bc900998b5e11c03023264208James Dong i = 0; 51829a84457aed4c45bc900998b5e11c03023264208James Dong do 51929a84457aed4c45bc900998b5e11c03023264208James Dong { 52029a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->reordering_of_pic_nums_idc_l0[i]); 52129a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->reordering_of_pic_nums_idc_l0[i] == 0 || 52229a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->reordering_of_pic_nums_idc_l0[i] == 1) 52329a84457aed4c45bc900998b5e11c03023264208James Dong { 52429a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->abs_diff_pic_num_minus1_l0[i]); 52529a84457aed4c45bc900998b5e11c03023264208James Dong /* this check should be in InitSlice(), if we ever use it */ 52629a84457aed4c45bc900998b5e11c03023264208James Dong /*if(sliceHdr->reordering_of_pic_nums_idc_l0[i] == 0 && 52729a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->abs_diff_pic_num_minus1_l0[i] > video->MaxPicNum/2 -1) 52829a84457aed4c45bc900998b5e11c03023264208James Dong { 52929a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_REF_PIC_REORDER_FAIL; // out of range 53029a84457aed4c45bc900998b5e11c03023264208James Dong } 53129a84457aed4c45bc900998b5e11c03023264208James Dong if(sliceHdr->reordering_of_pic_nums_idc_l0[i] == 1 && 53229a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->abs_diff_pic_num_minus1_l0[i] > video->MaxPicNum/2 -2) 53329a84457aed4c45bc900998b5e11c03023264208James Dong { 53429a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_REF_PIC_REORDER_FAIL; // out of range 53529a84457aed4c45bc900998b5e11c03023264208James Dong }*/ 53629a84457aed4c45bc900998b5e11c03023264208James Dong } 53729a84457aed4c45bc900998b5e11c03023264208James Dong else if (sliceHdr->reordering_of_pic_nums_idc_l0[i] == 2) 53829a84457aed4c45bc900998b5e11c03023264208James Dong { 53929a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->long_term_pic_num_l0[i]); 54029a84457aed4c45bc900998b5e11c03023264208James Dong } 54129a84457aed4c45bc900998b5e11c03023264208James Dong i++; 54229a84457aed4c45bc900998b5e11c03023264208James Dong } 54329a84457aed4c45bc900998b5e11c03023264208James Dong while (sliceHdr->reordering_of_pic_nums_idc_l0[i] != 3 54429a84457aed4c45bc900998b5e11c03023264208James Dong && i <= (int)sliceHdr->num_ref_idx_l0_active_minus1 + 1) ; 54529a84457aed4c45bc900998b5e11c03023264208James Dong } 54629a84457aed4c45bc900998b5e11c03023264208James Dong } 54729a84457aed4c45bc900998b5e11c03023264208James Dong if (slice_type == AVC_B_SLICE) 54829a84457aed4c45bc900998b5e11c03023264208James Dong { 54929a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, sliceHdr->ref_pic_list_reordering_flag_l1); 55029a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->ref_pic_list_reordering_flag_l1) 55129a84457aed4c45bc900998b5e11c03023264208James Dong { 55229a84457aed4c45bc900998b5e11c03023264208James Dong i = 0; 55329a84457aed4c45bc900998b5e11c03023264208James Dong do 55429a84457aed4c45bc900998b5e11c03023264208James Dong { 55529a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->reordering_of_pic_nums_idc_l1[i]); 55629a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->reordering_of_pic_nums_idc_l1[i] == 0 || 55729a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->reordering_of_pic_nums_idc_l1[i] == 1) 55829a84457aed4c45bc900998b5e11c03023264208James Dong { 55929a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->abs_diff_pic_num_minus1_l1[i]); 56029a84457aed4c45bc900998b5e11c03023264208James Dong /* This check should be in InitSlice() if we ever use it 56129a84457aed4c45bc900998b5e11c03023264208James Dong if(sliceHdr->reordering_of_pic_nums_idc_l1[i] == 0 && 56229a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->abs_diff_pic_num_minus1_l1[i] > video->MaxPicNum/2 -1) 56329a84457aed4c45bc900998b5e11c03023264208James Dong { 56429a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_REF_PIC_REORDER_FAIL; // out of range 56529a84457aed4c45bc900998b5e11c03023264208James Dong } 56629a84457aed4c45bc900998b5e11c03023264208James Dong if(sliceHdr->reordering_of_pic_nums_idc_l1[i] == 1 && 56729a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->abs_diff_pic_num_minus1_l1[i] > video->MaxPicNum/2 -2) 56829a84457aed4c45bc900998b5e11c03023264208James Dong { 56929a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_REF_PIC_REORDER_FAIL; // out of range 57029a84457aed4c45bc900998b5e11c03023264208James Dong }*/ 57129a84457aed4c45bc900998b5e11c03023264208James Dong } 57229a84457aed4c45bc900998b5e11c03023264208James Dong else if (sliceHdr->reordering_of_pic_nums_idc_l1[i] == 2) 57329a84457aed4c45bc900998b5e11c03023264208James Dong { 57429a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->long_term_pic_num_l1[i]); 57529a84457aed4c45bc900998b5e11c03023264208James Dong } 57629a84457aed4c45bc900998b5e11c03023264208James Dong i++; 57729a84457aed4c45bc900998b5e11c03023264208James Dong } 57829a84457aed4c45bc900998b5e11c03023264208James Dong while (sliceHdr->reordering_of_pic_nums_idc_l1[i] != 3 57929a84457aed4c45bc900998b5e11c03023264208James Dong && i <= (int)sliceHdr->num_ref_idx_l1_active_minus1 + 1) ; 58029a84457aed4c45bc900998b5e11c03023264208James Dong } 58129a84457aed4c45bc900998b5e11c03023264208James Dong } 58229a84457aed4c45bc900998b5e11c03023264208James Dong 58329a84457aed4c45bc900998b5e11c03023264208James Dong return status; 58429a84457aed4c45bc900998b5e11c03023264208James Dong} 58529a84457aed4c45bc900998b5e11c03023264208James Dong 58629a84457aed4c45bc900998b5e11c03023264208James Dong/** see subclause 7.4.3.3 */ 58729a84457aed4c45bc900998b5e11c03023264208James DongAVCEnc_Status dec_ref_pic_marking(AVCCommonObj *video, AVCEncBitstream *stream, AVCSliceHeader *sliceHdr) 58829a84457aed4c45bc900998b5e11c03023264208James Dong{ 58929a84457aed4c45bc900998b5e11c03023264208James Dong int i; 59029a84457aed4c45bc900998b5e11c03023264208James Dong AVCEnc_Status status = AVCENC_SUCCESS; 59129a84457aed4c45bc900998b5e11c03023264208James Dong 59229a84457aed4c45bc900998b5e11c03023264208James Dong if (video->nal_unit_type == AVC_NALTYPE_IDR) 59329a84457aed4c45bc900998b5e11c03023264208James Dong { 59429a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, sliceHdr->no_output_of_prior_pics_flag); 59529a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, sliceHdr->long_term_reference_flag); 59629a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->long_term_reference_flag == 0) /* used for short-term */ 59729a84457aed4c45bc900998b5e11c03023264208James Dong { 59829a84457aed4c45bc900998b5e11c03023264208James Dong video->MaxLongTermFrameIdx = -1; /* no long-term frame indx */ 59929a84457aed4c45bc900998b5e11c03023264208James Dong } 60029a84457aed4c45bc900998b5e11c03023264208James Dong else /* used for long-term */ 60129a84457aed4c45bc900998b5e11c03023264208James Dong { 60229a84457aed4c45bc900998b5e11c03023264208James Dong video->MaxLongTermFrameIdx = 0; 60329a84457aed4c45bc900998b5e11c03023264208James Dong video->LongTermFrameIdx = 0; 60429a84457aed4c45bc900998b5e11c03023264208James Dong } 60529a84457aed4c45bc900998b5e11c03023264208James Dong } 60629a84457aed4c45bc900998b5e11c03023264208James Dong else 60729a84457aed4c45bc900998b5e11c03023264208James Dong { 60829a84457aed4c45bc900998b5e11c03023264208James Dong status = BitstreamWrite1Bit(stream, sliceHdr->adaptive_ref_pic_marking_mode_flag); /* default to zero */ 60929a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->adaptive_ref_pic_marking_mode_flag) 61029a84457aed4c45bc900998b5e11c03023264208James Dong { 61129a84457aed4c45bc900998b5e11c03023264208James Dong i = 0; 61229a84457aed4c45bc900998b5e11c03023264208James Dong do 61329a84457aed4c45bc900998b5e11c03023264208James Dong { 61429a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->memory_management_control_operation[i]); 61529a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->memory_management_control_operation[i] == 1 || 61629a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->memory_management_control_operation[i] == 3) 61729a84457aed4c45bc900998b5e11c03023264208James Dong { 61829a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->difference_of_pic_nums_minus1[i]); 61929a84457aed4c45bc900998b5e11c03023264208James Dong } 62029a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->memory_management_control_operation[i] == 2) 62129a84457aed4c45bc900998b5e11c03023264208James Dong { 62229a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->long_term_pic_num[i]); 62329a84457aed4c45bc900998b5e11c03023264208James Dong } 62429a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->memory_management_control_operation[i] == 3 || 62529a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->memory_management_control_operation[i] == 6) 62629a84457aed4c45bc900998b5e11c03023264208James Dong { 62729a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->long_term_frame_idx[i]); 62829a84457aed4c45bc900998b5e11c03023264208James Dong } 62929a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->memory_management_control_operation[i] == 4) 63029a84457aed4c45bc900998b5e11c03023264208James Dong { 63129a84457aed4c45bc900998b5e11c03023264208James Dong status = ue_v(stream, sliceHdr->max_long_term_frame_idx_plus1[i]); 63229a84457aed4c45bc900998b5e11c03023264208James Dong } 63329a84457aed4c45bc900998b5e11c03023264208James Dong i++; 63429a84457aed4c45bc900998b5e11c03023264208James Dong } 63529a84457aed4c45bc900998b5e11c03023264208James Dong while (sliceHdr->memory_management_control_operation[i] != 0 && i < MAX_DEC_REF_PIC_MARKING); 63629a84457aed4c45bc900998b5e11c03023264208James Dong if (i >= MAX_DEC_REF_PIC_MARKING && sliceHdr->memory_management_control_operation[i] != 0) 63729a84457aed4c45bc900998b5e11c03023264208James Dong { 63829a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_DEC_REF_PIC_MARK_FAIL; /* we're screwed!!, not enough memory */ 63929a84457aed4c45bc900998b5e11c03023264208James Dong } 64029a84457aed4c45bc900998b5e11c03023264208James Dong } 64129a84457aed4c45bc900998b5e11c03023264208James Dong } 64229a84457aed4c45bc900998b5e11c03023264208James Dong 64329a84457aed4c45bc900998b5e11c03023264208James Dong return status; 64429a84457aed4c45bc900998b5e11c03023264208James Dong} 64529a84457aed4c45bc900998b5e11c03023264208James Dong 64629a84457aed4c45bc900998b5e11c03023264208James Dong/* see subclause 8.2.1 Decoding process for picture order count. 64729a84457aed4c45bc900998b5e11c03023264208James DongSee also PostPOC() for initialization of some variables. */ 64829a84457aed4c45bc900998b5e11c03023264208James DongAVCEnc_Status InitPOC(AVCEncObject *encvid) 64929a84457aed4c45bc900998b5e11c03023264208James Dong{ 65029a84457aed4c45bc900998b5e11c03023264208James Dong AVCCommonObj *video = encvid->common; 65129a84457aed4c45bc900998b5e11c03023264208James Dong AVCSeqParamSet *currSPS = video->currSeqParams; 65229a84457aed4c45bc900998b5e11c03023264208James Dong AVCSliceHeader *sliceHdr = video->sliceHdr; 65329a84457aed4c45bc900998b5e11c03023264208James Dong AVCFrameIO *currInput = encvid->currInput; 65429a84457aed4c45bc900998b5e11c03023264208James Dong int i; 65529a84457aed4c45bc900998b5e11c03023264208James Dong 65629a84457aed4c45bc900998b5e11c03023264208James Dong switch (currSPS->pic_order_cnt_type) 65729a84457aed4c45bc900998b5e11c03023264208James Dong { 65829a84457aed4c45bc900998b5e11c03023264208James Dong case 0: /* POC MODE 0 , subclause 8.2.1.1 */ 65929a84457aed4c45bc900998b5e11c03023264208James Dong /* encoding part */ 66029a84457aed4c45bc900998b5e11c03023264208James Dong if (video->nal_unit_type == AVC_NALTYPE_IDR) 66129a84457aed4c45bc900998b5e11c03023264208James Dong { 66229a84457aed4c45bc900998b5e11c03023264208James Dong encvid->dispOrdPOCRef = currInput->disp_order; 66329a84457aed4c45bc900998b5e11c03023264208James Dong } 66429a84457aed4c45bc900998b5e11c03023264208James Dong while (currInput->disp_order < encvid->dispOrdPOCRef) 66529a84457aed4c45bc900998b5e11c03023264208James Dong { 66629a84457aed4c45bc900998b5e11c03023264208James Dong encvid->dispOrdPOCRef -= video->MaxPicOrderCntLsb; 66729a84457aed4c45bc900998b5e11c03023264208James Dong } 66829a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->pic_order_cnt_lsb = currInput->disp_order - encvid->dispOrdPOCRef; 66929a84457aed4c45bc900998b5e11c03023264208James Dong while (sliceHdr->pic_order_cnt_lsb >= video->MaxPicOrderCntLsb) 67029a84457aed4c45bc900998b5e11c03023264208James Dong { 67129a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->pic_order_cnt_lsb -= video->MaxPicOrderCntLsb; 67229a84457aed4c45bc900998b5e11c03023264208James Dong } 67329a84457aed4c45bc900998b5e11c03023264208James Dong /* decoding part */ 67429a84457aed4c45bc900998b5e11c03023264208James Dong /* Calculate the MSBs of current picture */ 67529a84457aed4c45bc900998b5e11c03023264208James Dong if (video->nal_unit_type == AVC_NALTYPE_IDR) 67629a84457aed4c45bc900998b5e11c03023264208James Dong { 67729a84457aed4c45bc900998b5e11c03023264208James Dong video->prevPicOrderCntMsb = 0; 67829a84457aed4c45bc900998b5e11c03023264208James Dong video->prevPicOrderCntLsb = 0; 67929a84457aed4c45bc900998b5e11c03023264208James Dong } 68029a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->pic_order_cnt_lsb < video->prevPicOrderCntLsb && 68129a84457aed4c45bc900998b5e11c03023264208James Dong (video->prevPicOrderCntLsb - sliceHdr->pic_order_cnt_lsb) >= (video->MaxPicOrderCntLsb / 2)) 68229a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCntMsb = video->prevPicOrderCntMsb + video->MaxPicOrderCntLsb; 68329a84457aed4c45bc900998b5e11c03023264208James Dong else if (sliceHdr->pic_order_cnt_lsb > video->prevPicOrderCntLsb && 68429a84457aed4c45bc900998b5e11c03023264208James Dong (sliceHdr->pic_order_cnt_lsb - video->prevPicOrderCntLsb) > (video->MaxPicOrderCntLsb / 2)) 68529a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCntMsb = video->prevPicOrderCntMsb - video->MaxPicOrderCntLsb; 68629a84457aed4c45bc900998b5e11c03023264208James Dong else 68729a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCntMsb = video->prevPicOrderCntMsb; 68829a84457aed4c45bc900998b5e11c03023264208James Dong 68929a84457aed4c45bc900998b5e11c03023264208James Dong /* JVT-I010 page 81 is different from JM7.3 */ 69029a84457aed4c45bc900998b5e11c03023264208James Dong if (!sliceHdr->field_pic_flag || !sliceHdr->bottom_field_flag) 69129a84457aed4c45bc900998b5e11c03023264208James Dong { 69229a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCnt = video->TopFieldOrderCnt = video->PicOrderCntMsb + sliceHdr->pic_order_cnt_lsb; 69329a84457aed4c45bc900998b5e11c03023264208James Dong } 69429a84457aed4c45bc900998b5e11c03023264208James Dong 69529a84457aed4c45bc900998b5e11c03023264208James Dong if (!sliceHdr->field_pic_flag) 69629a84457aed4c45bc900998b5e11c03023264208James Dong { 69729a84457aed4c45bc900998b5e11c03023264208James Dong video->BottomFieldOrderCnt = video->TopFieldOrderCnt + sliceHdr->delta_pic_order_cnt_bottom; 69829a84457aed4c45bc900998b5e11c03023264208James Dong } 69929a84457aed4c45bc900998b5e11c03023264208James Dong else if (sliceHdr->bottom_field_flag) 70029a84457aed4c45bc900998b5e11c03023264208James Dong { 70129a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCnt = video->BottomFieldOrderCnt = video->PicOrderCntMsb + sliceHdr->pic_order_cnt_lsb; 70229a84457aed4c45bc900998b5e11c03023264208James Dong } 70329a84457aed4c45bc900998b5e11c03023264208James Dong 70429a84457aed4c45bc900998b5e11c03023264208James Dong if (!sliceHdr->field_pic_flag) 70529a84457aed4c45bc900998b5e11c03023264208James Dong { 70629a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCnt = AVC_MIN(video->TopFieldOrderCnt, video->BottomFieldOrderCnt); 70729a84457aed4c45bc900998b5e11c03023264208James Dong } 70829a84457aed4c45bc900998b5e11c03023264208James Dong 70929a84457aed4c45bc900998b5e11c03023264208James Dong if (video->currPicParams->pic_order_present_flag && !sliceHdr->field_pic_flag) 71029a84457aed4c45bc900998b5e11c03023264208James Dong { 71129a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->delta_pic_order_cnt_bottom = 0; /* defaulted to zero */ 71229a84457aed4c45bc900998b5e11c03023264208James Dong } 71329a84457aed4c45bc900998b5e11c03023264208James Dong 71429a84457aed4c45bc900998b5e11c03023264208James Dong break; 71529a84457aed4c45bc900998b5e11c03023264208James Dong case 1: /* POC MODE 1, subclause 8.2.1.2 */ 71629a84457aed4c45bc900998b5e11c03023264208James Dong /* calculate FrameNumOffset */ 71729a84457aed4c45bc900998b5e11c03023264208James Dong if (video->nal_unit_type == AVC_NALTYPE_IDR) 71829a84457aed4c45bc900998b5e11c03023264208James Dong { 71929a84457aed4c45bc900998b5e11c03023264208James Dong encvid->dispOrdPOCRef = currInput->disp_order; /* reset the reference point */ 72029a84457aed4c45bc900998b5e11c03023264208James Dong video->prevFrameNumOffset = 0; 72129a84457aed4c45bc900998b5e11c03023264208James Dong video->FrameNumOffset = 0; 72229a84457aed4c45bc900998b5e11c03023264208James Dong } 72329a84457aed4c45bc900998b5e11c03023264208James Dong else if (video->prevFrameNum > sliceHdr->frame_num) 72429a84457aed4c45bc900998b5e11c03023264208James Dong { 72529a84457aed4c45bc900998b5e11c03023264208James Dong video->FrameNumOffset = video->prevFrameNumOffset + video->MaxFrameNum; 72629a84457aed4c45bc900998b5e11c03023264208James Dong } 72729a84457aed4c45bc900998b5e11c03023264208James Dong else 72829a84457aed4c45bc900998b5e11c03023264208James Dong { 72929a84457aed4c45bc900998b5e11c03023264208James Dong video->FrameNumOffset = video->prevFrameNumOffset; 73029a84457aed4c45bc900998b5e11c03023264208James Dong } 73129a84457aed4c45bc900998b5e11c03023264208James Dong /* calculate absFrameNum */ 73229a84457aed4c45bc900998b5e11c03023264208James Dong if (currSPS->num_ref_frames_in_pic_order_cnt_cycle) 73329a84457aed4c45bc900998b5e11c03023264208James Dong { 73429a84457aed4c45bc900998b5e11c03023264208James Dong video->absFrameNum = video->FrameNumOffset + sliceHdr->frame_num; 73529a84457aed4c45bc900998b5e11c03023264208James Dong } 73629a84457aed4c45bc900998b5e11c03023264208James Dong else 73729a84457aed4c45bc900998b5e11c03023264208James Dong { 73829a84457aed4c45bc900998b5e11c03023264208James Dong video->absFrameNum = 0; 73929a84457aed4c45bc900998b5e11c03023264208James Dong } 74029a84457aed4c45bc900998b5e11c03023264208James Dong 74129a84457aed4c45bc900998b5e11c03023264208James Dong if (video->absFrameNum > 0 && video->nal_ref_idc == 0) 74229a84457aed4c45bc900998b5e11c03023264208James Dong { 74329a84457aed4c45bc900998b5e11c03023264208James Dong video->absFrameNum--; 74429a84457aed4c45bc900998b5e11c03023264208James Dong } 74529a84457aed4c45bc900998b5e11c03023264208James Dong 74629a84457aed4c45bc900998b5e11c03023264208James Dong /* derive picOrderCntCycleCnt and frameNumInPicOrderCntCycle */ 74729a84457aed4c45bc900998b5e11c03023264208James Dong if (video->absFrameNum > 0) 74829a84457aed4c45bc900998b5e11c03023264208James Dong { 74929a84457aed4c45bc900998b5e11c03023264208James Dong video->picOrderCntCycleCnt = (video->absFrameNum - 1) / currSPS->num_ref_frames_in_pic_order_cnt_cycle; 75029a84457aed4c45bc900998b5e11c03023264208James Dong video->frameNumInPicOrderCntCycle = (video->absFrameNum - 1) % currSPS->num_ref_frames_in_pic_order_cnt_cycle; 75129a84457aed4c45bc900998b5e11c03023264208James Dong } 75229a84457aed4c45bc900998b5e11c03023264208James Dong /* derive expectedDeltaPerPicOrderCntCycle, this value can be computed up front. */ 75329a84457aed4c45bc900998b5e11c03023264208James Dong video->expectedDeltaPerPicOrderCntCycle = 0; 75429a84457aed4c45bc900998b5e11c03023264208James Dong for (i = 0; i < (int)currSPS->num_ref_frames_in_pic_order_cnt_cycle; i++) 75529a84457aed4c45bc900998b5e11c03023264208James Dong { 75629a84457aed4c45bc900998b5e11c03023264208James Dong video->expectedDeltaPerPicOrderCntCycle += currSPS->offset_for_ref_frame[i]; 75729a84457aed4c45bc900998b5e11c03023264208James Dong } 75829a84457aed4c45bc900998b5e11c03023264208James Dong /* derive expectedPicOrderCnt */ 75929a84457aed4c45bc900998b5e11c03023264208James Dong if (video->absFrameNum) 76029a84457aed4c45bc900998b5e11c03023264208James Dong { 76129a84457aed4c45bc900998b5e11c03023264208James Dong video->expectedPicOrderCnt = video->picOrderCntCycleCnt * video->expectedDeltaPerPicOrderCntCycle; 76229a84457aed4c45bc900998b5e11c03023264208James Dong for (i = 0; i <= video->frameNumInPicOrderCntCycle; i++) 76329a84457aed4c45bc900998b5e11c03023264208James Dong { 76429a84457aed4c45bc900998b5e11c03023264208James Dong video->expectedPicOrderCnt += currSPS->offset_for_ref_frame[i]; 76529a84457aed4c45bc900998b5e11c03023264208James Dong } 76629a84457aed4c45bc900998b5e11c03023264208James Dong } 76729a84457aed4c45bc900998b5e11c03023264208James Dong else 76829a84457aed4c45bc900998b5e11c03023264208James Dong { 76929a84457aed4c45bc900998b5e11c03023264208James Dong video->expectedPicOrderCnt = 0; 77029a84457aed4c45bc900998b5e11c03023264208James Dong } 77129a84457aed4c45bc900998b5e11c03023264208James Dong 77229a84457aed4c45bc900998b5e11c03023264208James Dong if (video->nal_ref_idc == 0) 77329a84457aed4c45bc900998b5e11c03023264208James Dong { 77429a84457aed4c45bc900998b5e11c03023264208James Dong video->expectedPicOrderCnt += currSPS->offset_for_non_ref_pic; 77529a84457aed4c45bc900998b5e11c03023264208James Dong } 77629a84457aed4c45bc900998b5e11c03023264208James Dong /* derive TopFieldOrderCnt and BottomFieldOrderCnt */ 77729a84457aed4c45bc900998b5e11c03023264208James Dong /* encoding part */ 77829a84457aed4c45bc900998b5e11c03023264208James Dong if (!currSPS->delta_pic_order_always_zero_flag) 77929a84457aed4c45bc900998b5e11c03023264208James Dong { 78029a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->delta_pic_order_cnt[0] = currInput->disp_order - encvid->dispOrdPOCRef - video->expectedPicOrderCnt; 78129a84457aed4c45bc900998b5e11c03023264208James Dong 78229a84457aed4c45bc900998b5e11c03023264208James Dong if (video->currPicParams->pic_order_present_flag && !sliceHdr->field_pic_flag) 78329a84457aed4c45bc900998b5e11c03023264208James Dong { 78429a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->delta_pic_order_cnt[1] = sliceHdr->delta_pic_order_cnt[0]; /* should be calculated from currInput->bottom_field->disp_order */ 78529a84457aed4c45bc900998b5e11c03023264208James Dong } 78629a84457aed4c45bc900998b5e11c03023264208James Dong else 78729a84457aed4c45bc900998b5e11c03023264208James Dong { 78829a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->delta_pic_order_cnt[1] = 0; 78929a84457aed4c45bc900998b5e11c03023264208James Dong } 79029a84457aed4c45bc900998b5e11c03023264208James Dong } 79129a84457aed4c45bc900998b5e11c03023264208James Dong else 79229a84457aed4c45bc900998b5e11c03023264208James Dong { 79329a84457aed4c45bc900998b5e11c03023264208James Dong sliceHdr->delta_pic_order_cnt[0] = sliceHdr->delta_pic_order_cnt[1] = 0; 79429a84457aed4c45bc900998b5e11c03023264208James Dong } 79529a84457aed4c45bc900998b5e11c03023264208James Dong 79629a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->field_pic_flag == 0) 79729a84457aed4c45bc900998b5e11c03023264208James Dong { 79829a84457aed4c45bc900998b5e11c03023264208James Dong video->TopFieldOrderCnt = video->expectedPicOrderCnt + sliceHdr->delta_pic_order_cnt[0]; 79929a84457aed4c45bc900998b5e11c03023264208James Dong video->BottomFieldOrderCnt = video->TopFieldOrderCnt + currSPS->offset_for_top_to_bottom_field + sliceHdr->delta_pic_order_cnt[1]; 80029a84457aed4c45bc900998b5e11c03023264208James Dong 80129a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCnt = AVC_MIN(video->TopFieldOrderCnt, video->BottomFieldOrderCnt); 80229a84457aed4c45bc900998b5e11c03023264208James Dong } 80329a84457aed4c45bc900998b5e11c03023264208James Dong else if (sliceHdr->bottom_field_flag == 0) 80429a84457aed4c45bc900998b5e11c03023264208James Dong { 80529a84457aed4c45bc900998b5e11c03023264208James Dong video->TopFieldOrderCnt = video->expectedPicOrderCnt + sliceHdr->delta_pic_order_cnt[0]; 80629a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCnt = video->TopFieldOrderCnt; 80729a84457aed4c45bc900998b5e11c03023264208James Dong } 80829a84457aed4c45bc900998b5e11c03023264208James Dong else 80929a84457aed4c45bc900998b5e11c03023264208James Dong { 81029a84457aed4c45bc900998b5e11c03023264208James Dong video->BottomFieldOrderCnt = video->expectedPicOrderCnt + currSPS->offset_for_top_to_bottom_field + sliceHdr->delta_pic_order_cnt[0]; 81129a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCnt = video->BottomFieldOrderCnt; 81229a84457aed4c45bc900998b5e11c03023264208James Dong } 81329a84457aed4c45bc900998b5e11c03023264208James Dong break; 81429a84457aed4c45bc900998b5e11c03023264208James Dong 81529a84457aed4c45bc900998b5e11c03023264208James Dong 81629a84457aed4c45bc900998b5e11c03023264208James Dong case 2: /* POC MODE 2, subclause 8.2.1.3 */ 81729a84457aed4c45bc900998b5e11c03023264208James Dong /* decoding order must be the same as display order */ 81829a84457aed4c45bc900998b5e11c03023264208James Dong /* we don't check for that. The decoder will just output in decoding order. */ 81929a84457aed4c45bc900998b5e11c03023264208James Dong /* Check for 2 consecutive non-reference frame */ 82029a84457aed4c45bc900998b5e11c03023264208James Dong if (video->nal_ref_idc == 0) 82129a84457aed4c45bc900998b5e11c03023264208James Dong { 82229a84457aed4c45bc900998b5e11c03023264208James Dong if (encvid->dispOrdPOCRef == 1) 82329a84457aed4c45bc900998b5e11c03023264208James Dong { 82429a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_CONSECUTIVE_NONREF; 82529a84457aed4c45bc900998b5e11c03023264208James Dong } 82629a84457aed4c45bc900998b5e11c03023264208James Dong encvid->dispOrdPOCRef = 1; /* act as a flag for non ref */ 82729a84457aed4c45bc900998b5e11c03023264208James Dong } 82829a84457aed4c45bc900998b5e11c03023264208James Dong else 82929a84457aed4c45bc900998b5e11c03023264208James Dong { 83029a84457aed4c45bc900998b5e11c03023264208James Dong encvid->dispOrdPOCRef = 0; 83129a84457aed4c45bc900998b5e11c03023264208James Dong } 83229a84457aed4c45bc900998b5e11c03023264208James Dong 83329a84457aed4c45bc900998b5e11c03023264208James Dong 83429a84457aed4c45bc900998b5e11c03023264208James Dong if (video->nal_unit_type == AVC_NALTYPE_IDR) 83529a84457aed4c45bc900998b5e11c03023264208James Dong { 83629a84457aed4c45bc900998b5e11c03023264208James Dong video->FrameNumOffset = 0; 83729a84457aed4c45bc900998b5e11c03023264208James Dong } 83829a84457aed4c45bc900998b5e11c03023264208James Dong else if (video->prevFrameNum > sliceHdr->frame_num) 83929a84457aed4c45bc900998b5e11c03023264208James Dong { 84029a84457aed4c45bc900998b5e11c03023264208James Dong video->FrameNumOffset = video->prevFrameNumOffset + video->MaxFrameNum; 84129a84457aed4c45bc900998b5e11c03023264208James Dong } 84229a84457aed4c45bc900998b5e11c03023264208James Dong else 84329a84457aed4c45bc900998b5e11c03023264208James Dong { 84429a84457aed4c45bc900998b5e11c03023264208James Dong video->FrameNumOffset = video->prevFrameNumOffset; 84529a84457aed4c45bc900998b5e11c03023264208James Dong } 84629a84457aed4c45bc900998b5e11c03023264208James Dong /* derive tempPicOrderCnt, we just use PicOrderCnt */ 84729a84457aed4c45bc900998b5e11c03023264208James Dong if (video->nal_unit_type == AVC_NALTYPE_IDR) 84829a84457aed4c45bc900998b5e11c03023264208James Dong { 84929a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCnt = 0; 85029a84457aed4c45bc900998b5e11c03023264208James Dong } 85129a84457aed4c45bc900998b5e11c03023264208James Dong else if (video->nal_ref_idc == 0) 85229a84457aed4c45bc900998b5e11c03023264208James Dong { 85329a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCnt = 2 * (video->FrameNumOffset + sliceHdr->frame_num) - 1; 85429a84457aed4c45bc900998b5e11c03023264208James Dong } 85529a84457aed4c45bc900998b5e11c03023264208James Dong else 85629a84457aed4c45bc900998b5e11c03023264208James Dong { 85729a84457aed4c45bc900998b5e11c03023264208James Dong video->PicOrderCnt = 2 * (video->FrameNumOffset + sliceHdr->frame_num); 85829a84457aed4c45bc900998b5e11c03023264208James Dong } 85929a84457aed4c45bc900998b5e11c03023264208James Dong /* derive TopFieldOrderCnt and BottomFieldOrderCnt */ 86029a84457aed4c45bc900998b5e11c03023264208James Dong if (sliceHdr->field_pic_flag == 0) 86129a84457aed4c45bc900998b5e11c03023264208James Dong { 86229a84457aed4c45bc900998b5e11c03023264208James Dong video->TopFieldOrderCnt = video->BottomFieldOrderCnt = video->PicOrderCnt; 86329a84457aed4c45bc900998b5e11c03023264208James Dong } 86429a84457aed4c45bc900998b5e11c03023264208James Dong else if (sliceHdr->bottom_field_flag) 86529a84457aed4c45bc900998b5e11c03023264208James Dong { 86629a84457aed4c45bc900998b5e11c03023264208James Dong video->BottomFieldOrderCnt = video->PicOrderCnt; 86729a84457aed4c45bc900998b5e11c03023264208James Dong } 86829a84457aed4c45bc900998b5e11c03023264208James Dong else 86929a84457aed4c45bc900998b5e11c03023264208James Dong { 87029a84457aed4c45bc900998b5e11c03023264208James Dong video->TopFieldOrderCnt = video->PicOrderCnt; 87129a84457aed4c45bc900998b5e11c03023264208James Dong } 87229a84457aed4c45bc900998b5e11c03023264208James Dong break; 87329a84457aed4c45bc900998b5e11c03023264208James Dong default: 87429a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_POC_FAIL; 87529a84457aed4c45bc900998b5e11c03023264208James Dong } 87629a84457aed4c45bc900998b5e11c03023264208James Dong 87729a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_SUCCESS; 87829a84457aed4c45bc900998b5e11c03023264208James Dong} 87929a84457aed4c45bc900998b5e11c03023264208James Dong 88029a84457aed4c45bc900998b5e11c03023264208James Dong/** see subclause 8.2.1 */ 88129a84457aed4c45bc900998b5e11c03023264208James DongAVCEnc_Status PostPOC(AVCCommonObj *video) 88229a84457aed4c45bc900998b5e11c03023264208James Dong{ 88329a84457aed4c45bc900998b5e11c03023264208James Dong AVCSliceHeader *sliceHdr = video->sliceHdr; 88429a84457aed4c45bc900998b5e11c03023264208James Dong AVCSeqParamSet *currSPS = video->currSeqParams; 88529a84457aed4c45bc900998b5e11c03023264208James Dong 88629a84457aed4c45bc900998b5e11c03023264208James Dong video->prevFrameNum = sliceHdr->frame_num; 88729a84457aed4c45bc900998b5e11c03023264208James Dong 88829a84457aed4c45bc900998b5e11c03023264208James Dong switch (currSPS->pic_order_cnt_type) 88929a84457aed4c45bc900998b5e11c03023264208James Dong { 89029a84457aed4c45bc900998b5e11c03023264208James Dong case 0: /* subclause 8.2.1.1 */ 89129a84457aed4c45bc900998b5e11c03023264208James Dong if (video->mem_mgr_ctrl_eq_5) 89229a84457aed4c45bc900998b5e11c03023264208James Dong { 89329a84457aed4c45bc900998b5e11c03023264208James Dong video->prevPicOrderCntMsb = 0; 89429a84457aed4c45bc900998b5e11c03023264208James Dong video->prevPicOrderCntLsb = video->TopFieldOrderCnt; 89529a84457aed4c45bc900998b5e11c03023264208James Dong } 89629a84457aed4c45bc900998b5e11c03023264208James Dong else 89729a84457aed4c45bc900998b5e11c03023264208James Dong { 89829a84457aed4c45bc900998b5e11c03023264208James Dong video->prevPicOrderCntMsb = video->PicOrderCntMsb; 89929a84457aed4c45bc900998b5e11c03023264208James Dong video->prevPicOrderCntLsb = sliceHdr->pic_order_cnt_lsb; 90029a84457aed4c45bc900998b5e11c03023264208James Dong } 90129a84457aed4c45bc900998b5e11c03023264208James Dong break; 90229a84457aed4c45bc900998b5e11c03023264208James Dong case 1: /* subclause 8.2.1.2 and 8.2.1.3 */ 90329a84457aed4c45bc900998b5e11c03023264208James Dong case 2: 90429a84457aed4c45bc900998b5e11c03023264208James Dong if (video->mem_mgr_ctrl_eq_5) 90529a84457aed4c45bc900998b5e11c03023264208James Dong { 90629a84457aed4c45bc900998b5e11c03023264208James Dong video->prevFrameNumOffset = 0; 90729a84457aed4c45bc900998b5e11c03023264208James Dong } 90829a84457aed4c45bc900998b5e11c03023264208James Dong else 90929a84457aed4c45bc900998b5e11c03023264208James Dong { 91029a84457aed4c45bc900998b5e11c03023264208James Dong video->prevFrameNumOffset = video->FrameNumOffset; 91129a84457aed4c45bc900998b5e11c03023264208James Dong } 91229a84457aed4c45bc900998b5e11c03023264208James Dong break; 91329a84457aed4c45bc900998b5e11c03023264208James Dong } 91429a84457aed4c45bc900998b5e11c03023264208James Dong 91529a84457aed4c45bc900998b5e11c03023264208James Dong return AVCENC_SUCCESS; 91629a84457aed4c45bc900998b5e11c03023264208James Dong} 91729a84457aed4c45bc900998b5e11c03023264208James Dong 918