Disable view source for Developer Tools.
[chromium-blink-merge.git] / chrome / browser / content_settings / tab_specific_content_settings.cc
blob8403054d81f4246083330c180709bea8c308c684
1 // 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.
5 #include "chrome/browser/content_settings/tab_specific_content_settings.h"
7 #include <list>
9 #include "base/command_line.h"
10 #include "base/lazy_instance.h"
11 #include "base/strings/utf_string_conversions.h"
12 #include "chrome/browser/browsing_data/browsing_data_appcache_helper.h"
13 #include "chrome/browser/browsing_data/browsing_data_cookie_helper.h"
14 #include "chrome/browser/browsing_data/browsing_data_database_helper.h"
15 #include "chrome/browser/browsing_data/browsing_data_file_system_helper.h"
16 #include "chrome/browser/browsing_data/browsing_data_indexed_db_helper.h"
17 #include "chrome/browser/browsing_data/browsing_data_local_storage_helper.h"
18 #include "chrome/browser/browsing_data/cookies_tree_model.h"
19 #include "chrome/browser/chrome_notification_types.h"
20 #include "chrome/browser/content_settings/content_settings_details.h"
21 #include "chrome/browser/content_settings/content_settings_utils.h"
22 #include "chrome/browser/content_settings/host_content_settings_map.h"
23 #include "chrome/browser/prerender/prerender_manager.h"
24 #include "chrome/browser/profiles/profile.h"
25 #include "chrome/common/chrome_switches.h"
26 #include "chrome/common/render_messages.h"
27 #include "content/public/browser/browser_thread.h"
28 #include "content/public/browser/navigation_controller.h"
29 #include "content/public/browser/navigation_details.h"
30 #include "content/public/browser/navigation_entry.h"
31 #include "content/public/browser/notification_service.h"
32 #include "content/public/browser/render_frame_host.h"
33 #include "content/public/browser/render_view_host.h"
34 #include "content/public/browser/web_contents.h"
35 #include "content/public/browser/web_contents_delegate.h"
36 #include "net/cookies/canonical_cookie.h"
37 #include "webkit/common/fileapi/file_system_types.h"
39 using content::BrowserThread;
40 using content::NavigationController;
41 using content::NavigationEntry;
42 using content::RenderViewHost;
43 using content::WebContents;
45 DEFINE_WEB_CONTENTS_USER_DATA_KEY(TabSpecificContentSettings);
47 TabSpecificContentSettings::SiteDataObserver::SiteDataObserver(
48 TabSpecificContentSettings* tab_specific_content_settings)
49 : tab_specific_content_settings_(tab_specific_content_settings) {
50 tab_specific_content_settings_->AddSiteDataObserver(this);
53 TabSpecificContentSettings::SiteDataObserver::~SiteDataObserver() {
54 if (tab_specific_content_settings_)
55 tab_specific_content_settings_->RemoveSiteDataObserver(this);
58 void TabSpecificContentSettings::SiteDataObserver::ContentSettingsDestroyed() {
59 tab_specific_content_settings_ = NULL;
62 TabSpecificContentSettings::TabSpecificContentSettings(WebContents* tab)
63 : content::WebContentsObserver(tab),
64 profile_(Profile::FromBrowserContext(tab->GetBrowserContext())),
65 allowed_local_shared_objects_(profile_),
66 blocked_local_shared_objects_(profile_),
67 geolocation_usages_state_(profile_, CONTENT_SETTINGS_TYPE_GEOLOCATION),
68 midi_usages_state_(profile_, CONTENT_SETTINGS_TYPE_MIDI_SYSEX),
69 pending_protocol_handler_(ProtocolHandler::EmptyProtocolHandler()),
70 previous_protocol_handler_(ProtocolHandler::EmptyProtocolHandler()),
71 pending_protocol_handler_setting_(CONTENT_SETTING_DEFAULT),
72 load_plugins_link_enabled_(true) {
73 ClearBlockedContentSettingsExceptForCookies();
74 ClearCookieSpecificContentSettings();
76 registrar_.Add(this, chrome::NOTIFICATION_CONTENT_SETTINGS_CHANGED,
77 content::Source<HostContentSettingsMap>(
78 profile_->GetHostContentSettingsMap()));
81 TabSpecificContentSettings::~TabSpecificContentSettings() {
82 FOR_EACH_OBSERVER(
83 SiteDataObserver, observer_list_, ContentSettingsDestroyed());
86 TabSpecificContentSettings* TabSpecificContentSettings::Get(
87 int render_process_id, int render_view_id) {
88 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
90 RenderViewHost* view = RenderViewHost::FromID(render_process_id,
91 render_view_id);
92 if (!view)
93 return NULL;
95 WebContents* web_contents = WebContents::FromRenderViewHost(view);
96 if (!web_contents)
97 return NULL;
99 return TabSpecificContentSettings::FromWebContents(web_contents);
102 TabSpecificContentSettings* TabSpecificContentSettings::GetForFrame(
103 int render_process_id, int render_frame_id) {
104 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
106 content::RenderFrameHost* frame = content::RenderFrameHost::FromID(
107 render_process_id, render_frame_id);
108 if (!frame)
109 return NULL;
111 WebContents* web_contents = WebContents::FromRenderFrameHost(frame);
112 if (!web_contents)
113 return NULL;
115 return TabSpecificContentSettings::FromWebContents(web_contents);
118 // static
119 void TabSpecificContentSettings::CookiesRead(int render_process_id,
120 int render_frame_id,
121 const GURL& url,
122 const GURL& frame_url,
123 const net::CookieList& cookie_list,
124 bool blocked_by_policy) {
125 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
126 TabSpecificContentSettings* settings =
127 GetForFrame(render_process_id, render_frame_id);
128 if (settings) {
129 settings->OnCookiesRead(url, frame_url, cookie_list,
130 blocked_by_policy);
132 prerender::PrerenderManager::RecordCookieEvent(
133 render_process_id,
134 render_frame_id,
135 url,
136 frame_url,
137 prerender::PrerenderContents::COOKIE_EVENT_SEND,
138 &cookie_list);
141 // static
142 void TabSpecificContentSettings::CookieChanged(
143 int render_process_id,
144 int render_frame_id,
145 const GURL& url,
146 const GURL& frame_url,
147 const std::string& cookie_line,
148 const net::CookieOptions& options,
149 bool blocked_by_policy) {
150 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
151 TabSpecificContentSettings* settings =
152 GetForFrame(render_process_id, render_frame_id);
153 if (settings)
154 settings->OnCookieChanged(url, frame_url, cookie_line, options,
155 blocked_by_policy);
156 prerender::PrerenderManager::RecordCookieEvent(
157 render_process_id,
158 render_frame_id,
159 url,
160 frame_url,
161 prerender::PrerenderContents::COOKIE_EVENT_CHANGE,
162 NULL);
165 // static
166 void TabSpecificContentSettings::WebDatabaseAccessed(
167 int render_process_id,
168 int render_frame_id,
169 const GURL& url,
170 const base::string16& name,
171 const base::string16& display_name,
172 bool blocked_by_policy) {
173 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
174 TabSpecificContentSettings* settings = GetForFrame(
175 render_process_id, render_frame_id);
176 if (settings)
177 settings->OnWebDatabaseAccessed(url, name, display_name, blocked_by_policy);
180 // static
181 void TabSpecificContentSettings::DOMStorageAccessed(int render_process_id,
182 int render_frame_id,
183 const GURL& url,
184 bool local,
185 bool blocked_by_policy) {
186 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
187 TabSpecificContentSettings* settings = GetForFrame(
188 render_process_id, render_frame_id);
189 if (settings)
190 settings->OnLocalStorageAccessed(url, local, blocked_by_policy);
193 // static
194 void TabSpecificContentSettings::IndexedDBAccessed(
195 int render_process_id,
196 int render_frame_id,
197 const GURL& url,
198 const base::string16& description,
199 bool blocked_by_policy) {
200 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
201 TabSpecificContentSettings* settings = GetForFrame(
202 render_process_id, render_frame_id);
203 if (settings)
204 settings->OnIndexedDBAccessed(url, description, blocked_by_policy);
207 // static
208 void TabSpecificContentSettings::FileSystemAccessed(int render_process_id,
209 int render_frame_id,
210 const GURL& url,
211 bool blocked_by_policy) {
212 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
213 TabSpecificContentSettings* settings = GetForFrame(
214 render_process_id, render_frame_id);
215 if (settings)
216 settings->OnFileSystemAccessed(url, blocked_by_policy);
219 bool TabSpecificContentSettings::IsContentBlocked(
220 ContentSettingsType content_type) const {
221 DCHECK(content_type != CONTENT_SETTINGS_TYPE_GEOLOCATION)
222 << "Geolocation settings handled by ContentSettingGeolocationImageModel";
223 DCHECK(content_type != CONTENT_SETTINGS_TYPE_NOTIFICATIONS)
224 << "Notifications settings handled by "
225 << "ContentSettingsNotificationsImageModel";
227 if (content_type == CONTENT_SETTINGS_TYPE_IMAGES ||
228 content_type == CONTENT_SETTINGS_TYPE_JAVASCRIPT ||
229 content_type == CONTENT_SETTINGS_TYPE_PLUGINS ||
230 content_type == CONTENT_SETTINGS_TYPE_COOKIES ||
231 content_type == CONTENT_SETTINGS_TYPE_POPUPS ||
232 content_type == CONTENT_SETTINGS_TYPE_MIXEDSCRIPT ||
233 content_type == CONTENT_SETTINGS_TYPE_MEDIASTREAM ||
234 content_type == CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC ||
235 content_type == CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA ||
236 content_type == CONTENT_SETTINGS_TYPE_PPAPI_BROKER ||
237 content_type == CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS ||
238 content_type == CONTENT_SETTINGS_TYPE_MIDI_SYSEX) {
239 return content_blocked_[content_type];
242 return false;
245 bool TabSpecificContentSettings::IsBlockageIndicated(
246 ContentSettingsType content_type) const {
247 return content_blockage_indicated_to_user_[content_type];
250 void TabSpecificContentSettings::SetBlockageHasBeenIndicated(
251 ContentSettingsType content_type) {
252 content_blockage_indicated_to_user_[content_type] = true;
255 bool TabSpecificContentSettings::IsContentAllowed(
256 ContentSettingsType content_type) const {
257 // This method currently only returns meaningful values for the content type
258 // cookies, mediastream, PPAPI broker, and downloads.
259 if (content_type != CONTENT_SETTINGS_TYPE_COOKIES &&
260 content_type != CONTENT_SETTINGS_TYPE_MEDIASTREAM &&
261 content_type != CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC &&
262 content_type != CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA &&
263 content_type != CONTENT_SETTINGS_TYPE_PPAPI_BROKER &&
264 content_type != CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS &&
265 content_type != CONTENT_SETTINGS_TYPE_MIDI_SYSEX) {
266 return false;
269 return content_allowed_[content_type];
272 void TabSpecificContentSettings::OnContentBlocked(ContentSettingsType type) {
273 DCHECK(type != CONTENT_SETTINGS_TYPE_GEOLOCATION)
274 << "Geolocation settings handled by OnGeolocationPermissionSet";
275 if (type < 0 || type >= CONTENT_SETTINGS_NUM_TYPES)
276 return;
278 // Media is different from other content setting types since it allows new
279 // setting to kick in without reloading the page, and the UI for media is
280 // always reflecting the newest permission setting.
281 switch (type) {
282 case CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC:
283 case CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA:
284 #if defined(OS_ANDROID)
285 case CONTENT_SETTINGS_TYPE_PROTECTED_MEDIA_IDENTIFIER:
286 #endif
287 content_allowed_[type] = false;
288 break;
289 default:
290 content_allowed_[type] = true;
291 break;
294 #if defined(OS_ANDROID)
295 if (type == CONTENT_SETTINGS_TYPE_POPUPS) {
296 // For Android we do not have a persistent button that will always be
297 // visible for blocked popups. Instead we have info bars which could be
298 // dismissed. Have to clear the blocked state so we properly notify the
299 // relevant pieces again.
300 content_blocked_[type] = false;
301 content_blockage_indicated_to_user_[type] = false;
303 #endif
305 if (!content_blocked_[type]) {
306 content_blocked_[type] = true;
307 // TODO: it would be nice to have a way of mocking this in tests.
308 content::NotificationService::current()->Notify(
309 chrome::NOTIFICATION_WEB_CONTENT_SETTINGS_CHANGED,
310 content::Source<WebContents>(web_contents()),
311 content::NotificationService::NoDetails());
315 void TabSpecificContentSettings::OnContentAllowed(ContentSettingsType type) {
316 DCHECK(type != CONTENT_SETTINGS_TYPE_GEOLOCATION)
317 << "Geolocation settings handled by OnGeolocationPermissionSet";
318 bool access_changed = false;
319 switch (type) {
320 case CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC:
321 case CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA:
322 #if defined(OS_ANDROID)
323 case CONTENT_SETTINGS_TYPE_PROTECTED_MEDIA_IDENTIFIER:
324 #endif
325 // The setting for media is overwritten here because media does not need
326 // to reload the page to have the new setting kick in. See issue/175993.
327 if (content_blocked_[type]) {
328 content_blocked_[type] = false;
329 access_changed = true;
331 break;
332 default:
333 break;
336 if (!content_allowed_[type]) {
337 content_allowed_[type] = true;
338 access_changed = true;
341 if (access_changed) {
342 content::NotificationService::current()->Notify(
343 chrome::NOTIFICATION_WEB_CONTENT_SETTINGS_CHANGED,
344 content::Source<WebContents>(web_contents()),
345 content::NotificationService::NoDetails());
349 void TabSpecificContentSettings::OnCookiesRead(
350 const GURL& url,
351 const GURL& frame_url,
352 const net::CookieList& cookie_list,
353 bool blocked_by_policy) {
354 if (cookie_list.empty())
355 return;
356 if (blocked_by_policy) {
357 blocked_local_shared_objects_.cookies()->AddReadCookies(
358 frame_url, url, cookie_list);
359 OnContentBlocked(CONTENT_SETTINGS_TYPE_COOKIES);
360 } else {
361 allowed_local_shared_objects_.cookies()->AddReadCookies(
362 frame_url, url, cookie_list);
363 OnContentAllowed(CONTENT_SETTINGS_TYPE_COOKIES);
366 NotifySiteDataObservers();
369 void TabSpecificContentSettings::OnCookieChanged(
370 const GURL& url,
371 const GURL& frame_url,
372 const std::string& cookie_line,
373 const net::CookieOptions& options,
374 bool blocked_by_policy) {
375 if (blocked_by_policy) {
376 blocked_local_shared_objects_.cookies()->AddChangedCookie(
377 frame_url, url, cookie_line, options);
378 OnContentBlocked(CONTENT_SETTINGS_TYPE_COOKIES);
379 } else {
380 allowed_local_shared_objects_.cookies()->AddChangedCookie(
381 frame_url, url, cookie_line, options);
382 OnContentAllowed(CONTENT_SETTINGS_TYPE_COOKIES);
385 NotifySiteDataObservers();
388 void TabSpecificContentSettings::OnIndexedDBAccessed(
389 const GURL& url,
390 const base::string16& description,
391 bool blocked_by_policy) {
392 if (blocked_by_policy) {
393 blocked_local_shared_objects_.indexed_dbs()->AddIndexedDB(
394 url, description);
395 OnContentBlocked(CONTENT_SETTINGS_TYPE_COOKIES);
396 } else {
397 allowed_local_shared_objects_.indexed_dbs()->AddIndexedDB(
398 url, description);
399 OnContentAllowed(CONTENT_SETTINGS_TYPE_COOKIES);
402 NotifySiteDataObservers();
405 void TabSpecificContentSettings::OnLocalStorageAccessed(
406 const GURL& url,
407 bool local,
408 bool blocked_by_policy) {
409 LocalSharedObjectsContainer& container = blocked_by_policy ?
410 blocked_local_shared_objects_ : allowed_local_shared_objects_;
411 CannedBrowsingDataLocalStorageHelper* helper =
412 local ? container.local_storages() : container.session_storages();
413 helper->AddLocalStorage(url);
415 if (blocked_by_policy)
416 OnContentBlocked(CONTENT_SETTINGS_TYPE_COOKIES);
417 else
418 OnContentAllowed(CONTENT_SETTINGS_TYPE_COOKIES);
420 NotifySiteDataObservers();
423 void TabSpecificContentSettings::OnWebDatabaseAccessed(
424 const GURL& url,
425 const base::string16& name,
426 const base::string16& display_name,
427 bool blocked_by_policy) {
428 if (blocked_by_policy) {
429 blocked_local_shared_objects_.databases()->AddDatabase(
430 url, base::UTF16ToUTF8(name), base::UTF16ToUTF8(display_name));
431 OnContentBlocked(CONTENT_SETTINGS_TYPE_COOKIES);
432 } else {
433 allowed_local_shared_objects_.databases()->AddDatabase(
434 url, base::UTF16ToUTF8(name), base::UTF16ToUTF8(display_name));
435 OnContentAllowed(CONTENT_SETTINGS_TYPE_COOKIES);
438 NotifySiteDataObservers();
441 void TabSpecificContentSettings::OnFileSystemAccessed(
442 const GURL& url,
443 bool blocked_by_policy) {
444 if (blocked_by_policy) {
445 blocked_local_shared_objects_.file_systems()->AddFileSystem(url,
446 fileapi::kFileSystemTypeTemporary, 0);
447 OnContentBlocked(CONTENT_SETTINGS_TYPE_COOKIES);
448 } else {
449 allowed_local_shared_objects_.file_systems()->AddFileSystem(url,
450 fileapi::kFileSystemTypeTemporary, 0);
451 OnContentAllowed(CONTENT_SETTINGS_TYPE_COOKIES);
454 NotifySiteDataObservers();
457 void TabSpecificContentSettings::OnGeolocationPermissionSet(
458 const GURL& requesting_origin,
459 bool allowed) {
460 geolocation_usages_state_.OnPermissionSet(requesting_origin, allowed);
461 content::NotificationService::current()->Notify(
462 chrome::NOTIFICATION_WEB_CONTENT_SETTINGS_CHANGED,
463 content::Source<WebContents>(web_contents()),
464 content::NotificationService::NoDetails());
467 #if defined(OS_ANDROID)
468 void TabSpecificContentSettings::OnProtectedMediaIdentifierPermissionSet(
469 const GURL& requesting_origin,
470 bool allowed) {
471 if (allowed) {
472 OnContentAllowed(CONTENT_SETTINGS_TYPE_PROTECTED_MEDIA_IDENTIFIER);
473 } else {
474 OnContentBlocked(CONTENT_SETTINGS_TYPE_PROTECTED_MEDIA_IDENTIFIER);
477 #endif
479 TabSpecificContentSettings::MicrophoneCameraState
480 TabSpecificContentSettings::GetMicrophoneCameraState() const {
481 if (IsContentAllowed(CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC) &&
482 IsContentAllowed(CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA)) {
483 return MICROPHONE_CAMERA_ACCESSED;
484 } else if (IsContentAllowed(CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC)) {
485 return MICROPHONE_ACCESSED;
486 } else if (IsContentAllowed(CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA)) {
487 return CAMERA_ACCESSED;
490 if (IsContentBlocked(CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC) &&
491 IsContentBlocked(CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA)) {
492 return MICROPHONE_CAMERA_BLOCKED;
493 } else if (IsContentBlocked(CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC)) {
494 return MICROPHONE_BLOCKED;
495 } else if (IsContentBlocked(CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA)) {
496 return CAMERA_BLOCKED;
499 return MICROPHONE_CAMERA_NOT_ACCESSED;
502 void TabSpecificContentSettings::OnMediaStreamPermissionSet(
503 const GURL& request_origin,
504 const MediaStreamDevicesController::MediaStreamTypeSettingsMap&
505 request_permissions) {
506 media_stream_access_origin_ = request_origin;
508 MediaStreamDevicesController::MediaStreamTypeSettingsMap::const_iterator it =
509 request_permissions.find(content::MEDIA_DEVICE_AUDIO_CAPTURE);
510 if (it != request_permissions.end()) {
511 media_stream_requested_audio_device_ = it->second.requested_device_id;
512 switch (it->second.permission) {
513 case MediaStreamDevicesController::MEDIA_NONE:
514 NOTREACHED();
515 break;
516 case MediaStreamDevicesController::MEDIA_ALLOWED:
517 OnContentAllowed(CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC);
518 break;
519 // TODO(grunell): UI should show for what reason access has been blocked.
520 case MediaStreamDevicesController::MEDIA_BLOCKED_BY_POLICY:
521 case MediaStreamDevicesController::MEDIA_BLOCKED_BY_USER_SETTING:
522 case MediaStreamDevicesController::MEDIA_BLOCKED_BY_USER:
523 OnContentBlocked(CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC);
524 break;
528 it = request_permissions.find(content::MEDIA_DEVICE_VIDEO_CAPTURE);
529 if (it != request_permissions.end()) {
530 media_stream_requested_video_device_ = it->second.requested_device_id;
531 switch (it->second.permission) {
532 case MediaStreamDevicesController::MEDIA_NONE:
533 NOTREACHED();
534 break;
535 case MediaStreamDevicesController::MEDIA_ALLOWED:
536 OnContentAllowed(CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA);
537 break;
538 // TODO(grunell): UI should show for what reason access has been blocked.
539 case MediaStreamDevicesController::MEDIA_BLOCKED_BY_POLICY:
540 case MediaStreamDevicesController::MEDIA_BLOCKED_BY_USER_SETTING:
541 case MediaStreamDevicesController::MEDIA_BLOCKED_BY_USER:
542 OnContentBlocked(CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA);
543 break;
548 void TabSpecificContentSettings::OnMIDISysExAccessed(
549 const GURL& requesting_origin) {
550 midi_usages_state_.OnPermissionSet(requesting_origin, true);
551 OnContentAllowed(CONTENT_SETTINGS_TYPE_MIDI_SYSEX);
554 void TabSpecificContentSettings::OnMIDISysExAccessBlocked(
555 const GURL& requesting_origin) {
556 midi_usages_state_.OnPermissionSet(requesting_origin, false);
557 OnContentBlocked(CONTENT_SETTINGS_TYPE_MIDI_SYSEX);
560 void TabSpecificContentSettings::ClearBlockedContentSettingsExceptForCookies() {
561 for (size_t i = 0; i < arraysize(content_blocked_); ++i) {
562 if (i == CONTENT_SETTINGS_TYPE_COOKIES)
563 continue;
564 content_blocked_[i] = false;
565 content_allowed_[i] = false;
566 content_blockage_indicated_to_user_[i] = false;
568 load_plugins_link_enabled_ = true;
569 content::NotificationService::current()->Notify(
570 chrome::NOTIFICATION_WEB_CONTENT_SETTINGS_CHANGED,
571 content::Source<WebContents>(web_contents()),
572 content::NotificationService::NoDetails());
575 void TabSpecificContentSettings::ClearCookieSpecificContentSettings() {
576 blocked_local_shared_objects_.Reset();
577 allowed_local_shared_objects_.Reset();
578 content_blocked_[CONTENT_SETTINGS_TYPE_COOKIES] = false;
579 content_allowed_[CONTENT_SETTINGS_TYPE_COOKIES] = false;
580 content_blockage_indicated_to_user_[CONTENT_SETTINGS_TYPE_COOKIES] = false;
581 content::NotificationService::current()->Notify(
582 chrome::NOTIFICATION_WEB_CONTENT_SETTINGS_CHANGED,
583 content::Source<WebContents>(web_contents()),
584 content::NotificationService::NoDetails());
587 void TabSpecificContentSettings::SetDownloadsBlocked(bool blocked) {
588 content_blocked_[CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS] = blocked;
589 content_allowed_[CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS] = !blocked;
590 content_blockage_indicated_to_user_[
591 CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS] = false;
592 content::NotificationService::current()->Notify(
593 chrome::NOTIFICATION_WEB_CONTENT_SETTINGS_CHANGED,
594 content::Source<WebContents>(web_contents()),
595 content::NotificationService::NoDetails());
598 void TabSpecificContentSettings::SetPopupsBlocked(bool blocked) {
599 content_blocked_[CONTENT_SETTINGS_TYPE_POPUPS] = blocked;
600 content_blockage_indicated_to_user_[CONTENT_SETTINGS_TYPE_POPUPS] = false;
601 content::NotificationService::current()->Notify(
602 chrome::NOTIFICATION_WEB_CONTENT_SETTINGS_CHANGED,
603 content::Source<WebContents>(web_contents()),
604 content::NotificationService::NoDetails());
607 void TabSpecificContentSettings::GeolocationDidNavigate(
608 const content::LoadCommittedDetails& details) {
609 geolocation_usages_state_.DidNavigate(details);
612 void TabSpecificContentSettings::MIDIDidNavigate(
613 const content::LoadCommittedDetails& details) {
614 midi_usages_state_.DidNavigate(details);
617 void TabSpecificContentSettings::ClearGeolocationContentSettings() {
618 geolocation_usages_state_.ClearStateMap();
621 void TabSpecificContentSettings::ClearMIDIContentSettings() {
622 midi_usages_state_.ClearStateMap();
625 void TabSpecificContentSettings::SetPepperBrokerAllowed(bool allowed) {
626 if (allowed) {
627 OnContentAllowed(CONTENT_SETTINGS_TYPE_PPAPI_BROKER);
628 } else {
629 OnContentBlocked(CONTENT_SETTINGS_TYPE_PPAPI_BROKER);
633 void TabSpecificContentSettings::RenderFrameForInterstitialPageCreated(
634 content::RenderFrameHost* render_frame_host) {
635 // We want to tell the renderer-side code to ignore content settings for this
636 // page.
637 render_frame_host->Send(new ChromeViewMsg_SetAsInterstitial(
638 render_frame_host->GetRoutingID()));
641 bool TabSpecificContentSettings::OnMessageReceived(
642 const IPC::Message& message) {
643 bool handled = true;
644 IPC_BEGIN_MESSAGE_MAP(TabSpecificContentSettings, message)
645 IPC_MESSAGE_HANDLER(ChromeViewHostMsg_ContentBlocked, OnContentBlocked)
646 IPC_MESSAGE_UNHANDLED(handled = false)
647 IPC_END_MESSAGE_MAP()
648 return handled;
651 void TabSpecificContentSettings::DidNavigateMainFrame(
652 const content::LoadCommittedDetails& details,
653 const content::FrameNavigateParams& params) {
654 if (!details.is_in_page) {
655 // Clear "blocked" flags.
656 ClearBlockedContentSettingsExceptForCookies();
657 GeolocationDidNavigate(details);
658 MIDIDidNavigate(details);
662 void TabSpecificContentSettings::DidStartProvisionalLoadForFrame(
663 int64 frame_id,
664 int64 parent_frame_id,
665 bool is_main_frame,
666 const GURL& validated_url,
667 bool is_error_page,
668 bool is_iframe_srcdoc,
669 RenderViewHost* render_view_host) {
670 if (!is_main_frame)
671 return;
673 // If we're displaying a network error page do not reset the content
674 // settings delegate's cookies so the user has a chance to modify cookie
675 // settings.
676 if (!is_error_page)
677 ClearCookieSpecificContentSettings();
678 ClearGeolocationContentSettings();
679 ClearMIDIContentSettings();
680 ClearPendingProtocolHandler();
683 void TabSpecificContentSettings::AppCacheAccessed(const GURL& manifest_url,
684 bool blocked_by_policy) {
685 if (blocked_by_policy) {
686 blocked_local_shared_objects_.appcaches()->AddAppCache(manifest_url);
687 OnContentBlocked(CONTENT_SETTINGS_TYPE_COOKIES);
688 } else {
689 allowed_local_shared_objects_.appcaches()->AddAppCache(manifest_url);
690 OnContentAllowed(CONTENT_SETTINGS_TYPE_COOKIES);
694 void TabSpecificContentSettings::Observe(
695 int type,
696 const content::NotificationSource& source,
697 const content::NotificationDetails& details) {
698 DCHECK(type == chrome::NOTIFICATION_CONTENT_SETTINGS_CHANGED);
700 content::Details<const ContentSettingsDetails> settings_details(details);
701 const NavigationController& controller = web_contents()->GetController();
702 NavigationEntry* entry = controller.GetVisibleEntry();
703 GURL entry_url;
704 if (entry)
705 entry_url = entry->GetURL();
706 if (settings_details.ptr()->update_all() ||
707 // The visible NavigationEntry is the URL in the URL field of a tab.
708 // Currently this should be matched by the |primary_pattern|.
709 settings_details.ptr()->primary_pattern().Matches(entry_url)) {
710 Profile* profile =
711 Profile::FromBrowserContext(web_contents()->GetBrowserContext());
712 RendererContentSettingRules rules;
713 GetRendererContentSettingRules(profile->GetHostContentSettingsMap(),
714 &rules);
715 Send(new ChromeViewMsg_SetContentSettingRules(rules));
719 void TabSpecificContentSettings::AddSiteDataObserver(
720 SiteDataObserver* observer) {
721 observer_list_.AddObserver(observer);
724 void TabSpecificContentSettings::RemoveSiteDataObserver(
725 SiteDataObserver* observer) {
726 observer_list_.RemoveObserver(observer);
729 void TabSpecificContentSettings::NotifySiteDataObservers() {
730 FOR_EACH_OBSERVER(SiteDataObserver, observer_list_, OnSiteDataAccessed());