webrtc中的带宽自适应算法

WebRTC的拥塞控制技术(Congestion Control) 算法(1)由数据的接收方实现,接收方需要记录每个数据包到达的时间和大小,并计算每个数据分组之间(inter-group)的延迟的变化,由此判断当前网络的拥塞情况,并最终输出码率估计值由RTCP feedback(TMMBR或 REMB)反馈给发送方;测量方程进一步改写为 d(i) = m(i) + v(i),其中m(i)符合均值为0的正态分布(标准正态分布),v(i)表示为网络抖动等因素带来的对数据延迟的影响。其中,当|m(i)| < del_var_th(i-1)时K(i)=K_d; 阅读详情

webrtc中的带宽自适应算法分为两种:

1, 发端带宽控制, 原理是由rtcp中的丢包统计来动态的增加或减少带宽,在减少带宽时使用TFRC算法来增加平滑度。

2, 收端带宽估算, 原理是并由收到rtp数据,估出带宽; 用卡尔曼滤波,对每一帧的发送时间和接收时间进行分析, 从而得出网络带宽利用情况,修正估出的带宽。


两种算法相辅相成, 收端将估算的带宽发送给发端, 发端结合收到的带宽以及丢包率,调整发送的带宽。


下面具体分析两种算法:




2,  接收端带宽估算算法分析

     结合文档http://tools.ietf.org/html/draft-alvestrand-rtcweb-congestion-02以及源码webrtc/modules/remote_bitrate_estimator/overuse_detector.cc进行分析

     带宽估算模型: d(i) = dL(i) / c + w(i)     d(i)两帧数据的网络传输时间差,dL(i)两帧数据的大小差, c为网络传输能力, w(i)是我们关注的重点, 它主要由三个因素决定:发送速率, 网络路由能力, 以及网络传输能力。w(i)符合高斯分布, 有如下结论:当w(i)增加是,占用过多带宽(over-using);当w(i)减少时,占用较少带宽(under-using);为0时,用到恰好的带宽。所以,只要我们能计算出w(i),即能判断目前的网络使用情况,从而增加或减少发送的速率。


     算法原理:即应用kalman-filters
     theta_hat(i) = [1/C_hat(i) m_hat(i)]^T   // i时间点的状态由C, m共同表示,theta_hat(i)即此时的估算值

     z(i) = d(i) - h_bar(i)^T * theta_hat(i-1)  //d(i)为测试值,可以很容易计算出, 后面的可以认为是d(i-1)的估算值, 因此z(i)就是d(i)的偏差,即residual

     theta_hat(i) = theta_hat(i-1) + z(i) * k_bar(i) //好了,这个就是我们要的结果,关键是k值的选取,下面两个公式即是取k值的,具体推导见后继博文。

                              E(i-1) * h_bar(i)
     k_bar(i) = --------------------------------------------
                  var_v_hat + h_bar(i)^T * E(i-1) * h_bar(i)


     E(i) = (I - K_bar(i) * h_bar(i)^T) * E(i-1) + Q(i)   // h_bar(i)由帧的数据包大小算出

     由此可见,我们只需要知道当前帧的长度,发送时间,接收时间以及前一帧的状态,就可以计算出网络使用情况。

     接下来具体看一下代码:
     

