| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 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 #include "net/spdy/hpack_huffman_aggregator.h" | 4 #include "net/spdy/hpack_huffman_aggregator.h" |
| 5 | 5 |
| 6 #include "base/metrics/bucket_ranges.h" | 6 #include "base/metrics/bucket_ranges.h" |
| 7 #include "base/metrics/field_trial.h" | 7 #include "base/metrics/field_trial.h" |
| 8 #include "base/metrics/histogram.h" | 8 #include "base/metrics/histogram.h" |
| 9 #include "base/metrics/sample_vector.h" | 9 #include "base/metrics/sample_vector.h" |
| 10 #include "base/stl_util.h" | 10 #include "base/stl_util.h" |
| (...skipping 13 matching lines...) Expand all Loading... |
| 24 const char kHistogramName[] = "Net.SpdyHpackEncodedCharacterFrequency"; | 24 const char kHistogramName[] = "Net.SpdyHpackEncodedCharacterFrequency"; |
| 25 | 25 |
| 26 const size_t kTotalCountsPublishThreshold = 50000; | 26 const size_t kTotalCountsPublishThreshold = 50000; |
| 27 | 27 |
| 28 // Each encoder uses the default dynamic table size of 4096 total bytes. | 28 // Each encoder uses the default dynamic table size of 4096 total bytes. |
| 29 const size_t kMaxEncoders = 20; | 29 const size_t kMaxEncoders = 20; |
| 30 | 30 |
| 31 } // namespace | 31 } // namespace |
| 32 | 32 |
| 33 HpackHuffmanAggregator::HpackHuffmanAggregator() | 33 HpackHuffmanAggregator::HpackHuffmanAggregator() |
| 34 : counts_(256, 0), | 34 : counts_(256, 0), total_counts_(0), max_encoders_(kMaxEncoders) { |
| 35 total_counts_(0), | |
| 36 max_encoders_(kMaxEncoders) { | |
| 37 } | 35 } |
| 38 | 36 |
| 39 HpackHuffmanAggregator::~HpackHuffmanAggregator() { | 37 HpackHuffmanAggregator::~HpackHuffmanAggregator() { |
| 40 STLDeleteContainerPairSecondPointers(encoders_.begin(), encoders_.end()); | 38 STLDeleteContainerPairSecondPointers(encoders_.begin(), encoders_.end()); |
| 41 encoders_.clear(); | 39 encoders_.clear(); |
| 42 } | 40 } |
| 43 | 41 |
| 44 void HpackHuffmanAggregator::AggregateTransactionCharacterCounts( | 42 void HpackHuffmanAggregator::AggregateTransactionCharacterCounts( |
| 45 const HttpRequestInfo& request, | 43 const HttpRequestInfo& request, |
| 46 const HttpRequestHeaders& request_headers, | 44 const HttpRequestHeaders& request_headers, |
| 47 const ProxyServer& proxy, | 45 const ProxyServer& proxy, |
| 48 const HttpResponseHeaders& response_headers) { | 46 const HttpResponseHeaders& response_headers) { |
| 49 if (IsCrossOrigin(request)) { | 47 if (IsCrossOrigin(request)) { |
| 50 return; | 48 return; |
| 51 } | 49 } |
| 52 HostPortPair endpoint = HostPortPair(request.url.HostNoBrackets(), | 50 HostPortPair endpoint = HostPortPair(request.url.HostNoBrackets(), |
| 53 request.url.EffectiveIntPort()); | 51 request.url.EffectiveIntPort()); |
| 54 HpackEncoder* encoder = ObtainEncoder( | 52 HpackEncoder* encoder = |
| 55 SpdySessionKey(endpoint, proxy, request.privacy_mode)); | 53 ObtainEncoder(SpdySessionKey(endpoint, proxy, request.privacy_mode)); |
| 56 | 54 |
| 57 // Convert and encode the request and response header sets. | 55 // Convert and encode the request and response header sets. |
| 58 { | 56 { |
| 59 SpdyHeaderBlock headers; | 57 SpdyHeaderBlock headers; |
| 60 CreateSpdyHeadersFromHttpRequest( | 58 CreateSpdyHeadersFromHttpRequest( |
| 61 request, request_headers, &headers, SPDY4, false); | 59 request, request_headers, &headers, SPDY4, false); |
| 62 | 60 |
| 63 std::string tmp_out; | 61 std::string tmp_out; |
| 64 encoder->EncodeHeaderSet(headers, &tmp_out); | 62 encoder->EncodeHeaderSet(headers, &tmp_out); |
| 65 } | 63 } |
| (...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 111 HostPortPair endpoint = HostPortPair(request.url.HostNoBrackets(), | 109 HostPortPair endpoint = HostPortPair(request.url.HostNoBrackets(), |
| 112 request.url.EffectiveIntPort()); | 110 request.url.EffectiveIntPort()); |
| 113 if ((request.load_flags & LOAD_MAIN_FRAME) == 0) { | 111 if ((request.load_flags & LOAD_MAIN_FRAME) == 0) { |
| 114 std::string referer_str; | 112 std::string referer_str; |
| 115 if (!request.extra_headers.GetHeader(HttpRequestHeaders::kReferer, | 113 if (!request.extra_headers.GetHeader(HttpRequestHeaders::kReferer, |
| 116 &referer_str)) { | 114 &referer_str)) { |
| 117 // Require a referer. | 115 // Require a referer. |
| 118 return true; | 116 return true; |
| 119 } | 117 } |
| 120 GURL referer(referer_str); | 118 GURL referer(referer_str); |
| 121 HostPortPair referer_endpoint = HostPortPair(referer.HostNoBrackets(), | 119 HostPortPair referer_endpoint = |
| 122 referer.EffectiveIntPort()); | 120 HostPortPair(referer.HostNoBrackets(), referer.EffectiveIntPort()); |
| 123 if (!endpoint.Equals(referer_endpoint)) { | 121 if (!endpoint.Equals(referer_endpoint)) { |
| 124 // Cross-origin request. | 122 // Cross-origin request. |
| 125 return true; | 123 return true; |
| 126 } | 124 } |
| 127 } | 125 } |
| 128 return false; | 126 return false; |
| 129 } | 127 } |
| 130 | 128 |
| 131 HpackEncoder* HpackHuffmanAggregator::ObtainEncoder(const SpdySessionKey& key) { | 129 HpackEncoder* HpackHuffmanAggregator::ObtainEncoder(const SpdySessionKey& key) { |
| 132 for (OriginEncoders::iterator it = encoders_.begin(); | 130 for (OriginEncoders::iterator it = encoders_.begin(); it != encoders_.end(); |
| 133 it != encoders_.end(); ++it) { | 131 ++it) { |
| 134 if (key.Equals(it->first)) { | 132 if (key.Equals(it->first)) { |
| 135 // Move to head of list and return. | 133 // Move to head of list and return. |
| 136 OriginEncoder origin_encoder = *it; | 134 OriginEncoder origin_encoder = *it; |
| 137 encoders_.erase(it); | 135 encoders_.erase(it); |
| 138 encoders_.push_front(origin_encoder); | 136 encoders_.push_front(origin_encoder); |
| 139 return origin_encoder.second; | 137 return origin_encoder.second; |
| 140 } | 138 } |
| 141 } | 139 } |
| 142 // Not found. Create a new encoder, evicting one if needed. | 140 // Not found. Create a new encoder, evicting one if needed. |
| 143 encoders_.push_front(std::make_pair( | 141 encoders_.push_front( |
| 144 key, new HpackEncoder(ObtainHpackHuffmanTable()))); | 142 std::make_pair(key, new HpackEncoder(ObtainHpackHuffmanTable()))); |
| 145 if (encoders_.size() > max_encoders_) { | 143 if (encoders_.size() > max_encoders_) { |
| 146 delete encoders_.back().second; | 144 delete encoders_.back().second; |
| 147 encoders_.pop_back(); | 145 encoders_.pop_back(); |
| 148 } | 146 } |
| 149 encoders_.front().second->SetCharCountsStorage(&counts_, &total_counts_); | 147 encoders_.front().second->SetCharCountsStorage(&counts_, &total_counts_); |
| 150 return encoders_.front().second; | 148 return encoders_.front().second; |
| 151 } | 149 } |
| 152 | 150 |
| 153 void HpackHuffmanAggregator::PublishCounts() { | 151 void HpackHuffmanAggregator::PublishCounts() { |
| 154 // base::Histogram requires that values be 1-indexed. | 152 // base::Histogram requires that values be 1-indexed. |
| (...skipping 10 matching lines...) Expand all Loading... |
| 165 // Copy |counts_| into a SampleVector. | 163 // Copy |counts_| into a SampleVector. |
| 166 base::SampleVector samples(&ranges); | 164 base::SampleVector samples(&ranges); |
| 167 for (size_t i = 0; i != counts_.size(); ++i) { | 165 for (size_t i = 0; i != counts_.size(); ++i) { |
| 168 samples.Accumulate(i + 1, counts_[i]); | 166 samples.Accumulate(i + 1, counts_[i]); |
| 169 } | 167 } |
| 170 | 168 |
| 171 STATIC_HISTOGRAM_POINTER_BLOCK( | 169 STATIC_HISTOGRAM_POINTER_BLOCK( |
| 172 kHistogramName, | 170 kHistogramName, |
| 173 AddSamples(samples), | 171 AddSamples(samples), |
| 174 base::LinearHistogram::FactoryGet( | 172 base::LinearHistogram::FactoryGet( |
| 175 kHistogramName, kRangeMin, kRangeMax, kBucketCount, | 173 kHistogramName, |
| 174 kRangeMin, |
| 175 kRangeMax, |
| 176 kBucketCount, |
| 176 base::HistogramBase::kUmaTargetedHistogramFlag)); | 177 base::HistogramBase::kUmaTargetedHistogramFlag)); |
| 177 | 178 |
| 178 // Clear counts. | 179 // Clear counts. |
| 179 counts_.assign(counts_.size(), 0); | 180 counts_.assign(counts_.size(), 0); |
| 180 total_counts_ = 0; | 181 total_counts_ = 0; |
| 181 } | 182 } |
| 182 | 183 |
| 183 } // namespace net | 184 } // namespace net |
| OLD | NEW |