Bug 1290830 - [Part2] Remove the GMP types using genral types instead. r=cpearce

MozReview-Commit-ID: 3EKwTNPddI1

--HG--
extra : rebase_source : 00f7267a76ad299b52d02b16425bb266ee58985b
This commit is contained in:
James Cheng 2016-08-02 15:05:21 +08:00
Родитель b74f50bca9
Коммит c6899c4863
13 изменённых файлов: 167 добавлений и 86 удалений

Просмотреть файл

@ -43,14 +43,15 @@ CDMCaps::AutoLock::~AutoLock()
mData.Unlock();
}
// Keys with kGMPUsable, kGMPOutputDownscaled, or kGMPOutputRestricted status
// can be used by the CDM to decrypt or decrypt-and-decode samples.
// Keys with MediaKeyStatus::Usable, MediaKeyStatus::Output_downscaled,
// or MediaKeyStatus::Output_restricted status can be used by the CDM
// to decrypt or decrypt-and-decode samples.
static bool
IsUsableStatus(GMPMediaKeyStatus aStatus)
IsUsableStatus(dom::MediaKeyStatus aStatus)
{
return aStatus == kGMPUsable ||
aStatus == kGMPOutputRestricted ||
aStatus == kGMPOutputDownscaled;
return aStatus == dom::MediaKeyStatus::Usable ||
aStatus == dom::MediaKeyStatus::Output_restricted ||
aStatus == dom::MediaKeyStatus::Output_downscaled;
}
bool
@ -68,24 +69,27 @@ CDMCaps::AutoLock::IsKeyUsable(const CencKeyId& aKeyId)
bool
CDMCaps::AutoLock::SetKeyStatus(const CencKeyId& aKeyId,
const nsString& aSessionId,
GMPMediaKeyStatus aStatus)
const dom::Optional<dom::MediaKeyStatus>& aStatus)
{
mData.mMonitor.AssertCurrentThreadOwns();
KeyStatus key(aKeyId, aSessionId, aStatus);
if (aStatus == kGMPUnknown) {
if (!aStatus.WasPassed()) {
// Called from ForgetKeyStatus.
// Return true if the element is found to notify key changes.
return mData.mKeyStatuses.RemoveElement(key);
return mData.mKeyStatuses.RemoveElement(KeyStatus(aKeyId,
aSessionId,
dom::MediaKeyStatus::Internal_error));
}
KeyStatus key(aKeyId, aSessionId, aStatus.Value());
auto index = mData.mKeyStatuses.IndexOf(key);
if (index != mData.mKeyStatuses.NoIndex) {
if (mData.mKeyStatuses[index].mStatus == aStatus) {
if (mData.mKeyStatuses[index].mStatus == aStatus.Value()) {
// No change.
return false;
}
auto oldStatus = mData.mKeyStatuses[index].mStatus;
mData.mKeyStatuses[index].mStatus = aStatus;
mData.mKeyStatuses[index].mStatus = aStatus.Value();
// The old key status was one for which we can decrypt media. We don't
// need to do the "notify usable" step below, as it should be impossible
// for us to have anything waiting on this key to become usable, since it
@ -99,7 +103,7 @@ CDMCaps::AutoLock::SetKeyStatus(const CencKeyId& aKeyId,
// Only call NotifyUsable() for a key when we are going from non-usable
// to usable state.
if (!IsUsableStatus(aStatus)) {
if (!IsUsableStatus(aStatus.Value())) {
return true;
}
@ -155,8 +159,10 @@ CDMCaps::AutoLock::RemoveKeysForSession(const nsString& aSessionId)
bool changed = false;
nsTArray<KeyStatus> statuses;
GetKeyStatusesForSession(aSessionId, statuses);
for (const KeyStatus& keyStatus : statuses) {
changed |= SetKeyStatus(keyStatus.mId, aSessionId, kGMPUnknown);
for (const KeyStatus& status : statuses) {
changed |= SetKeyStatus(status.mId,
aSessionId,
dom::Optional<dom::MediaKeyStatus>());
}
return changed;
}

Просмотреть файл

@ -7,13 +7,16 @@
#ifndef CDMCaps_h_
#define CDMCaps_h_
#include "nsString.h"
#include "mozilla/Monitor.h"
#include "gmp-decryption.h"
#include "nsIThread.h"
#include "nsTArray.h"
#include "mozilla/Attributes.h"
#include "nsString.h"
#include "SamplesWaitingForKey.h"
#include "gmp-decryption.h"
#include "mozilla/Monitor.h"
#include "mozilla/Attributes.h"
#include "mozilla/dom/MediaKeyStatusMapBinding.h" // For MediaKeyStatus
#include "mozilla/dom/BindingDeclarations.h" // For Optional
namespace mozilla {
@ -27,7 +30,7 @@ public:
struct KeyStatus {
KeyStatus(const CencKeyId& aId,
const nsString& aSessionId,
GMPMediaKeyStatus aStatus)
dom::MediaKeyStatus aStatus)
: mId(aId)
, mSessionId(aSessionId)
, mStatus(aStatus)
@ -44,7 +47,7 @@ public:
CencKeyId mId;
nsString mSessionId;
GMPMediaKeyStatus mStatus;
dom::MediaKeyStatus mStatus;
};
// Locks the CDMCaps. It must be locked to access its shared state.
@ -58,7 +61,9 @@ public:
// Returns true if key status changed,
// i.e. the key status changed from usable to expired.
bool SetKeyStatus(const CencKeyId& aKeyId, const nsString& aSessionId, GMPMediaKeyStatus aStatus);
bool SetKeyStatus(const CencKeyId& aKeyId,
const nsString& aSessionId,
const dom::Optional<dom::MediaKeyStatus>& aStatus);
void GetKeyStatusesForSession(const nsAString& aSessionId,
nsTArray<KeyStatus>& aOutKeyStatuses);

Просмотреть файл

@ -34,6 +34,8 @@ struct DecryptResult {
RefPtr<MediaRawData> mSample;
};
typedef int64_t UnixTime;
// Proxies calls CDM, and proxies calls back.
// Note: Promises are passed in via a PromiseId, so that the ID can be
// passed via IPC to the CDM, which can then signal when to reject or
@ -142,7 +144,7 @@ public:
// Main thread only.
virtual void OnExpirationChange(const nsAString& aSessionId,
int64_t aExpiryTime) = 0;
UnixTime aExpiryTime) = 0;
// Main thread only.
virtual void OnSessionClosed(const nsAString& aSessionId) = 0;

Просмотреть файл

@ -6,8 +6,13 @@
#ifndef DecryptorProxyCallback_h_
#define DecryptorProxyCallback_h_
#include "mozilla/dom/MediaKeyStatusMapBinding.h" // For MediaKeyStatus
#include "mozilla/dom/MediaKeyMessageEventBinding.h" // For MediaKeyMessageType
#include "mozilla/CDMProxy.h"
class DecryptorProxyCallback {
public:
virtual ~DecryptorProxyCallback() {}
virtual void SetSessionId(uint32_t aCreateSessionId,
@ -23,11 +28,11 @@ public:
const nsCString& aSessionId) = 0;
virtual void SessionMessage(const nsCString& aSessionId,
GMPSessionMessageType aMessageType,
mozilla::dom::MediaKeyMessageType aMessageType,
const nsTArray<uint8_t>& aMessage) = 0;
virtual void ExpirationChange(const nsCString& aSessionId,
GMPTimestamp aExpiryTime) = 0;
mozilla::UnixTime aExpiryTime) = 0;
virtual void SessionClosed(const nsCString& aSessionId) = 0;
@ -38,10 +43,13 @@ public:
virtual void KeyStatusChanged(const nsCString& aSessionId,
const nsTArray<uint8_t>& aKeyId,
GMPMediaKeyStatus aStatus) = 0;
mozilla::dom::MediaKeyStatus aStatus) = 0;
virtual void ForgetKeyStatus(const nsCString& aSessionId,
const nsTArray<uint8_t>& aKeyId) = 0;
virtual void Decrypted(uint32_t aId,
GMPErr aResult,
mozilla::DecryptStatus aResult,
const nsTArray<uint8_t>& aDecryptedData) = 0;
};

Просмотреть файл

@ -144,9 +144,10 @@ MediaKeySession::UpdateKeyStatusMap()
nsAutoCString message(
nsPrintfCString("MediaKeySession[%p,'%s'] key statuses change {",
this, NS_ConvertUTF16toUTF8(mSessionId).get()));
using IntegerType = typename std::underlying_type<MediaKeyStatus>::type;
for (const CDMCaps::KeyStatus& status : keyStatuses) {
message.Append(nsPrintfCString(" (%s,%s)", ToBase64(status.mId).get(),
MediaKeyStatusValues::strings[status.mStatus].value));
MediaKeyStatusValues::strings[static_cast<IntegerType>(status.mStatus)].value));
}
message.Append(" }");
EME_LOG(message.get());

Просмотреть файл

@ -108,26 +108,12 @@ MediaKeyStatusMap::Size() const
return mStatuses.Length();
}
static MediaKeyStatus
ToMediaKeyStatus(GMPMediaKeyStatus aStatus) {
switch (aStatus) {
case kGMPUsable: return MediaKeyStatus::Usable;
case kGMPExpired: return MediaKeyStatus::Expired;
case kGMPOutputDownscaled: return MediaKeyStatus::Output_downscaled;
case kGMPOutputRestricted: return MediaKeyStatus::Output_restricted;
case kGMPInternalError: return MediaKeyStatus::Internal_error;
case kGMPReleased: return MediaKeyStatus::Released;
case kGMPStatusPending: return MediaKeyStatus::Status_pending;
default: return MediaKeyStatus::Internal_error;
}
}
void
MediaKeyStatusMap::Update(const nsTArray<CDMCaps::KeyStatus>& aKeys)
{
mStatuses.Clear();
for (const auto& key : aKeys) {
mStatuses.InsertElementSorted(KeyStatus(key.mId, ToMediaKeyStatus(key.mStatus)));
mStatuses.InsertElementSorted(KeyStatus(key.mId, key.mStatus));
}
}