[cpp]  view plain copy
  1. void OveruseDetector::UpdateKalman(int64_t t_delta,  
  2.                                    double ts_delta,  
  3.                                    uint32_t frame_size,  
  4.                                    uint32_t prev_frame_size) {  
  5.   const double min_frame_period = UpdateMinFramePeriod(ts_delta);  
  6.   const double drift = CurrentDrift();  
  7.   // Compensate for drift  
  8.   const double t_ts_delta = t_delta - ts_delta / drift;  //即d(i)  
  9.   double fs_delta = static_cast<double>(frame_size) - prev_frame_size;   
  10.   
  11.   // Update the Kalman filter  
  12.   const double scale_factor =  min_frame_period / (1000.0 / 30.0);  
  13.   E_[0][0] += process_noise_[0] * scale_factor;  
  14.   E_[1][1] += process_noise_[1] * scale_factor;  
  15.   
  16.   if ((hypothesis_ == kBwOverusing && offset_ < prev_offset_) ||  
  17.       (hypothesis_ == kBwUnderusing && offset_ > prev_offset_)) {  
  18.     E_[1][1] += 10 * process_noise_[1] * scale_factor;  
  19.   }  
  20.   
  21.   const double h[2] = {fs_delta, 1.0}; //即h_bar  
  22.   const double Eh[2] = {E_[0][0]*h[0] + E_[0][1]*h[1],  
  23.                         E_[1][0]*h[0] + E_[1][1]*h[1]};  
  24.   
  25.   const double residual = t_ts_delta - slope_*h[0] - offset_; //即z(i), slope为1/C  
  26.   
  27.   const bool stable_state =  
  28.       (BWE_MIN(num_of_deltas_, 60) * fabsf(offset_) < threshold_);  
  29.   // We try to filter out very late frames. For instance periodic key  
  30.   // frames doesn't fit the Gaussian model well.  
  31.   if (fabsf(residual) < 3 * sqrt(var_noise_)) {  
  32.     UpdateNoiseEstimate(residual, min_frame_period, stable_state);  
  33.   } else {  
  34.     UpdateNoiseEstimate(3 * sqrt(var_noise_), min_frame_period, stable_state);  
  35.   }  
  36.   
  37.   const double denom = var_noise_ + h[0]*Eh[0] + h[1]*Eh[1];  
  38.   
  39.   const double K[2] = {Eh[0] / denom,  
  40.                        Eh[1] / denom}; //即k_bar  
  41.   
  42.   const double IKh[2][2] = {{1.0 - K[0]*h[0], -K[0]*h[1]},  
  43.                             {-K[1]*h[0], 1.0 - K[1]*h[1]}};  
  44.   const double e00 = E_[0][0];  
  45.   const double e01 = E_[0][1];  
  46.   
  47.   // Update state  
  48.   E_[0][0] = e00 * IKh[0][0] + E_[1][0] * IKh[0][1];  
  49.   E_[0][1] = e01 * IKh[0][0] + E_[1][1] * IKh[0][1];  
  50.   E_[1][0] = e00 * IKh[1][0] + E_[1][0] * IKh[1][1];  
  51.   E_[1][1] = e01 * IKh[1][0] + E_[1][1] * IKh[1][1];  
  52.   
  53.   // Covariance matrix, must be positive semi-definite  
  54.   assert(E_[0][0] + E_[1][1] >= 0 &&  
  55.          E_[0][0] * E_[1][1] - E_[0][1] * E_[1][0] >= 0 &&  
  56.          E_[0][0] >= 0);  
  57.   
  58.   
  59.   slope_ = slope_ + K[0] * residual; //1/C  
  60.   prev_offset_ = offset_;  
  61.   offset_ = offset_ + K[1] * residual; //theta_hat(i)  
  62.   
  63.   Detect(ts_delta);  
  64. }  

[cpp]  view plain copy
  1. BandwidthUsage OveruseDetector::Detect(double ts_delta) {  
  2.   if (num_of_deltas_ < 2) {  
  3.     return kBwNormal;  
  4.   }  
  5.   const double T = BWE_MIN(num_of_deltas_, 60) * offset_; //即gamma_1  
  6.   if (fabsf(T) > threshold_) {  
  7.     if (offset_ > 0) {  
  8.       if (time_over_using_ == -1) {  
  9.         // Initialize the timer. Assume that we've been  
  10.         // over-using half of the time since the previous  
  11.         // sample.  
  12.         time_over_using_ = ts_delta / 2;  
  13.       } else {  
  14.         // Increment timer  
  15.         time_over_using_ += ts_delta;  
  16.       }  
  17.       over_use_counter_++;  
  18.       if (time_over_using_ > kOverUsingTimeThreshold  //kOverUsingTimeThreshold是gamma_2, gamama_3=1  
  19.           && over_use_counter_ > 1) {  
  20.         if (offset_ >= prev_offset_) {  
  21.           time_over_using_ = 0;  
  22.           over_use_counter_ = 0;  
  23.           hypothesis_ = kBwOverusing;  
  24.         }  
  25.       }  
  26.     } else {  
  27.       time_over_using_ = -1;  
  28.       over_use_counter_ = 0;  
  29.  hypothesis_ = kBwUnderusing;  
  30.     }  
  31.   } else {  
  32.     time_over_using_ = -1;  
  33.     over_use_counter_ = 0;  
  34.     hypothesis_ = kBwNormal;  
  35.   }  
  36.   return hypothesis_;  
  37. }  


