1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181
|
// Copyright 2017 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CONTENT_BROWSER_MEDIA_MEDIA_DEVICES_UTIL_H_
#define CONTENT_BROWSER_MEDIA_MEDIA_DEVICES_UTIL_H_
#include <optional>
#include <string>
#include <utility>
#include "base/functional/callback.h"
#include "content/common/content_export.h"
#include "content/common/features.h"
#include "content/public/browser/global_routing_id.h"
#include "services/metrics/public/cpp/ukm_source_id.h"
#include "third_party/blink/public/common/mediastream/media_devices.h"
#include "third_party/blink/public/mojom/mediastream/media_stream.mojom.h"
#include "url/origin.h"
namespace content {
using DeviceIdCallback = base::OnceCallback<void(const std::string&)>;
class CONTENT_EXPORT MediaDeviceSaltAndOrigin {
public:
MediaDeviceSaltAndOrigin(
std::string device_id_salt,
url::Origin origin,
std::string group_id_salt = std::string(),
bool has_focus = false,
bool is_background = false,
std::optional<ukm::SourceId> ukm_source_id = std::nullopt);
MediaDeviceSaltAndOrigin(const MediaDeviceSaltAndOrigin& other);
MediaDeviceSaltAndOrigin& operator=(const MediaDeviceSaltAndOrigin& other);
MediaDeviceSaltAndOrigin(MediaDeviceSaltAndOrigin&& other);
MediaDeviceSaltAndOrigin& operator=(MediaDeviceSaltAndOrigin&& other);
~MediaDeviceSaltAndOrigin();
static MediaDeviceSaltAndOrigin Empty();
const std::string& device_id_salt() const { return device_id_salt_; }
const std::string& group_id_salt() const { return group_id_salt_; }
const url::Origin& origin() const { return origin_; }
const std::optional<ukm::SourceId>& ukm_source_id() const {
return ukm_source_id_;
}
bool has_focus() const { return has_focus_; }
bool is_background() const { return is_background_; }
void set_device_id_salt(std::string salt) {
device_id_salt_ = std::move(salt);
}
void set_group_id_salt(std::string salt) { group_id_salt_ = std::move(salt); }
void set_ukm_source_id(std::optional<ukm::SourceId> ukm_source_id) {
ukm_source_id_ = std::move(ukm_source_id);
}
void set_origin(url::Origin origin) { origin_ = std::move(origin); }
void set_has_focus(bool has_focus) { has_focus_ = has_focus; }
void set_is_background(bool is_background) { is_background_ = is_background; }
private:
std::string device_id_salt_;
std::string group_id_salt_;
// Last committed origin of the frame making a media device request.
url::Origin origin_;
// ukm::SourceId of the main frame making the media device request.
std::optional<ukm::SourceId> ukm_source_id_;
bool has_focus_;
bool is_background_;
};
// Returns the current media device ID salt and security origin for the given
// `render_frame_host_id`. The returned value can be used to produce unique
// media-device IDs for the origin associated with `render_frame_host_id` and
// it should not be cached since the user can explicitly change it at any time.
// This function must run on the UI thread.
using MediaDeviceSaltAndOriginCallback =
base::OnceCallback<void(const MediaDeviceSaltAndOrigin&)>;
CONTENT_EXPORT void GetMediaDeviceSaltAndOrigin(
GlobalRenderFrameHostId render_frame_host_id,
MediaDeviceSaltAndOriginCallback callback);
// Type definition to make it easier to use mock alternatives to
// GetMediaDeviceSaltAndOrigin.
using GetMediaDeviceSaltAndOriginCallback =
base::RepeatingCallback<void(GlobalRenderFrameHostId,
MediaDeviceSaltAndOriginCallback)>;
// Returns a translated (HMAC) version of (raw) `device_info` suitable for use
// in a renderer process.
// The `device_id` field is hashed using the `device_id_salt` and `origin` in
// `salt_and_origin`.
// The `group_id` field is hashed using the `group_id_salt` and `origin` in
// `salt_and_origin`.
// If `has_permission` is false all fields in the returned value are empty.
CONTENT_EXPORT blink::WebMediaDeviceInfo TranslateMediaDeviceInfo(
bool has_permission,
const MediaDeviceSaltAndOrigin& salt_and_origin,
const blink::WebMediaDeviceInfo& device_info);
// Returns a translated (HMAC) version of raw `device_infos`, with each element
// translated using TranslateMediaDeviceInfo(). If `has_permission` is false,
// the output will contain at most one element per device type with empty values
// for all fields, as per
// https://w3c.github.io/mediacapture-main/#access-control-model
CONTENT_EXPORT blink::WebMediaDeviceInfoArray TranslateMediaDeviceInfoArray(
bool has_permission,
const MediaDeviceSaltAndOrigin& salt_and_origin,
const blink::WebMediaDeviceInfoArray& device_infos);
// Creates a random salt that can be used to generate media device IDs that can
// be sent to the renderer process.
CONTENT_EXPORT std::string CreateRandomMediaDeviceIDSalt();
// Returns via `hmac_device_id_callback` an HMAC-translated version of
//`raw_device_id` suitable for use by the given `render_frame_host_id`.
CONTENT_EXPORT void GetHMACFromRawDeviceId(
GlobalRenderFrameHostId render_frame_host_id,
const std::string& raw_device_id,
DeviceIdCallback hmac_device_id_callback);
using OptionalDeviceIdCallback =
base::OnceCallback<void(const std::optional<std::string>&)>;
// Returns via `raw_device_id_callback` the raw version of `hmac_device_id`.
// The salt for the given `render_frame_host_id` is used to translate
// `hmac_device_id`. If no device of type `media_device_type` which corresponds
// to the given `hmac_device_id` is found in the system, this function returns
// `std::nullopt`.
CONTENT_EXPORT void GetRawDeviceIdFromHMAC(
GlobalRenderFrameHostId render_frame_host_id,
const std::string& hmac_device_id,
blink::mojom::MediaDeviceType media_device_type,
OptionalDeviceIdCallback raw_device_id_callback);
// Generates an HMAC device ID for `raw_device_id` using the given
// `salt_and_origin`. If `use_group_salt` is true,
// `salt_and_origin.group_id_salt()` will be used as salt. Otherwise,
// `salt_and_origin.device_id_salt()` is used as salt.
CONTENT_EXPORT std::string GetHMACForRawMediaDeviceID(
const MediaDeviceSaltAndOrigin& salt_and_origin,
const std::string& raw_device_id,
bool use_group_salt = false);
// Checks if `hmac_device_id` is an HMAC of |raw_device_id| for the given
// `salt_and_origin`.
CONTENT_EXPORT bool DoesRawMediaDeviceIDMatchHMAC(
const MediaDeviceSaltAndOrigin& salt_and_origin,
const std::string& hmac_device_id,
const std::string& raw_unique_id);
// Returns the raw device ID for `hmac_device_id` for the given
// `salt_and_origin`. `stream_type` must be
// blink::mojom::MediaStreamType::DEVICE_AUDIO_CAPTURE or
// blink::mojom::MediaStreamType::DEVICE_VIDEO_CAPTURE. The result will
// be returned via `callback` on the given `task_runner`.
// Must be called on the IO thread.
CONTENT_EXPORT void GetRawDeviceIDForMediaStreamHMAC(
blink::mojom::MediaStreamType stream_type,
MediaDeviceSaltAndOrigin salt_and_origin,
std::string hmac_device_id,
scoped_refptr<base::SequencedTaskRunner> task_runner,
OptionalDeviceIdCallback callback);
// Returns the raw device ID of type `device_type` for `hmac_device_id` for the
// given `salt_and_origin`. The result will be returned via `callback` on the
// given `task_runner`.
// Must be called on the IO thread.
CONTENT_EXPORT void GetRawDeviceIDForMediaDeviceHMAC(
blink::mojom::MediaDeviceType device_type,
MediaDeviceSaltAndOrigin salt_and_origin,
std::string hmac_device_id,
scoped_refptr<base::SequencedTaskRunner> task_runner,
OptionalDeviceIdCallback callback);
} // namespace content
#endif // CONTENT_BROWSER_MEDIA_MEDIA_DEVICES_UTIL_H_
|