Просмотреть файл

@ -138,22 +138,11 @@ GMPCDMCallbackProxy::RejectPromise(uint32_t aPromiseId,
NS_DispatchToMainThread(task);
}
static dom::MediaKeyMessageType
ToMediaKeyMessageType(GMPSessionMessageType aMessageType) {
switch (aMessageType) {
case kGMPLicenseRequest: return dom::MediaKeyMessageType::License_request;
case kGMPLicenseRenewal: return dom::MediaKeyMessageType::License_renewal;
case kGMPLicenseRelease: return dom::MediaKeyMessageType::License_release;
case kGMPIndividualizationRequest: return dom::MediaKeyMessageType::Individualization_request;
default: return dom::MediaKeyMessageType::License_request;
};
};
class SessionMessageTask : public Runnable {
public:
SessionMessageTask(CDMProxy* aProxy,
const nsCString& aSessionId,
GMPSessionMessageType aMessageType,
dom::MediaKeyMessageType aMessageType,
const nsTArray<uint8_t>& aMessage)
: mProxy(aProxy)
, mSid(NS_ConvertUTF8toUTF16(aSessionId))
@ -163,20 +152,20 @@ public:
}
NS_IMETHOD Run() override {
mProxy->OnSessionMessage(mSid, ToMediaKeyMessageType(mMsgType), mMsg);
mProxy->OnSessionMessage(mSid, mMsgType, mMsg);
return NS_OK;
}
RefPtr<CDMProxy> mProxy;
dom::PromiseId mPid;
nsString mSid;
GMPSessionMessageType mMsgType;
dom::MediaKeyMessageType mMsgType;
nsTArray<uint8_t> mMsg;
};
void
GMPCDMCallbackProxy::SessionMessage(const nsCString& aSessionId,
GMPSessionMessageType aMessageType,
dom::MediaKeyMessageType aMessageType,
const nsTArray<uint8_t>& aMessage)
{
MOZ_ASSERT(mProxy->IsOnOwnerThread());
@ -294,10 +283,31 @@ GMPCDMCallbackProxy::SessionError(const nsCString& aSessionId,
void
GMPCDMCallbackProxy::KeyStatusChanged(const nsCString& aSessionId,
const nsTArray<uint8_t>& aKeyId,
GMPMediaKeyStatus aStatus)
dom::MediaKeyStatus aStatus)
{
MOZ_ASSERT(mProxy->IsOnOwnerThread());
KeyStatusChangedInternal(aSessionId,
aKeyId,
dom::Optional<dom::MediaKeyStatus>(aStatus));
}
void
GMPCDMCallbackProxy::ForgetKeyStatus(const nsCString& aSessionId,
const nsTArray<uint8_t>& aKeyId)
{
MOZ_ASSERT(mProxy->IsOnOwnerThread());
KeyStatusChangedInternal(aSessionId,
aKeyId,
dom::Optional<dom::MediaKeyStatus>());
}
void
GMPCDMCallbackProxy::KeyStatusChangedInternal(const nsCString& aSessionId,
const nsTArray<uint8_t>& aKeyId,
const dom::Optional<dom::MediaKeyStatus>& aStatus)
{
bool keyStatusesChange = false;
{
CDMCaps::AutoLock caps(mProxy->Capabilites());
@ -314,25 +324,14 @@ GMPCDMCallbackProxy::KeyStatusChanged(const nsCString& aSessionId,
}
}
DecryptStatus
ToDecryptStatus(GMPErr aError)
{
switch (aError) {
case GMPNoErr: return Ok;
case GMPNoKeyErr: return NoKeyErr;
case GMPAbortedErr: return AbortedErr;
default: return GenericErr;
}
}
void
GMPCDMCallbackProxy::Decrypted(uint32_t aId,
GMPErr aResult,
DecryptStatus aResult,
const nsTArray<uint8_t>& aDecryptedData)
{
MOZ_ASSERT(mProxy->IsOnOwnerThread());
mProxy->OnDecrypted(aId, ToDecryptStatus(aResult), aDecryptedData);
mProxy->OnDecrypted(aId, aResult, aDecryptedData);
}
void

Просмотреть файл

@ -30,11 +30,11 @@ public:
const nsCString& aSessionId) override;
void SessionMessage(const nsCString& aSessionId,
GMPSessionMessageType aMessageType,
dom::MediaKeyMessageType aMessageType,
const nsTArray<uint8_t>& aMessage) override;
void ExpirationChange(const nsCString& aSessionId,
GMPTimestamp aExpiryTime) override;
UnixTime aExpiryTime) override;
void SessionClosed(const nsCString& aSessionId) override;
@ -45,10 +45,13 @@ public:
void KeyStatusChanged(const nsCString& aSessionId,
const nsTArray<uint8_t>& aKeyId,
GMPMediaKeyStatus aStatus) override;
dom::MediaKeyStatus aStatus) override;
void ForgetKeyStatus(const nsCString& aSessionId,
const nsTArray<uint8_t>& aKeyId) override;
void Decrypted(uint32_t aId,
GMPErr aResult,
DecryptStatus aResult,
const nsTArray<uint8_t>& aDecryptedData) override;
void Terminated() override;
@ -58,6 +61,9 @@ public:
private:
friend class GMPCDMProxy;
explicit GMPCDMCallbackProxy(CDMProxy* aProxy);
void KeyStatusChangedInternal(const nsCString& aSessionId,
const nsTArray<uint8_t>& aKeyId,
const dom::Optional<dom::MediaKeyStatus>& aStatus);
// Warning: Weak ref.
CDMProxy* mProxy;