参考文档:

  1. http://www.swarthmore.edu/NatSci/echeeve1/Ref/Kalman/ScalarKalman.html
  2. http://tools.ietf.org/html/draft-alvestrand-rtcweb-congestion-02
WEBRTC实时音视频输算法 VP8/VP9 编码H.264 编码带宽自适应算法丢包恢复算法拥塞控制算法总之,WebRTC 实时音视频传输算法通过音频编码、视频编码、网络适应性和抗抖动等多种算法的协同作用,实现了高质量、低延迟的实时音视频通信。这些算法不断优化和改进,以适应不断变化的网络环境和用户需求。 阅读详情

相关推荐

WebRTC GCC算法实战:从卡曼滤波到带宽动态调整

本文深入解析了WebRTC中GCC(谷歌拥塞控制)算法的核心原理与实战应用。通过将卡曼滤波(Kalman Filter)技术应用于网络延迟梯度的动态分析,GCC算法能够精准预测并动态调整带宽,有效缓解视频通话中的卡顿问题。文章以通俗易懂的方式拆解了算法公式,并提供了代码层面的实现思路与工程优化指南,帮助开发者深入理解并应用这一关键的实时通信网络优化技术。

weixin_29070721的博客 340

WebRTC自适应网络带宽的记录和思考

       这篇文章的主要目的是记录一下搜索到的有关”WebRTC自适应网络带宽“的文章。链接稍后列出。在此之前, 先思考一个问题: 该设计一个怎样的方案,来应对不同带宽环境下的音视频流实时传输?      这个问题可以展开为2个:      (1) 非实时传输,如 点播。 如果服务器比较强大(如国内比较大的视频网站优酷,腾讯等),支持负载均衡,                高并发,只...

happy08god的专栏 3421

WebRTC中的动态带宽调整算法

在WebRTC中,带宽自适应是一项关键技术,它能够根据网络条件动态调整传输的带宽,以确保良好的通信质量。带宽自适应算法的核心思想是根据网络情况动态调整传输参数,以提供最佳的通信质量。通过实时监测网络状态,并基于网络指标进行带宽评估和参数调整,WebRTC应用可以在不同网络环境下实现稳定可靠的通信。请注意,以上代码仅为示例,实际应用中可能需要更复杂的逻辑和算法来实现更准确的带宽自适应功能。它通过测量网络延迟、丢包率和带宽容量等指标,实时评估网络质量,并根据评估结果调整传输的带宽和质量参数。

FdviAutoit的博客 312

WebRTC 带宽自适应:Congestion Control 算法调优与弱网场景适配

拥塞控制算法调优和弱网适配是WebRTC性能优化的关键。

qrewxqdw的博客 870

示波器学习(一):示波器的作用、类型和基本结构

示波器的作用、使用场景;示波器的类型和基本结构介绍

qq_41300605的博客 9140

Intel AX系列网卡5G热点开启失败?Linux下3种修复方案实测(含Ubuntu/OpenWRT)

本文针对Intel AX系列网卡在Linux系统下无法开启5G热点的常见问题,深入剖析了其根源在于内核LAR机制与驱动的兼容性。文章提供了三种实测有效的修复方案:针对内核低于5.5的模块参数法、适用于高内核版本的hostapd补丁编译法以及高阶的驱动修改法,帮助用户在Ubuntu、OpenWRT等环境中成功启用5G热点功能。

weixin_29291863的博客 733

