| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 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 "chrome/browser/media/webrtc/media_stream_devices_controller.h" | 5 #include "chrome/browser/media/webrtc/media_stream_devices_controller.h" |
| 6 | 6 |
| 7 #include <map> | 7 #include <map> |
| 8 #include <utility> | 8 #include <utility> |
| 9 | 9 |
| 10 #include "base/callback_helpers.h" | 10 #include "base/callback_helpers.h" |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 49 #include "content/public/browser/android/content_view_core.h" | 49 #include "content/public/browser/android/content_view_core.h" |
| 50 #include "ui/android/window_android.h" | 50 #include "ui/android/window_android.h" |
| 51 #endif // defined(OS_ANDROID) | 51 #endif // defined(OS_ANDROID) |
| 52 | 52 |
| 53 using content::BrowserThread; | 53 using content::BrowserThread; |
| 54 | 54 |
| 55 namespace { | 55 namespace { |
| 56 | 56 |
| 57 // Returns true if the given ContentSettingsType is being requested in | 57 // Returns true if the given ContentSettingsType is being requested in |
| 58 // |request|. | 58 // |request|. |
| 59 bool ContentTypeIsRequested(content::PermissionType type, | 59 bool ContentTypeIsRequested(ContentSettingsType type, |
| 60 const content::MediaStreamRequest& request) { | 60 const content::MediaStreamRequest& request) { |
| 61 if (request.request_type == content::MEDIA_OPEN_DEVICE_PEPPER_ONLY) | 61 if (request.request_type == content::MEDIA_OPEN_DEVICE_PEPPER_ONLY) |
| 62 return true; | 62 return true; |
| 63 | 63 |
| 64 if (type == content::PermissionType::AUDIO_CAPTURE) | 64 if (type == CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC) |
| 65 return request.audio_type == content::MEDIA_DEVICE_AUDIO_CAPTURE; | 65 return request.audio_type == content::MEDIA_DEVICE_AUDIO_CAPTURE; |
| 66 | 66 |
| 67 if (type == content::PermissionType::VIDEO_CAPTURE) | 67 if (type == CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA) |
| 68 return request.video_type == content::MEDIA_DEVICE_VIDEO_CAPTURE; | 68 return request.video_type == content::MEDIA_DEVICE_VIDEO_CAPTURE; |
| 69 | 69 |
| 70 return false; | 70 return false; |
| 71 } | 71 } |
| 72 | 72 |
| 73 using PermissionActionCallback = | 73 using PermissionActionCallback = |
| 74 base::Callback<void(content::PermissionType, | 74 base::Callback<void(ContentSettingsType, |
| 75 PermissionRequestGestureType, | 75 PermissionRequestGestureType, |
| 76 const GURL&, | 76 const GURL&, |
| 77 Profile*)>; | 77 Profile*)>; |
| 78 | 78 |
| 79 void RecordSinglePermissionAction(const content::MediaStreamRequest& request, | 79 void RecordSinglePermissionAction(const content::MediaStreamRequest& request, |
| 80 content::PermissionType permission_type, | 80 ContentSettingsType content_type, |
| 81 Profile* profile, | 81 Profile* profile, |
| 82 PermissionActionCallback callback) { | 82 PermissionActionCallback callback) { |
| 83 if (ContentTypeIsRequested(permission_type, request)) { | 83 if (ContentTypeIsRequested(content_type, request)) { |
| 84 // TODO(stefanocs): Pass the actual |gesture_type| once this file has been | 84 // TODO(stefanocs): Pass the actual |gesture_type| once this file has been |
| 85 // refactored into PermissionContext. | 85 // refactored into PermissionContext. |
| 86 callback.Run(permission_type, PermissionRequestGestureType::UNKNOWN, | 86 callback.Run(content_type, PermissionRequestGestureType::UNKNOWN, |
| 87 request.security_origin, profile); | 87 request.security_origin, profile); |
| 88 } | 88 } |
| 89 } | 89 } |
| 90 | 90 |
| 91 // Calls |action_function| for each permission requested by |request|. | 91 // Calls |action_function| for each permission requested by |request|. |
| 92 void RecordPermissionAction(const content::MediaStreamRequest& request, | 92 void RecordPermissionAction(const content::MediaStreamRequest& request, |
| 93 Profile* profile, | 93 Profile* profile, |
| 94 PermissionActionCallback callback) { | 94 PermissionActionCallback callback) { |
| 95 RecordSinglePermissionAction(request, content::PermissionType::AUDIO_CAPTURE, | 95 RecordSinglePermissionAction(request, CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC, |
| 96 profile, callback); | 96 profile, callback); |
| 97 RecordSinglePermissionAction(request, content::PermissionType::VIDEO_CAPTURE, | 97 RecordSinglePermissionAction( |
| 98 profile, callback); | 98 request, CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA, profile, callback); |
| 99 } | 99 } |
| 100 | 100 |
| 101 // This helper class helps to measure the number of media stream requests that | 101 // This helper class helps to measure the number of media stream requests that |
| 102 // occur. It ensures that only one request will be recorded per navigation, per | 102 // occur. It ensures that only one request will be recorded per navigation, per |
| 103 // frame. TODO(raymes): Remove this when https://crbug.com/526324 is fixed. | 103 // frame. TODO(raymes): Remove this when https://crbug.com/526324 is fixed. |
| 104 class MediaPermissionRequestLogger : content::WebContentsObserver { | 104 class MediaPermissionRequestLogger : content::WebContentsObserver { |
| 105 // Map of <render process id, render frame id> -> | 105 // Map of <render process id, render frame id> -> |
| 106 // MediaPermissionRequestLogger. | 106 // MediaPermissionRequestLogger. |
| 107 using RequestMap = std::map<std::pair<int, int>, | 107 using RequestMap = std::map<std::pair<int, int>, |
| 108 std::unique_ptr<MediaPermissionRequestLogger>>; | 108 std::unique_ptr<MediaPermissionRequestLogger>>; |
| (...skipping 139 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 248 if (!IsAskingForAudio()) | 248 if (!IsAskingForAudio()) |
| 249 message_id = IDS_MEDIA_CAPTURE_VIDEO_ONLY; | 249 message_id = IDS_MEDIA_CAPTURE_VIDEO_ONLY; |
| 250 else if (!IsAskingForVideo()) | 250 else if (!IsAskingForVideo()) |
| 251 message_id = IDS_MEDIA_CAPTURE_AUDIO_ONLY; | 251 message_id = IDS_MEDIA_CAPTURE_AUDIO_ONLY; |
| 252 return l10n_util::GetStringFUTF16( | 252 return l10n_util::GetStringFUTF16( |
| 253 message_id, | 253 message_id, |
| 254 url_formatter::FormatUrlForSecurityDisplay( | 254 url_formatter::FormatUrlForSecurityDisplay( |
| 255 GetOrigin(), url_formatter::SchemeDisplay::OMIT_CRYPTOGRAPHIC)); | 255 GetOrigin(), url_formatter::SchemeDisplay::OMIT_CRYPTOGRAPHIC)); |
| 256 } | 256 } |
| 257 | 257 |
| 258 content::PermissionType | |
| 259 MediaStreamDevicesController::GetPermissionTypeForContentSettingsType( | |
| 260 ContentSettingsType content_type) const { | |
| 261 DCHECK(content_type == CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC || | |
| 262 content_type == CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA); | |
| 263 content::PermissionType permission = content::PermissionType::NUM; | |
| 264 CHECK(PermissionUtil::GetPermissionType(content_type, &permission)); | |
| 265 return permission; | |
| 266 } | |
| 267 | |
| 268 void MediaStreamDevicesController::ForcePermissionDeniedTemporarily() { | 258 void MediaStreamDevicesController::ForcePermissionDeniedTemporarily() { |
| 269 set_persist(false); | 259 set_persist(false); |
| 270 // TODO(tsergeant): Determine whether it is appropriate to record permission | 260 // TODO(tsergeant): Determine whether it is appropriate to record permission |
| 271 // action metrics here, as this is a different sort of user action. | 261 // action metrics here, as this is a different sort of user action. |
| 272 RunCallback(CONTENT_SETTING_BLOCK, | 262 RunCallback(CONTENT_SETTING_BLOCK, |
| 273 CONTENT_SETTING_BLOCK, | 263 CONTENT_SETTING_BLOCK, |
| 274 content::MEDIA_DEVICE_PERMISSION_DENIED); | 264 content::MEDIA_DEVICE_PERMISSION_DENIED); |
| 275 set_persist(true); | 265 set_persist(true); |
| 276 } | 266 } |
| 277 | 267 |
| (...skipping 282 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 560 if (content_type == CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC) | 550 if (content_type == CONTENT_SETTINGS_TYPE_MEDIASTREAM_MIC) |
| 561 requested_device_id = request.requested_audio_device_id; | 551 requested_device_id = request.requested_audio_device_id; |
| 562 else if (content_type == CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA) | 552 else if (content_type == CONTENT_SETTINGS_TYPE_MEDIASTREAM_CAMERA) |
| 563 requested_device_id = request.requested_video_device_id; | 553 requested_device_id = request.requested_video_device_id; |
| 564 | 554 |
| 565 if (!IsUserAcceptAllowed(content_type)) { | 555 if (!IsUserAcceptAllowed(content_type)) { |
| 566 *denial_reason = content::MEDIA_DEVICE_PERMISSION_DENIED; | 556 *denial_reason = content::MEDIA_DEVICE_PERMISSION_DENIED; |
| 567 return CONTENT_SETTING_BLOCK; | 557 return CONTENT_SETTING_BLOCK; |
| 568 } | 558 } |
| 569 | 559 |
| 570 content::PermissionType permission_type = | 560 if (ContentTypeIsRequested(content_type, request)) { |
| 571 GetPermissionTypeForContentSettingsType(content_type); | |
| 572 if (ContentTypeIsRequested(permission_type, request)) { | |
| 573 DCHECK(content::IsOriginSecure(request_.security_origin) || | 561 DCHECK(content::IsOriginSecure(request_.security_origin) || |
| 574 request_.request_type == content::MEDIA_OPEN_DEVICE_PEPPER_ONLY); | 562 request_.request_type == content::MEDIA_OPEN_DEVICE_PEPPER_ONLY); |
| 575 MediaPermission permission(content_type, request.security_origin, | 563 MediaPermission permission(content_type, request.security_origin, |
| 576 web_contents_->GetLastCommittedURL().GetOrigin(), profile_); | 564 web_contents_->GetLastCommittedURL().GetOrigin(), profile_); |
| 577 return permission.GetPermissionStatusWithDeviceRequired(requested_device_id, | 565 return permission.GetPermissionStatusWithDeviceRequired(requested_device_id, |
| 578 denial_reason); | 566 denial_reason); |
| 579 } | 567 } |
| 580 // Return the default content setting if the device is not requested. | 568 // Return the default content setting if the device is not requested. |
| 581 return CONTENT_SETTING_DEFAULT; | 569 return CONTENT_SETTING_DEFAULT; |
| 582 } | 570 } |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 622 if (android_permission_blocked) | 610 if (android_permission_blocked) |
| 623 return false; | 611 return false; |
| 624 | 612 |
| 625 // Don't approve device requests if the tab was hidden. | 613 // Don't approve device requests if the tab was hidden. |
| 626 // TODO(qinmin): Add a test for this. http://crbug.com/396869. | 614 // TODO(qinmin): Add a test for this. http://crbug.com/396869. |
| 627 // TODO(raymes): Shouldn't this apply to all permissions not just audio/video? | 615 // TODO(raymes): Shouldn't this apply to all permissions not just audio/video? |
| 628 return web_contents_->GetRenderWidgetHostView()->IsShowing(); | 616 return web_contents_->GetRenderWidgetHostView()->IsShowing(); |
| 629 #endif | 617 #endif |
| 630 return true; | 618 return true; |
| 631 } | 619 } |
| OLD | NEW |