Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(114)

Side by Side Diff: webrtc/media/engine/webrtcvoiceengine.cc

Issue 1920123002: Cap the send bitrate for opus and iSAC before passing down to VoE. (Closed) Base URL: https://chromium.googlesource.com/external/webrtc.git@master
Patch Set: Reverting patch set 3. Created 4 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright (c) 2004 The WebRTC project authors. All Rights Reserved. 2 * Copyright (c) 2004 The WebRTC project authors. All Rights Reserved.
3 * 3 *
4 * Use of this source code is governed by a BSD-style license 4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source 5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found 6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may 7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree. 8 * be found in the AUTHORS file in the root of the source tree.
9 */ 9 */
10 10
(...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after
76 // The current implementation applies the following values to mono signals, 76 // The current implementation applies the following values to mono signals,
77 // and multiplies them by 2 for stereo. 77 // and multiplies them by 2 for stereo.
78 const int kOpusBitrateNb = 12000; 78 const int kOpusBitrateNb = 12000;
79 const int kOpusBitrateWb = 20000; 79 const int kOpusBitrateWb = 20000;
80 const int kOpusBitrateFb = 32000; 80 const int kOpusBitrateFb = 32000;
81 81
82 // Opus bitrate should be in the range between 6000 and 510000. 82 // Opus bitrate should be in the range between 6000 and 510000.
83 const int kOpusMinBitrate = 6000; 83 const int kOpusMinBitrate = 6000;
84 const int kOpusMaxBitrate = 510000; 84 const int kOpusMaxBitrate = 510000;
85 85
86 // iSAC bitrate should be <= 56000.
87 const int kIsacMaxBitrate = 56000;
88
86 // Default audio dscp value. 89 // Default audio dscp value.
87 // See http://tools.ietf.org/html/rfc2474 for details. 90 // See http://tools.ietf.org/html/rfc2474 for details.
88 // See also http://tools.ietf.org/html/draft-jennings-rtcweb-qos-00 91 // See also http://tools.ietf.org/html/draft-jennings-rtcweb-qos-00
89 const rtc::DiffServCodePoint kAudioDscpValue = rtc::DSCP_EF; 92 const rtc::DiffServCodePoint kAudioDscpValue = rtc::DSCP_EF;
90 93
91 // Constants from voice_engine_defines.h. 94 // Constants from voice_engine_defines.h.
92 const int kMinTelephoneEventCode = 0; // RFC4733 (Section 2.3.1) 95 const int kMinTelephoneEventCode = 0; // RFC4733 (Section 2.3.1)
93 const int kMaxTelephoneEventCode = 255; 96 const int kMaxTelephoneEventCode = 255;
94 const int kMinTelephoneEventDuration = 100; 97 const int kMinTelephoneEventDuration = 100;
95 const int kMaxTelephoneEventDuration = 60000; // Actual limit is 2^16 98 const int kMaxTelephoneEventDuration = 60000; // Actual limit is 2^16
(...skipping 245 matching lines...) Expand 10 before | Expand all | Expand 10 after
341 static bool IsCodecMultiRate(const webrtc::CodecInst& codec) { 344 static bool IsCodecMultiRate(const webrtc::CodecInst& codec) {
342 for (size_t i = 0; i < arraysize(kCodecPrefs); ++i) { 345 for (size_t i = 0; i < arraysize(kCodecPrefs); ++i) {
343 if (IsCodec(codec, kCodecPrefs[i].name) && 346 if (IsCodec(codec, kCodecPrefs[i].name) &&
344 kCodecPrefs[i].clockrate == codec.plfreq) { 347 kCodecPrefs[i].clockrate == codec.plfreq) {
345 return kCodecPrefs[i].is_multi_rate; 348 return kCodecPrefs[i].is_multi_rate;
346 } 349 }
347 } 350 }
348 return false; 351 return false;
349 } 352 }
350 353
354 static int MaxBitrateBps(const webrtc::CodecInst& codec) {
355 for (size_t i = 0; i < arraysize(kCodecPrefs); ++i) {
356 if (IsCodec(codec, kCodecPrefs[i].name) &&
357 kCodecPrefs[i].clockrate == codec.plfreq) {
358 return kCodecPrefs[i].max_bitrate_bps;
359 }
360 }
361 return 0;
362 }
363
351 // If the AudioCodec param kCodecParamPTime is set, then we will set it to 364 // If the AudioCodec param kCodecParamPTime is set, then we will set it to
352 // codec pacsize if it's valid, or we will pick the next smallest value we 365 // codec pacsize if it's valid, or we will pick the next smallest value we
353 // support. 366 // support.
354 // TODO(Brave): Query supported packet sizes from ACM when the API is ready. 367 // TODO(Brave): Query supported packet sizes from ACM when the API is ready.
355 static bool SetPTimeAsPacketSize(webrtc::CodecInst* codec, int ptime_ms) { 368 static bool SetPTimeAsPacketSize(webrtc::CodecInst* codec, int ptime_ms) {
356 for (const CodecPref& codec_pref : kCodecPrefs) { 369 for (const CodecPref& codec_pref : kCodecPrefs) {
357 if ((IsCodec(*codec, codec_pref.name) && 370 if ((IsCodec(*codec, codec_pref.name) &&
358 codec_pref.clockrate == codec->plfreq) || 371 codec_pref.clockrate == codec->plfreq) ||
359 IsCodec(*codec, kG722CodecName)) { 372 IsCodec(*codec, kG722CodecName)) {
360 int packet_size_ms = SelectPacketSize(codec_pref, ptime_ms); 373 int packet_size_ms = SelectPacketSize(codec_pref, ptime_ms);
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after
411 424
412 private: 425 private:
413 static const int kMaxNumPacketSize = 6; 426 static const int kMaxNumPacketSize = 6;
414 struct CodecPref { 427 struct CodecPref {
415 const char* name; 428 const char* name;
416 int clockrate; 429 int clockrate;
417 size_t channels; 430 size_t channels;
418 int payload_type; 431 int payload_type;
419 bool is_multi_rate; 432 bool is_multi_rate;
420 int packet_sizes_ms[kMaxNumPacketSize]; 433 int packet_sizes_ms[kMaxNumPacketSize];
434 int max_bitrate_bps;
421 }; 435 };
422 // Note: keep the supported packet sizes in ascending order. 436 // Note: keep the supported packet sizes in ascending order.
423 static const CodecPref kCodecPrefs[12]; 437 static const CodecPref kCodecPrefs[12];
424 438
425 static int SelectPacketSize(const CodecPref& codec_pref, int ptime_ms) { 439 static int SelectPacketSize(const CodecPref& codec_pref, int ptime_ms) {
426 int selected_packet_size_ms = codec_pref.packet_sizes_ms[0]; 440 int selected_packet_size_ms = codec_pref.packet_sizes_ms[0];
427 for (int packet_size_ms : codec_pref.packet_sizes_ms) { 441 for (int packet_size_ms : codec_pref.packet_sizes_ms) {
428 if (packet_size_ms && packet_size_ms <= ptime_ms) { 442 if (packet_size_ms && packet_size_ms <= ptime_ms) {
429 selected_packet_size_ms = packet_size_ms; 443 selected_packet_size_ms = packet_size_ms;
430 } 444 }
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after
477 if (codec.id == red_pt) { 491 if (codec.id == red_pt) {
478 return &codec; 492 return &codec;
479 } 493 }
480 } 494 }
481 LOG(LS_WARNING) << "RED params " << red_params << " are invalid."; 495 LOG(LS_WARNING) << "RED params " << red_params << " are invalid.";
482 return nullptr; 496 return nullptr;
483 } 497 }
484 }; 498 };
485 499
486 const WebRtcVoiceCodecs::CodecPref WebRtcVoiceCodecs::kCodecPrefs[12] = { 500 const WebRtcVoiceCodecs::CodecPref WebRtcVoiceCodecs::kCodecPrefs[12] = {
487 { kOpusCodecName, 48000, 2, 111, true, { 10, 20, 40, 60 } }, 501 {kOpusCodecName, 48000, 2, 111, true, {10, 20, 40, 60}, kOpusMaxBitrate},
488 { kIsacCodecName, 16000, 1, 103, true, { 30, 60 } }, 502 {kIsacCodecName, 16000, 1, 103, true, {30, 60}, kIsacMaxBitrate},
489 { kIsacCodecName, 32000, 1, 104, true, { 30 } }, 503 {kIsacCodecName, 32000, 1, 104, true, {30}, kIsacMaxBitrate},
490 // G722 should be advertised as 8000 Hz because of the RFC "bug". 504 // G722 should be advertised as 8000 Hz because of the RFC "bug".
491 { kG722CodecName, 8000, 1, 9, false, { 10, 20, 30, 40, 50, 60 } }, 505 {kG722CodecName, 8000, 1, 9, false, {10, 20, 30, 40, 50, 60}},
492 { kIlbcCodecName, 8000, 1, 102, false, { 20, 30, 40, 60 } }, 506 {kIlbcCodecName, 8000, 1, 102, false, {20, 30, 40, 60}},
493 { kPcmuCodecName, 8000, 1, 0, false, { 10, 20, 30, 40, 50, 60 } }, 507 {kPcmuCodecName, 8000, 1, 0, false, {10, 20, 30, 40, 50, 60}},
494 { kPcmaCodecName, 8000, 1, 8, false, { 10, 20, 30, 40, 50, 60 } }, 508 {kPcmaCodecName, 8000, 1, 8, false, {10, 20, 30, 40, 50, 60}},
495 { kCnCodecName, 32000, 1, 106, false, { } }, 509 {kCnCodecName, 32000, 1, 106, false, {}},
496 { kCnCodecName, 16000, 1, 105, false, { } }, 510 {kCnCodecName, 16000, 1, 105, false, {}},
497 { kCnCodecName, 8000, 1, 13, false, { } }, 511 {kCnCodecName, 8000, 1, 13, false, {}},
498 { kRedCodecName, 8000, 1, 127, false, { } }, 512 {kRedCodecName, 8000, 1, 127, false, {}},
499 { kDtmfCodecName, 8000, 1, 126, false, { } }, 513 {kDtmfCodecName, 8000, 1, 126, false, {}},
500 }; 514 };
501 } // namespace { 515 } // namespace {
502 516
503 bool WebRtcVoiceEngine::ToCodecInst(const AudioCodec& in, 517 bool WebRtcVoiceEngine::ToCodecInst(const AudioCodec& in,
504 webrtc::CodecInst* out) { 518 webrtc::CodecInst* out) {
505 return WebRtcVoiceCodecs::ToCodecInst(in, out); 519 return WebRtcVoiceCodecs::ToCodecInst(in, out);
506 } 520 }
507 521
508 WebRtcVoiceEngine::WebRtcVoiceEngine(webrtc::AudioDeviceModule* adm) 522 WebRtcVoiceEngine::WebRtcVoiceEngine(webrtc::AudioDeviceModule* adm)
509 : WebRtcVoiceEngine(adm, new VoEWrapper()) { 523 : WebRtcVoiceEngine(adm, new VoEWrapper()) {
(...skipping 850 matching lines...) Expand 10 before | Expand all | Expand 10 after
1360 std::vector<webrtc::RtpExtension> filtered_extensions = 1374 std::vector<webrtc::RtpExtension> filtered_extensions =
1361 FilterRtpExtensions(params.extensions, 1375 FilterRtpExtensions(params.extensions,
1362 webrtc::RtpExtension::IsSupportedForAudio, true); 1376 webrtc::RtpExtension::IsSupportedForAudio, true);
1363 if (send_rtp_extensions_ != filtered_extensions) { 1377 if (send_rtp_extensions_ != filtered_extensions) {
1364 send_rtp_extensions_.swap(filtered_extensions); 1378 send_rtp_extensions_.swap(filtered_extensions);
1365 for (auto& it : send_streams_) { 1379 for (auto& it : send_streams_) {
1366 it.second->RecreateAudioSendStream(send_rtp_extensions_); 1380 it.second->RecreateAudioSendStream(send_rtp_extensions_);
1367 } 1381 }
1368 } 1382 }
1369 1383
1370 if (!SetSendBitrate(params.max_bandwidth_bps)) { 1384 if (!SetMaxSendBitrate(params.max_bandwidth_bps)) {
1371 return false; 1385 return false;
1372 } 1386 }
1373 return SetOptions(params.options); 1387 return SetOptions(params.options);
1374 } 1388 }
1375 1389
1376 bool WebRtcVoiceMediaChannel::SetRecvParameters( 1390 bool WebRtcVoiceMediaChannel::SetRecvParameters(
1377 const AudioRecvParameters& params) { 1391 const AudioRecvParameters& params) {
1378 TRACE_EVENT0("webrtc", "WebRtcVoiceMediaChannel::SetRecvParameters"); 1392 TRACE_EVENT0("webrtc", "WebRtcVoiceMediaChannel::SetRecvParameters");
1379 RTC_DCHECK(worker_thread_checker_.CalledOnValidThread()); 1393 RTC_DCHECK(worker_thread_checker_.CalledOnValidThread());
1380 LOG(LS_INFO) << "WebRtcVoiceMediaChannel::SetRecvParameters: " 1394 LOG(LS_INFO) << "WebRtcVoiceMediaChannel::SetRecvParameters: "
(...skipping 359 matching lines...) Expand 10 before | Expand all | Expand 10 after
1740 << " Hz on channel " 1754 << " Hz on channel "
1741 << channel; 1755 << channel;
1742 if (engine()->voe()->codec()->SetOpusMaxPlaybackRate( 1756 if (engine()->voe()->codec()->SetOpusMaxPlaybackRate(
1743 channel, send_codec_spec_.opus_max_playback_rate) == -1) { 1757 channel, send_codec_spec_.opus_max_playback_rate) == -1) {
1744 LOG_RTCERR2(SetOpusMaxPlaybackRate, channel, 1758 LOG_RTCERR2(SetOpusMaxPlaybackRate, channel,
1745 send_codec_spec_.opus_max_playback_rate); 1759 send_codec_spec_.opus_max_playback_rate);
1746 return false; 1760 return false;
1747 } 1761 }
1748 } 1762 }
1749 } 1763 }
1750 // TODO(solenberg): SetSendBitrate() yields another call to SetSendCodec(). 1764 // TODO(solenberg): SetMaxSendBitrate() yields another call to SetSendCodec().
1751 // Check if it is possible to fuse with the previous call in this function. 1765 // Check if it is possible to fuse with the previous call in this function.
1752 SetChannelParameters(channel, rtp_parameters); 1766 SetChannelParameters(channel, rtp_parameters);
1753 1767
1754 // Set the CN payloadtype and the VAD status. 1768 // Set the CN payloadtype and the VAD status.
1755 if (send_codec_spec_.cng_payload_type != -1) { 1769 if (send_codec_spec_.cng_payload_type != -1) {
1756 // The CN payload type for 8000 Hz clockrate is fixed at 13. 1770 // The CN payload type for 8000 Hz clockrate is fixed at 13.
1757 if (send_codec_spec_.cng_plfreq != 8000) { 1771 if (send_codec_spec_.cng_plfreq != 8000) {
1758 webrtc::PayloadFrequencies cn_freq; 1772 webrtc::PayloadFrequencies cn_freq;
1759 switch (send_codec_spec_.cng_plfreq) { 1773 switch (send_codec_spec_.cng_plfreq) {
1760 case 16000: 1774 case 16000:
(...skipping 615 matching lines...) Expand 10 before | Expand all | Expand 10 after
2376 } 2390 }
2377 } 2391 }
2378 2392
2379 webrtc::AudioProcessing* ap = engine()->voe()->base()->audio_processing(); 2393 webrtc::AudioProcessing* ap = engine()->voe()->base()->audio_processing();
2380 if (ap) { 2394 if (ap) {
2381 ap->set_output_will_be_muted(all_muted); 2395 ap->set_output_will_be_muted(all_muted);
2382 } 2396 }
2383 return true; 2397 return true;
2384 } 2398 }
2385 2399
2386 bool WebRtcVoiceMediaChannel::SetSendBitrate(int bps) { 2400 bool WebRtcVoiceMediaChannel::SetMaxSendBitrate(int bps) {
2387 LOG(LS_INFO) << "WebRtcVoiceMediaChannel::SetSendBitrate."; 2401 LOG(LS_INFO) << "WebRtcVoiceMediaChannel::SetMaxSendBitrate.";
2388 send_bitrate_bps_ = bps; 2402 max_send_bitrate_bps_ = bps;
2389 2403
2390 for (const auto& kv : send_streams_) { 2404 for (const auto& kv : send_streams_) {
2391 if (!SetChannelParameters(kv.second->channel(), 2405 if (!SetChannelParameters(kv.second->channel(),
2392 kv.second->rtp_parameters())) { 2406 kv.second->rtp_parameters())) {
2393 return false; 2407 return false;
2394 } 2408 }
2395 } 2409 }
2396 return true; 2410 return true;
2397 } 2411 }
2398 2412
2399 bool WebRtcVoiceMediaChannel::SetChannelParameters( 2413 bool WebRtcVoiceMediaChannel::SetChannelParameters(
2400 int channel, 2414 int channel,
2401 const webrtc::RtpParameters& parameters) { 2415 const webrtc::RtpParameters& parameters) {
2402 RTC_CHECK_EQ(1UL, parameters.encodings.size()); 2416 RTC_CHECK_EQ(1UL, parameters.encodings.size());
2403 // TODO(deadbeef): Handle setting parameters with a list of codecs in a 2417 // TODO(deadbeef): Handle setting parameters with a list of codecs in a
2404 // different order (which should change the send codec). 2418 // different order (which should change the send codec).
2405 return SetSendBitrate( 2419 return SetMaxSendBitrate(
2406 channel, 2420 channel, MinPositive(max_send_bitrate_bps_,
2407 MinPositive(send_bitrate_bps_, parameters.encodings[0].max_bitrate_bps)); 2421 parameters.encodings[0].max_bitrate_bps));
2408 } 2422 }
2409 2423
2410 bool WebRtcVoiceMediaChannel::SetSendBitrate(int channel, int bps) { 2424 bool WebRtcVoiceMediaChannel::SetMaxSendBitrate(int channel, int bps) {
2411 // Bitrate is auto by default. 2425 // Bitrate is auto by default.
2412 // TODO(bemasc): Fix this so that if SetMaxSendBandwidth(50) is followed by 2426 // TODO(bemasc): Fix this so that if SetMaxSendBandwidth(50) is followed by
2413 // SetMaxSendBandwith(0), the second call removes the previous limit. 2427 // SetMaxSendBandwith(0), the second call removes the previous limit.
2414 if (bps <= 0) 2428 if (bps <= 0) {
2415 return true; 2429 return true;
2430 }
2416 2431
2417 if (!HasSendCodec()) { 2432 if (!HasSendCodec()) {
2418 LOG(LS_INFO) << "The send codec has not been set up yet. " 2433 LOG(LS_INFO) << "The send codec has not been set up yet. "
2419 << "The send bitrate setting will be applied later."; 2434 << "The send bitrate setting will be applied later.";
2420 return true; 2435 return true;
2421 } 2436 }
2422 2437
2423 webrtc::CodecInst codec = send_codec_spec_.codec_inst; 2438 webrtc::CodecInst codec = send_codec_spec_.codec_inst;
2424 bool is_multi_rate = WebRtcVoiceCodecs::IsCodecMultiRate(codec); 2439 bool is_multi_rate = WebRtcVoiceCodecs::IsCodecMultiRate(codec);
2425 2440
2426 if (is_multi_rate) { 2441 if (is_multi_rate) {
2427 // If codec is multi-rate then just set the bitrate. 2442 // If codec is multi-rate then just set the bitrate.
2428 codec.rate = bps; 2443 int max_bitrate_bps = WebRtcVoiceCodecs::MaxBitrateBps(codec);
2444 codec.rate = std::min(bps, max_bitrate_bps);
2445 LOG(LS_INFO) << "Setting codec " << codec.plname << " to bitrate " << bps
2446 << " bps.";
2429 if (!SetSendCodec(channel, codec)) { 2447 if (!SetSendCodec(channel, codec)) {
2430 LOG(LS_INFO) << "Failed to set codec " << codec.plname << " to bitrate " 2448 LOG(LS_ERROR) << "Failed to set codec " << codec.plname << " to bitrate "
2431 << bps << " bps."; 2449 << bps << " bps.";
2432 return false; 2450 return false;
2433 } 2451 }
2434 return true; 2452 return true;
2435 } else { 2453 } else {
2436 // If codec is not multi-rate and |bps| is less than the fixed bitrate 2454 // If codec is not multi-rate and |bps| is less than the fixed bitrate
2437 // then fail. If codec is not multi-rate and |bps| exceeds or equal the 2455 // then fail. If codec is not multi-rate and |bps| exceeds or equal the
2438 // fixed bitrate then ignore. 2456 // fixed bitrate then ignore.
2439 if (bps < codec.rate) { 2457 if (bps < codec.rate) {
2440 LOG(LS_INFO) << "Failed to set codec " << codec.plname 2458 LOG(LS_ERROR) << "Failed to set codec " << codec.plname << " to bitrate "
2441 << " to bitrate " << bps << " bps" 2459 << bps << " bps"
2442 << ", requires at least " << codec.rate << " bps."; 2460 << ", requires at least " << codec.rate << " bps.";
2443 return false; 2461 return false;
2444 } 2462 }
2445 return true; 2463 return true;
2446 } 2464 }
2447 } 2465 }
2448 2466
2449 void WebRtcVoiceMediaChannel::OnReadyToSend(bool ready) { 2467 void WebRtcVoiceMediaChannel::OnReadyToSend(bool ready) {
2450 RTC_DCHECK(worker_thread_checker_.CalledOnValidThread()); 2468 RTC_DCHECK(worker_thread_checker_.CalledOnValidThread());
2451 LOG(LS_VERBOSE) << "OnReadyToSend: " << (ready ? "Ready." : "Not ready."); 2469 LOG(LS_VERBOSE) << "OnReadyToSend: " << (ready ? "Ready." : "Not ready.");
2452 call_->SignalChannelNetworkState( 2470 call_->SignalChannelNetworkState(
(...skipping 122 matching lines...) Expand 10 before | Expand all | Expand 10 after
2575 } 2593 }
2576 } else { 2594 } else {
2577 LOG(LS_INFO) << "Stopping playout for channel #" << channel; 2595 LOG(LS_INFO) << "Stopping playout for channel #" << channel;
2578 engine()->voe()->base()->StopPlayout(channel); 2596 engine()->voe()->base()->StopPlayout(channel);
2579 } 2597 }
2580 return true; 2598 return true;
2581 } 2599 }
2582 } // namespace cricket 2600 } // namespace cricket
2583 2601
2584 #endif // HAVE_WEBRTC_VOICE 2602 #endif // HAVE_WEBRTC_VOICE
OLDNEW
« no previous file with comments | « webrtc/media/engine/webrtcvoiceengine.h ('k') | webrtc/media/engine/webrtcvoiceengine_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698