WebRTC自适应控制算法

该文章系总结性文章,主要参考一下文章: 1、webrtc视频jitterbuffer原理机制(描述版) - 简书 http://www.jianshu.com/p/bd10d60cebcd 2、WebRTC视频接收缓冲区基于KalmanFilter的延迟模型 - 简书 http://www.jianshu.com/p/bb34995c549a 3、WebRTC基于GCC的拥塞控制(上) ...

站在人文与技术的交汇点 2331

别再手动测接口了!用Pytest+Requests+Allure搭建你的第一个自动化框架(附完整源码)

本文详细介绍了如何使用Pytest+Requests+Allure搭建Python接口自动化测试框架,涵盖环境准备、核心组件封装、测试用例设计、报告生成及CI/CD集成等关键步骤。通过实战案例和完整源码,帮助开发者快速构建高效的接口自动化测试解决方案,提升测试效率和质量。

weixin_42546508的博客 320

网络带宽_WebRTC 拥塞控制 | 网络带宽过载检测

本文是 WebRTC 拥塞控制 第 3 篇导读网络带宽使用状态自适应阈值的设计为什么要动态自适应?阈值自适应算法源码分析Detect 函数UpdateThreshold 函数测试用例导读 上一篇介绍了 Trendline 滤波器计算延迟梯度趋势的过程,求得了最终值 trendline_slope。接下来,就要用这个斜率值与阈值进行比较,从而检测网络带宽的使用状态,比如是否过载。实际的带宽...

weixin_34479122的博客 961

从CD4051到现代模拟开关:40年芯片演进史与选型避坑指南

本文回顾了从CD4051到现代模拟开关的40年技术演进,详细对比了导通电阻、带宽等关键参数的显著提升。通过实际案例和选型矩阵,揭示现代模拟开关在精度、功耗和集成度方面的优势,并提供高精度测量、电池供电等场景的选型策略与避坑指南,帮助工程师优化设计。

weixin_42543046的博客 153

《软件工程——实践者的研究方法》重难点复习笔记(第八章——理解需求)

