1b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* 2b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. 3b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * 4b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * Use of this source code is governed by a BSD-style license 5b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * that can be found in the LICENSE file in the root of the source 6b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * tree. An additional intellectual property rights grant can be found 7b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * in the file PATENTS. All contributing project authors may 8b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * be found in the AUTHORS file in the root of the source tree. 9b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org */ 10b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 11b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* 12b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * BwEstimator.c 13b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * 14b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * This file contains the code for the Bandwidth Estimator designed 15b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * for iSAC. 16b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * 17b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org */ 18b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 19b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org#include "bandwidth_estimator.h" 20b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org#include "settings.h" 21b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org#include "isac.h" 22b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 23b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org#include <math.h> 24b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 25b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* array of quantization levels for bottle neck info; Matlab code: */ 26b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* sprintf('%4.1ff, ', logspace(log10(5000), log10(40000), 12)) */ 27b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgstatic const float kQRateTableWb[12] = 28b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 29b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 10000.0f, 11115.3f, 12355.1f, 13733.1f, 15264.8f, 16967.3f, 30b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 18859.8f, 20963.3f, 23301.4f, 25900.3f, 28789.0f, 32000.0f}; 31b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 32b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 33b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgstatic const float kQRateTableSwb[24] = 34b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 35b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 10000.0f, 11115.3f, 12355.1f, 13733.1f, 15264.8f, 16967.3f, 36b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 18859.8f, 20963.3f, 23153.1f, 25342.9f, 27532.7f, 29722.5f, 37b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 31912.3f, 34102.1f, 36291.9f, 38481.7f, 40671.4f, 42861.2f, 38b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 45051.0f, 47240.8f, 49430.6f, 51620.4f, 53810.2f, 56000.0f, 39b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org}; 40b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 41b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 42b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 43b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 44fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.orgint32_t WebRtcIsac_InitBandwidthEstimator( 45b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org BwEstimatorstr* bwest_str, 46b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org enum IsacSamplingRate encoderSampRate, 47b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org enum IsacSamplingRate decoderSampRate) 48b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 49b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org switch(encoderSampRate) 50b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 51b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org case kIsacWideband: 52b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 53b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->send_bw_avg = INIT_BN_EST_WB; 54b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org break; 55b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 56b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org case kIsacSuperWideband: 57b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 58b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->send_bw_avg = INIT_BN_EST_SWB; 59b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org break; 60b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 61b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 62b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 63b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org switch(decoderSampRate) 64b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 65b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org case kIsacWideband: 66b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 67b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_frame_length = INIT_FRAME_LEN_WB; 68b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_inv = 1.0f / 69b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (INIT_BN_EST_WB + INIT_HDR_RATE_WB); 70fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org bwest_str->rec_bw = (int32_t)INIT_BN_EST_WB; 71b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_avg_Q = INIT_BN_EST_WB; 72b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_avg = INIT_BN_EST_WB + INIT_HDR_RATE_WB; 73b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate = INIT_HDR_RATE_WB; 74b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org break; 75b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 76b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org case kIsacSuperWideband: 77b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 78b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_frame_length = INIT_FRAME_LEN_SWB; 79b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_inv = 1.0f / 80b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (INIT_BN_EST_SWB + INIT_HDR_RATE_SWB); 81fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org bwest_str->rec_bw = (int32_t)INIT_BN_EST_SWB; 82b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_avg_Q = INIT_BN_EST_SWB; 83b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_avg = INIT_BN_EST_SWB + INIT_HDR_RATE_SWB; 84b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate = INIT_HDR_RATE_SWB; 85b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org break; 86b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 87b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 88b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 89b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_rec_rtp_number = 0; 90b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_rec_arr_ts = 0; 91b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_rec_send_ts = 0; 92b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_rec_rtp_rate = 1.0f; 93b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_update_ts = 0; 94b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_reduction_ts = 0; 95b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->count_tot_updates_rec = -9; 96b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_jitter = 10.0f; 97b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_jitter_short_term = 0.0f; 98b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_jitter_short_term_abs = 5.0f; 99b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_max_delay = 10.0f; 100b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_max_delay_avg_Q = 10.0f; 101b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->num_pkts_rec = 0; 102b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 103b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->send_max_delay_avg = 10.0f; 104b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 105b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->hsn_detect_rec = 0; 106b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 107b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->num_consec_rec_pkts_over_30k = 0; 108b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 109b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->hsn_detect_snd = 0; 110b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 111b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->num_consec_snt_pkts_over_30k = 0; 112b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 113b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->in_wait_period = 0; 114b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 115b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->change_to_WB = 0; 116b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 117b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->numConsecLatePkts = 0; 118b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->consecLatency = 0; 119b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->inWaitLatePkts = 0; 120b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->senderTimestamp = 0; 121b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->receiverTimestamp = 0; 122b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return 0; 123b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 124b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 125b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* This function updates both bottle neck rates */ 126b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* Parameters: */ 127b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* rtp_number - value from RTP packet, from NetEq */ 128b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* frame length - length of signal frame in ms, from iSAC decoder */ 129b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* send_ts - value in RTP header giving send time in samples */ 130b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* arr_ts - value given by timeGetTime() time of arrival in samples of packet from NetEq */ 131b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* pksize - size of packet in bytes, from NetEq */ 132b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* Index - integer (range 0...23) indicating bottle neck & jitter as estimated by other side */ 133b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* returns 0 if everything went fine, -1 otherwise */ 134fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.orgint16_t WebRtcIsac_UpdateBandwidthEstimator( 135b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org BwEstimatorstr *bwest_str, 136fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org const uint16_t rtp_number, 137fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org const int32_t frame_length, 138fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org const uint32_t send_ts, 139fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org const uint32_t arr_ts, 140fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org const int32_t pksize 141fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org /*, const uint16_t Index*/) 142b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 143b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float weight = 0.0f; 144b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float curr_bw_inv = 0.0f; 145b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float rec_rtp_rate; 146b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float t_diff_proj; 147b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float arr_ts_diff; 148b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float send_ts_diff; 149b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float arr_time_noise; 150b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float arr_time_noise_abs; 151b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 152b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float delay_correction_factor = 1; 153b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float late_diff = 0.0f; 154b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org int immediate_set = 0; 155b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org int num_pkts_expected; 156b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 157b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 158b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // We have to adjust the header-rate if the first packet has a 159b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // frame-size different than the initialized value. 160b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if ( frame_length != bwest_str->prev_frame_length ) 161b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 162b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate = (float)HEADER_SIZE * 8.0f * 163b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 1000.0f / (float)frame_length; /* bits/s */ 164b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 165b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 166b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* UPDATE ESTIMATES ON THIS SIDE */ 167b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* compute far-side transmission rate */ 168b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org rec_rtp_rate = ((float)pksize * 8.0f * 1000.0f / (float)frame_length) + 169b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate; 170b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // rec_rtp_rate packet bits/s + header bits/s 171b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 172b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* check for timer wrap-around */ 173b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (arr_ts < bwest_str->prev_rec_arr_ts) 174b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 175b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_rec_arr_ts = arr_ts; 176b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_update_ts = arr_ts; 177b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_reduction_ts = arr_ts + 3*FS; 178b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->num_pkts_rec = 0; 179b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 180b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* store frame length */ 181b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_frame_length = frame_length; 182b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 183b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* store far-side transmission rate */ 184b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_rec_rtp_rate = rec_rtp_rate; 185b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 186b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* store far-side RTP time stamp */ 187b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_rec_rtp_number = rtp_number; 188b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 189b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return 0; 190b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 191b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 192b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->num_pkts_rec++; 193b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 194b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* check that it's not one of the first 9 packets */ 195b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if ( bwest_str->count_tot_updates_rec > 0 ) 196b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 197b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(bwest_str->in_wait_period > 0 ) 198b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 199b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->in_wait_period--; 200b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 201b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 202b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->inWaitLatePkts -= ((bwest_str->inWaitLatePkts > 0)? 1:0); 203b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org send_ts_diff = (float)(send_ts - bwest_str->prev_rec_send_ts); 204b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 205b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (send_ts_diff <= (16 * frame_length)*2) 206b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org //doesn't allow for a dropped packet, not sure necessary to be 207b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // that strict -DH 208b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 209b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* if not been updated for a long time, reduce the BN estimate */ 210fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org if((uint32_t)(arr_ts - bwest_str->last_update_ts) * 211b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 1000.0f / FS > 3000) 212b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 213b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org //how many frames should have been received since the last 214b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // update if too many have been dropped or there have been 215b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // big delays won't allow this reduction may no longer need 216b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // the send_ts_diff here 217b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org num_pkts_expected = (int)(((float)(arr_ts - 218b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_update_ts) * 1000.0f /(float) FS) / 219b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (float)frame_length); 220b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 221b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(((float)bwest_str->num_pkts_rec/(float)num_pkts_expected) > 222b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 0.9) 223b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 224b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float inv_bitrate = (float) pow( 0.99995, 225fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org (double)((uint32_t)(arr_ts - 226b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_reduction_ts)*1000.0f/FS) ); 227b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 228b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if ( inv_bitrate ) 229b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 230b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_inv /= inv_bitrate; 231b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 232b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org //precautionary, likely never necessary 233b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bwest_str->hsn_detect_snd && 234b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->hsn_detect_rec) 235b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 236b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bwest_str->rec_bw_inv > 0.000066f) 237b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 238b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_inv = 0.000066f; 239b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 240b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 241b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 242b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 243b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 244b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_inv = 1.0f / 245b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (INIT_BN_EST_WB + INIT_HDR_RATE_WB); 246b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 247b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* reset time-since-update counter */ 248b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_reduction_ts = arr_ts; 249b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 250b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 251b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org //reset here? 252b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 253b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_reduction_ts = arr_ts + 3*FS; 254b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_update_ts = arr_ts; 255b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->num_pkts_rec = 0; 256b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 257b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 258b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 259b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 260b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 261b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_reduction_ts = arr_ts + 3*FS; 262b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_update_ts = arr_ts; 263b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->num_pkts_rec = 0; 264b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 265b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 266b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 267b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* temporarily speed up adaptation if frame length has changed */ 268b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if ( frame_length != bwest_str->prev_frame_length ) 269b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 270b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->count_tot_updates_rec = 10; 271b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate = (float)HEADER_SIZE * 8.0f * 272b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 1000.0f / (float)frame_length; /* bits/s */ 273b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 274b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_inv = 1.0f /((float)bwest_str->rec_bw + 275b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate); 276b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 277b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 278b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org //////////////////////// 279b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org arr_ts_diff = (float)(arr_ts - bwest_str->prev_rec_arr_ts); 280b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 281b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (send_ts_diff > 0 ) 282b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 283b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org late_diff = arr_ts_diff - send_ts_diff; 284b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 285b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 286b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 287b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org late_diff = arr_ts_diff - (float)(16 * frame_length); 288b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 289b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 290b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if((late_diff > 0) && !bwest_str->inWaitLatePkts) 291b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 292b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->numConsecLatePkts++; 293b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->consecLatency += late_diff; 294b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 295b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 296b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 297b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->numConsecLatePkts = 0; 298b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->consecLatency = 0; 299b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 300b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(bwest_str->numConsecLatePkts > 50) 301b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 302b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float latencyMs = bwest_str->consecLatency/(FS/1000); 303b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float averageLatencyMs = latencyMs / bwest_str->numConsecLatePkts; 304b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org delay_correction_factor = frame_length / (frame_length + averageLatencyMs); 305b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org immediate_set = 1; 306fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org bwest_str->inWaitLatePkts = (int16_t)((bwest_str->consecLatency/(FS/1000)) / 30);// + 150; 307b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->start_wait_period = arr_ts; 308b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 309b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /////////////////////////////////////////////// 310b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 311b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 312b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 313b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* update only if previous packet was not lost */ 314b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if ( rtp_number == bwest_str->prev_rec_rtp_number + 1 ) 315b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 316b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 317b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 318b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (!(bwest_str->hsn_detect_snd && bwest_str->hsn_detect_rec)) 319b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 320b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if ((arr_ts_diff > (float)(16 * frame_length))) 321b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 322b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org //1/2 second 323b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if ((late_diff > 8000.0f) && !bwest_str->in_wait_period) 324b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 325b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org delay_correction_factor = 0.7f; 326b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->in_wait_period = 55; 327b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->start_wait_period = arr_ts; 328b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org immediate_set = 1; 329b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 330b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org //320 ms 331b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else if (late_diff > 5120.0f && !bwest_str->in_wait_period) 332b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 333b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org delay_correction_factor = 0.8f; 334b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org immediate_set = 1; 335b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->in_wait_period = 44; 336b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->start_wait_period = arr_ts; 337b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 338b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 339b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 340b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 341b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 342b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if ((bwest_str->prev_rec_rtp_rate > bwest_str->rec_bw_avg) && 343b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (rec_rtp_rate > bwest_str->rec_bw_avg) && 344b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org !bwest_str->in_wait_period) 345b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 346b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* test if still in initiation period and increment counter */ 347b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bwest_str->count_tot_updates_rec++ > 99) 348b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 349b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* constant weight after initiation part */ 350b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org weight = 0.01f; 351b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 352b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 353b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 354b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* weight decreases with number of updates */ 355b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org weight = 1.0f / (float) bwest_str->count_tot_updates_rec; 356b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 357b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* Bottle Neck Estimation */ 358b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 359b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* limit outliers */ 360b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* if more than 25 ms too much */ 361b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (arr_ts_diff > frame_length * FS/1000 + 400.0f) 362b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 363b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // in samples, why 25ms?? 364b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org arr_ts_diff = frame_length * FS/1000 + 400.0f; 365b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 366b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(arr_ts_diff < (frame_length * FS/1000) - 160.0f) 367b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 368b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* don't allow it to be less than frame rate - 10 ms */ 369b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org arr_ts_diff = (float)frame_length * FS/1000 - 160.0f; 370b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 371b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 372b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* compute inverse receiving rate for last packet */ 373b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org curr_bw_inv = arr_ts_diff / ((float)(pksize + HEADER_SIZE) * 374b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 8.0f * FS); // (180+35)*8*16000 = 27.5 Mbit.... 375b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 376b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 377b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(curr_bw_inv < 378b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (1.0f / (MAX_ISAC_BW + bwest_str->rec_header_rate))) 379b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 380b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // don't allow inv rate to be larger than MAX 381b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org curr_bw_inv = (1.0f / 382b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (MAX_ISAC_BW + bwest_str->rec_header_rate)); 383b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 384b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 385b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* update bottle neck rate estimate */ 386b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_inv = weight * curr_bw_inv + 387b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (1.0f - weight) * bwest_str->rec_bw_inv; 388b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 389b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* reset time-since-update counter */ 390b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_update_ts = arr_ts; 391b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_reduction_ts = arr_ts + 3 * FS; 392b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->num_pkts_rec = 0; 393b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 394b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* Jitter Estimation */ 395b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* projected difference between arrival times */ 396b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org t_diff_proj = ((float)(pksize + HEADER_SIZE) * 8.0f * 397b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 1000.0f) / bwest_str->rec_bw_avg; 398b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 399b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 400b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // difference between projected and actual 401b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // arrival time differences 402b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org arr_time_noise = (float)(arr_ts_diff*1000.0f/FS) - 403b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org t_diff_proj; 404b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org arr_time_noise_abs = (float) fabs( arr_time_noise ); 405b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 406b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* long term averaged absolute jitter */ 407b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_jitter = weight * arr_time_noise_abs + 408b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (1.0f - weight) * bwest_str->rec_jitter; 409b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bwest_str->rec_jitter > 10.0f) 410b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 411b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_jitter = 10.0f; 412b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 413b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* short term averaged absolute jitter */ 414b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_jitter_short_term_abs = 0.05f * 415b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org arr_time_noise_abs + 0.95f * 416b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_jitter_short_term_abs; 417b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 418b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* short term averaged jitter */ 419b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_jitter_short_term = 0.05f * arr_time_noise + 420b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 0.95f * bwest_str->rec_jitter_short_term; 421b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 422b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 423b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 424b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 425b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 426b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // reset time-since-update counter when 427b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // receiving the first 9 packets 428b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_update_ts = arr_ts; 429b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->last_reduction_ts = arr_ts + 3*FS; 430b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->num_pkts_rec = 0; 431b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 432b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->count_tot_updates_rec++; 433b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 434b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 435b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* limit minimum bottle neck rate */ 436b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bwest_str->rec_bw_inv > 1.0f / ((float)MIN_ISAC_BW + 437b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate)) 438b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 439b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_inv = 1.0f / ((float)MIN_ISAC_BW + 440b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate); 441b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 442b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 443b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // limit maximum bitrate 444b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bwest_str->rec_bw_inv < 1.0f / ((float)MAX_ISAC_BW + 445b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate)) 446b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 447b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_inv = 1.0f / ((float)MAX_ISAC_BW + 448b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate); 449b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 450b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 451b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* store frame length */ 452b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_frame_length = frame_length; 453b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 454b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* store far-side transmission rate */ 455b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_rec_rtp_rate = rec_rtp_rate; 456b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 457b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* store far-side RTP time stamp */ 458b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_rec_rtp_number = rtp_number; 459b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 460b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // Replace bwest_str->rec_max_delay by the new 461b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // value (atomic operation) 462b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_max_delay = 3.0f * bwest_str->rec_jitter; 463b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 464b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* store send and arrival time stamp */ 465b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_rec_arr_ts = arr_ts ; 466b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->prev_rec_send_ts = send_ts; 467b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 468b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* Replace bwest_str->rec_bw by the new value (atomic operation) */ 469fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org bwest_str->rec_bw = (int32_t)(1.0f / bwest_str->rec_bw_inv - 470b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate); 471b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 472b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (immediate_set) 473b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 474fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org bwest_str->rec_bw = (int32_t) (delay_correction_factor * 475b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (float) bwest_str->rec_bw); 476b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 477fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org if (bwest_str->rec_bw < (int32_t) MIN_ISAC_BW) 478b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 479fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org bwest_str->rec_bw = (int32_t) MIN_ISAC_BW; 480b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 481b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 482b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_avg = bwest_str->rec_bw + 483b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate; 484b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 485b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_avg_Q = (float) bwest_str->rec_bw; 486b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 487b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_jitter_short_term = 0.0f; 488b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 489b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_inv = 1.0f / (bwest_str->rec_bw + 490b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_header_rate); 491b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 492b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->count_tot_updates_rec = 1; 493b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 494b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org immediate_set = 0; 495b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->consecLatency = 0; 496b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->numConsecLatePkts = 0; 497b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 498b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 499b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return 0; 500b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 501b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 502b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 503b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* This function updates the send bottle neck rate */ 504b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* Index - integer (range 0...23) indicating bottle neck & jitter as estimated by other side */ 505b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* returns 0 if everything went fine, -1 otherwise */ 506fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.orgint16_t WebRtcIsac_UpdateUplinkBwImpl( 507b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org BwEstimatorstr* bwest_str, 508fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int16_t index, 509b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org enum IsacSamplingRate encoderSamplingFreq) 510b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 511b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if((index < 0) || (index > 23)) 512b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 513b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return -ISAC_RANGE_ERROR_BW_ESTIMATOR; 514b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 515b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 516b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* UPDATE ESTIMATES FROM OTHER SIDE */ 517b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(encoderSamplingFreq == kIsacWideband) 518b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 519b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(index > 11) 520b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 521b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org index -= 12; 522b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* compute the jitter estimate as decoded on the other side */ 523b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->send_max_delay_avg = 0.9f * bwest_str->send_max_delay_avg + 524b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 0.1f * (float)MAX_ISAC_MD; 525b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 526b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 527b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 528b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* compute the jitter estimate as decoded on the other side */ 529b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->send_max_delay_avg = 0.9f * bwest_str->send_max_delay_avg + 530b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 0.1f * (float)MIN_ISAC_MD; 531b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 532b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 533b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* compute the BN estimate as decoded on the other side */ 534b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->send_bw_avg = 0.9f * bwest_str->send_bw_avg + 535b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 0.1f * kQRateTableWb[index]; 536b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 537b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 538b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 539b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* compute the BN estimate as decoded on the other side */ 540b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->send_bw_avg = 0.9f * bwest_str->send_bw_avg + 541b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 0.1f * kQRateTableSwb[index]; 542b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 543b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 544b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bwest_str->send_bw_avg > (float) 28000 && !bwest_str->hsn_detect_snd) 545b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 546b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->num_consec_snt_pkts_over_30k++; 547b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 548b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bwest_str->num_consec_snt_pkts_over_30k >= 66) 549b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 550b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org //approx 2 seconds with 30ms frames 551b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->hsn_detect_snd = 1; 552b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 553b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 554b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else if (!bwest_str->hsn_detect_snd) 555b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 556b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->num_consec_snt_pkts_over_30k = 0; 557b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 558b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return 0; 559b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 560b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 561b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org// called when there is upper-band bit-stream to update jitter 562b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org// statistics. 563fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.orgint16_t WebRtcIsac_UpdateUplinkJitter( 564b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org BwEstimatorstr* bwest_str, 565fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int32_t index) 566b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 567b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if((index < 0) || (index > 23)) 568b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 569b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return -ISAC_RANGE_ERROR_BW_ESTIMATOR; 570b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 571b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 572b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(index > 0) 573b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 574b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* compute the jitter estimate as decoded on the other side */ 575b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->send_max_delay_avg = 0.9f * bwest_str->send_max_delay_avg + 576b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 0.1f * (float)MAX_ISAC_MD; 577b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 578b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 579b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 580b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* compute the jitter estimate as decoded on the other side */ 581b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->send_max_delay_avg = 0.9f * bwest_str->send_max_delay_avg + 582b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 0.1f * (float)MIN_ISAC_MD; 583b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 584b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 585b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return 0; 586b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 587b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 588b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 589b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 590b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org// Returns the bandwidth/jitter estimation code (integer 0...23) 591b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org// to put in the sending iSAC payload 592fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.orguint16_t 593b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgWebRtcIsac_GetDownlinkBwJitIndexImpl( 594b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org BwEstimatorstr* bwest_str, 595fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int16_t* bottleneckIndex, 596fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int16_t* jitterInfo, 597b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org enum IsacSamplingRate decoderSamplingFreq) 598b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 599b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float MaxDelay; 600fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org //uint16_t MaxDelayBit; 601b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 602b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float rate; 603b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float r; 604b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float e1, e2; 605b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const float weight = 0.1f; 606b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const float* ptrQuantizationTable; 607fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int16_t addJitterInfo; 608fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int16_t minInd; 609fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int16_t maxInd; 610fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int16_t midInd; 611b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 612b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* Get Max Delay Bit */ 613b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* get unquantized max delay */ 614b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org MaxDelay = (float)WebRtcIsac_GetDownlinkMaxDelay(bwest_str); 615b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 616b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if ( ((1.f - weight) * bwest_str->rec_max_delay_avg_Q + weight * 617b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org MAX_ISAC_MD - MaxDelay) > (MaxDelay - (1.f-weight) * 618b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_max_delay_avg_Q - weight * MIN_ISAC_MD) ) 619b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 620b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org jitterInfo[0] = 0; 621b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* update quantized average */ 622b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_max_delay_avg_Q = 623b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (1.f - weight) * bwest_str->rec_max_delay_avg_Q + weight * 624b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (float)MIN_ISAC_MD; 625b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 626b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 627b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 628b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org jitterInfo[0] = 1; 629b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* update quantized average */ 630b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_max_delay_avg_Q = 631b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (1.f-weight) * bwest_str->rec_max_delay_avg_Q + weight * 632b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (float)MAX_ISAC_MD; 633b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 634b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 635b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // Get unquantized rate. 636b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org rate = (float)WebRtcIsac_GetDownlinkBandwidth(bwest_str); 637b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 638b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* Get Rate Index */ 639b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(decoderSamplingFreq == kIsacWideband) 640b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 641b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org ptrQuantizationTable = kQRateTableWb; 642b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org addJitterInfo = 1; 643b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org maxInd = 11; 644b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 645b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 646b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 647b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org ptrQuantizationTable = kQRateTableSwb; 648b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org addJitterInfo = 0; 649b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org maxInd = 23; 650b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 651b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 652b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org minInd = 0; 653b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org while(maxInd > minInd + 1) 654b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 655b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org midInd = (maxInd + minInd) >> 1; 656b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(rate > ptrQuantizationTable[midInd]) 657b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 658b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org minInd = midInd; 659b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 660b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 661b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 662b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org maxInd = midInd; 663b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 664b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 665b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // Chose the index which gives results an average which is closest 666b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // to rate 667b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org r = (1 - weight) * bwest_str->rec_bw_avg_Q - rate; 668b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org e1 = weight * ptrQuantizationTable[minInd] + r; 669b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org e2 = weight * ptrQuantizationTable[maxInd] + r; 670b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org e1 = (e1 > 0)? e1:-e1; 671b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org e2 = (e2 > 0)? e2:-e2; 672b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(e1 < e2) 673b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 674b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bottleneckIndex[0] = minInd; 675b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 676b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 677b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 678b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bottleneckIndex[0] = maxInd; 679b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 680b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 681b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_avg_Q = (1 - weight) * bwest_str->rec_bw_avg_Q + 682b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org weight * ptrQuantizationTable[bottleneckIndex[0]]; 683b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bottleneckIndex[0] += jitterInfo[0] * 12 * addJitterInfo; 684b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 685b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_bw_avg = (1 - weight) * bwest_str->rec_bw_avg + weight * 686b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (rate + bwest_str->rec_header_rate); 687b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 688b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return 0; 689b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 690b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 691b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 692b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 693b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* get the bottle neck rate from far side to here, as estimated on this side */ 694fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.orgint32_t WebRtcIsac_GetDownlinkBandwidth( const BwEstimatorstr *bwest_str) 695b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 696fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int32_t rec_bw; 697b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float jitter_sign; 698b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org float bw_adjust; 699b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 700b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* create a value between -1.0 and 1.0 indicating "average sign" of jitter */ 701b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org jitter_sign = bwest_str->rec_jitter_short_term / 702b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bwest_str->rec_jitter_short_term_abs; 703b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 704b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* adjust bw proportionally to negative average jitter sign */ 705b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bw_adjust = 1.0f - jitter_sign * (0.15f + 0.15f * jitter_sign * jitter_sign); 706b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 707b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* adjust Rate if jitter sign is mostly constant */ 708fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org rec_bw = (int32_t)(bwest_str->rec_bw * bw_adjust); 709b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 710b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* limit range of bottle neck rate */ 711b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (rec_bw < MIN_ISAC_BW) 712b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 713b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org rec_bw = MIN_ISAC_BW; 714b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 715b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else if (rec_bw > MAX_ISAC_BW) 716b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 717b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org rec_bw = MAX_ISAC_BW; 718b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 719b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return rec_bw; 720b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 721b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 722b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* Returns the max delay (in ms) */ 723fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.orgint32_t 724b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgWebRtcIsac_GetDownlinkMaxDelay(const BwEstimatorstr *bwest_str) 725b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 726fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int32_t rec_max_delay; 727b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 728fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org rec_max_delay = (int32_t)(bwest_str->rec_max_delay); 729b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 730b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* limit range of jitter estimate */ 731b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (rec_max_delay < MIN_ISAC_MD) 732b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 733b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org rec_max_delay = MIN_ISAC_MD; 734b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 735b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else if (rec_max_delay > MAX_ISAC_MD) 736b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 737b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org rec_max_delay = MAX_ISAC_MD; 738b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 739b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return rec_max_delay; 740b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 741b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 742b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* get the bottle neck rate from here to far side, as estimated by far side */ 743b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgvoid 744b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgWebRtcIsac_GetUplinkBandwidth( 745b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const BwEstimatorstr* bwest_str, 746fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int32_t* bitRate) 747b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 748b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* limit range of bottle neck rate */ 749b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bwest_str->send_bw_avg < MIN_ISAC_BW) 750b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 751b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org *bitRate = MIN_ISAC_BW; 752b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 753b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else if (bwest_str->send_bw_avg > MAX_ISAC_BW) 754b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 755b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org *bitRate = MAX_ISAC_BW; 756b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 757b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 758b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 759fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org *bitRate = (int32_t)(bwest_str->send_bw_avg); 760b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 761b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return; 762b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 763b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 764b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* Returns the max delay value from the other side in ms */ 765fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.orgint32_t 766b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgWebRtcIsac_GetUplinkMaxDelay(const BwEstimatorstr *bwest_str) 767b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 768fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org int32_t send_max_delay; 769b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 770fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org send_max_delay = (int32_t)(bwest_str->send_max_delay_avg); 771b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 772b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* limit range of jitter estimate */ 773b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (send_max_delay < MIN_ISAC_MD) 774b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 775b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org send_max_delay = MIN_ISAC_MD; 776b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 777b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else if (send_max_delay > MAX_ISAC_MD) 778b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 779b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org send_max_delay = MAX_ISAC_MD; 780b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 781b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return send_max_delay; 782b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 783b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 784b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 785b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* 786b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * update long-term average bitrate and amount of data in buffer 787b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * returns minimum payload size (bytes) 788b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org */ 789b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgint WebRtcIsac_GetMinBytes( 790b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org RateModel* State, 791b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org int StreamSize, /* bytes in bitstream */ 792b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const int FrameSamples, /* samples per frame */ 793b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double BottleNeck, /* bottle neck rate; excl headers (bps) */ 794b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double DelayBuildUp, /* max delay from bottleneck buffering (ms) */ 795b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org enum ISACBandwidth bandwidth 796fbda0fcf2f9e82c82bcaac138f44d4e5144f6e0dpbos@webrtc.org /*,int16_t frequentLargePackets*/) 797b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 798b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org double MinRate = 0.0; 799b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org int MinBytes; 800b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org double TransmissionTime; 801b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org int burstInterval = BURST_INTERVAL; 802b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 803b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // first 10 packets @ low rate, then INIT_BURST_LEN packets @ 804b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // fixed rate of INIT_RATE bps 805b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (State->InitCounter > 0) 806b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 807b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (State->InitCounter-- <= INIT_BURST_LEN) 808b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 809b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if(bandwidth == isac8kHz) 810b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 811b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org MinRate = INIT_RATE_WB; 812b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 813b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 814b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 815b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org MinRate = INIT_RATE_SWB; 816b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 817b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 818b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 819b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 820b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org MinRate = 0; 821b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 822b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 823b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 824b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 825b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* handle burst */ 826b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (State->BurstCounter) 827b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 828b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (State->StillBuffered < (1.0 - 1.0/BURST_LEN) * DelayBuildUp) 829b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 830b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* max bps derived from BottleNeck and DelayBuildUp values */ 831b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org MinRate = (1.0 + (FS/1000) * DelayBuildUp / 832b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (double)(BURST_LEN * FrameSamples)) * BottleNeck; 833b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 834b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 835b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 836b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // max bps derived from StillBuffered and DelayBuildUp 837b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org // values 838b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org MinRate = (1.0 + (FS/1000) * (DelayBuildUp - 839b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->StillBuffered) / (double)FrameSamples) * BottleNeck; 840b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (MinRate < 1.04 * BottleNeck) 841b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 842b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org MinRate = 1.04 * BottleNeck; 843b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 844b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 845b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->BurstCounter--; 846b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 847b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 848b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 849b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 850b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* convert rate from bits/second to bytes/packet */ 851b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org MinBytes = (int) (MinRate * FrameSamples / (8.0 * FS)); 852b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 853b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* StreamSize will be adjusted if less than MinBytes */ 854b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (StreamSize < MinBytes) 855b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 856b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org StreamSize = MinBytes; 857b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 858b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 859b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* keep track of when bottle neck was last exceeded by at least 1% */ 860b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (StreamSize * 8.0 * FS / FrameSamples > 1.01 * BottleNeck) { 861b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (State->PrevExceed) { 862b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* bottle_neck exceded twice in a row, decrease ExceedAgo */ 863b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->ExceedAgo -= /*BURST_INTERVAL*/ burstInterval / (BURST_LEN - 1); 864b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (State->ExceedAgo < 0) 865b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->ExceedAgo = 0; 866b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 867b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 868b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 869b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->ExceedAgo += (FrameSamples * 1000) / FS; /* ms */ 870b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->PrevExceed = 1; 871b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 872b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 873b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 874b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 875b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->PrevExceed = 0; 876b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->ExceedAgo += (FrameSamples * 1000) / FS; /* ms */ 877b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 878b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 879b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* set burst flag if bottle neck not exceeded for long time */ 880b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if ((State->ExceedAgo > burstInterval) && 881b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org (State->BurstCounter == 0)) 882b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 883b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (State->PrevExceed) 884b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 885b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->BurstCounter = BURST_LEN - 1; 886b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 887b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else 888b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 889b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->BurstCounter = BURST_LEN; 890b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 891b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 892b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 893b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 894b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* Update buffer delay */ 895b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org TransmissionTime = StreamSize * 8.0 * 1000.0 / BottleNeck; /* ms */ 896b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->StillBuffered += TransmissionTime; 897b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->StillBuffered -= (FrameSamples * 1000) / FS; /* ms */ 898b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (State->StillBuffered < 0.0) 899b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org { 900b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->StillBuffered = 0.0; 901b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 902b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 903b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return MinBytes; 904b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 905b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 906b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 907b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* 908b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * update long-term average bitrate and amount of data in buffer 909b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org */ 910b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgvoid WebRtcIsac_UpdateRateModel( 911b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org RateModel *State, 912b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org int StreamSize, /* bytes in bitstream */ 913b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const int FrameSamples, /* samples per frame */ 914b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double BottleNeck) /* bottle neck rate; excl headers (bps) */ 915b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 916b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org double TransmissionTime; 917b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 918b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* avoid the initial "high-rate" burst */ 919b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->InitCounter = 0; 920b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 921b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* Update buffer delay */ 922b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org TransmissionTime = StreamSize * 8.0 * 1000.0 / BottleNeck; /* ms */ 923b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->StillBuffered += TransmissionTime; 924b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->StillBuffered -= (FrameSamples * 1000) / FS; /* ms */ 925b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (State->StillBuffered < 0.0) 926b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->StillBuffered = 0.0; 927b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 928b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 929b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 930b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 931b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgvoid WebRtcIsac_InitRateModel( 932b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org RateModel *State) 933b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 934b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->PrevExceed = 0; /* boolean */ 935b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->ExceedAgo = 0; /* ms */ 936b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->BurstCounter = 0; /* packets */ 937b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->InitCounter = INIT_BURST_LEN + 10; /* packets */ 938b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org State->StillBuffered = 1.0; /* ms */ 939b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 940b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 941b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgint WebRtcIsac_GetNewFrameLength( 942b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org double bottle_neck, 943b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org int current_framesamples) 944b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 945b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org int new_framesamples; 946b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 947b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const int Thld_20_30 = 20000; 948b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 949b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org //const int Thld_30_20 = 30000; 950b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const int Thld_30_20 = 1000000; // disable 20 ms frames 951b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 952b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const int Thld_30_60 = 18000; 953b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org //const int Thld_30_60 = 0; // disable 60 ms frames 954b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 955b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const int Thld_60_30 = 27000; 956b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 957b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 958b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org new_framesamples = current_framesamples; 959b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 960b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* find new framelength */ 961b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org switch(current_framesamples) { 962b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org case 320: 963b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bottle_neck < Thld_20_30) 964b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org new_framesamples = 480; 965b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org break; 966b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org case 480: 967b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bottle_neck < Thld_30_60) 968b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org new_framesamples = 960; 969b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org else if (bottle_neck > Thld_30_20) 970b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org new_framesamples = 320; 971b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org break; 972b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org case 960: 973b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (bottle_neck >= Thld_60_30) 974b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org new_framesamples = 480; 975b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org break; 976b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 977b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 978b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return new_framesamples; 979b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 980b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 981b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgdouble WebRtcIsac_GetSnr( 982b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org double bottle_neck, 983b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org int framesamples) 984b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org{ 985b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org double s2nr; 986b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 987b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double a_20 = -30.0; 988b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double b_20 = 0.8; 989b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double c_20 = 0.0; 990b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 991b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double a_30 = -23.0; 992b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double b_30 = 0.48; 993b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double c_30 = 0.0; 994b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 995b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double a_60 = -23.0; 996b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double b_60 = 0.53; 997b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org const double c_60 = 0.0; 998b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 999b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 1000b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org /* find new SNR value */ 1001b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org switch(framesamples) { 1002b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org case 320: 1003b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org s2nr = a_20 + b_20 * bottle_neck * 0.001 + c_20 * bottle_neck * 1004b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bottle_neck * 0.000001; 1005b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org break; 1006b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org case 480: 1007b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org s2nr = a_30 + b_30 * bottle_neck * 0.001 + c_30 * bottle_neck * 1008b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bottle_neck * 0.000001; 1009b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org break; 1010b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org case 960: 1011b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org s2nr = a_60 + b_60 * bottle_neck * 0.001 + c_60 * bottle_neck * 1012b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org bottle_neck * 0.000001; 1013b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org break; 1014b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org default: 1015b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org s2nr = 0; 1016b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 1017b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 1018b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org return s2nr; 1019b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 1020b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 1021