OLD | NEW |
1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 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 "chrome/browser/safe_browsing/certificate_reporting_service.h" | 4 #include "chrome/browser/safe_browsing/certificate_reporting_service.h" |
5 | 5 |
6 #include "base/bind_helpers.h" | 6 #include "base/bind_helpers.h" |
7 #include "base/metrics/histogram_macros.h" | 7 #include "base/metrics/histogram_macros.h" |
8 #include "base/metrics/sparse_histogram.h" | 8 #include "base/metrics/sparse_histogram.h" |
9 #include "base/time/clock.h" | 9 #include "base/time/clock.h" |
10 #include "chrome/browser/browser_process.h" | 10 #include "chrome/browser/browser_process.h" |
(...skipping 19 matching lines...) Expand all Loading... |
30 const CertificateReportingService::Report& item2) { | 30 const CertificateReportingService::Report& item2) { |
31 return item1.creation_time > item2.creation_time; | 31 return item1.creation_time > item2.creation_time; |
32 } | 32 } |
33 | 33 |
34 // Records an UMA histogram of the net errors when certificate reports | 34 // Records an UMA histogram of the net errors when certificate reports |
35 // fail to send. | 35 // fail to send. |
36 void RecordUMAOnFailure(int net_error) { | 36 void RecordUMAOnFailure(int net_error) { |
37 UMA_HISTOGRAM_SPARSE_SLOWLY("SSL.CertificateErrorReportFailure", -net_error); | 37 UMA_HISTOGRAM_SPARSE_SLOWLY("SSL.CertificateErrorReportFailure", -net_error); |
38 } | 38 } |
39 | 39 |
40 void RecordUMAEvent(CertificateReportingService::ReportOutcome outcome) { | |
41 UMA_HISTOGRAM_ENUMERATION(CertificateReportingService::kReportEventHistogram, | |
42 outcome, | |
43 CertificateReportingService::REPORT_EVENT_COUNT); | |
44 } | |
45 | |
46 void CleanupOnIOThread( | 40 void CleanupOnIOThread( |
47 std::unique_ptr<CertificateReportingService::Reporter> reporter) { | 41 std::unique_ptr<CertificateReportingService::Reporter> reporter) { |
48 reporter.reset(); | 42 reporter.reset(); |
49 } | 43 } |
50 | 44 |
51 } // namespace | 45 } // namespace |
52 | 46 |
53 const char CertificateReportingService::kReportEventHistogram[] = | |
54 "SSL.CertificateErrorReportEvent"; | |
55 | |
56 CertificateReportingService::BoundedReportList::BoundedReportList( | 47 CertificateReportingService::BoundedReportList::BoundedReportList( |
57 size_t max_size) | 48 size_t max_size) |
58 : max_size_(max_size) { | 49 : max_size_(max_size) { |
59 CHECK(max_size <= 20) | 50 CHECK(max_size <= 20) |
60 << "Current implementation is not efficient for a large list."; | 51 << "Current implementation is not efficient for a large list."; |
61 DCHECK(thread_checker_.CalledOnValidThread()); | 52 DCHECK(thread_checker_.CalledOnValidThread()); |
62 } | 53 } |
63 | 54 |
64 CertificateReportingService::BoundedReportList::~BoundedReportList() {} | 55 CertificateReportingService::BoundedReportList::~BoundedReportList() {} |
65 | 56 |
66 void CertificateReportingService::BoundedReportList::Add(const Report& item) { | 57 void CertificateReportingService::BoundedReportList::Add(const Report& item) { |
67 DCHECK(thread_checker_.CalledOnValidThread()); | 58 DCHECK(thread_checker_.CalledOnValidThread()); |
68 DCHECK(items_.size() <= max_size_); | 59 DCHECK(items_.size() <= max_size_); |
69 if (items_.size() == max_size_) { | 60 if (items_.size() == max_size_) { |
70 const Report& last = items_.back(); | 61 const Report& last = items_.back(); |
71 if (item.creation_time <= last.creation_time) { | 62 if (item.creation_time <= last.creation_time) { |
72 // Report older than the oldest item in the queue, ignore. | 63 // Report older than the oldest item in the queue, ignore. |
73 RecordUMAEvent(REPORT_DROPPED_OR_IGNORED); | |
74 return; | 64 return; |
75 } | 65 } |
76 // Reached the maximum item count, remove the oldest item. | 66 // Reached the maximum item count, remove the oldest item. |
77 items_.pop_back(); | 67 items_.pop_back(); |
78 RecordUMAEvent(REPORT_DROPPED_OR_IGNORED); | |
79 } | 68 } |
80 items_.push_back(item); | 69 items_.push_back(item); |
81 std::sort(items_.begin(), items_.end(), ReportCompareFunc); | 70 std::sort(items_.begin(), items_.end(), ReportCompareFunc); |
82 } | 71 } |
83 | 72 |
84 void CertificateReportingService::BoundedReportList::Clear() { | 73 void CertificateReportingService::BoundedReportList::Clear() { |
85 items_.clear(); | 74 items_.clear(); |
86 } | 75 } |
87 | 76 |
88 const std::vector<CertificateReportingService::Report>& | 77 const std::vector<CertificateReportingService::Report>& |
(...skipping 29 matching lines...) Expand all Loading... |
118 if (!retries_enabled_) { | 107 if (!retries_enabled_) { |
119 return; | 108 return; |
120 } | 109 } |
121 const base::Time now = clock_->Now(); | 110 const base::Time now = clock_->Now(); |
122 // Copy pending reports and clear the retry list. | 111 // Copy pending reports and clear the retry list. |
123 std::vector<Report> items = retry_list_->items(); | 112 std::vector<Report> items = retry_list_->items(); |
124 retry_list_->Clear(); | 113 retry_list_->Clear(); |
125 for (Report& report : items) { | 114 for (Report& report : items) { |
126 if (report.creation_time < now - report_ttl_) { | 115 if (report.creation_time < now - report_ttl_) { |
127 // Report too old, ignore. | 116 // Report too old, ignore. |
128 RecordUMAEvent(REPORT_DROPPED_OR_IGNORED); | |
129 continue; | 117 continue; |
130 } | 118 } |
131 if (!report.is_retried) { | 119 if (!report.is_retried) { |
132 // If this is the first retry, deserialize the report, set its retry bit | 120 // If this is the first retry, deserialize the report, set its retry bit |
133 // and serialize again. | 121 // and serialize again. |
134 certificate_reporting::ErrorReport error_report; | 122 certificate_reporting::ErrorReport error_report; |
135 CHECK(error_report.InitializeFromString(report.serialized_report)); | 123 CHECK(error_report.InitializeFromString(report.serialized_report)); |
136 error_report.SetIsRetryUpload(true); | 124 error_report.SetIsRetryUpload(true); |
137 CHECK(error_report.Serialize(&report.serialized_report)); | 125 CHECK(error_report.Serialize(&report.serialized_report)); |
138 } | 126 } |
(...skipping 10 matching lines...) Expand all Loading... |
149 | 137 |
150 CertificateReportingService::BoundedReportList* | 138 CertificateReportingService::BoundedReportList* |
151 CertificateReportingService::Reporter::GetQueueForTesting() const { | 139 CertificateReportingService::Reporter::GetQueueForTesting() const { |
152 return retry_list_.get(); | 140 return retry_list_.get(); |
153 } | 141 } |
154 | 142 |
155 void CertificateReportingService::Reporter::SendInternal( | 143 void CertificateReportingService::Reporter::SendInternal( |
156 const CertificateReportingService::Report& report) { | 144 const CertificateReportingService::Report& report) { |
157 DCHECK_CURRENTLY_ON(content::BrowserThread::IO); | 145 DCHECK_CURRENTLY_ON(content::BrowserThread::IO); |
158 inflight_reports_.insert(std::make_pair(report.report_id, report)); | 146 inflight_reports_.insert(std::make_pair(report.report_id, report)); |
159 RecordUMAEvent(REPORT_SUBMITTED); | |
160 error_reporter_->SendExtendedReportingReport( | 147 error_reporter_->SendExtendedReportingReport( |
161 report.serialized_report, | 148 report.serialized_report, |
162 base::Bind(&CertificateReportingService::Reporter::SuccessCallback, | 149 base::Bind(&CertificateReportingService::Reporter::SuccessCallback, |
163 weak_factory_.GetWeakPtr(), report.report_id), | 150 weak_factory_.GetWeakPtr(), report.report_id), |
164 base::Bind(&CertificateReportingService::Reporter::ErrorCallback, | 151 base::Bind(&CertificateReportingService::Reporter::ErrorCallback, |
165 weak_factory_.GetWeakPtr(), report.report_id)); | 152 weak_factory_.GetWeakPtr(), report.report_id)); |
166 } | 153 } |
167 | 154 |
168 void CertificateReportingService::Reporter::ErrorCallback( | 155 void CertificateReportingService::Reporter::ErrorCallback( |
169 int report_id, | 156 int report_id, |
170 const GURL& url, | 157 const GURL& url, |
171 int net_error, | 158 int net_error, |
172 int http_response_code) { | 159 int http_response_code) { |
173 DCHECK_CURRENTLY_ON(content::BrowserThread::IO); | 160 DCHECK_CURRENTLY_ON(content::BrowserThread::IO); |
174 RecordUMAOnFailure(net_error); | 161 RecordUMAOnFailure(net_error); |
175 RecordUMAEvent(REPORT_FAILED); | |
176 if (retries_enabled_) { | 162 if (retries_enabled_) { |
177 auto it = inflight_reports_.find(report_id); | 163 auto it = inflight_reports_.find(report_id); |
178 DCHECK(it != inflight_reports_.end()); | 164 DCHECK(it != inflight_reports_.end()); |
179 retry_list_->Add(it->second); | 165 retry_list_->Add(it->second); |
180 } | 166 } |
181 CHECK_GT(inflight_reports_.erase(report_id), 0u); | 167 CHECK_GT(inflight_reports_.erase(report_id), 0u); |
182 } | 168 } |
183 | 169 |
184 void CertificateReportingService::Reporter::SuccessCallback(int report_id) { | 170 void CertificateReportingService::Reporter::SuccessCallback(int report_id) { |
185 DCHECK_CURRENTLY_ON(content::BrowserThread::IO); | 171 DCHECK_CURRENTLY_ON(content::BrowserThread::IO); |
186 RecordUMAEvent(REPORT_SUCCESSFUL); | |
187 CHECK_GT(inflight_reports_.erase(report_id), 0u); | 172 CHECK_GT(inflight_reports_.erase(report_id), 0u); |
188 } | 173 } |
189 | 174 |
190 CertificateReportingService::CertificateReportingService( | 175 CertificateReportingService::CertificateReportingService( |
191 safe_browsing::SafeBrowsingService* safe_browsing_service, | 176 safe_browsing::SafeBrowsingService* safe_browsing_service, |
192 scoped_refptr<net::URLRequestContextGetter> url_request_context_getter, | 177 scoped_refptr<net::URLRequestContextGetter> url_request_context_getter, |
193 Profile* profile, | 178 Profile* profile, |
194 uint8_t server_public_key[/* 32 */], | 179 uint8_t server_public_key[/* 32 */], |
195 uint32_t server_public_key_version, | 180 uint32_t server_public_key_version, |
196 size_t max_queued_report_count, | 181 size_t max_queued_report_count, |
(...skipping 140 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
337 } | 322 } |
338 | 323 |
339 void CertificateReportingService::OnPreferenceChanged() { | 324 void CertificateReportingService::OnPreferenceChanged() { |
340 safe_browsing::SafeBrowsingService* safe_browsing_service_ = | 325 safe_browsing::SafeBrowsingService* safe_browsing_service_ = |
341 g_browser_process->safe_browsing_service(); | 326 g_browser_process->safe_browsing_service(); |
342 const bool enabled = safe_browsing_service_ && | 327 const bool enabled = safe_browsing_service_ && |
343 safe_browsing_service_->enabled_by_prefs() && | 328 safe_browsing_service_->enabled_by_prefs() && |
344 safe_browsing::IsExtendedReportingEnabled(pref_service_); | 329 safe_browsing::IsExtendedReportingEnabled(pref_service_); |
345 SetEnabled(enabled); | 330 SetEnabled(enabled); |
346 } | 331 } |
OLD | NEW |