8项需求工程任务 inception 开始 8.1.1 identify stakeholders 定义:从软件开发中收益 例如:市场人员、销售经理、顾客、顾问、维护团队等(P139) 8.1.2 这个阶段的问题是context-free的。有三套(P140) 8.1.3 提到NFR(nonfunctional requirement)和QFD(quality

whooiif的博客 1814

音视频传输-带宽评估

音视频传输 - 带宽评估 网络拥塞是基于IP协议的数据宝交换网络中常见的一种网络传输问题。网络拥塞是导致网络吞吐降低,网络丢包等的主要原因之一。 WebRTC中传输的采用的是UDP协议,WebRTC的传输层采用的拥塞算法是GCC算法。 Google congestion control 1. 基于丢包的拥塞机制 基于丢包的拥塞控制比较简单。其基本思想是根据丢包的多少来判断网络的拥塞程度,丢包越多则...

loycine的博客 2887

1976国际标准大气_Matlab

输入高度,计算空气密度、气压、温度、声速 function [airDens,airPress,temp,soundSpeed]=Atmos(geomAlt) %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % 1976 U.S Standard Atmosphere Interpolation % % Note: Function does not extr.

JISANSAN的博客 1万+

webrtc弱网-TrendlineEstimator类源码分析与算法原理

TrendlineEstimator是WebRTC GCC拥塞控制的核心算法组件,通过统计分析数据包延迟变化趋势来检测网络拥塞状态。它使用滑动窗口收集延迟数据,基于最小二乘法进行线性回归拟合得到趋势斜率,通过自适应阈值机制判断网络处于正常、过载或欠载状态。该算法采用指数平滑滤波抵抗瞬时波动,具备斜率限制等抗突发干扰设计,为带宽估计提供准确的网络状态判断,是WebRTC实现高效自适应码率控制的关键技术基础。

talkRTC的博客 995

YOLOv9电力巡检实战:绝缘子破裂/鸟巢识别+无人机自动定位

摘要:本文聚焦电力输电线路巡检的效率与安全痛点,提出基于YOLOv9与无人机的智能巡检解决方案。针对绝缘子破裂、鸟巢等高危缺陷,通过“无人机改装-模型训练-缺陷识别-工单生成”四阶段工程落地流程,实现全自动化巡检。系统采用大疆M300无人机搭载RTK模块与Jetson边缘计算盒,结合改进YOLOv9模型实时识别5类缺陷,通过4G传输将GPS定位与缺陷数据同步至工单系统。实测表明,该方案巡检效率达50公里/天(较人工提升10倍),缺陷发现率95%(提升40%),事故预防率98%。

专注于人工智能、软件开发、工控自动化、工厂数字化及智能化等领域,希望和大家共同进步! 1509

【PINN高级教程】范式融合与前沿应用 第5讲:贝叶斯推断与生成式建模的深度融合

正规化流(Normalizing Flow, NF)通过一系列可逆变换把简单分布映射为复杂后验,从而获得更好的表达能力。算子学习保持映射的物理正确性。贝叶斯推断给出了自然的框架,但直接对高维函数空间做采样(如 MCMC)几乎不可行。1️⃣ 在自己的 PDE 上跑一遍完整的 Bayesian PINN 流模型。的学习机制深度融合,以在保持物理一致性的前提下,高效地从后验分布中采样。2️⃣ 将每个 θ 直接映射到 FNO 权重,得到不同解的采样。的后验 p(θ∣x,y)p(θ∣x,y) 进行近似。

u012133341的博客 474

小议WebRTC拥塞控制算法:GCC介绍

网络拥塞是基于IP协议的数据报交换网络中常见的一种网络传输问题,它对网络传输的质量有严重的影响,网络拥塞是导致网络吞吐降低,网络丢包等的主要原因之一,这些问题使得上层应用无法有效的利用网络带宽获得高质量的网络传输效果。特别是在通信领域,网络拥塞导致的丢包,延迟,抖动等问题,严重的影响了通信质量,如果不能很好的解决这些问题,一个通信产品就无法在现实环境中正常使用。在这方面WebRTC中的...

weixin_30721077的博客 333

jre9下载 jdk9

(Java SE Runtime Environment 9.0) 9.0u175 官方最新版 【x86|x64】

webrtc弱网-FrameDropper 源码分析与算法原理

WebRTC 视频编码模块中的帧丢弃控制器。

talkRTC的博客 1025

TMS_WebGMaps_1.9.8.0_Full_Source

TMS_WebGMaps_1.9.8.0_Full_Source 全源码 delphi cbuilder

温度PID控制PLC程序

温度PID稳定控制程序,适用于欧姆龙PLC,对其他PLC也具有很大参考价值

webrtc弱网-LossBasedBandwidthEstimation类源码分析与算法原理

LossBasedBandwidthEstimation类基于网络丢包率动态估算可用带宽上限。它通过分析丢包统计数据,使用多阈值控制和RTT自适应算法,决定增加、减少或保持当前带宽估计,实现网络拥塞控制,是WebRTC GCC拥塞控制体系的核心组件之一。

talkRTC的博客 1175

efm32 入门.pdf

本PDF共计22页,介绍的是操作驱动API,下载与否自己斟酌。

突破网络波动:Janus WebRTC Server带宽自适应策略全解析

Janus WebRTC Server是一款功能强大的开源实时通信服务器,它通过多种智能技术实现带宽自适应,确保在网络波动情况下仍能提供流畅的音视频体验。本文将深入解析Janus的核心自适应机制,帮助开发者和用户理解其如何应对复杂网络环境。 ## 📊 网络波动的隐形挑战 在实时通信中,网络带宽的不稳定性是影响体验的主要因素。无论是家庭WiFi的信号干扰,还是移动网络的切换,都会导致数据包丢失

gitblog_01065的博客 363
上一篇: 根据浏览器 user-agent 按需加载CSS 文件
下一篇: webrtc 资料汇集
bamboolsu
博客等级 码龄22年 200粉丝 394原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值