blob: b3a573603ff727d99ae100e86c4555dd56b34476 [file] [log] [blame]
[email protected]03ef4b2a2012-03-06 15:04:201// Copyright (c) 2012 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
[email protected]4237dd52012-06-05 00:00:325#include "chrome/browser/ui/website_settings/website_settings.h"
[email protected]03ef4b2a2012-03-06 15:04:206
7#include <string>
8#include <vector>
9
[email protected]15b092542012-05-16 13:08:1410#include "base/bind.h"
11#include "base/bind_helpers.h"
[email protected]eb2140c2013-07-29 12:37:3412#include "base/command_line.h"
[email protected]15b092542012-05-16 13:08:1413#include "base/i18n/time_formatting.h"
[email protected]71cd5ef2014-08-13 21:22:0414#include "base/metrics/field_trial.h"
[email protected]3ea1b182013-02-08 22:38:4115#include "base/metrics/histogram.h"
16#include "base/strings/string_number_conversions.h"
[email protected]774cc3c2013-06-07 20:26:4517#include "base/strings/utf_string_conversions.h"
[email protected]0b9fdd72012-04-04 10:00:3318#include "base/values.h"
[email protected]6b8a3c742014-07-25 00:25:3519#include "chrome/browser/browsing_data/browsing_data_channel_id_helper.h"
[email protected]b0cb5e82012-07-19 19:22:4720#include "chrome/browser/browsing_data/browsing_data_cookie_helper.h"
21#include "chrome/browser/browsing_data/browsing_data_database_helper.h"
22#include "chrome/browser/browsing_data/browsing_data_file_system_helper.h"
23#include "chrome/browser/browsing_data/browsing_data_indexed_db_helper.h"
24#include "chrome/browser/browsing_data/browsing_data_local_storage_helper.h"
[email protected]77a91c72012-08-13 16:19:3425#include "chrome/browser/history/history_service_factory.h"
[email protected]03ef4b2a2012-03-06 15:04:2026#include "chrome/browser/profiles/profile.h"
[email protected]71cd5ef2014-08-13 21:22:0427#include "chrome/browser/ssl/chrome_ssl_host_state_delegate.h"
28#include "chrome/browser/ssl/chrome_ssl_host_state_delegate_factory.h"
[email protected]03ef4b2a2012-03-06 15:04:2029#include "chrome/browser/ssl/ssl_error_info.h"
[email protected]66f157312012-08-01 13:50:2630#include "chrome/browser/ui/website_settings/website_settings_infobar_delegate.h"
[email protected]4237dd52012-06-05 00:00:3231#include "chrome/browser/ui/website_settings/website_settings_ui.h"
[email protected]71cd5ef2014-08-13 21:22:0432#include "chrome/common/chrome_switches.h"
thestig884a1602014-08-27 01:29:3933#include "chrome/grit/chromium_strings.h"
34#include "chrome/grit/generated_resources.h"
mukai8eaec822014-10-25 17:53:1635#include "components/content_settings/core/browser/content_settings_utils.h"
36#include "components/content_settings/core/browser/host_content_settings_map.h"
vabr48565592014-10-08 15:06:0237#include "components/content_settings/core/browser/local_shared_objects_counter.h"
palmer0da10b32015-02-11 00:42:1938#include "components/content_settings/core/common/content_settings.h"
vasiliif62dbf92014-09-05 10:23:1339#include "components/content_settings/core/common/content_settings_pattern.h"
[email protected]0b9fdd72012-04-04 10:00:3340#include "content/public/browser/browser_thread.h"
[email protected]b59c6cf02012-03-12 20:51:4241#include "content/public/browser/cert_store.h"
[email protected]e22d64f2012-09-10 09:03:2342#include "content/public/browser/user_metrics.h"
[email protected]eb2140c2013-07-29 12:37:3443#include "content/public/common/content_switches.h"
[email protected]03ef4b2a2012-03-06 15:04:2044#include "content/public/common/ssl_status.h"
45#include "content/public/common/url_constants.h"
[email protected]be28b5f42012-07-20 11:31:2546#include "net/base/registry_controlled_domains/registry_controlled_domain.h"
[email protected]6e7845ae2013-03-29 21:48:1147#include "net/cert/cert_status_flags.h"
48#include "net/cert/x509_certificate.h"
[email protected]536fd0b2013-03-14 17:41:5749#include "net/ssl/ssl_cipher_suite_names.h"
50#include "net/ssl/ssl_connection_status_flags.h"
[email protected]03ef4b2a2012-03-06 15:04:2051#include "ui/base/l10n/l10n_util.h"
[email protected]03ef4b2a2012-03-06 15:04:2052
[email protected]24a9f1c92013-11-13 12:33:3753#if defined(OS_CHROMEOS)
54#include "chrome/browser/chromeos/policy/policy_cert_service.h"
55#include "chrome/browser/chromeos/policy/policy_cert_service_factory.h"
56#endif
57
[email protected]ab6df3b12013-12-24 23:32:2658using base::ASCIIToUTF16;
59using base::UTF8ToUTF16;
[email protected]f729d7a2013-12-26 07:07:5660using base::UTF16ToUTF8;
[email protected]0b9fdd72012-04-04 10:00:3361using content::BrowserThread;
62
63namespace {
64
jww1ed8ea72014-09-02 20:43:2565// Events for UMA. Do not reorder or change!
66enum SSLCertificateDecisionsDidRevoke {
67 USER_CERT_DECISIONS_NOT_REVOKED = 0,
68 USER_CERT_DECISIONS_REVOKED,
69 END_OF_SSL_CERTIFICATE_DECISIONS_DID_REVOKE_ENUM
70};
71
palmer0da10b32015-02-11 00:42:1972// The list of content settings types to display on the Website Settings UI. THE
73// ORDER OF THESE ITEMS IS IMPORTANT. To propose changing it, email
74// [email protected].
[email protected]0b9fdd72012-04-04 10:00:3375ContentSettingsType kPermissionType[] = {
sashab2b2a314f2015-01-17 06:42:2176 CONTENT_SETTINGS_TYPE_GEOLOCATION,
sashab2b2a314f2015-01-17 06:42:2177 CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA,
78 CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC,
palmer0da10b32015-02-11 00:42:1979 CONTENT_SETTINGS_TYPE_NOTIFICATIONS,
80 CONTENT_SETTINGS_TYPE_IMAGES,
81 CONTENT_SETTINGS_TYPE_JAVASCRIPT,
82 CONTENT_SETTINGS_TYPE_POPUPS,
83 CONTENT_SETTINGS_TYPE_FULLSCREEN,
sashab2b2a314f2015-01-17 06:42:2184 CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS,
palmer0da10b32015-02-11 00:42:1985 CONTENT_SETTINGS_TYPE_PLUGINS,
86 CONTENT_SETTINGS_TYPE_MOUSELOCK,
sashab2b2a314f2015-01-17 06:42:2187 CONTENT_SETTINGS_TYPE_MIDI_SYSEX,
benwellsa68ed4b2014-11-13 03:25:3688#if defined(OS_ANDROID)
sashab2b2a314f2015-01-17 06:42:2189 CONTENT_SETTINGS_TYPE_PUSH_MESSAGING,
benwellsa68ed4b2014-11-13 03:25:3690#endif
[email protected]0b9fdd72012-04-04 10:00:3391};
92
[email protected]94c74b42013-12-02 15:19:4993bool CertificateTransparencyStatusMatch(
94 const content::SignedCertificateTimestampIDStatusList& scts,
95 net::ct::SCTVerifyStatus status) {
96 for (content::SignedCertificateTimestampIDStatusList::const_iterator it =
97 scts.begin();
98 it != scts.end();
99 ++it) {
100 if (it->status == status)
101 return true;
102 }
103
104 return false;
105}
106
107int GetSiteIdentityDetailsMessageByCTInfo(
108 const content::SignedCertificateTimestampIDStatusList& scts,
109 bool is_ev) {
110 // No SCTs - no CT information.
111 if (scts.empty())
112 return (is_ev ? IDS_PAGE_INFO_SECURITY_TAB_SECURE_IDENTITY_EV_NO_CT
113 : IDS_PAGE_INFO_SECURITY_TAB_SECURE_IDENTITY_NO_CT);
114
115 if (CertificateTransparencyStatusMatch(scts, net::ct::SCT_STATUS_OK))
116 return (is_ev ? IDS_PAGE_INFO_SECURITY_TAB_SECURE_IDENTITY_EV_CT_VERIFIED
117 : IDS_PAGE_INFO_SECURITY_TAB_SECURE_IDENTITY_CT_VERIFIED);
118
119 if (CertificateTransparencyStatusMatch(scts, net::ct::SCT_STATUS_INVALID))
120 return (is_ev ? IDS_PAGE_INFO_SECURITY_TAB_SECURE_IDENTITY_EV_CT_INVALID
121 : IDS_PAGE_INFO_SECURITY_TAB_SECURE_IDENTITY_CT_INVALID);
122
123 // status is SCT_STATUS_LOG_UNKNOWN
124 return (is_ev ? IDS_PAGE_INFO_SECURITY_TAB_SECURE_IDENTITY_EV_CT_UNVERIFIED
125 : IDS_PAGE_INFO_SECURITY_TAB_SECURE_IDENTITY_CT_UNVERIFIED);
126}
127
128// This function will return SITE_IDENTITY_STATUS_CERT or
129// SITE_IDENTITY_STATUS_EV_CERT depending on |is_ev| unless there are SCTs
130// which failed verification, in which case it will return
131// SITE_IDENTITY_STATUS_ERROR.
132WebsiteSettings::SiteIdentityStatus GetSiteIdentityStatusByCTInfo(
133 const content::SignedCertificateTimestampIDStatusList& scts,
134 bool is_ev) {
135 if (CertificateTransparencyStatusMatch(scts, net::ct::SCT_STATUS_INVALID))
136 return WebsiteSettings::SITE_IDENTITY_STATUS_ERROR;
137
138 return is_ev ? WebsiteSettings::SITE_IDENTITY_STATUS_EV_CERT
139 : WebsiteSettings::SITE_IDENTITY_STATUS_CERT;
140}
141
[email protected]71cd5ef2014-08-13 21:22:04142const char kRememberCertificateErrorDecisionsFieldTrialName[] =
143 "RememberCertificateErrorDecisions";
144const char kRememberCertificateErrorDecisionsFieldTrialDefaultGroup[] =
145 "Default";
146const char kRememberCertificateErrorDecisionsFieldTrialDisableGroup[] =
147 "Disable";
148// Returns true if the user is in the experimental group or has the flag enabled
149// for remembering SSL error decisions, otherwise false.
150//
151// TODO(jww): The field trial is scheduled to end 2015/02/28. This should be
152// removed at that point unless the field trial or flag continues.
153bool InRememberCertificateErrorDecisionsGroup() {
154 std::string group_name = base::FieldTrialList::FindFullName(
155 kRememberCertificateErrorDecisionsFieldTrialName);
156
157 // The Default and Disable groups are the "old-style" forget-at-session
158 // restart groups, so they do not get the button.
159 bool in_experimental_group = !group_name.empty() &&
160 group_name.compare(
161 kRememberCertificateErrorDecisionsFieldTrialDefaultGroup) != 0 &&
162 group_name.compare(
163 kRememberCertificateErrorDecisionsFieldTrialDisableGroup) != 0;
avi556c05022014-12-22 23:31:43164 bool has_command_line_switch =
165 base::CommandLine::ForCurrentProcess()->HasSwitch(
166 switches::kRememberCertErrorDecisions);
[email protected]71cd5ef2014-08-13 21:22:04167 return in_experimental_group || has_command_line_switch;
168}
169
[email protected]0b9fdd72012-04-04 10:00:33170} // namespace
171
172WebsiteSettings::WebsiteSettings(
173 WebsiteSettingsUI* ui,
174 Profile* profile,
[email protected]df818272012-04-20 13:10:50175 TabSpecificContentSettings* tab_specific_content_settings,
[email protected]4f822f022012-12-20 19:11:42176 InfoBarService* infobar_service,
[email protected]0b9fdd72012-04-04 10:00:33177 const GURL& url,
178 const content::SSLStatus& ssl,
179 content::CertStore* cert_store)
[email protected]df818272012-04-20 13:10:50180 : TabSpecificContentSettings::SiteDataObserver(
181 tab_specific_content_settings),
182 ui_(ui),
[email protected]4f822f022012-12-20 19:11:42183 infobar_service_(infobar_service),
[email protected]66f157312012-08-01 13:50:26184 show_info_bar_(false),
[email protected]0b9fdd72012-04-04 10:00:33185 site_url_(url),
186 site_identity_status_(SITE_IDENTITY_STATUS_UNKNOWN),
[email protected]f61c1ce2012-05-09 13:55:11187 cert_id_(0),
[email protected]03ef4b2a2012-03-06 15:04:20188 site_connection_status_(SITE_CONNECTION_STATUS_UNKNOWN),
[email protected]0b9fdd72012-04-04 10:00:33189 cert_store_(cert_store),
[email protected]71cd5ef2014-08-13 21:22:04190 content_settings_(profile->GetHostContentSettingsMap()),
191 chrome_ssl_host_state_delegate_(
jww1ed8ea72014-09-02 20:43:25192 ChromeSSLHostStateDelegateFactory::GetForProfile(profile)),
193 did_revoke_user_ssl_decisions_(false) {
[email protected]03ef4b2a2012-03-06 15:04:20194 Init(profile, url, ssl);
[email protected]0b9fdd72012-04-04 10:00:33195
sdefresnec62efa32015-03-12 22:46:31196 history::HistoryService* history_service =
197 HistoryServiceFactory::GetForProfile(profile,
198 ServiceAccessType::EXPLICIT_ACCESS);
[email protected]15b092542012-05-16 13:08:14199 if (history_service) {
200 history_service->GetVisibleVisitCountToHost(
201 site_url_,
[email protected]15b092542012-05-16 13:08:14202 base::Bind(&WebsiteSettings::OnGotVisitCountToHost,
[email protected]e800fe742014-07-01 10:38:19203 base::Unretained(this)),
204 &visit_count_task_tracker_);
[email protected]15b092542012-05-16 13:08:14205 }
206
[email protected]0b9fdd72012-04-04 10:00:33207 PresentSitePermissions();
[email protected]df818272012-04-20 13:10:50208 PresentSiteData();
[email protected]24c8818c2012-04-25 09:57:41209 PresentSiteIdentity();
[email protected]15b092542012-05-16 13:08:14210 PresentHistoryInfo(base::Time());
[email protected]e22d64f2012-09-10 09:03:23211
212 // Every time the Website Settings UI is opened a |WebsiteSettings| object is
213 // created. So this counts how ofter the Website Settings UI is opened.
lgarron04a93502014-11-04 22:25:04214 RecordWebsiteSettingsAction(WEBSITE_SETTINGS_OPENED);
[email protected]03ef4b2a2012-03-06 15:04:20215}
216
[email protected]0b9fdd72012-04-04 10:00:33217WebsiteSettings::~WebsiteSettings() {
[email protected]03ef4b2a2012-03-06 15:04:20218}
219
lgarron04a93502014-11-04 22:25:04220void WebsiteSettings::RecordWebsiteSettingsAction(
221 WebsiteSettingsAction action) {
222 UMA_HISTOGRAM_ENUMERATION("WebsiteSettings.Action",
223 action,
224 WEBSITE_SETTINGS_COUNT);
225
226 // Use a separate histogram to record actions if they are done on a page with
227 // an HTTPS URL. Note that this *disregards* security status.
228 if (site_url_.SchemeIs(url::kHttpsScheme)) {
229 UMA_HISTOGRAM_ENUMERATION("WebsiteSettings.Action.HttpsUrl",
230 action,
231 WEBSITE_SETTINGS_COUNT);
232 }
233}
234
235
[email protected]df818272012-04-20 13:10:50236void WebsiteSettings::OnSitePermissionChanged(ContentSettingsType type,
237 ContentSetting setting) {
[email protected]e22d64f2012-09-10 09:03:23238 // Count how often a permission for a specific content type is changed using
239 // the Website Settings UI.
sashab9debecd2014-12-18 04:15:56240 ContentSettingsTypeHistogram histogram_value =
241 ContentSettingTypeToHistogramValue(type);
242 DCHECK_NE(histogram_value, CONTENT_SETTINGS_TYPE_HISTOGRAM_INVALID)
243 << "Invalid content setting type specified.";
244 UMA_HISTOGRAM_ENUMERATION("WebsiteSettings.OriginInfo.PermissionChanged",
245 histogram_value,
246 CONTENT_SETTINGS_HISTOGRAM_NUM_TYPES);
247
248 if (setting == ContentSetting::CONTENT_SETTING_ALLOW) {
249 UMA_HISTOGRAM_ENUMERATION(
250 "WebsiteSettings.OriginInfo.PermissionChanged.Allowed", histogram_value,
251 CONTENT_SETTINGS_HISTOGRAM_NUM_TYPES);
252 } else if (setting == ContentSetting::CONTENT_SETTING_BLOCK) {
253 UMA_HISTOGRAM_ENUMERATION(
254 "WebsiteSettings.OriginInfo.PermissionChanged.Blocked", histogram_value,
255 CONTENT_SETTINGS_HISTOGRAM_NUM_TYPES);
256 }
[email protected]e22d64f2012-09-10 09:03:23257
lgarron04a93502014-11-04 22:25:04258 // This is technically redundant given the histogram above, but putting the
259 // total count of permission changes in another histogram makes it easier to
260 // compare it against other kinds of actions in WebsiteSettings[PopupView].
261 RecordWebsiteSettingsAction(WEBSITE_SETTINGS_CHANGED_PERMISSION);
262
[email protected]df818272012-04-20 13:10:50263 ContentSettingsPattern primary_pattern;
264 ContentSettingsPattern secondary_pattern;
265 switch (type) {
266 case CONTENT_SETTINGS_TYPE_GEOLOCATION:
[email protected]eb2140c2013-07-29 12:37:34267 case CONTENT_SETTINGS_TYPE_MIDI_SYSEX:
mlamouriab1897c2015-02-18 12:09:32268 case CONTENT_SETTINGS_TYPE_FULLSCREEN:
[email protected]df818272012-04-20 13:10:50269 // TODO(markusheintz): The rule we create here should also change the
270 // location permission for iframed content.
271 primary_pattern = ContentSettingsPattern::FromURLNoWildcard(site_url_);
272 secondary_pattern = ContentSettingsPattern::FromURLNoWildcard(site_url_);
273 break;
274 case CONTENT_SETTINGS_TYPE_NOTIFICATIONS:
275 primary_pattern = ContentSettingsPattern::FromURLNoWildcard(site_url_);
276 secondary_pattern = ContentSettingsPattern::Wildcard();
277 break;
[email protected]b1d113d2012-06-27 21:27:34278 case CONTENT_SETTINGS_TYPE_IMAGES:
279 case CONTENT_SETTINGS_TYPE_JAVASCRIPT:
[email protected]df818272012-04-20 13:10:50280 case CONTENT_SETTINGS_TYPE_PLUGINS:
281 case CONTENT_SETTINGS_TYPE_POPUPS:
[email protected]b1d113d2012-06-27 21:27:34282 case CONTENT_SETTINGS_TYPE_MOUSELOCK:
[email protected]ad635b12013-07-22 21:53:27283 case CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS:
benwellsa68ed4b2014-11-13 03:25:36284 case CONTENT_SETTINGS_TYPE_PUSH_MESSAGING:
[email protected]df818272012-04-20 13:10:50285 primary_pattern = ContentSettingsPattern::FromURL(site_url_);
286 secondary_pattern = ContentSettingsPattern::Wildcard();
287 break;
sashab2b2a314f2015-01-17 06:42:21288 case CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC:
289 case CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA:
[email protected]0bacc1912012-12-11 11:05:34290 primary_pattern = ContentSettingsPattern::FromURLNoWildcard(site_url_);
291 secondary_pattern = ContentSettingsPattern::Wildcard();
[email protected]0bacc1912012-12-11 11:05:34292 break;
[email protected]df818272012-04-20 13:10:50293 default:
294 NOTREACHED() << "ContentSettingsType " << type << "is not supported.";
295 break;
[email protected]0b9fdd72012-04-04 10:00:33296 }
297
[email protected]0bacc1912012-12-11 11:05:34298 // Permission settings are specified via rules. There exists always at least
299 // one rule for the default setting. Get the rule that currently defines
300 // the permission for the given permission |type|. Then test whether the
301 // existing rule is more specific than the rule we are about to create. If
302 // the existing rule is more specific, than change the existing rule instead
303 // of creating a new rule that would be hidden behind the existing rule.
[email protected]0bacc1912012-12-11 11:05:34304 content_settings::SettingInfo info;
dhnishid5770d212014-09-18 21:59:18305 scoped_ptr<base::Value> v =
306 content_settings_->GetWebsiteSettingWithoutOverride(
307 site_url_, site_url_, type, std::string(), &info);
[email protected]6b3552a2014-08-21 21:10:12308 content_settings_->SetNarrowestWebsiteSetting(
309 primary_pattern, secondary_pattern, type, std::string(), setting, info);
[email protected]df818272012-04-20 13:10:50310
[email protected]66f157312012-08-01 13:50:26311 show_info_bar_ = true;
[email protected]2f45d542012-08-22 08:47:24312
[email protected]76955932012-12-06 11:01:10313// TODO(markusheintz): This is a temporary hack to fix issue:
314// http://crbug.com/144203.
[email protected]e379ba42012-08-22 22:40:25315#if defined(OS_MACOSX)
[email protected]2f45d542012-08-22 08:47:24316 // Refresh the UI to reflect the new setting.
317 PresentSitePermissions();
[email protected]e379ba42012-08-22 22:40:25318#endif
[email protected]df818272012-04-20 13:10:50319}
320
[email protected]e800fe742014-07-01 10:38:19321void WebsiteSettings::OnGotVisitCountToHost(bool found_visits,
[email protected]15b092542012-05-16 13:08:14322 int visit_count,
323 base::Time first_visit) {
324 if (!found_visits) {
325 // This indicates an error, such as the page's URL scheme wasn't
326 // http/https.
327 first_visit = base::Time();
328 } else if (visit_count == 0) {
329 first_visit = base::Time::Now();
330 }
331 PresentHistoryInfo(first_visit);
332}
333
[email protected]df818272012-04-20 13:10:50334void WebsiteSettings::OnSiteDataAccessed() {
335 PresentSiteData();
[email protected]0b9fdd72012-04-04 10:00:33336}
337
[email protected]66f157312012-08-01 13:50:26338void WebsiteSettings::OnUIClosing() {
[email protected]0be09932013-01-08 02:03:50339 if (show_info_bar_)
[email protected]ed9bc652013-07-11 17:17:36340 WebsiteSettingsInfoBarDelegate::Create(infobar_service_);
jww1ed8ea72014-09-02 20:43:25341
342 SSLCertificateDecisionsDidRevoke user_decision =
343 did_revoke_user_ssl_decisions_ ? USER_CERT_DECISIONS_REVOKED
344 : USER_CERT_DECISIONS_NOT_REVOKED;
345
346 UMA_HISTOGRAM_ENUMERATION("interstitial.ssl.did_user_revoke_decisions",
347 user_decision,
348 END_OF_SSL_CERTIFICATE_DECISIONS_DID_REVOKE_ENUM);
349}
350
351void WebsiteSettings::OnRevokeSSLErrorBypassButtonPressed() {
352 DCHECK(chrome_ssl_host_state_delegate_);
jww6a55df72014-09-05 19:59:29353 chrome_ssl_host_state_delegate_->RevokeUserAllowExceptionsHard(
354 site_url().host());
jww1ed8ea72014-09-02 20:43:25355 did_revoke_user_ssl_decisions_ = true;
[email protected]66f157312012-08-01 13:50:26356}
357
[email protected]0b9fdd72012-04-04 10:00:33358void WebsiteSettings::Init(Profile* profile,
359 const GURL& url,
360 const content::SSLStatus& ssl) {
sashab97894ce2014-10-22 10:08:33361 bool isChromeUINativeScheme = false;
362#if defined(OS_ANDROID)
363 isChromeUINativeScheme = url.SchemeIs(chrome::kChromeUINativeScheme);
364#endif
365
366 if (url.SchemeIs(content::kChromeUIScheme) ||
367 url.SchemeIs(url::kAboutScheme) || isChromeUINativeScheme) {
[email protected]03ef4b2a2012-03-06 15:04:20368 site_identity_status_ = SITE_IDENTITY_STATUS_INTERNAL_PAGE;
369 site_identity_details_ =
370 l10n_util::GetStringUTF16(IDS_PAGE_INFO_INTERNAL_PAGE);
371 site_connection_status_ = SITE_CONNECTION_STATUS_INTERNAL_PAGE;
372 return;
373 }
374
375 scoped_refptr<net::X509Certificate> cert;
376
377 // Identity section.
[email protected]a04db822013-12-11 19:14:40378 base::string16 subject_name(UTF8ToUTF16(url.host()));
[email protected]03ef4b2a2012-03-06 15:04:20379 if (subject_name.empty()) {
380 subject_name.assign(
381 l10n_util::GetStringUTF16(IDS_PAGE_INFO_SECURITY_TAB_UNKNOWN_PARTY));
[email protected]03ef4b2a2012-03-06 15:04:20382 }
383
[email protected]f61c1ce2012-05-09 13:55:11384 cert_id_ = ssl.cert_id;
385
[email protected]3d6d34b12013-12-23 00:34:02386 if (ssl.cert_id && !ssl.signed_certificate_timestamp_ids.empty()) {
387 signed_certificate_timestamp_ids_.assign(
388 ssl.signed_certificate_timestamp_ids.begin(),
389 ssl.signed_certificate_timestamp_ids.end());
390 }
391
[email protected]03ef4b2a2012-03-06 15:04:20392 if (ssl.cert_id &&
393 cert_store_->RetrieveCert(ssl.cert_id, &cert) &&
394 (!net::IsCertStatusError(ssl.cert_status) ||
395 net::IsCertStatusMinorError(ssl.cert_status))) {
396 // There are no major errors. Check for minor errors.
[email protected]24a9f1c92013-11-13 12:33:37397#if defined(OS_CHROMEOS)
398 policy::PolicyCertService* service =
399 policy::PolicyCertServiceFactory::GetForProfile(profile);
400 const bool used_policy_certs = service && service->UsedPolicyCertificates();
401#else
402 const bool used_policy_certs = false;
403#endif
404 if (used_policy_certs) {
[email protected]eaf3f322013-04-25 21:53:59405 site_identity_status_ = SITE_IDENTITY_STATUS_ADMIN_PROVIDED_CERT;
[email protected]24a9f1c92013-11-13 12:33:37406 site_identity_details_ = l10n_util::GetStringFUTF16(
407 IDS_CERT_POLICY_PROVIDED_CERT_MESSAGE, UTF8ToUTF16(url.host()));
[email protected]eaf3f322013-04-25 21:53:59408 } else if (net::IsCertStatusMinorError(ssl.cert_status)) {
[email protected]03ef4b2a2012-03-06 15:04:20409 site_identity_status_ = SITE_IDENTITY_STATUS_CERT_REVOCATION_UNKNOWN;
[email protected]a04db822013-12-11 19:14:40410 base::string16 issuer_name(UTF8ToUTF16(cert->issuer().GetDisplayName()));
[email protected]03ef4b2a2012-03-06 15:04:20411 if (issuer_name.empty()) {
412 issuer_name.assign(l10n_util::GetStringUTF16(
413 IDS_PAGE_INFO_SECURITY_TAB_UNKNOWN_PARTY));
414 }
[email protected]94c74b42013-12-02 15:19:49415
[email protected]03ef4b2a2012-03-06 15:04:20416 site_identity_details_.assign(l10n_util::GetStringFUTF16(
[email protected]94c74b42013-12-02 15:19:49417 GetSiteIdentityDetailsMessageByCTInfo(
418 ssl.signed_certificate_timestamp_ids, false /* not EV */),
419 issuer_name));
[email protected]03ef4b2a2012-03-06 15:04:20420
421 site_identity_details_ += ASCIIToUTF16("\n\n");
422 if (ssl.cert_status & net::CERT_STATUS_UNABLE_TO_CHECK_REVOCATION) {
423 site_identity_details_ += l10n_util::GetStringUTF16(
424 IDS_PAGE_INFO_SECURITY_TAB_UNABLE_TO_CHECK_REVOCATION);
425 } else if (ssl.cert_status & net::CERT_STATUS_NO_REVOCATION_MECHANISM) {
426 site_identity_details_ += l10n_util::GetStringUTF16(
427 IDS_PAGE_INFO_SECURITY_TAB_NO_REVOCATION_MECHANISM);
428 } else {
429 NOTREACHED() << "Need to specify string for this warning";
430 }
[email protected]03ef4b2a2012-03-06 15:04:20431 } else {
rsleevi4f8012722014-09-30 01:28:01432 if (ssl.cert_status & net::CERT_STATUS_IS_EV) {
433 // EV HTTPS page.
434 site_identity_status_ = GetSiteIdentityStatusByCTInfo(
435 ssl.signed_certificate_timestamp_ids, true);
436 DCHECK(!cert->subject().organization_names.empty());
437 organization_name_ = UTF8ToUTF16(cert->subject().organization_names[0]);
438 // An EV Cert is required to have a city (localityName) and country but
439 // state is "if any".
440 DCHECK(!cert->subject().locality_name.empty());
441 DCHECK(!cert->subject().country_name.empty());
442 base::string16 locality;
443 if (!cert->subject().state_or_province_name.empty()) {
444 locality = l10n_util::GetStringFUTF16(
445 IDS_PAGEINFO_ADDRESS,
446 UTF8ToUTF16(cert->subject().locality_name),
447 UTF8ToUTF16(cert->subject().state_or_province_name),
448 UTF8ToUTF16(cert->subject().country_name));
449 } else {
450 locality = l10n_util::GetStringFUTF16(
451 IDS_PAGEINFO_PARTIAL_ADDRESS,
452 UTF8ToUTF16(cert->subject().locality_name),
453 UTF8ToUTF16(cert->subject().country_name));
454 }
455 DCHECK(!cert->subject().organization_names.empty());
456 site_identity_details_.assign(l10n_util::GetStringFUTF16(
457 GetSiteIdentityDetailsMessageByCTInfo(
458 ssl.signed_certificate_timestamp_ids, true /* is EV */),
459 UTF8ToUTF16(cert->subject().organization_names[0]),
460 locality,
461 UTF8ToUTF16(cert->issuer().GetDisplayName())));
462 } else {
463 // Non-EV OK HTTPS page.
464 site_identity_status_ = GetSiteIdentityStatusByCTInfo(
465 ssl.signed_certificate_timestamp_ids, false);
466 base::string16 issuer_name(
467 UTF8ToUTF16(cert->issuer().GetDisplayName()));
468 if (issuer_name.empty()) {
469 issuer_name.assign(l10n_util::GetStringUTF16(
470 IDS_PAGE_INFO_SECURITY_TAB_UNKNOWN_PARTY));
471 }
[email protected]94c74b42013-12-02 15:19:49472
rsleevi4f8012722014-09-30 01:28:01473 site_identity_details_.assign(l10n_util::GetStringFUTF16(
474 GetSiteIdentityDetailsMessageByCTInfo(
475 ssl.signed_certificate_timestamp_ids, false /* not EV */),
476 issuer_name));
477 }
478 // The date after which no new SHA-1 certificates may be issued.
479 // 2016-01-01 00:00:00 UTC
480 static const int64_t kSHA1LastIssuanceDate = INT64_C(13096080000000000);
481 if ((ssl.cert_status & net::CERT_STATUS_SHA1_SIGNATURE_PRESENT) &&
482 cert->valid_expiry() >
483 base::Time::FromInternalValue(kSHA1LastIssuanceDate) &&
484 base::FieldTrialList::FindFullName("SHA1IdentityUIWarning") ==
485 "Enabled") {
486 site_identity_status_ =
487 SITE_IDENTITY_STATUS_DEPRECATED_SIGNATURE_ALGORITHM;
488 site_identity_details_ +=
489 UTF8ToUTF16("\n\n") +
490 l10n_util::GetStringUTF16(
491 IDS_PAGE_INFO_SECURITY_TAB_DEPRECATED_SIGNATURE_ALGORITHM);
492 }
[email protected]03ef4b2a2012-03-06 15:04:20493 }
494 } else {
495 // HTTP or HTTPS with errors (not warnings).
496 site_identity_details_.assign(l10n_util::GetStringUTF16(
497 IDS_PAGE_INFO_SECURITY_TAB_INSECURE_IDENTITY));
498 if (ssl.security_style == content::SECURITY_STYLE_UNAUTHENTICATED)
499 site_identity_status_ = SITE_IDENTITY_STATUS_NO_CERT;
500 else
501 site_identity_status_ = SITE_IDENTITY_STATUS_ERROR;
502
[email protected]a04db822013-12-11 19:14:40503 const base::string16 bullet = UTF8ToUTF16("\n • ");
[email protected]03ef4b2a2012-03-06 15:04:20504 std::vector<SSLErrorInfo> errors;
505 SSLErrorInfo::GetErrorsForCertStatus(ssl.cert_id, ssl.cert_status,
506 url, &errors);
507 for (size_t i = 0; i < errors.size(); ++i) {
508 site_identity_details_ += bullet;
509 site_identity_details_ += errors[i].short_description();
510 }
511
512 if (ssl.cert_status & net::CERT_STATUS_NON_UNIQUE_NAME) {
513 site_identity_details_ += ASCIIToUTF16("\n\n");
514 site_identity_details_ += l10n_util::GetStringUTF16(
515 IDS_PAGE_INFO_SECURITY_TAB_NON_UNIQUE_NAME);
516 }
517 }
518
519 // Site Connection
520 // We consider anything less than 80 bits encryption to be weak encryption.
521 // TODO(wtc): Bug 1198735: report mixed/unsafe content for unencrypted and
522 // weakly encrypted connections.
523 site_connection_status_ = SITE_CONNECTION_STATUS_UNKNOWN;
524
[email protected]1c1051d2014-05-10 11:39:58525 if (ssl.security_style == content::SECURITY_STYLE_UNKNOWN) {
526 // Page is still loading, so SSL status is not yet available. Say nothing.
527 DCHECK_EQ(ssl.security_bits, -1);
528 site_connection_status_ = SITE_CONNECTION_STATUS_UNENCRYPTED;
529
530 site_connection_details_.assign(l10n_util::GetStringFUTF16(
531 IDS_PAGE_INFO_SECURITY_TAB_NOT_ENCRYPTED_CONNECTION_TEXT,
532 subject_name));
533 } else if (ssl.security_style == content::SECURITY_STYLE_UNAUTHENTICATED) {
534 // HTTPS without a certificate, or not HTTPS.
535 DCHECK(!ssl.cert_id);
536 site_connection_status_ = SITE_CONNECTION_STATUS_UNENCRYPTED;
[email protected]03ef4b2a2012-03-06 15:04:20537
538 site_connection_details_.assign(l10n_util::GetStringFUTF16(
539 IDS_PAGE_INFO_SECURITY_TAB_NOT_ENCRYPTED_CONNECTION_TEXT,
540 subject_name));
541 } else if (ssl.security_bits < 0) {
542 // Security strength is unknown. Say nothing.
543 site_connection_status_ = SITE_CONNECTION_STATUS_ENCRYPTED_ERROR;
544 } else if (ssl.security_bits == 0) {
545 DCHECK_NE(ssl.security_style, content::SECURITY_STYLE_UNAUTHENTICATED);
546 site_connection_status_ = SITE_CONNECTION_STATUS_ENCRYPTED_ERROR;
547 site_connection_details_.assign(l10n_util::GetStringFUTF16(
548 IDS_PAGE_INFO_SECURITY_TAB_NOT_ENCRYPTED_CONNECTION_TEXT,
549 subject_name));
[email protected]03ef4b2a2012-03-06 15:04:20550 } else {
551 site_connection_status_ = SITE_CONNECTION_STATUS_ENCRYPTED;
Adam Langley71c2b59b2014-11-13 00:34:22552
553 if (net::SSLConnectionStatusToVersion(ssl.connection_status) >=
554 net::SSL_CONNECTION_VERSION_TLS1_2 &&
555 net::IsSecureTLSCipherSuite(
556 net::SSLConnectionStatusToCipherSuite(ssl.connection_status))) {
557 site_connection_details_.assign(l10n_util::GetStringFUTF16(
558 IDS_PAGE_INFO_SECURITY_TAB_ENCRYPTED_CONNECTION_TEXT,
559 subject_name));
560 } else {
561 site_connection_details_.assign(l10n_util::GetStringFUTF16(
562 IDS_PAGE_INFO_SECURITY_TAB_WEAK_ENCRYPTION_CONNECTION_TEXT,
563 subject_name));
564 }
565
[email protected]03ef4b2a2012-03-06 15:04:20566 if (ssl.content_status) {
567 bool ran_insecure_content =
568 !!(ssl.content_status & content::SSLStatus::RAN_INSECURE_CONTENT);
569 site_connection_status_ = ran_insecure_content ?
570 SITE_CONNECTION_STATUS_ENCRYPTED_ERROR
571 : SITE_CONNECTION_STATUS_MIXED_CONTENT;
572 site_connection_details_.assign(l10n_util::GetStringFUTF16(
573 IDS_PAGE_INFO_SECURITY_TAB_ENCRYPTED_SENTENCE_LINK,
574 site_connection_details_,
575 l10n_util::GetStringUTF16(ran_insecure_content ?
576 IDS_PAGE_INFO_SECURITY_TAB_ENCRYPTED_INSECURE_CONTENT_ERROR :
577 IDS_PAGE_INFO_SECURITY_TAB_ENCRYPTED_INSECURE_CONTENT_WARNING)));
578 }
579 }
580
581 uint16 cipher_suite =
582 net::SSLConnectionStatusToCipherSuite(ssl.connection_status);
583 if (ssl.security_bits > 0 && cipher_suite) {
584 int ssl_version =
585 net::SSLConnectionStatusToVersion(ssl.connection_status);
586 const char* ssl_version_str;
587 net::SSLVersionToString(&ssl_version_str, ssl_version);
588 site_connection_details_ += ASCIIToUTF16("\n\n");
589 site_connection_details_ += l10n_util::GetStringFUTF16(
590 IDS_PAGE_INFO_SECURITY_TAB_SSL_VERSION,
591 ASCIIToUTF16(ssl_version_str));
592
[email protected]03ef4b2a2012-03-06 15:04:20593 bool no_renegotiation =
594 (ssl.connection_status &
595 net::SSL_CONNECTION_NO_RENEGOTIATION_EXTENSION) != 0;
596 const char *key_exchange, *cipher, *mac;
[email protected]b6c1d9e82013-06-12 17:26:57597 bool is_aead;
598 net::SSLCipherSuiteToStrings(
599 &key_exchange, &cipher, &mac, &is_aead, cipher_suite);
[email protected]03ef4b2a2012-03-06 15:04:20600
601 site_connection_details_ += ASCIIToUTF16("\n\n");
[email protected]b6c1d9e82013-06-12 17:26:57602 if (is_aead) {
603 site_connection_details_ += l10n_util::GetStringFUTF16(
604 IDS_PAGE_INFO_SECURITY_TAB_ENCRYPTION_DETAILS_AEAD,
605 ASCIIToUTF16(cipher), ASCIIToUTF16(key_exchange));
606 } else {
607 site_connection_details_ += l10n_util::GetStringFUTF16(
608 IDS_PAGE_INFO_SECURITY_TAB_ENCRYPTION_DETAILS,
609 ASCIIToUTF16(cipher), ASCIIToUTF16(mac), ASCIIToUTF16(key_exchange));
610 }
[email protected]03ef4b2a2012-03-06 15:04:20611
agl078d2102014-10-20 22:03:22612 if (ssl_version == net::SSL_CONNECTION_VERSION_SSL3 &&
613 site_connection_status_ < SITE_CONNECTION_STATUS_MIXED_CONTENT) {
614 site_connection_status_ = SITE_CONNECTION_STATUS_ENCRYPTED_ERROR;
615 }
616
617 const bool did_fallback =
618 (ssl.connection_status & net::SSL_CONNECTION_VERSION_FALLBACK) != 0;
[email protected]03ef4b2a2012-03-06 15:04:20619 if (did_fallback) {
[email protected]03ef4b2a2012-03-06 15:04:20620 site_connection_details_ += ASCIIToUTF16("\n\n");
621 site_connection_details_ += l10n_util::GetStringUTF16(
622 IDS_PAGE_INFO_SECURITY_TAB_FALLBACK_MESSAGE);
623 }
agl078d2102014-10-20 22:03:22624
[email protected]03ef4b2a2012-03-06 15:04:20625 if (no_renegotiation) {
626 site_connection_details_ += ASCIIToUTF16("\n\n");
627 site_connection_details_ += l10n_util::GetStringUTF16(
628 IDS_PAGE_INFO_SECURITY_TAB_RENEGOTIATION_MESSAGE);
629 }
630 }
[email protected]e583f752012-08-30 13:26:21631
[email protected]71cd5ef2014-08-13 21:22:04632 // Check if a user decision has been made to allow or deny certificates with
633 // errors on this site.
634 ChromeSSLHostStateDelegate* delegate =
635 ChromeSSLHostStateDelegateFactory::GetForProfile(profile);
636 DCHECK(delegate);
637 // Only show an SSL decision revoke button if both the user has chosen to
638 // bypass SSL host errors for this host in the past and the user is not using
639 // the traditional "forget-at-session-restart" error decision memory.
jww6a55df72014-09-05 19:59:29640 show_ssl_decision_revoke_button_ = delegate->HasAllowException(url.host()) &&
641 InRememberCertificateErrorDecisionsGroup();
[email protected]71cd5ef2014-08-13 21:22:04642
[email protected]e583f752012-08-30 13:26:21643 // By default select the permissions tab that displays all the site
644 // permissions. In case of a connection error or an issue with the
645 // certificate presented by the website, select the connection tab to draw
646 // the user's attention to the issue. If the site does not provide a
647 // certificate because it was loaded over an unencrypted connection, don't
648 // select the connection tab.
649 WebsiteSettingsUI::TabId tab_id = WebsiteSettingsUI::TAB_ID_PERMISSIONS;
650 if (site_connection_status_ == SITE_CONNECTION_STATUS_ENCRYPTED_ERROR ||
651 site_connection_status_ == SITE_CONNECTION_STATUS_MIXED_CONTENT ||
652 site_identity_status_ == SITE_IDENTITY_STATUS_ERROR ||
[email protected]eaf3f322013-04-25 21:53:59653 site_identity_status_ == SITE_IDENTITY_STATUS_CERT_REVOCATION_UNKNOWN ||
rsleevi4f8012722014-09-30 01:28:01654 site_identity_status_ == SITE_IDENTITY_STATUS_ADMIN_PROVIDED_CERT ||
655 site_identity_status_ ==
lgarron04a93502014-11-04 22:25:04656 SITE_IDENTITY_STATUS_DEPRECATED_SIGNATURE_ALGORITHM) {
[email protected]e583f752012-08-30 13:26:21657 tab_id = WebsiteSettingsUI::TAB_ID_CONNECTION;
lgarron04a93502014-11-04 22:25:04658 RecordWebsiteSettingsAction(
659 WEBSITE_SETTINGS_CONNECTION_TAB_SHOWN_IMMEDIATELY);
660 }
[email protected]e583f752012-08-30 13:26:21661 ui_->SetSelectedTab(tab_id);
[email protected]03ef4b2a2012-03-06 15:04:20662}
[email protected]0b9fdd72012-04-04 10:00:33663
[email protected]df818272012-04-20 13:10:50664void WebsiteSettings::PresentSitePermissions() {
665 PermissionInfoList permission_info_list;
666
667 WebsiteSettingsUI::PermissionInfo permission_info;
668 for (size_t i = 0; i < arraysize(kPermissionType); ++i) {
669 permission_info.type = kPermissionType[i];
[email protected]df818272012-04-20 13:10:50670
671 content_settings::SettingInfo info;
sashab2b2a314f2015-01-17 06:42:21672 scoped_ptr<base::Value> value =
673 content_settings_->GetWebsiteSettingWithoutOverride(
674 site_url_, site_url_, permission_info.type, std::string(), &info);
675 DCHECK(value.get());
676 if (value->GetType() == base::Value::TYPE_INTEGER) {
677 permission_info.setting =
678 content_settings::ValueToContentSetting(value.get());
[email protected]fe4686a2012-10-19 15:38:26679 } else {
sashab2b2a314f2015-01-17 06:42:21680 NOTREACHED();
[email protected]fe4686a2012-10-19 15:38:26681 }
682
[email protected]8bdf45c32012-08-04 00:12:55683 permission_info.source = info.source;
[email protected]df818272012-04-20 13:10:50684
[email protected]b1d113d2012-06-27 21:27:34685 if (info.primary_pattern == ContentSettingsPattern::Wildcard() &&
sashab2b2a314f2015-01-17 06:42:21686 info.secondary_pattern == ContentSettingsPattern::Wildcard()) {
[email protected]b1d113d2012-06-27 21:27:34687 permission_info.default_setting = permission_info.setting;
688 permission_info.setting = CONTENT_SETTING_DEFAULT;
689 } else {
690 permission_info.default_setting =
691 content_settings_->GetDefaultContentSetting(permission_info.type,
692 NULL);
[email protected]df818272012-04-20 13:10:50693 }
palmer0da10b32015-02-11 00:42:19694
695 if (permission_info.setting != CONTENT_SETTING_DEFAULT &&
696 permission_info.setting != permission_info.default_setting) {
697 permission_info_list.push_back(permission_info);
698 }
[email protected]df818272012-04-20 13:10:50699 }
700
701 ui_->SetPermissionInfo(permission_info_list);
[email protected]0b9fdd72012-04-04 10:00:33702}
703
[email protected]df818272012-04-20 13:10:50704void WebsiteSettings::PresentSiteData() {
705 CookieInfoList cookie_info_list;
vabrd5e30cd2014-10-02 11:06:03706 const LocalSharedObjectsCounter& allowed_objects =
[email protected]e0ac35892012-05-15 12:53:34707 tab_specific_content_settings()->allowed_local_shared_objects();
vabrd5e30cd2014-10-02 11:06:03708 const LocalSharedObjectsCounter& blocked_objects =
[email protected]e0ac35892012-05-15 12:53:34709 tab_specific_content_settings()->blocked_local_shared_objects();
710
711 // Add first party cookie and site data counts.
[email protected]df818272012-04-20 13:10:50712 WebsiteSettingsUI::CookieInfo cookie_info;
[email protected]e0ac35892012-05-15 12:53:34713 std::string cookie_source =
[email protected]ed32c212013-05-14 20:49:29714 net::registry_controlled_domains::GetDomainAndRegistry(
715 site_url_,
[email protected]aabe1792014-01-30 21:37:46716 net::registry_controlled_domains::INCLUDE_PRIVATE_REGISTRIES);
[email protected]e0ac35892012-05-15 12:53:34717 if (cookie_source.empty())
718 cookie_source = site_url_.host();
719 cookie_info.cookie_source = cookie_source;
720 cookie_info.allowed = allowed_objects.GetObjectCountForDomain(site_url_);
721 cookie_info.blocked = blocked_objects.GetObjectCountForDomain(site_url_);
722 cookie_info_list.push_back(cookie_info);
723
724 // Add third party cookie counts.
725 cookie_info.cookie_source = l10n_util::GetStringUTF8(
726 IDS_WEBSITE_SETTINGS_THIRD_PARTY_SITE_DATA);
727 cookie_info.allowed = allowed_objects.GetObjectCount() - cookie_info.allowed;
728 cookie_info.blocked = blocked_objects.GetObjectCount() - cookie_info.blocked;
[email protected]df818272012-04-20 13:10:50729 cookie_info_list.push_back(cookie_info);
[email protected]0b9fdd72012-04-04 10:00:33730
[email protected]df818272012-04-20 13:10:50731 ui_->SetCookieInfo(cookie_info_list);
[email protected]0b9fdd72012-04-04 10:00:33732}
[email protected]16de6de2012-04-04 12:24:14733
[email protected]24c8818c2012-04-25 09:57:41734void WebsiteSettings::PresentSiteIdentity() {
735 // After initialization the status about the site's connection
736 // and it's identity must be available.
737 DCHECK_NE(site_identity_status_, SITE_IDENTITY_STATUS_UNKNOWN);
738 DCHECK_NE(site_connection_status_, SITE_CONNECTION_STATUS_UNKNOWN);
739 WebsiteSettingsUI::IdentityInfo info;
740 if (site_identity_status_ == SITE_IDENTITY_STATUS_EV_CERT)
741 info.site_identity = UTF16ToUTF8(organization_name());
742 else
743 info.site_identity = site_url_.host();
744
745 info.connection_status = site_connection_status_;
746 info.connection_status_description =
747 UTF16ToUTF8(site_connection_details_);
748 info.identity_status = site_identity_status_;
749 info.identity_status_description =
750 UTF16ToUTF8(site_identity_details_);
[email protected]f61c1ce2012-05-09 13:55:11751 info.cert_id = cert_id_;
[email protected]3d6d34b12013-12-23 00:34:02752 info.signed_certificate_timestamp_ids.assign(
753 signed_certificate_timestamp_ids_.begin(),
754 signed_certificate_timestamp_ids_.end());
[email protected]71cd5ef2014-08-13 21:22:04755 info.show_ssl_decision_revoke_button = show_ssl_decision_revoke_button_;
[email protected]24c8818c2012-04-25 09:57:41756 ui_->SetIdentityInfo(info);
757}
758
[email protected]15b092542012-05-16 13:08:14759void WebsiteSettings::PresentHistoryInfo(base::Time first_visit) {
760 if (first_visit == base::Time()) {
[email protected]b959d7d42013-12-13 17:26:37761 ui_->SetFirstVisit(base::string16());
[email protected]15b092542012-05-16 13:08:14762 return;
763 }
764
765 bool visited_before_today = false;
766 base::Time today = base::Time::Now().LocalMidnight();
767 base::Time first_visit_midnight = first_visit.LocalMidnight();
768 visited_before_today = (first_visit_midnight < today);
769
[email protected]a04db822013-12-11 19:14:40770 base::string16 first_visit_text;
[email protected]15b092542012-05-16 13:08:14771 if (visited_before_today) {
772 first_visit_text = l10n_util::GetStringFUTF16(
773 IDS_PAGE_INFO_SECURITY_TAB_VISITED_BEFORE_TODAY,
774 base::TimeFormatShortDate(first_visit));
775 } else {
776 first_visit_text = l10n_util::GetStringUTF16(
777 IDS_PAGE_INFO_SECURITY_TAB_FIRST_VISITED_TODAY);
[email protected]15b092542012-05-16 13:08:14778 }
779 ui_->SetFirstVisit(first_visit_text);
780}