Просмотреть файл

@ -161,9 +161,16 @@ GMPDecryptorChild::KeyStatusChanged(const char* aSessionId,
{
AutoTArray<uint8_t, 16> kid;
kid.AppendElements(aKeyId, aKeyIdLength);
CALL_ON_GMP_THREAD(SendKeyStatusChanged,
nsCString(aSessionId, aSessionIdLength), kid,
aStatus);
if (aStatus == kGMPUnknown) {
CALL_ON_GMP_THREAD(SendForgetKeyStatus,
nsCString(aSessionId, aSessionIdLength),
kid);
} else {
CALL_ON_GMP_THREAD(SendKeyStatusChanged,
nsCString(aSessionId, aSessionIdLength),
kid,
aStatus);
}
}
void

Просмотреть файл

@ -265,6 +265,18 @@ GMPDecryptorParent::RecvRejectPromise(const uint32_t& aPromiseId,
return true;
}
static dom::MediaKeyMessageType
ToMediaKeyMessageType(GMPSessionMessageType aMessageType) {
switch (aMessageType) {
case kGMPLicenseRequest: return dom::MediaKeyMessageType::License_request;
case kGMPLicenseRenewal: return dom::MediaKeyMessageType::License_renewal;
case kGMPLicenseRelease: return dom::MediaKeyMessageType::License_release;
case kGMPIndividualizationRequest: return dom::MediaKeyMessageType::Individualization_request;
default: return dom::MediaKeyMessageType::License_request;
};
};
bool
GMPDecryptorParent::RecvSessionMessage(const nsCString& aSessionId,
const GMPSessionMessageType& aMessageType,
@ -277,7 +289,7 @@ GMPDecryptorParent::RecvSessionMessage(const nsCString& aSessionId,
NS_WARNING("Trying to use a dead GMP decrypter!");
return false;
}
mCallback->SessionMessage(aSessionId, aMessageType, aMessage);
mCallback->SessionMessage(aSessionId, ToMediaKeyMessageType(aMessageType), aMessage);
return true;
}
@ -331,6 +343,20 @@ GMPDecryptorParent::RecvSessionError(const nsCString& aSessionId,
return true;
}
static dom::MediaKeyStatus
ToMediaKeyStatus(GMPMediaKeyStatus aStatus) {
switch (aStatus) {
case kGMPUsable: return dom::MediaKeyStatus::Usable;
case kGMPExpired: return dom::MediaKeyStatus::Expired;
case kGMPOutputDownscaled: return dom::MediaKeyStatus::Output_downscaled;
case kGMPOutputRestricted: return dom::MediaKeyStatus::Output_restricted;
case kGMPInternalError: return dom::MediaKeyStatus::Internal_error;
case kGMPReleased: return dom::MediaKeyStatus::Released;
case kGMPStatusPending: return dom::MediaKeyStatus::Status_pending;
default: return dom::MediaKeyStatus::Internal_error;
}
}
bool
GMPDecryptorParent::RecvKeyStatusChanged(const nsCString& aSessionId,
InfallibleTArray<uint8_t>&& aKeyId,
@ -340,11 +366,35 @@ GMPDecryptorParent::RecvKeyStatusChanged(const nsCString& aSessionId,
this, aSessionId.get(), ToBase64(aKeyId).get(), aStatus));
if (mIsOpen) {
mCallback->KeyStatusChanged(aSessionId, aKeyId, aStatus);
mCallback->KeyStatusChanged(aSessionId, aKeyId, ToMediaKeyStatus(aStatus));
}
return true;
}
bool
GMPDecryptorParent::RecvForgetKeyStatus(const nsCString& aSessionId,
InfallibleTArray<uint8_t>&& aKeyId)
{
LOGD(("GMPDecryptorParent[%p]::RecvForgetKeyStatus(sessionId='%s', keyId=%s)",
this, aSessionId.get(), ToBase64(aKeyId).get()));
if (mIsOpen) {
mCallback->ForgetKeyStatus(aSessionId, aKeyId);
}
return true;
}
DecryptStatus
ToDecryptStatus(GMPErr aError)
{
switch (aError) {
case GMPNoErr: return Ok;
case GMPNoKeyErr: return NoKeyErr;
case GMPAbortedErr: return AbortedErr;
default: return GenericErr;
}
}
bool
GMPDecryptorParent::RecvDecrypted(const uint32_t& aId,
const GMPErr& aErr,
@ -357,7 +407,7 @@ GMPDecryptorParent::RecvDecrypted(const uint32_t& aId,
NS_WARNING("Trying to use a dead GMP decrypter!");
return false;
}
mCallback->Decrypted(aId, aErr, aBuffer);
mCallback->Decrypted(aId, ToDecryptStatus(aErr), aBuffer);
return true;
}

