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 /* File Includes                                                             */
23 /*****************************************************************************/
24 
25 /* System include files */
26 #include <stdio.h>
27 
28 /* User include files */
29 #include "irc_datatypes.h"
30 #include "irc_common.h"
31 #include "irc_cntrl_param.h"
32 #include "irc_mem_req_and_acq.h"
33 #include "irc_fixed_point_error_bits.h"
34 
35 typedef struct error_bits_t
36 {
37     /* Max tgt frm rate so that dynamic change in frm rate can be handled */
38     WORD32 i4_max_tgt_frm_rate;
39 
40     /* Cur frm rate */
41     WORD32 i4_cur_tgt_frm_rate;
42 
43     /* tgt frame rate*/
44     WORD32 i4_tgt_frm_rate;
45 
46     /* tgt frm rate increment */
47     WORD32 i4_tgt_frm_rate_incr;
48 
49     /* flag to indicate 1 second is up */
50     UWORD8 u1_compute_error_bits;
51 
52     /* Bitrate/frame rate value added over a period */
53     WORD32 i4_accum_bitrate;
54 
55     /* bitrate */
56     WORD32 i4_bitrate;
57 
58 } error_bits_t;
59 
irc_error_bits_num_fill_use_free_memtab(error_bits_t ** pps_error_bits,itt_memtab_t * ps_memtab,ITT_FUNC_TYPE_E e_func_type)60 WORD32 irc_error_bits_num_fill_use_free_memtab(error_bits_t **pps_error_bits,
61                                                itt_memtab_t *ps_memtab,
62                                                ITT_FUNC_TYPE_E e_func_type)
63 {
64     WORD32 i4_mem_tab_idx = 0;
65     error_bits_t s_error_bits_temp;
66 
67     /*
68      * Hack for all alloc, during which we don't have any state memory.
69      * Dereferencing can cause issues
70      */
71     if(e_func_type == GET_NUM_MEMTAB || e_func_type == FILL_MEMTAB)
72         (*pps_error_bits) = &s_error_bits_temp;
73 
74     /* For src rate control state structure */
75     if(e_func_type != GET_NUM_MEMTAB)
76     {
77         fill_memtab(&ps_memtab[i4_mem_tab_idx], sizeof(error_bits_t),
78                     ALIGN_128_BYTE, PERSISTENT, DDR);
79         use_or_fill_base(&ps_memtab[0], (void**)pps_error_bits, e_func_type);
80     }
81     i4_mem_tab_idx++;
82 
83     return (i4_mem_tab_idx);
84 }
85 
86 /*******************************************************************************
87  * @brief Calculates the error bits due to fixed point divisions
88  ******************************************************************************/
irc_init_error_bits(error_bits_t * ps_error_bits,WORD32 i4_max_tgt_frm_rate,WORD32 i4_bitrate)89 void irc_init_error_bits(error_bits_t *ps_error_bits,
90                          WORD32 i4_max_tgt_frm_rate,
91                          WORD32 i4_bitrate)
92 {
93     /* Initializing the parameters*/
94     ps_error_bits->i4_cur_tgt_frm_rate = 0;
95     ps_error_bits->i4_max_tgt_frm_rate = i4_max_tgt_frm_rate;
96 
97     /* Value by which i4_cur_tgt_frm_rate is incremented every VOP*/
98     ps_error_bits->i4_tgt_frm_rate_incr = 1000;
99 
100     /*Compute error bits is set to 1 at the end of 1 second*/
101     ps_error_bits->u1_compute_error_bits = 0;
102     ps_error_bits->i4_tgt_frm_rate = i4_max_tgt_frm_rate;
103     ps_error_bits->i4_accum_bitrate = 0;
104     ps_error_bits->i4_bitrate = i4_bitrate;
105 }
106 
107 /*******************************************************************************
108  * @brief Updates the error state
109  ******************************************************************************/
irc_update_error_bits(error_bits_t * ps_error_bits)110 void irc_update_error_bits(error_bits_t *ps_error_bits)
111 {
112     WORD32 i4_bits_per_frame;
113 
114     X_PROD_Y_DIV_Z(ps_error_bits->i4_bitrate, 1000,
115                    ps_error_bits->i4_tgt_frm_rate, i4_bits_per_frame);
116 
117     /*
118      * This value is incremented every at the end of every VOP by
119      * i4_tgt_frm_rate_incr
120      */
121     ps_error_bits->i4_cur_tgt_frm_rate += ps_error_bits->i4_tgt_frm_rate_incr;
122     if(ps_error_bits->u1_compute_error_bits == 1)
123     {
124         ps_error_bits->i4_accum_bitrate = 0;
125     }
126     ps_error_bits->i4_accum_bitrate += i4_bits_per_frame;
127 
128     /*
129      * When current tgt frm rate is equal or greater than max tgt frame rate
130      * 1 second is up , compute the error bits
131      */
132     if(ps_error_bits->i4_cur_tgt_frm_rate >= ps_error_bits->i4_max_tgt_frm_rate)
133     {
134         ps_error_bits->i4_cur_tgt_frm_rate -=
135                         ps_error_bits->i4_max_tgt_frm_rate;
136         ps_error_bits->u1_compute_error_bits = 1;
137     }
138     else
139     {
140         ps_error_bits->u1_compute_error_bits = 0;
141     }
142 }
143 
144 /*******************************************************************************
145  * @brief Returns the error bits for the current frame if there are any
146  *
147  ******************************************************************************/
irc_get_error_bits(error_bits_t * ps_error_bits)148 WORD32 irc_get_error_bits(error_bits_t *ps_error_bits)
149 {
150     WORD32 i4_error_bits = 0;
151 
152     /*If 1s is up calculate error for the last 1s worth of frames*/
153     if(ps_error_bits->u1_compute_error_bits == 1)
154     {
155         /*Error = Actual bitrate - bits_per_frame * num of frames*/
156         i4_error_bits = ps_error_bits->i4_bitrate
157                         - ps_error_bits->i4_accum_bitrate;
158     }
159 
160     return (i4_error_bits);
161 }
162 
163 /* *****************************************************************************
164  *
165  * @brief Change the frame rate parameter for the error bits state
166  *
167  ******************************************************************************/
irc_change_frm_rate_in_error_bits(error_bits_t * ps_error_bits,WORD32 i4_tgt_frm_rate)168 void irc_change_frm_rate_in_error_bits(error_bits_t *ps_error_bits,
169                                        WORD32 i4_tgt_frm_rate)
170 {
171     /* Value by which i4_cur_tgt_frm_rate is incremented every VOP*/
172     ps_error_bits->i4_tgt_frm_rate_incr = (ps_error_bits->i4_max_tgt_frm_rate
173                                            * 1000) / i4_tgt_frm_rate;
174     ps_error_bits->i4_tgt_frm_rate = i4_tgt_frm_rate;
175 }
176 
177 /*******************************************************************************
178  * @brief Change the bitrate value for error bits module
179  ******************************************************************************/
irc_change_bitrate_in_error_bits(error_bits_t * ps_error_bits,WORD32 i4_bitrate)180 void irc_change_bitrate_in_error_bits(error_bits_t *ps_error_bits,
181                                       WORD32 i4_bitrate)
182 {
183     ps_error_bits->i4_bitrate = i4_bitrate;
184 }
185 
186