| OLD | NEW |
| 1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "net/quic/quic_connection_logger.h" | 5 #include "net/quic/quic_connection_logger.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 #include <string> | 8 #include <string> |
| 9 #include <utility> | 9 #include <utility> |
| 10 | 10 |
| (...skipping 15 matching lines...) Expand all Loading... |
| 26 #include "net/quic/quic_socket_address_coder.h" | 26 #include "net/quic/quic_socket_address_coder.h" |
| 27 #include "net/quic/quic_time.h" | 27 #include "net/quic/quic_time.h" |
| 28 | 28 |
| 29 using base::StringPiece; | 29 using base::StringPiece; |
| 30 using std::string; | 30 using std::string; |
| 31 | 31 |
| 32 namespace net { | 32 namespace net { |
| 33 | 33 |
| 34 namespace { | 34 namespace { |
| 35 | 35 |
| 36 // We have ranges-of-buckets in the cumulative histogram (covering 21 packet | |
| 37 // sequences) of length 2, 3, 4, ... 22. | |
| 38 // Hence the largest sample is bounded by the sum of those numbers. | |
| 39 const int kBoundingSampleInCumulativeHistogram = ((2 + 22) * 21) / 2; | |
| 40 | |
| 41 scoped_ptr<base::Value> NetLogQuicPacketCallback( | 36 scoped_ptr<base::Value> NetLogQuicPacketCallback( |
| 42 const IPEndPoint* self_address, | 37 const IPEndPoint* self_address, |
| 43 const IPEndPoint* peer_address, | 38 const IPEndPoint* peer_address, |
| 44 size_t packet_size, | 39 size_t packet_size, |
| 45 NetLogCaptureMode /* capture_mode */) { | 40 NetLogCaptureMode /* capture_mode */) { |
| 46 scoped_ptr<base::DictionaryValue> dict(new base::DictionaryValue()); | 41 scoped_ptr<base::DictionaryValue> dict(new base::DictionaryValue()); |
| 47 dict->SetString("self_address", self_address->ToString()); | 42 dict->SetString("self_address", self_address->ToString()); |
| 48 dict->SetString("peer_address", peer_address->ToString()); | 43 dict->SetString("peer_address", peer_address->ToString()); |
| 49 dict->SetInteger("size", packet_size); | 44 dict->SetInteger("size", packet_size); |
| 50 return std::move(dict); | 45 return std::move(dict); |
| (...skipping 651 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 702 | 697 |
| 703 base::HistogramBase* QuicConnectionLogger::GetPacketNumberHistogram( | 698 base::HistogramBase* QuicConnectionLogger::GetPacketNumberHistogram( |
| 704 const char* statistic_name) const { | 699 const char* statistic_name) const { |
| 705 string prefix("Net.QuicSession.PacketReceived_"); | 700 string prefix("Net.QuicSession.PacketReceived_"); |
| 706 return base::LinearHistogram::FactoryGet( | 701 return base::LinearHistogram::FactoryGet( |
| 707 prefix + statistic_name + connection_description_, 1, | 702 prefix + statistic_name + connection_description_, 1, |
| 708 received_packets_.size(), received_packets_.size() + 1, | 703 received_packets_.size(), received_packets_.size() + 1, |
| 709 base::HistogramBase::kUmaTargetedHistogramFlag); | 704 base::HistogramBase::kUmaTargetedHistogramFlag); |
| 710 } | 705 } |
| 711 | 706 |
| 712 base::HistogramBase* QuicConnectionLogger::Get6PacketHistogram( | |
| 713 const char* which_6) const { | |
| 714 // This histogram takes a binary encoding of the 6 consecutive packets | |
| 715 // received. As a result, there are 64 possible sample-patterns. | |
| 716 string prefix("Net.QuicSession.6PacketsPatternsReceived_"); | |
| 717 return base::LinearHistogram::FactoryGet( | |
| 718 prefix + which_6 + connection_description_, 1, 64, 65, | |
| 719 base::HistogramBase::kUmaTargetedHistogramFlag); | |
| 720 } | |
| 721 | |
| 722 base::HistogramBase* QuicConnectionLogger::Get21CumulativeHistogram( | |
| 723 const char* which_21) const { | |
| 724 // This histogram contains, for each sequence of 21 packets, the results from | |
| 725 // 21 distinct questions about that sequence. Conceptually the histogtram is | |
| 726 // broken into 21 distinct ranges, and one sample is added into each of those | |
| 727 // ranges whenever we process a set of 21 packets. | |
| 728 // There is a little rendundancy, as each "range" must have the same number | |
| 729 // of samples, all told, but the histogram is a tad easier to read this way. | |
| 730 // The questions are: | |
| 731 // Was the first packet present (bucket 0==>no; bucket 1==>yes) | |
| 732 // Of the first two packets, how many were present? (bucket 2==> none; | |
| 733 // bucket 3==> 1 of 2; bucket 4==> 2 of 2) | |
| 734 // Of the first three packets, how many were present? (bucket 5==>none; | |
| 735 // bucket 6==> 1 of 3; bucket 7==> 2 of 3; bucket 8==> 3 of 3). | |
| 736 // etc. | |
| 737 string prefix("Net.QuicSession.21CumulativePacketsReceived_"); | |
| 738 return base::LinearHistogram::FactoryGet( | |
| 739 prefix + which_21 + connection_description_, 1, | |
| 740 kBoundingSampleInCumulativeHistogram, | |
| 741 kBoundingSampleInCumulativeHistogram + 1, | |
| 742 base::HistogramBase::kUmaTargetedHistogramFlag); | |
| 743 } | |
| 744 | |
| 745 // static | |
| 746 void QuicConnectionLogger::AddTo21CumulativeHistogram( | |
| 747 base::HistogramBase* histogram, | |
| 748 int bit_mask_of_packets, | |
| 749 int valid_bits_in_mask) { | |
| 750 DCHECK_LE(valid_bits_in_mask, 21); | |
| 751 DCHECK_LT(bit_mask_of_packets, 1 << 21); | |
| 752 const int blank_bits_in_mask = 21 - valid_bits_in_mask; | |
| 753 DCHECK_EQ(bit_mask_of_packets & ((1 << blank_bits_in_mask) - 1), 0); | |
| 754 bit_mask_of_packets >>= blank_bits_in_mask; | |
| 755 int bits_so_far = 0; | |
| 756 int range_start = 0; | |
| 757 for (int i = 1; i <= valid_bits_in_mask; ++i) { | |
| 758 bits_so_far += bit_mask_of_packets & 1; | |
| 759 bit_mask_of_packets >>= 1; | |
| 760 DCHECK_LT(range_start + bits_so_far, kBoundingSampleInCumulativeHistogram); | |
| 761 histogram->Add(range_start + bits_so_far); | |
| 762 range_start += i + 1; | |
| 763 } | |
| 764 } | |
| 765 | |
| 766 float QuicConnectionLogger::ReceivedPacketLossRate() const { | 707 float QuicConnectionLogger::ReceivedPacketLossRate() const { |
| 767 if (largest_received_packet_number_ <= num_packets_received_) | 708 if (largest_received_packet_number_ <= num_packets_received_) |
| 768 return 0.0f; | 709 return 0.0f; |
| 769 float num_received = largest_received_packet_number_ - num_packets_received_; | 710 float num_received = largest_received_packet_number_ - num_packets_received_; |
| 770 return num_received / largest_received_packet_number_; | 711 return num_received / largest_received_packet_number_; |
| 771 } | 712 } |
| 772 | 713 |
| 773 void QuicConnectionLogger::OnRttChanged(QuicTime::Delta rtt) const { | 714 void QuicConnectionLogger::OnRttChanged(QuicTime::Delta rtt) const { |
| 774 // Notify socket performance watcher of the updated RTT value. | 715 // Notify socket performance watcher of the updated RTT value. |
| 775 if (!socket_performance_watcher_) | 716 if (!socket_performance_watcher_) |
| (...skipping 30 matching lines...) Expand all Loading... |
| 806 RecordAggregatePacketLossRate(); | 747 RecordAggregatePacketLossRate(); |
| 807 | 748 |
| 808 base::HistogramBase* is_not_ack_histogram = | 749 base::HistogramBase* is_not_ack_histogram = |
| 809 GetPacketNumberHistogram("IsNotAck_"); | 750 GetPacketNumberHistogram("IsNotAck_"); |
| 810 base::HistogramBase* is_an_ack_histogram = | 751 base::HistogramBase* is_an_ack_histogram = |
| 811 GetPacketNumberHistogram("IsAnAck_"); | 752 GetPacketNumberHistogram("IsAnAck_"); |
| 812 base::HistogramBase* packet_arrived_histogram = | 753 base::HistogramBase* packet_arrived_histogram = |
| 813 GetPacketNumberHistogram("Ack_"); | 754 GetPacketNumberHistogram("Ack_"); |
| 814 base::HistogramBase* packet_missing_histogram = | 755 base::HistogramBase* packet_missing_histogram = |
| 815 GetPacketNumberHistogram("Nack_"); | 756 GetPacketNumberHistogram("Nack_"); |
| 816 base::HistogramBase* ongoing_cumulative_packet_histogram = | |
| 817 Get21CumulativeHistogram("Some21s_"); | |
| 818 base::HistogramBase* first_cumulative_packet_histogram = | |
| 819 Get21CumulativeHistogram("First21_"); | |
| 820 base::HistogramBase* six_packet_histogram = Get6PacketHistogram("Some6s_"); | |
| 821 | 757 |
| 822 DCHECK_EQ(received_packets_.size(), received_acks_.size()); | 758 DCHECK_EQ(received_packets_.size(), received_acks_.size()); |
| 823 const QuicPacketNumber last_index = std::min<QuicPacketNumber>( | 759 const QuicPacketNumber last_index = std::min<QuicPacketNumber>( |
| 824 received_packets_.size() - 1, largest_received_packet_number_); | 760 received_packets_.size() - 1, largest_received_packet_number_); |
| 825 const QuicPacketNumber index_of_first_21_contribution = | |
| 826 std::min<QuicPacketNumber>(21, last_index); | |
| 827 // Bit pattern of consecutively received packets that is maintained as we scan | 761 // Bit pattern of consecutively received packets that is maintained as we scan |
| 828 // through the received_packets_ vector. Less significant bits correspond to | 762 // through the received_packets_ vector. Less significant bits correspond to |
| 829 // less recent packets, and only the low order 21 bits are ever defined. | 763 // less recent packets, and only the low order 21 bits are ever defined. |
| 830 // Bit is 1 iff corresponding packet was received. | 764 // Bit is 1 iff corresponding packet was received. |
| 831 int packet_pattern_21 = 0; | 765 int packet_pattern_21 = 0; |
| 832 // Zero is an invalid packet sequence number. | 766 // Zero is an invalid packet sequence number. |
| 833 DCHECK(!received_packets_[0]); | 767 DCHECK(!received_packets_[0]); |
| 834 for (size_t i = 1; i <= last_index; ++i) { | 768 for (size_t i = 1; i <= last_index; ++i) { |
| 835 if (received_acks_[i]) | 769 if (received_acks_[i]) |
| 836 is_an_ack_histogram->Add(i); | 770 is_an_ack_histogram->Add(i); |
| 837 else | 771 else |
| 838 is_not_ack_histogram->Add(i); | 772 is_not_ack_histogram->Add(i); |
| 839 | 773 |
| 840 packet_pattern_21 >>= 1; | 774 packet_pattern_21 >>= 1; |
| 841 if (received_packets_[i]) { | 775 if (received_packets_[i]) { |
| 842 packet_arrived_histogram->Add(i); | 776 packet_arrived_histogram->Add(i); |
| 843 packet_pattern_21 |= (1 << 20); // Turn on the 21st bit. | 777 packet_pattern_21 |= (1 << 20); // Turn on the 21st bit. |
| 844 } else { | 778 } else { |
| 845 packet_missing_histogram->Add(i); | 779 packet_missing_histogram->Add(i); |
| 846 } | 780 } |
| 847 | 781 |
| 848 if (i == index_of_first_21_contribution) { | |
| 849 AddTo21CumulativeHistogram(first_cumulative_packet_histogram, | |
| 850 packet_pattern_21, i); | |
| 851 } | |
| 852 // We'll just record for non-overlapping ranges, to reduce histogramming | |
| 853 // cost for now. Each call does 21 separate histogram additions. | |
| 854 if (i > 21 || i % 21 == 0) { | |
| 855 AddTo21CumulativeHistogram(ongoing_cumulative_packet_histogram, | |
| 856 packet_pattern_21, 21); | |
| 857 } | |
| 858 | |
| 859 if (i < 6) | 782 if (i < 6) |
| 860 continue; // Not enough packets to do any pattern recording. | 783 continue; // Not enough packets to do any pattern recording. |
| 861 int recent_6_mask = packet_pattern_21 >> 15; | 784 int recent_6_mask = packet_pattern_21 >> 15; |
| 862 DCHECK_LT(recent_6_mask, 64); | 785 DCHECK_LT(recent_6_mask, 64); |
| 863 if (i == 6) { | 786 if (i == 6) { |
| 864 Get6PacketHistogram("First6_")->Add(recent_6_mask); | |
| 865 continue; | 787 continue; |
| 866 } | 788 } |
| 867 // Record some overlapping patterns, to get a better picture, since this is | |
| 868 // not very expensive. | |
| 869 if (i % 3 == 0) | |
| 870 six_packet_histogram->Add(recent_6_mask); | |
| 871 } | 789 } |
| 872 } | 790 } |
| 873 | 791 |
| 874 } // namespace net | 792 } // namespace net |
| OLD | NEW |