Просмотреть файл

@ -102,6 +102,9 @@ private:
InfallibleTArray<uint8_t>&& aKeyId,
const GMPMediaKeyStatus& aStatus) override;
bool RecvForgetKeyStatus(const nsCString& aSessionId,
InfallibleTArray<uint8_t>&& aKeyId) override;
bool RecvDecrypted(const uint32_t& aId,
const GMPErr& aErr,
InfallibleTArray<uint8_t>&& aBuffer) override;

Просмотреть файл

@ -82,6 +82,8 @@ parent:
async KeyStatusChanged(nsCString aSessionId, uint8_t[] aKey,
GMPMediaKeyStatus aStatus);
async ForgetKeyStatus(nsCString aSessionId, uint8_t[] aKey);
async Decrypted(uint32_t aId, GMPErr aResult, uint8_t[] aBuffer);
async Shutdown();

Просмотреть файл

@ -22,6 +22,8 @@
#include "nsNSSComponent.h"
#include "mozilla/DebugOnly.h"
#include "GMPDeviceBinding.h"
#include "mozilla/dom/MediaKeyStatusMapBinding.h" // For MediaKeyStatus
#include "mozilla/dom/MediaKeyMessageEventBinding.h" // For MediaKeyMessageType
#if defined(XP_WIN)
#include "mozilla/WindowsVersion.h"
@ -1344,7 +1346,7 @@ class GMPStorageTest : public GMPDecryptorProxyCallback
}
void SessionMessage(const nsCString& aSessionId,
GMPSessionMessageType aMessageType,
mozilla::dom::MediaKeyMessageType aMessageType,
const nsTArray<uint8_t>& aMessage) override
{
MonitorAutoLock mon(mMonitor);
@ -1371,7 +1373,7 @@ class GMPStorageTest : public GMPDecryptorProxyCallback
nsresult aException,
const nsCString& aSessionId) override { }
void ExpirationChange(const nsCString& aSessionId,
GMPTimestamp aExpiryTime) override {}
UnixTime aExpiryTime) override {}
void SessionClosed(const nsCString& aSessionId) override {}
void SessionError(const nsCString& aSessionId,
nsresult aException,
@ -1379,9 +1381,13 @@ class GMPStorageTest : public GMPDecryptorProxyCallback
const nsCString& aMessage) override {}
void KeyStatusChanged(const nsCString& aSessionId,
const nsTArray<uint8_t>& aKeyId,
GMPMediaKeyStatus aStatus) override { }
mozilla::dom::MediaKeyStatus aStatus) override { }
void ForgetKeyStatus(const nsCString& aSessionId,
const nsTArray<uint8_t>& aKeyId) override { }
void Decrypted(uint32_t aId,
GMPErr aResult,
mozilla::DecryptStatus aResult,
const nsTArray<uint8_t>& aDecryptedData) override { }
void Terminated() override {
if (mDecryptor) {