irc_est_sad.c revision c22addc6ee9c96f2996001362dbe39dd5e14038d
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/* Includes */ 23/*****************************************************************************/ 24 25/* User include files */ 26#include "irc_datatypes.h" 27#include "irc_cntrl_param.h" 28#include "irc_mem_req_and_acq.h" 29#include "irc_est_sad.h" 30#include "irc_common.h" 31 32typedef struct est_sad_t 33{ 34 WORD32 i4_use_est_intra_sad; 35 36 /* Previous frame SAD */ 37 UWORD32 au4_prev_frm_sad[MAX_PIC_TYPE]; 38 39 /* Current (nth) ifi average P frame SAD */ 40 UWORD32 u4_n_p_frm_ifi_avg_sad; 41 42 /* (n-1)th ifi average P frame SAD */ 43 UWORD32 u4_n_1_p_frm_ifi_avg_sad; 44 45 /* (n-2)th ifi average P frame SAD */ 46 UWORD32 u4_n_2_p_frm_ifi_avg_sad; 47 48 /* number of ifi encoded till now */ 49 WORD32 i4_num_ifi_encoded; 50 51 /* number of P frames in the current IFI */ 52 WORD32 i4_num_p_frm_in_cur_ifi; 53 54} est_sad_t; 55 56WORD32 irc_est_sad_num_fill_use_free_memtab(est_sad_t **pps_est_sad, 57 itt_memtab_t *ps_memtab, 58 ITT_FUNC_TYPE_E e_func_type) 59{ 60 WORD32 i4_mem_tab_idx = 0; 61 est_sad_t s_est_sad; 62 63 /* Hack for al alloc, during which we don't have any state memory. 64 * Dereferencing can cause issues 65 */ 66 if(e_func_type == GET_NUM_MEMTAB || e_func_type == FILL_MEMTAB) 67 (*pps_est_sad) = &s_est_sad; 68 69 /* For src rate control state structure */ 70 if(e_func_type != GET_NUM_MEMTAB) 71 { 72 fill_memtab(&ps_memtab[i4_mem_tab_idx], sizeof(est_sad_t), 73 ALIGN_128_BYTE, PERSISTENT, DDR); 74 use_or_fill_base(&ps_memtab[0], (void**)pps_est_sad, e_func_type); 75 } 76 i4_mem_tab_idx++; 77 78 return (i4_mem_tab_idx); 79} 80 81void irc_init_est_sad(est_sad_t *ps_est_sad, WORD32 i4_use_est_intra_sad) 82{ 83 WORD32 i; 84 ps_est_sad->i4_use_est_intra_sad = i4_use_est_intra_sad; 85 86 for(i = 0; i < MAX_PIC_TYPE; i++) 87 { 88 ps_est_sad->au4_prev_frm_sad[i] = 0; 89 } 90 91 ps_est_sad->u4_n_p_frm_ifi_avg_sad = 0; 92 ps_est_sad->u4_n_1_p_frm_ifi_avg_sad = 0; 93 ps_est_sad->u4_n_2_p_frm_ifi_avg_sad = 0; 94 ps_est_sad->i4_num_ifi_encoded = 0; 95 ps_est_sad->i4_num_p_frm_in_cur_ifi = 0; 96} 97 98void irc_reset_est_sad(est_sad_t *ps_est_sad) 99{ 100 irc_init_est_sad(ps_est_sad, ps_est_sad->i4_use_est_intra_sad); 101} 102 103/* 104 * Get estimated SAD can be called at any point. The various use cases are: 105 * 1) When a I frame is getting encoded, 106 * - get the estimated of P => No issues since we use the last coded P frame 107 * value 108 * - get estimated of I => This call for two cases: 109 * => a) if num_ifi_encoded is less than 2 110 * then return the previous encoded I frame sad 111 * => b) if num_ifi_encoded is more than 2, then we scale 112 * the prev I sad by the ratio of (n-1) ifi P to n-2 ifi P 113 * 2) When P frame is getting encoded, 114 * - get the estimated of P => No issues since we use the last coded P frame value 115 * - get the estimated of I => Simillar to I we have two cases. 116 * To handle the b) case extra logic had to introduced using 117 * u1_is_n_1_p_frm_ifi_avg_sad_usable flag 118 */ 119UWORD32 irc_get_est_sad(est_sad_t *ps_est_sad, picture_type_e e_pic_type) 120{ 121 if(ps_est_sad->i4_use_est_intra_sad) 122 { 123 UWORD32 u4_estimated_sad; 124 if(e_pic_type == P_PIC) 125 { 126 u4_estimated_sad = ps_est_sad->au4_prev_frm_sad[P_PIC]; 127 } 128 else if(e_pic_type == B_PIC) 129 { 130 u4_estimated_sad = ps_est_sad->au4_prev_frm_sad[B_PIC]; 131 } 132 else 133 { 134 if(ps_est_sad->i4_num_ifi_encoded < 2) 135 { 136 /* 137 * Only one IFI has been encoded and so use the previous I 138 * frames SAD 139 */ 140 u4_estimated_sad = ps_est_sad->au4_prev_frm_sad[I_PIC]; 141 } 142 else 143 { 144 /* 145 * Since the n-1 'P' frame IFI would have just accumulated the 146 * frame sads we average it out here 147 */ 148 UWORD32 u4_n_1_p_frm_ifi_avg_sad, u4_n_2_p_frm_ifi_avg_sad; 149 number_t vq_n_1_p_frm_ifi_avg_sad, vq_n_2_p_frm_ifi_avg_sad; 150 number_t vq_prev_frm_sad_i; 151 152 /* 153 * If there are frames in the current IFI start using it to 154 * estimate the I frame SAD 155 */ 156 if(ps_est_sad->i4_num_p_frm_in_cur_ifi) 157 { 158 u4_n_1_p_frm_ifi_avg_sad = 159 (ps_est_sad->u4_n_p_frm_ifi_avg_sad 160 / ps_est_sad->i4_num_p_frm_in_cur_ifi); 161 u4_n_2_p_frm_ifi_avg_sad = 162 ps_est_sad->u4_n_1_p_frm_ifi_avg_sad; 163 } 164 else 165 { 166 u4_n_1_p_frm_ifi_avg_sad = 167 ps_est_sad->u4_n_1_p_frm_ifi_avg_sad; 168 u4_n_2_p_frm_ifi_avg_sad = 169 ps_est_sad->u4_n_2_p_frm_ifi_avg_sad; 170 } 171 172 /* 173 * If any of the previous p frame SADs are zeros we just return 174 * the previous I frame SAD 175 */ 176 if(u4_n_1_p_frm_ifi_avg_sad && u4_n_2_p_frm_ifi_avg_sad) 177 { 178 SET_VAR_Q(vq_prev_frm_sad_i, 179 ps_est_sad->au4_prev_frm_sad[I_PIC], 0); 180 SET_VAR_Q(vq_n_1_p_frm_ifi_avg_sad, 181 u4_n_1_p_frm_ifi_avg_sad, 0); 182 SET_VAR_Q(vq_n_2_p_frm_ifi_avg_sad, 183 u4_n_2_p_frm_ifi_avg_sad, 0); 184 /* 185 * Estimated SAD = 186 *(n-1)th intra frame interval(ifi) P frame Avg SAD * 187 *(prev I frame SAD / 188 *(prev (n-2)nd intra frame interval(ifi) P frame Avg SAD) 189 */ 190 mult32_var_q(vq_prev_frm_sad_i, vq_n_1_p_frm_ifi_avg_sad, 191 &vq_prev_frm_sad_i); 192 div32_var_q(vq_prev_frm_sad_i, vq_n_2_p_frm_ifi_avg_sad, 193 &vq_prev_frm_sad_i); 194 number_t_to_word32(vq_prev_frm_sad_i, 195 (WORD32*)&u4_estimated_sad); 196 } 197 else 198 { 199 u4_estimated_sad = ps_est_sad->au4_prev_frm_sad[I_PIC]; 200 } 201 } 202 } 203 return u4_estimated_sad; 204 } 205 else 206 { 207 return ps_est_sad->au4_prev_frm_sad[e_pic_type]; 208 } 209} 210 211void irc_update_actual_sad(est_sad_t *ps_est_sad, 212 UWORD32 u4_actual_sad, 213 picture_type_e e_pic_type) 214{ 215 ps_est_sad->au4_prev_frm_sad[e_pic_type] = u4_actual_sad; 216 217 if(ps_est_sad->i4_use_est_intra_sad) 218 { 219 if(e_pic_type == I_PIC) 220 { 221 /* The requirement is to have two IFI before estimating I frame SAD */ 222 if(ps_est_sad->i4_num_ifi_encoded < 2) 223 ps_est_sad->i4_num_ifi_encoded++; 224 225 /* Calculate the average SAD */ 226 if(ps_est_sad->i4_num_p_frm_in_cur_ifi) 227 { 228 ps_est_sad->u4_n_p_frm_ifi_avg_sad /= 229 ps_est_sad->i4_num_p_frm_in_cur_ifi; 230 } 231 else 232 { 233 ps_est_sad->u4_n_p_frm_ifi_avg_sad = 0; 234 } 235 /* Push the (n-1)th average SAD to the (n-2)th average SAD */ 236 ps_est_sad->u4_n_2_p_frm_ifi_avg_sad = 237 ps_est_sad->u4_n_1_p_frm_ifi_avg_sad; 238 /* Push the nth average SAD to the (n-1)th average SAD */ 239 ps_est_sad->u4_n_1_p_frm_ifi_avg_sad = 240 ps_est_sad->u4_n_p_frm_ifi_avg_sad; 241 /* Reset SAD and number of P frames */ 242 ps_est_sad->u4_n_p_frm_ifi_avg_sad = 0; 243 ps_est_sad->i4_num_p_frm_in_cur_ifi = 0; 244 } 245 else 246 { 247 ps_est_sad->u4_n_p_frm_ifi_avg_sad += u4_actual_sad; 248 ps_est_sad->i4_num_p_frm_in_cur_ifi++; 249 } 250 } 251} 252 253void irc_update_actual_sad_for_intra(est_sad_t *ps_est_sad, 254 WORD32 i4_intra_frm_cost) 255{ 256 if(!(ps_est_sad->i4_use_est_intra_sad)) 257 { 258 irc_update_actual_sad(ps_est_sad, i4_intra_frm_cost, I_PIC); 259 } 260} 261