Bug 1101304 - Handle CORS in EME - r=cpearce

This commit is contained in:
Edwin Flores 2015-01-29 20:30:38 +13:00
parent 7c8119a5cf
commit 592f17b93a
6 changed files with 33 additions and 45 deletions

View File

@ -3303,6 +3303,15 @@ bool HTMLMediaElement::ShouldCheckAllowOrigin()
return mCORSMode != CORS_NONE;
}
bool HTMLMediaElement::IsCORSSameOrigin()
{
bool subsumes;
nsRefPtr<nsIPrincipal> principal = GetCurrentPrincipal();
return
(NS_SUCCEEDED(NodePrincipal()->Subsumes(principal, &subsumes)) && subsumes) ||
ShouldCheckAllowOrigin();
}
void HTMLMediaElement::UpdateReadyStateForData(MediaDecoderOwner::NextFrameStatus aNextFrame)
{
mLastNextFrameStatus = aNextFrame;
@ -3648,22 +3657,13 @@ void HTMLMediaElement::NotifyDecoderPrincipalChanged()
{
nsRefPtr<nsIPrincipal> principal = GetCurrentPrincipal();
bool subsumes;
mDecoder->UpdateSameOriginStatus(
!principal ||
(NS_SUCCEEDED(NodePrincipal()->Subsumes(principal, &subsumes)) && subsumes) ||
mCORSMode != CORS_NONE);
mDecoder->UpdateSameOriginStatus(!principal || IsCORSSameOrigin());
for (uint32_t i = 0; i < mOutputStreams.Length(); ++i) {
OutputMediaStream* ms = &mOutputStreams[i];
ms->mStream->SetCORSMode(mCORSMode);
ms->mStream->CombineWithPrincipal(principal);
}
#ifdef MOZ_EME
if (mMediaKeys && NS_FAILED(mMediaKeys->CheckPrincipals())) {
mMediaKeys->Shutdown();
}
#endif
}
void HTMLMediaElement::UpdateMediaSize(nsIntSize size)
@ -4307,8 +4307,6 @@ HTMLMediaElement::SetMediaKeys(mozilla::dom::MediaKeys* aMediaKeys,
if (mDecoder) {
mDecoder->SetCDMProxy(mMediaKeys->GetCDMProxy());
}
// Update the same-origin status.
NotifyDecoderPrincipalChanged();
}
promise->MaybeResolve(JS::UndefinedHandleValue);
return promise.forget();
@ -4341,8 +4339,13 @@ void
HTMLMediaElement::DispatchEncrypted(const nsTArray<uint8_t>& aInitData,
const nsAString& aInitDataType)
{
nsRefPtr<MediaEncryptedEvent> event(
MediaEncryptedEvent::Constructor(this, aInitDataType, aInitData));
nsRefPtr<MediaEncryptedEvent> event;
if (IsCORSSameOrigin()) {
event = MediaEncryptedEvent::Constructor(this, aInitDataType, aInitData);
} else {
event = MediaEncryptedEvent::Constructor(this);
}
nsRefPtr<AsyncEventDispatcher> asyncDispatcher =
new AsyncEventDispatcher(this, event);
asyncDispatcher->PostDOMEvent();

View File

@ -245,6 +245,10 @@ public:
// Check if the media element had crossorigin set when loading started
bool ShouldCheckAllowOrigin();
// Returns true if the currently loaded resource is CORS same-origin with
// respect to the document.
bool IsCORSSameOrigin();
// Is the media element potentially playing as defined by the HTML 5 specification.
// http://www.whatwg.org/specs/web-apps/current-work/#potentially-playing
bool IsPotentiallyPlaying() const;

View File

@ -51,6 +51,15 @@ MediaEncryptedEvent::WrapObjectInternal(JSContext* aCx)
return MediaEncryptedEventBinding::Wrap(aCx, this);
}
already_AddRefed<MediaEncryptedEvent>
MediaEncryptedEvent::Constructor(EventTarget* aOwner)
{
nsRefPtr<MediaEncryptedEvent> e = new MediaEncryptedEvent(aOwner);
e->InitEvent(NS_LITERAL_STRING("encrypted"), false, false);
e->SetTrusted(true);
return e.forget();
}
already_AddRefed<MediaEncryptedEvent>
MediaEncryptedEvent::Constructor(EventTarget* aOwner,
const nsAString& aInitDataType,

View File

@ -38,6 +38,9 @@ public:
virtual JSObject* WrapObjectInternal(JSContext* aCx) MOZ_OVERRIDE;
static already_AddRefed<MediaEncryptedEvent>
Constructor(EventTarget* aOwner);
static already_AddRefed<MediaEncryptedEvent>
Constructor(EventTarget* aOwner,
const nsAString& aInitDataType,

View File

@ -433,33 +433,6 @@ MediaKeys::Bind(HTMLMediaElement* aElement)
}
mElement = aElement;
nsresult rv = CheckPrincipals();
if (NS_FAILED(rv)) {
mElement = nullptr;
return rv;
}
return NS_OK;
}
nsresult
MediaKeys::CheckPrincipals()
{
MOZ_ASSERT(NS_IsMainThread());
if (!IsBoundToMediaElement()) {
return NS_ERROR_FAILURE;
}
nsRefPtr<nsIPrincipal> elementPrincipal(mElement->GetCurrentPrincipal());
nsRefPtr<nsIPrincipal> elementTopLevelPrincipal(mElement->GetTopLevelPrincipal());
if (!elementPrincipal ||
!mPrincipal ||
!elementPrincipal->Equals(mPrincipal) ||
!elementTopLevelPrincipal ||
!mTopLevelPrincipal ||
!elementTopLevelPrincipal->Equals(mTopLevelPrincipal)) {
return NS_ERROR_FAILURE;
}
return NS_OK;
}

View File

@ -117,10 +117,6 @@ public:
// Returns true if this MediaKeys has been bound to a media element.
bool IsBoundToMediaElement() const;
// Return NS_OK if the principals are the same as when the MediaKeys
// was created, failure otherwise.
nsresult CheckPrincipals();
private:
bool IsInPrivateBrowsing();