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

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

Issue 1390753002: Implement AudioReceiveStream::GetStats(). (Closed) Base URL: https://chromium.googlesource.com/external/webrtc.git@master
Patch Set: one s Created 5 years, 2 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 * libjingle 2 * libjingle
3 * Copyright 2004 Google Inc. 3 * Copyright 2004 Google Inc.
4 * 4 *
5 * Redistribution and use in source and binary forms, with or without 5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met: 6 * modification, are permitted provided that the following conditions are met:
7 * 7 *
8 * 1. Redistributions of source code must retain the above copyright notice, 8 * 1. Redistributions of source code must retain the above copyright notice,
9 * this list of conditions and the following disclaimer. 9 * this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright notice, 10 * 2. Redistributions in binary form must reproduce the above copyright notice,
(...skipping 2607 matching lines...) Expand 10 before | Expand all | Expand 10 after
2618 2618
2619 int median, std; 2619 int median, std;
2620 float dummy; 2620 float dummy;
2621 if (engine()->voe()->processing()->GetEcDelayMetrics( 2621 if (engine()->voe()->processing()->GetEcDelayMetrics(
2622 median, std, dummy) != -1) { 2622 median, std, dummy) != -1) {
2623 echo_delay_median_ms = median; 2623 echo_delay_median_ms = median;
2624 echo_delay_std_ms = std; 2624 echo_delay_std_ms = std;
2625 } 2625 }
2626 } 2626 }
2627 2627
2628 webrtc::CallStatistics cs;
2629 unsigned int ssrc;
2630 webrtc::CodecInst codec;
2631 unsigned int level;
2632
2633 for (const auto& ch : send_channels_) { 2628 for (const auto& ch : send_channels_) {
2634 const int channel = ch.second->channel(); 2629 const int channel = ch.second->channel();
2635 2630
2636 // Fill in the sender info, based on what we know, and what the 2631 // Fill in the sender info, based on what we know, and what the
2637 // remote side told us it got from its RTCP report. 2632 // remote side told us it got from its RTCP report.
2638 VoiceSenderInfo sinfo; 2633 VoiceSenderInfo sinfo;
2639 2634
2635 webrtc::CallStatistics cs = {0};
2636 unsigned int ssrc = 0;
2640 if (engine()->voe()->rtp()->GetRTCPStatistics(channel, cs) == -1 || 2637 if (engine()->voe()->rtp()->GetRTCPStatistics(channel, cs) == -1 ||
2641 engine()->voe()->rtp()->GetLocalSSRC(channel, ssrc) == -1) { 2638 engine()->voe()->rtp()->GetLocalSSRC(channel, ssrc) == -1) {
2642 continue; 2639 continue;
2643 } 2640 }
2644 2641
2645 sinfo.add_ssrc(ssrc); 2642 sinfo.add_ssrc(ssrc);
2646 sinfo.codec_name = send_codec_.get() ? send_codec_->plname : ""; 2643 sinfo.codec_name = send_codec_.get() ? send_codec_->plname : "";
2647 sinfo.bytes_sent = cs.bytesSent; 2644 sinfo.bytes_sent = cs.bytesSent;
2648 sinfo.packets_sent = cs.packetsSent; 2645 sinfo.packets_sent = cs.packetsSent;
2649 // RTT isn't known until a RTCP report is received. Until then, VoiceEngine 2646 // RTT isn't known until a RTCP report is received. Until then, VoiceEngine
2650 // returns 0 to indicate an error value. 2647 // returns 0 to indicate an error value.
2651 sinfo.rtt_ms = (cs.rttMs > 0) ? cs.rttMs : -1; 2648 sinfo.rtt_ms = (cs.rttMs > 0) ? cs.rttMs : -1;
2652 2649
2653 // Get data from the last remote RTCP report. Use default values if no data 2650 // Get data from the last remote RTCP report. Use default values if no data
2654 // available. 2651 // available.
2655 sinfo.fraction_lost = -1.0; 2652 sinfo.fraction_lost = -1.0;
2656 sinfo.jitter_ms = -1; 2653 sinfo.jitter_ms = -1;
2657 sinfo.packets_lost = -1; 2654 sinfo.packets_lost = -1;
2658 sinfo.ext_seqnum = -1; 2655 sinfo.ext_seqnum = -1;
2659 std::vector<webrtc::ReportBlock> receive_blocks; 2656 std::vector<webrtc::ReportBlock> receive_blocks;
2657 webrtc::CodecInst codec = {0};
2660 if (engine()->voe()->rtp()->GetRemoteRTCPReportBlocks( 2658 if (engine()->voe()->rtp()->GetRemoteRTCPReportBlocks(
2661 channel, &receive_blocks) != -1 && 2659 channel, &receive_blocks) != -1 &&
2662 engine()->voe()->codec()->GetSendCodec(channel, codec) != -1) { 2660 engine()->voe()->codec()->GetSendCodec(channel, codec) != -1) {
2663 for (const webrtc::ReportBlock& block : receive_blocks) { 2661 for (const webrtc::ReportBlock& block : receive_blocks) {
2664 // Lookup report for send ssrc only. 2662 // Lookup report for send ssrc only.
2665 if (block.source_SSRC == sinfo.ssrc()) { 2663 if (block.source_SSRC == sinfo.ssrc()) {
2666 // Convert Q8 to floating point. 2664 // Convert Q8 to floating point.
2667 sinfo.fraction_lost = static_cast<float>(block.fraction_lost) / 256; 2665 sinfo.fraction_lost = static_cast<float>(block.fraction_lost) / 256;
2668 // Convert samples to milliseconds. 2666 // Convert samples to milliseconds.
2669 if (codec.plfreq / 1000 > 0) { 2667 if (codec.plfreq / 1000 > 0) {
2670 sinfo.jitter_ms = block.interarrival_jitter / (codec.plfreq / 1000); 2668 sinfo.jitter_ms = block.interarrival_jitter / (codec.plfreq / 1000);
2671 } 2669 }
2672 sinfo.packets_lost = block.cumulative_num_packets_lost; 2670 sinfo.packets_lost = block.cumulative_num_packets_lost;
2673 sinfo.ext_seqnum = block.extended_highest_sequence_number; 2671 sinfo.ext_seqnum = block.extended_highest_sequence_number;
2674 break; 2672 break;
2675 } 2673 }
2676 } 2674 }
2677 } 2675 }
2678 2676
2679 // Local speech level. 2677 // Local speech level.
2678 unsigned int level = 0;
2680 sinfo.audio_level = (engine()->voe()->volume()-> 2679 sinfo.audio_level = (engine()->voe()->volume()->
2681 GetSpeechInputLevelFullRange(level) != -1) ? level : -1; 2680 GetSpeechInputLevelFullRange(level) != -1) ? level : -1;
2682 2681
2683 // TODO(xians): We are injecting the same APM logging to all the send 2682 // TODO(xians): We are injecting the same APM logging to all the send
2684 // channels here because there is no good way to know which send channel 2683 // channels here because there is no good way to know which send channel
2685 // is using the APM. The correct fix is to allow the send channels to have 2684 // is using the APM. The correct fix is to allow the send channels to have
2686 // their own APM so that we can feed the correct APM logging to different 2685 // their own APM so that we can feed the correct APM logging to different
2687 // send channels. See issue crbug/264611 . 2686 // send channels. See issue crbug/264611 .
2688 sinfo.echo_return_loss = echo_return_loss; 2687 sinfo.echo_return_loss = echo_return_loss;
2689 sinfo.echo_return_loss_enhancement = echo_return_loss_enhancement; 2688 sinfo.echo_return_loss_enhancement = echo_return_loss_enhancement;
2690 sinfo.echo_delay_median_ms = echo_delay_median_ms; 2689 sinfo.echo_delay_median_ms = echo_delay_median_ms;
2691 sinfo.echo_delay_std_ms = echo_delay_std_ms; 2690 sinfo.echo_delay_std_ms = echo_delay_std_ms;
2692 // TODO(ajm): Re-enable this metric once we have a reliable implementation. 2691 // TODO(ajm): Re-enable this metric once we have a reliable implementation.
2693 sinfo.aec_quality_min = -1; 2692 sinfo.aec_quality_min = -1;
2694 sinfo.typing_noise_detected = typing_noise_detected_; 2693 sinfo.typing_noise_detected = typing_noise_detected_;
2695 2694
2696 info->senders.push_back(sinfo); 2695 info->senders.push_back(sinfo);
2697 } 2696 }
2698 2697
2699 // Get the SSRC and stats for each receiver. 2698 // Get the SSRC and stats for each receiver.
2700 for (const auto& ch : receive_channels_) { 2699 info->receivers.clear();
2701 int ch_id = ch.second->channel(); 2700 for (const auto& stream : receive_streams_) {
2702 memset(&cs, 0, sizeof(cs)); 2701 webrtc::AudioReceiveStream::Stats stats = stream.second->GetStats();
2703 if (engine()->voe()->rtp()->GetRemoteSSRC(ch_id, ssrc) != -1 && 2702 VoiceReceiverInfo rinfo;
2704 engine()->voe()->rtp()->GetRTCPStatistics(ch_id, cs) != -1 && 2703 rinfo.add_ssrc(stats.remote_ssrc);
2705 engine()->voe()->codec()->GetRecCodec(ch_id, codec) != -1) { 2704 rinfo.bytes_rcvd = stats.bytes_rcvd;
2706 VoiceReceiverInfo rinfo; 2705 rinfo.packets_rcvd = stats.packets_rcvd;
2707 rinfo.add_ssrc(ssrc); 2706 rinfo.packets_lost = stats.packets_lost;
2708 rinfo.bytes_rcvd = cs.bytesReceived; 2707 rinfo.fraction_lost = stats.fraction_lost;
2709 rinfo.packets_rcvd = cs.packetsReceived; 2708 rinfo.codec_name = stats.codec_name;
2710 // The next four fields are from the most recently sent RTCP report. 2709 rinfo.ext_seqnum = stats.ext_seqnum;
2711 // Convert Q8 to floating point. 2710 rinfo.jitter_ms = stats.jitter_ms;
2712 rinfo.fraction_lost = static_cast<float>(cs.fractionLost) / (1 << 8); 2711 rinfo.jitter_buffer_ms = stats.jitter_buffer_ms;
2713 rinfo.packets_lost = cs.cumulativeLost; 2712 rinfo.jitter_buffer_preferred_ms = stats.jitter_buffer_preferred_ms;
2714 rinfo.ext_seqnum = cs.extendedMax; 2713 rinfo.delay_estimate_ms = stats.delay_estimate_ms;
2715 rinfo.capture_start_ntp_time_ms = cs.capture_start_ntp_time_ms_; 2714 rinfo.audio_level = stats.audio_level;
2716 if (codec.pltype != -1) { 2715 rinfo.expand_rate = stats.expand_rate;
2717 rinfo.codec_name = codec.plname; 2716 rinfo.speech_expand_rate = stats.speech_expand_rate;
2718 } 2717 rinfo.secondary_decoded_rate = stats.secondary_decoded_rate;
2719 // Convert samples to milliseconds. 2718 rinfo.accelerate_rate = stats.accelerate_rate;
2720 if (codec.plfreq / 1000 > 0) { 2719 rinfo.preemptive_expand_rate = stats.preemptive_expand_rate;
2721 rinfo.jitter_ms = cs.jitterSamples / (codec.plfreq / 1000); 2720 rinfo.decoding_calls_to_silence_generator =
2722 } 2721 stats.decoding_calls_to_silence_generator;
2723 2722 rinfo.decoding_calls_to_neteq = stats.decoding_calls_to_neteq;
2724 // Get jitter buffer and total delay (alg + jitter + playout) stats. 2723 rinfo.decoding_normal = stats.decoding_normal;
2725 webrtc::NetworkStatistics ns; 2724 rinfo.decoding_plc = stats.decoding_plc;
2726 if (engine()->voe()->neteq() && 2725 rinfo.decoding_cng = stats.decoding_cng;
2727 engine()->voe()->neteq()->GetNetworkStatistics( 2726 rinfo.decoding_plc_cng = stats.decoding_plc_cng;
2728 ch_id, ns) != -1) { 2727 rinfo.capture_start_ntp_time_ms = stats.capture_start_ntp_time_ms;
2729 rinfo.jitter_buffer_ms = ns.currentBufferSize; 2728 info->receivers.push_back(rinfo);
2730 rinfo.jitter_buffer_preferred_ms = ns.preferredBufferSize;
2731 rinfo.expand_rate =
2732 static_cast<float>(ns.currentExpandRate) / (1 << 14);
2733 rinfo.speech_expand_rate =
2734 static_cast<float>(ns.currentSpeechExpandRate) / (1 << 14);
2735 rinfo.secondary_decoded_rate =
2736 static_cast<float>(ns.currentSecondaryDecodedRate) / (1 << 14);
2737 rinfo.accelerate_rate =
2738 static_cast<float>(ns.currentAccelerateRate) / (1 << 14);
2739 rinfo.preemptive_expand_rate =
2740 static_cast<float>(ns.currentPreemptiveRate) / (1 << 14);
2741 }
2742
2743 webrtc::AudioDecodingCallStats ds;
2744 if (engine()->voe()->neteq() &&
2745 engine()->voe()->neteq()->GetDecodingCallStatistics(
2746 ch_id, &ds) != -1) {
2747 rinfo.decoding_calls_to_silence_generator =
2748 ds.calls_to_silence_generator;
2749 rinfo.decoding_calls_to_neteq = ds.calls_to_neteq;
2750 rinfo.decoding_normal = ds.decoded_normal;
2751 rinfo.decoding_plc = ds.decoded_plc;
2752 rinfo.decoding_cng = ds.decoded_cng;
2753 rinfo.decoding_plc_cng = ds.decoded_plc_cng;
2754 }
2755
2756 if (engine()->voe()->sync()) {
2757 int jitter_buffer_delay_ms = 0;
2758 int playout_buffer_delay_ms = 0;
2759 engine()->voe()->sync()->GetDelayEstimate(
2760 ch_id, &jitter_buffer_delay_ms, &playout_buffer_delay_ms);
2761 rinfo.delay_estimate_ms = jitter_buffer_delay_ms +
2762 playout_buffer_delay_ms;
2763 }
2764
2765 // Get speech level.
2766 rinfo.audio_level = (engine()->voe()->volume()->
2767 GetSpeechOutputLevelFullRange(ch_id, level) != -1) ? level : -1;
2768 info->receivers.push_back(rinfo);
2769 }
2770 } 2729 }
2771 2730
2772 return true; 2731 return true;
2773 } 2732 }
2774 2733
2775 void WebRtcVoiceMediaChannel::OnError(int error) { 2734 void WebRtcVoiceMediaChannel::OnError(int error) {
2776 if (send_ == SEND_NOTHING) { 2735 if (send_ == SEND_NOTHING) {
2777 return; 2736 return;
2778 } 2737 }
2779 if (error == VE_TYPING_NOISE_WARNING) { 2738 if (error == VE_TYPING_NOISE_WARNING) {
(...skipping 191 matching lines...) Expand 10 before | Expand all | Expand 10 after
2971 LOG(LS_WARNING) << "Unknown codec " << ToString(codec); 2930 LOG(LS_WARNING) << "Unknown codec " << ToString(codec);
2972 return false; 2931 return false;
2973 } 2932 }
2974 } 2933 }
2975 return true; 2934 return true;
2976 } 2935 }
2977 2936
2978 } // namespace cricket 2937 } // namespace cricket
2979 2938
2980 #endif // HAVE_WEBRTC_VOICE 2939 #endif // HAVE_WEBRTC_VOICE
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698