Bug 1208371 - Ensure a media element's ImageContainer is protected when playing a stream. r=mt,jesup
HTMLMediaElement needs special protection when playing a stream since its ImageContainer can outlive the video track of a stream. Consider for instance when a (cross-origin) video track is removed from a DOMMediaStream by a user and the remaining video track (non-CORS) does not yet contain any actual video frames. The HTMLMediaElement will display a frame from the removed track but the DOMMediaStream's principal has been updated to not include the principal from the removed track. With this patch we handle this by letting VideoFrameContainer notify HTMLMediaElement when it has flushed out all video frames belonging to a certain PrincipalHandle. I.e., when a new PrincipalHandle has been applied to the underlying ImageContainer. MozReview-Commit-ID: LvIZPl6Rdgj
This commit is contained in:
@@ -4193,14 +4193,53 @@ HTMLMediaElement::PrincipalChanged(DOMMediaStream* aStream)
|
||||
"%p. Waiting for it to reach VideoFrameContainer before "
|
||||
"setting.", this, aStream->GetVideoPrincipal()));
|
||||
if (mVideoFrameContainer) {
|
||||
UpdateSrcStreamVideoPrincipal(aStream->GetVideoPrincipal());
|
||||
UpdateSrcStreamVideoPrincipal(mVideoFrameContainer->GetLastPrincipalHandle());
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
HTMLMediaElement::UpdateSrcStreamVideoPrincipal(nsIPrincipal* aPrincipal)
|
||||
HTMLMediaElement::UpdateSrcStreamVideoPrincipal(const PrincipalHandle& aPrincipalHandle)
|
||||
{
|
||||
mSrcStreamVideoPrincipal = aPrincipal;
|
||||
nsTArray<RefPtr<VideoStreamTrack>> videoTracks;
|
||||
mSrcStream->GetVideoTracks(videoTracks);
|
||||
|
||||
PrincipalHandle handle(aPrincipalHandle);
|
||||
bool matchesTrackPrincipal = false;
|
||||
for (const RefPtr<VideoStreamTrack>& track : videoTracks) {
|
||||
if (PrincipalHandleMatches(handle,
|
||||
track->GetPrincipal()) &&
|
||||
!track->Ended()) {
|
||||
// When the PrincipalHandle for the VideoFrameContainer changes to that of
|
||||
// a track in mSrcStream we know that a removed track was displayed but
|
||||
// is no longer so.
|
||||
matchesTrackPrincipal = true;
|
||||
LOG(LogLevel::Debug, ("HTMLMediaElement %p VideoFrameContainer's "
|
||||
"PrincipalHandle matches track %p. That's all we "
|
||||
"need.", this, track.get()));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (matchesTrackPrincipal) {
|
||||
mSrcStreamVideoPrincipal = mSrcStream->GetVideoPrincipal();
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
HTMLMediaElement::PrincipalHandleChangedForVideoFrameContainer(VideoFrameContainer* aContainer,
|
||||
const PrincipalHandle& aNewPrincipalHandle)
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
if (!mSrcStream) {
|
||||
return;
|
||||
}
|
||||
|
||||
LOG(LogLevel::Debug, ("HTMLMediaElement %p PrincipalHandle changed in "
|
||||
"VideoFrameContainer.",
|
||||
this));
|
||||
|
||||
UpdateSrcStreamVideoPrincipal(aNewPrincipalHandle);
|
||||
}
|
||||
|
||||
nsresult HTMLMediaElement::DispatchEvent(const nsAString& aName)
|
||||
|
||||
Reference in New Issue
Block a user