Integrate OnExpirationUpdate and OnSessionKeysChange with Android
Also removes OnSessionExpiration which is no longer needed with OnSessionKeysChange. Bug: 19771612 Bug: 19771431 Merged from Widevine CDM repo: https://widevine-internal-review.googlesource.com/#/c/13951/ Change-Id: I0603e808e8d50ff7bb1fb1d5e44fabd8d268ee8a
This commit is contained in:
@@ -32,7 +32,7 @@ using android::status_t;
|
||||
using android::String8;
|
||||
using android::Vector;
|
||||
using std::map;
|
||||
using wvcdm::CdmKeyInformation;
|
||||
using wvcdm::CdmKeyStatusMap;
|
||||
using wvcdm::CdmSessionId;
|
||||
using wvcdm::CdmResponseType;
|
||||
using wvcdm::WvContentDecryptionModule;
|
||||
@@ -142,15 +142,12 @@ class WVDrmPlugin : public android::DrmPlugin,
|
||||
|
||||
virtual void OnSessionRenewalNeeded(const CdmSessionId& cdmSessionId);
|
||||
|
||||
virtual void OnSessionExpiration(const CdmSessionId& cdmSessionId);
|
||||
|
||||
virtual void OnSessionKeysChange(
|
||||
const CdmSessionId& session_id,
|
||||
const std::vector<CdmKeyInformation>& cdm_keys_info,
|
||||
bool has_new_usable_key);
|
||||
virtual void OnSessionKeysChange(const CdmSessionId& cdmSessionId,
|
||||
const CdmKeyStatusMap& cdmKeysStatus,
|
||||
bool hasNewUsableKey);
|
||||
|
||||
virtual void OnExpirationUpdate(const CdmSessionId& cdmSessionId,
|
||||
int64_t new_expiry_time);
|
||||
int64_t newExpiryTime);
|
||||
|
||||
private:
|
||||
DISALLOW_EVIL_CONSTRUCTORS(WVDrmPlugin);
|
||||
|
||||
@@ -33,6 +33,13 @@ using namespace std;
|
||||
using namespace wvcdm;
|
||||
|
||||
namespace {
|
||||
|
||||
Vector<uint8_t> ToVector(const std::string& str) {
|
||||
Vector<uint8_t> vector;
|
||||
vector.appendArray(reinterpret_cast<const uint8_t*>(str.data()), str.size());
|
||||
return vector;
|
||||
}
|
||||
|
||||
DrmPlugin::KeyRequestType ConvertFromCdmKeyRequestType(
|
||||
CdmKeyRequestType keyRequestType) {
|
||||
switch (keyRequestType) {
|
||||
@@ -46,6 +53,23 @@ DrmPlugin::KeyRequestType ConvertFromCdmKeyRequestType(
|
||||
return DrmPlugin::kKeyRequestType_Unknown;
|
||||
}
|
||||
}
|
||||
|
||||
DrmPlugin::KeyStatusType ConvertFromCdmKeyStatus(CdmKeyStatus keyStatus) {
|
||||
switch (keyStatus) {
|
||||
case kKeyStatusUsable:
|
||||
return DrmPlugin::kKeyStatusType_Usable;
|
||||
case kKeyStatusExpired:
|
||||
return DrmPlugin::kKeyStatusType_Expired;
|
||||
case kKeyStatusOutputNotAllowed:
|
||||
return DrmPlugin::kKeyStatusType_OutputNotAllowed;
|
||||
case kKeyStatusPending:
|
||||
return DrmPlugin::kKeyStatusType_StatusPending;
|
||||
case kKeyStatusInternalError:
|
||||
default:
|
||||
return DrmPlugin::kKeyStatusType_InternalError;
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
WVDrmPlugin::WVDrmPlugin(WvContentDecryptionModule* cdm,
|
||||
@@ -941,30 +965,35 @@ status_t WVDrmPlugin::signRSA(const Vector<uint8_t>& /* sessionId */,
|
||||
}
|
||||
|
||||
void WVDrmPlugin::OnSessionRenewalNeeded(const CdmSessionId& cdmSessionId) {
|
||||
Vector<uint8_t> sessionId;
|
||||
sessionId.appendArray(reinterpret_cast<const uint8_t*>(cdmSessionId.data()),
|
||||
cdmSessionId.size());
|
||||
Vector<uint8_t> sessionId = ToVector(cdmSessionId);
|
||||
sendEvent(kDrmPluginEventKeyNeeded, 0, &sessionId, NULL);
|
||||
}
|
||||
|
||||
void WVDrmPlugin::OnSessionExpiration(const CdmSessionId& cdmSessionId) {
|
||||
Vector<uint8_t> sessionId;
|
||||
sessionId.appendArray(reinterpret_cast<const uint8_t*>(cdmSessionId.data()),
|
||||
cdmSessionId.size());
|
||||
sendEvent(kDrmPluginEventKeyExpired, 0, &sessionId, NULL);
|
||||
}
|
||||
void WVDrmPlugin::OnSessionKeysChange(const CdmSessionId& cdmSessionId,
|
||||
const CdmKeyStatusMap& cdmKeysStatus,
|
||||
bool hasNewUsableKey) {
|
||||
bool expired = false;
|
||||
Vector<KeyStatus> keyStatusList;
|
||||
for (CdmKeyStatusMap::const_iterator it = cdmKeysStatus.begin();
|
||||
it != cdmKeysStatus.end(); ++it) {
|
||||
const KeyId& keyId = it->first;
|
||||
const CdmKeyStatus cdmKeyStatus = it->second;
|
||||
if (cdmKeyStatus == kKeyStatusExpired) expired = true;
|
||||
|
||||
void WVDrmPlugin::OnSessionKeysChange(
|
||||
const CdmSessionId& session_id,
|
||||
const std::vector<CdmKeyInformation>& cdm_keys_info,
|
||||
bool has_new_usable_key) {
|
||||
// TODO(kqyang): Glue with DrmPlugin API when it is ready.
|
||||
keyStatusList.push(
|
||||
{ToVector(keyId), ConvertFromCdmKeyStatus(cdmKeyStatus)});
|
||||
}
|
||||
|
||||
Vector<uint8_t> sessionId = ToVector(cdmSessionId);
|
||||
sendKeysChange(&sessionId, &keyStatusList, hasNewUsableKey);
|
||||
// For backward compatibility.
|
||||
if (expired) sendEvent(kDrmPluginEventKeyExpired, 0, &sessionId, NULL);
|
||||
}
|
||||
|
||||
void WVDrmPlugin::OnExpirationUpdate(const CdmSessionId& cdmSessionId,
|
||||
int64_t new_expiry_time) {
|
||||
// TODO(kqyang): Glue with DrmPlugin API when it is ready. Note that
|
||||
// new_expiry_time is in seconds while Android API is in milliseconds.
|
||||
int64_t newExpiryTime) {
|
||||
Vector<uint8_t> sessionId = ToVector(cdmSessionId);
|
||||
sendExpirationUpdate(&sessionId, newExpiryTime * 1000);
|
||||
}
|
||||
|
||||
status_t WVDrmPlugin::mapAndNotifyOfCdmResponseType(
|
||||
|
||||
@@ -113,6 +113,9 @@ class MockDrmPluginListener : public DrmPluginListener {
|
||||
public:
|
||||
MOCK_METHOD4(sendEvent, void(DrmPlugin::EventType, int,
|
||||
const Vector<uint8_t>*, const Vector<uint8_t>*));
|
||||
MOCK_METHOD2(sendExpirationUpdate, void(const Vector<uint8_t>*, int64_t));
|
||||
MOCK_METHOD3(sendKeysChange, void(const Vector<uint8_t>*,
|
||||
const Vector<DrmPlugin::KeyStatus>*, bool));
|
||||
};
|
||||
|
||||
template <uint8_t DIGIT>
|
||||
@@ -1181,27 +1184,77 @@ TEST_F(WVDrmPluginTest, MarshalsEvents) {
|
||||
sp<StrictMock<MockDrmPluginListener> > listener =
|
||||
new StrictMock<MockDrmPluginListener>();
|
||||
|
||||
const int64_t kExpiryTimeInSeconds = 123456789012LL;
|
||||
const char kKeyId1[] = "Testing Key1 Id ";
|
||||
const char kKeyId2[] = "Testing Key2 Id ";
|
||||
const char kKeyId3[] = "Testing Key3 Id ";
|
||||
const char kKeyId4[] = "Testing Key4 Id ";
|
||||
|
||||
{
|
||||
InSequence calls;
|
||||
|
||||
EXPECT_CALL(*listener, sendEvent(DrmPlugin::kDrmPluginEventKeyExpired, 0,
|
||||
Pointee(ElementsAreArray(sessionIdRaw,
|
||||
kSessionIdSize)),
|
||||
NULL))
|
||||
.Times(1);
|
||||
|
||||
EXPECT_CALL(*listener, sendEvent(DrmPlugin::kDrmPluginEventKeyNeeded, 0,
|
||||
Pointee(ElementsAreArray(sessionIdRaw,
|
||||
kSessionIdSize)),
|
||||
NULL))
|
||||
.Times(1);
|
||||
EXPECT_CALL(*listener,
|
||||
sendKeysChange(
|
||||
Pointee(ElementsAreArray(sessionIdRaw, kSessionIdSize)),
|
||||
Pointee(UnorderedElementsAre(AllOf(
|
||||
Field(&DrmPlugin::KeyStatus::mKeyId,
|
||||
ElementsAreArray(kKeyId1, sizeof(kKeyId1) - 1)),
|
||||
Field(&DrmPlugin::KeyStatus::mType,
|
||||
DrmPlugin::kKeyStatusType_Expired)))),
|
||||
false));
|
||||
EXPECT_CALL(
|
||||
*listener,
|
||||
sendEvent(DrmPlugin::kDrmPluginEventKeyExpired, 0,
|
||||
Pointee(ElementsAreArray(sessionIdRaw, kSessionIdSize)),
|
||||
NULL));
|
||||
EXPECT_CALL(
|
||||
*listener,
|
||||
sendEvent(DrmPlugin::kDrmPluginEventKeyNeeded, 0,
|
||||
Pointee(ElementsAreArray(sessionIdRaw, kSessionIdSize)),
|
||||
NULL));
|
||||
EXPECT_CALL(*listener,
|
||||
sendExpirationUpdate(
|
||||
Pointee(ElementsAreArray(sessionIdRaw, kSessionIdSize)),
|
||||
kExpiryTimeInSeconds * 1000));
|
||||
EXPECT_CALL(
|
||||
*listener,
|
||||
sendKeysChange(
|
||||
Pointee(ElementsAreArray(sessionIdRaw, kSessionIdSize)),
|
||||
Pointee(UnorderedElementsAre(
|
||||
AllOf(Field(&DrmPlugin::KeyStatus::mKeyId,
|
||||
ElementsAreArray(kKeyId1, sizeof(kKeyId1) - 1)),
|
||||
Field(&DrmPlugin::KeyStatus::mType,
|
||||
DrmPlugin::kKeyStatusType_Usable)),
|
||||
AllOf(Field(&DrmPlugin::KeyStatus::mKeyId,
|
||||
ElementsAreArray(kKeyId2, sizeof(kKeyId2) - 1)),
|
||||
Field(&DrmPlugin::KeyStatus::mType,
|
||||
DrmPlugin::kKeyStatusType_OutputNotAllowed)),
|
||||
AllOf(Field(&DrmPlugin::KeyStatus::mKeyId,
|
||||
ElementsAreArray(kKeyId3, sizeof(kKeyId3) - 1)),
|
||||
Field(&DrmPlugin::KeyStatus::mType,
|
||||
DrmPlugin::kKeyStatusType_InternalError)),
|
||||
AllOf(Field(&DrmPlugin::KeyStatus::mKeyId,
|
||||
ElementsAreArray(kKeyId4, sizeof(kKeyId4) - 1)),
|
||||
Field(&DrmPlugin::KeyStatus::mType,
|
||||
DrmPlugin::kKeyStatusType_StatusPending)))),
|
||||
true));
|
||||
}
|
||||
|
||||
status_t res = plugin.setListener(listener);
|
||||
ASSERT_EQ(OK, res);
|
||||
|
||||
plugin.OnSessionExpiration(cdmSessionId);
|
||||
CdmKeyStatusMap cdmKeysStatus;
|
||||
cdmKeysStatus[kKeyId1] = kKeyStatusExpired;
|
||||
plugin.OnSessionKeysChange(cdmSessionId, cdmKeysStatus, false);
|
||||
|
||||
plugin.OnSessionRenewalNeeded(cdmSessionId);
|
||||
plugin.OnExpirationUpdate(cdmSessionId, kExpiryTimeInSeconds);
|
||||
|
||||
cdmKeysStatus[kKeyId1] = kKeyStatusUsable;
|
||||
cdmKeysStatus[kKeyId2] = kKeyStatusOutputNotAllowed;
|
||||
cdmKeysStatus[kKeyId3] = kKeyStatusInternalError;
|
||||
cdmKeysStatus[kKeyId4] = kKeyStatusPending;
|
||||
plugin.OnSessionKeysChange(cdmSessionId, cdmKeysStatus, true);
|
||||
}
|
||||
|
||||
TEST_F(WVDrmPluginTest, GeneratesProvisioningNeededEvent) {
|
||||
|
||||
Reference in New Issue
Block a user