#include "chrome/browser/media/router/mojo/media_router_desktop.h"
#include <stddef.h>
#include <utility>
#include <vector>
#include "base/command_line.h"
#include "base/containers/contains.h"
#include "base/functional/bind.h"
#include "base/functional/callback_helpers.h"
#include "base/metrics/histogram_functions.h"
#include "base/observer_list.h"
#include "base/ranges/algorithm.h"
#include "base/strings/string_util.h"
#include "base/strings/stringprintf.h"
#include "build/build_config.h"
#include "build/chromeos_buildflags.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/media/cast_mirroring_service_host.h"
#include "chrome/browser/media/cast_remoting_connector.h"
#include "chrome/browser/media/router/media_router_feature.h"
#include "chrome/browser/media/router/mojo/media_router_mojo_metrics.h"
#include "chrome/browser/media/router/mojo/media_sink_service_status.h"
#include "chrome/browser/media/router/providers/cast/cast_media_route_provider.h"
#include "chrome/browser/media/router/providers/cast/chrome_cast_message_handler.h"
#include "chrome/browser/media/router/providers/wired_display/wired_display_media_route_provider.h"
#include "chrome/browser/net/system_network_context_manager.h"
#include "chrome/browser/profiles/profile.h"
#include "chrome/grit/branded_strings.h"
#include "components/media_router/browser/issues_observer.h"
#include "components/media_router/browser/media_router.h"
#include "components/media_router/browser/media_router_factory.h"
#include "components/media_router/browser/media_router_metrics.h"
#include "components/media_router/browser/media_routes_observer.h"
#include "components/media_router/browser/media_sinks_observer.h"
#include "components/media_router/browser/mirroring_media_controller_host_impl.h"
#include "components/media_router/browser/presentation_connection_message_observer.h"
#include "components/media_router/common/media_source.h"
#include "components/media_router/common/providers/cast/cast_media_source.h"
#include "components/media_router/common/providers/cast/channel/cast_socket_service.h"
#include "components/openscreen_platform/network_context.h"
#include "content/public/browser/browser_task_traits.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/browser/render_frame_host.h"
#include "content/public/browser/render_process_host.h"
#include "mojo/public/cpp/bindings/pending_remote.h"
#include "mojo/public/cpp/bindings/remote.h"
#include "ui/base/l10n/l10n_util.h"
#if BUILDFLAG(IS_WIN)
#include "chrome/browser/media/router/mojo/media_route_provider_util_win.h"
#endif
#if BUILDFLAG(ENABLE_EXTENSIONS)
#include "extensions/common/constants.h"
#endif
namespace media_router {
namespace {
const int kDefaultFrameTreeNodeId = …;
constexpr char kLoggerComponent[] = …;
DesktopMediaPickerController::Params MakeDesktopPickerParams(
content::WebContents* web_contents) { … }
std::vector<MediaRoute> GetRouteSetDifference(
std::vector<MediaRoute> routes_a,
std::vector<MediaRoute> routes_b) { … }
}
MediaRouterDesktop::MediaRouterDesktop(content::BrowserContext* context)
: … { … }
MediaRouterDesktop::~MediaRouterDesktop() { … }
void MediaRouterDesktop::Initialize() { … }
void MediaRouterDesktop::CreateRoute(const MediaSource::Id& source_id,
const MediaSink::Id& sink_id,
const url::Origin& origin,
content::WebContents* web_contents,
MediaRouteResponseCallback callback,
base::TimeDelta timeout) { … }
void MediaRouterDesktop::JoinRoute(const MediaSource::Id& source_id,
const std::string& presentation_id,
const url::Origin& origin,
content::WebContents* web_contents,
MediaRouteResponseCallback callback,
base::TimeDelta timeout) { … }
void MediaRouterDesktop::TerminateRoute(const MediaRoute::Id& route_id) { … }
void MediaRouterDesktop::DetachRoute(MediaRoute::Id route_id) { … }
void MediaRouterDesktop::SendRouteMessage(const MediaRoute::Id& route_id,
const std::string& message) { … }
void MediaRouterDesktop::SendRouteBinaryMessage(
const MediaRoute::Id& route_id,
std::unique_ptr<std::vector<uint8_t>> data) { … }
void MediaRouterDesktop::OnUserGesture() { … }
std::vector<MediaRoute> MediaRouterDesktop::GetCurrentRoutes() const { … }
std::unique_ptr<media::FlingingController>
MediaRouterDesktop::GetFlingingController(const MediaRoute::Id& route_id) { … }
MirroringMediaControllerHost*
MediaRouterDesktop::GetMirroringMediaControllerHost(
const MediaRoute::Id& route_id) { … }
IssueManager* MediaRouterDesktop::GetIssueManager() { … }
void MediaRouterDesktop::GetMediaController(
const MediaRoute::Id& route_id,
mojo::PendingReceiver<mojom::MediaController> controller,
mojo::PendingRemote<mojom::MediaStatusObserver> observer) { … }
base::Value MediaRouterDesktop::GetLogs() const { … }
base::Value::Dict MediaRouterDesktop::GetState() const { … }
void MediaRouterDesktop::GetProviderState(
mojom::MediaRouteProviderId provider_id,
mojom::MediaRouteProvider::GetStateCallback callback) const { … }
LoggerImpl* MediaRouterDesktop::GetLogger() { … }
MediaRouterDebugger& MediaRouterDesktop::GetDebugger() { … }
bool MediaRouterDesktop::RegisterMediaSinksObserver(
MediaSinksObserver* observer) { … }
void MediaRouterDesktop::UnregisterMediaSinksObserver(
MediaSinksObserver* observer) { … }
void MediaRouterDesktop::RegisterMediaRoutesObserver(
MediaRoutesObserver* observer) { … }
void MediaRouterDesktop::UnregisterMediaRoutesObserver(
MediaRoutesObserver* observer) { … }
void MediaRouterDesktop::RegisterPresentationConnectionMessageObserver(
PresentationConnectionMessageObserver* observer) { … }
void MediaRouterDesktop::UnregisterPresentationConnectionMessageObserver(
PresentationConnectionMessageObserver* observer) { … }
void MediaRouterDesktop::RegisterMediaRouteProvider(
mojom::MediaRouteProviderId provider_id,
mojo::PendingRemote<mojom::MediaRouteProvider>
media_route_provider_remote) { … }
void MediaRouterDesktop::OnSinksReceived(
mojom::MediaRouteProviderId provider_id,
const std::string& media_source,
const std::vector<MediaSinkInternal>& internal_sinks,
const std::vector<url::Origin>& origins) { … }
void MediaRouterDesktop::OnIssue(const IssueInfo& issue) { … }
void MediaRouterDesktop::ClearTopIssueForSink(const MediaSink::Id& sink_id) { … }
void MediaRouterDesktop::OnRoutesUpdated(
mojom::MediaRouteProviderId provider_id,
const std::vector<MediaRoute>& routes) { … }
void MediaRouterDesktop::OnPresentationConnectionStateChanged(
const std::string& route_id,
blink::mojom::PresentationConnectionState state) { … }
void MediaRouterDesktop::OnPresentationConnectionClosed(
const std::string& route_id,
blink::mojom::PresentationConnectionCloseReason reason,
const std::string& message) { … }
void MediaRouterDesktop::OnRouteMessagesReceived(
const std::string& route_id,
std::vector<mojom::RouteMessagePtr> messages) { … }
void MediaRouterDesktop::GetMediaSinkServiceStatus(
mojom::MediaRouter::GetMediaSinkServiceStatusCallback callback) { … }
void MediaRouterDesktop::GetLogger(
mojo::PendingReceiver<mojom::Logger> receiver) { … }
void MediaRouterDesktop::GetDebugger(
mojo::PendingReceiver<mojom::Debugger> receiver) { … }
void MediaRouterDesktop::GetLogsAsString(GetLogsAsStringCallback callback) { … }
void MediaRouterDesktop::Shutdown() { … }
void MediaRouterDesktop::OnTerminateRouteResult(
const MediaRoute::Id& route_id,
mojom::MediaRouteProviderId provider_id,
const std::optional<std::string>& error_text,
mojom::RouteRequestResultCode result_code) { … }
void MediaRouterDesktop::OnRouteAdded(mojom::MediaRouteProviderId provider_id,
const MediaRoute& route) { … }
void MediaRouterDesktop::RouteResponseReceived(
const std::string& presentation_id,
mojom::MediaRouteProviderId provider_id,
MediaRouteResponseCallback callback,
bool is_join,
const std::optional<MediaRoute>& media_route,
mojom::RoutePresentationConnectionPtr connection,
const std::optional<std::string>& error_text,
mojom::RouteRequestResultCode result_code) { … }
void MediaRouterDesktop::OnLocalDiscoveryPermissionRejected() { … }
void MediaRouterDesktop::OnMediaControllerBound(const MediaRoute::Id& route_id,
bool success) { … }
void MediaRouterDesktop::AddMirroringMediaControllerHost(
const MediaRoute& route) { … }
void MediaRouterDesktop::InitializeMediaRouteProviders() { … }
void MediaRouterDesktop::InitializeWiredDisplayMediaRouteProvider() { … }
void MediaRouterDesktop::InitializeCastMediaRouteProvider() { … }
void MediaRouterDesktop::InitializeDialMediaRouteProvider() { … }
#if BUILDFLAG(IS_WIN)
void MediaRouterDesktop::EnsureMdnsDiscoveryEnabled() {
DCHECK(media_sink_service_);
media_sink_service_->StartMdnsDiscovery();
}
void MediaRouterDesktop::OnFirewallCheckComplete(
bool firewall_can_use_local_ports) {
if (firewall_can_use_local_ports) {
GetLogger()->LogInfo(
mojom::LogCategory::kDiscovery, kLoggerComponent,
"Windows firewall allows mDNS. Ensuring mDNS discovery is enabled.", "",
"", "");
EnsureMdnsDiscoveryEnabled();
} else {
GetLogger()->LogInfo(mojom::LogCategory::kDiscovery, kLoggerComponent,
"Windows firewall does not allows mDNS. mDNS "
"discovery can be enabled by user gesture.",
"", "", "");
}
}
#endif
std::string MediaRouterDesktop::GetHashToken() { … }
void MediaRouterDesktop::DiscoverSinksNow() { … }
void MediaRouterDesktop::OnProviderConnectionError(
mojom::MediaRouteProviderId provider_id) { … }
void MediaRouterDesktop::BindToMojoReceiver(
mojo::PendingReceiver<mojom::MediaRouter> receiver) { … }
void MediaRouterDesktop::CreateRouteWithSelectedDesktop(
mojom::MediaRouteProviderId provider_id,
const std::string& sink_id,
const std::string& presentation_id,
const url::Origin& origin,
content::WebContents* web_contents,
base::TimeDelta timeout,
mojom::MediaRouteProvider::CreateRouteCallback mr_callback,
const std::string& err,
content::DesktopMediaID media_id) { … }
std::optional<mojom::MediaRouteProviderId>
MediaRouterDesktop::GetProviderIdForPresentation(
const std::string& presentation_id) { … }
std::optional<mojom::MediaRouteProviderId>
MediaRouterDesktop::GetProviderIdForRoute(const MediaRoute::Id& route_id) { … }
std::optional<mojom::MediaRouteProviderId>
MediaRouterDesktop::GetProviderIdForSink(const MediaSink::Id& sink_id) { … }
const MediaSink* MediaRouterDesktop::GetSinkById(
const MediaSink::Id& sink_id) const { … }
const MediaRoute* MediaRouterDesktop::GetRoute(
const MediaRoute::Id& route_id) const { … }
void MediaRouterDesktop::NotifyNewObserversOfExistingRoutes() { … }
void MediaRouterDesktop::RecordPresentationRequestUrlBySink(
const MediaSource& source,
mojom::MediaRouteProviderId provider_id) { … }
bool MediaRouterDesktop::HasJoinableRoute() const { … }
bool MediaRouterDesktop::ShouldInitializeMediaRouteProviders() const { … }
MediaRouterDesktop::MediaSinksQuery::MediaSinksQuery() = default;
MediaRouterDesktop::MediaSinksQuery::~MediaSinksQuery() = default;
MediaSource MediaRouterDesktop::MediaSinksQuery::GetKey(
const MediaSource::Id& id) { … }
MediaSource MediaRouterDesktop::MediaSinksQuery::GetKey(
const MediaSinksObserver& observer) { … }
void MediaRouterDesktop::MediaSinksQuery::SetSinksForProvider(
mojom::MediaRouteProviderId provider_id,
const std::vector<MediaSink>& sinks) { … }
void MediaRouterDesktop::MediaSinksQuery::Reset() { … }
void MediaRouterDesktop::MediaSinksQuery::AddObserver(
MediaSinksObserver* observer) { … }
void MediaRouterDesktop::MediaSinksQuery::RemoveObserver(
MediaSinksObserver* observer) { … }
void MediaRouterDesktop::MediaSinksQuery::NotifyObservers() { … }
bool MediaRouterDesktop::MediaSinksQuery::HasObserver(
MediaSinksObserver* observer) const { … }
bool MediaRouterDesktop::MediaSinksQuery::HasObservers() const { … }
MediaRouterDesktop::MediaRoutesQuery::MediaRoutesQuery() = default;
MediaRouterDesktop::MediaRoutesQuery::~MediaRoutesQuery() = default;
void MediaRouterDesktop::MediaRoutesQuery::SetRoutesForProvider(
mojom::MediaRouteProviderId provider_id,
const std::vector<MediaRoute>& routes) { … }
bool MediaRouterDesktop::MediaRoutesQuery::AddRouteForProvider(
mojom::MediaRouteProviderId provider_id,
const MediaRoute& route) { … }
void MediaRouterDesktop::MediaRoutesQuery::UpdateCachedRouteList() { … }
void MediaRouterDesktop::MediaRoutesQuery::AddObserver(
MediaRoutesObserver* observer) { … }
void MediaRouterDesktop::MediaRoutesQuery::RemoveObserver(
MediaRoutesObserver* observer) { … }
void MediaRouterDesktop::MediaRoutesQuery::NotifyObservers() { … }
bool MediaRouterDesktop::MediaRoutesQuery::HasObserver(
MediaRoutesObserver* observer) const { … }
bool MediaRouterDesktop::MediaRoutesQuery::HasObservers() const { … }
void MediaRouterDesktop::MediaRoutesQuery::
NotifyNewObserversOfExistingRoutes() { … }
MediaRouterDesktop::InternalMediaRoutesObserver::InternalMediaRoutesObserver(
media_router::MediaRouter* router)
: … { … }
MediaRouterDesktop::InternalMediaRoutesObserver::
~InternalMediaRoutesObserver() = default;
void MediaRouterDesktop::InternalMediaRoutesObserver::OnRoutesUpdated(
const std::vector<MediaRoute>& routes) { … }
const std::vector<MediaRoute>&
MediaRouterDesktop::InternalMediaRoutesObserver::current_routes() const { … }
}