Fix AssetId overflow for classic WVM decryption
Javascript/JSON does not support int64_t or unsigned numbers. asset_id, if greater than 0x80000000 will be converted to negative number. Use double to represent asset_id instead as 32-bit integer can be lossless represented using double. Bug: 26309000 Change-Id: I3e800c396a1231375776295154fb0d96156e980b
This commit is contained in:
parent
a9b039c3f9
commit
a4659c40dd
|
@ -184,7 +184,9 @@ Status WidevineKeySource::FetchKeys(const std::vector<uint8_t>& pssh_data) {
|
|||
Status WidevineKeySource::FetchKeys(uint32_t asset_id) {
|
||||
base::AutoLock scoped_lock(lock_);
|
||||
request_dict_.Clear();
|
||||
request_dict_.SetInteger("asset_id", asset_id);
|
||||
// Javascript/JSON does not support int64_t or unsigned numbers. Use double
|
||||
// instead as 32-bit integer can be lossless represented using double.
|
||||
request_dict_.SetDouble("asset_id", asset_id);
|
||||
return FetchKeysInternal(!kEnableKeyRotation, 0, true);
|
||||
}
|
||||
|
||||
|
@ -381,12 +383,18 @@ void WidevineKeySource::FillRequest(bool enable_key_rotation,
|
|||
|
||||
// Build key rotation fields.
|
||||
if (enable_key_rotation) {
|
||||
request_dict_.SetInteger("first_crypto_period_index",
|
||||
// Javascript/JSON does not support int64_t or unsigned numbers. Use double
|
||||
// instead as 32-bit integer can be lossless represented using double.
|
||||
request_dict_.SetDouble("first_crypto_period_index",
|
||||
first_crypto_period_index);
|
||||
request_dict_.SetInteger("crypto_period_count", crypto_period_count_);
|
||||
}
|
||||
|
||||
base::JSONWriter::Write(request_dict_, request);
|
||||
base::JSONWriter::WriteWithOptions(
|
||||
request_dict_,
|
||||
// Write doubles that have no fractional part as a normal integer, i.e.
|
||||
// without using exponential notation or appending a '.0'.
|
||||
base::JSONWriter::OPTIONS_OMIT_DOUBLE_TYPE_PRESERVATION, request);
|
||||
}
|
||||
|
||||
Status WidevineKeySource::GenerateKeyMessage(const std::string& request,
|
||||
|
|
|
@ -43,6 +43,12 @@ const char kLicenseStatusUnknownError[] = "UNKNOWN_ERROR";
|
|||
const char kExpectedRequestMessageFormat[] =
|
||||
"{\"content_id\":\"%s\",\"drm_types\":[\"WIDEVINE\"],\"policy\":\"%s\","
|
||||
"\"tracks\":[{\"type\":\"SD\"},{\"type\":\"HD\"},{\"type\":\"AUDIO\"}]}";
|
||||
const char kExpectedRequestMessageWithAssetIdFormat[] =
|
||||
"{\"asset_id\":%u,\"drm_types\":[\"WIDEVINE\"],"
|
||||
"\"tracks\":[{\"type\":\"SD\"},{\"type\":\"HD\"},{\"type\":\"AUDIO\"}]}";
|
||||
const char kExpectedRequestMessageWithPsshFormat[] =
|
||||
"{\"drm_types\":[\"WIDEVINE\"],\"pssh_data\":\"%s\","
|
||||
"\"tracks\":[{\"type\":\"SD\"},{\"type\":\"HD\"},{\"type\":\"AUDIO\"}]}";
|
||||
const char kExpectedSignedMessageFormat[] =
|
||||
"{\"request\":\"%s\",\"signature\":\"%s\",\"signer\":\"%s\"}";
|
||||
const char kTrackFormat[] =
|
||||
|
@ -52,7 +58,9 @@ const char kClassicTrackFormat[] = "{\"type\":\"%s\",\"key\":\"%s\"}";
|
|||
const char kLicenseResponseFormat[] = "{\"status\":\"%s\",\"tracks\":[%s]}";
|
||||
const char kHttpResponseFormat[] = "{\"response\":\"%s\"}";
|
||||
const char kRequestPsshData[] = "PSSH data";
|
||||
const uint32_t kClassicAssetId = 1234;
|
||||
// 32-bit with leading bit set, to verify that big uint32_t can be handled
|
||||
// correctly.
|
||||
const uint32_t kClassicAssetId = 0x80038cd9;
|
||||
|
||||
std::string Base64Encode(const std::string& input) {
|
||||
std::string output;
|
||||
|
@ -212,7 +220,8 @@ TEST_F(WidevineKeySourceTest, GenerateSignatureFailure) {
|
|||
TEST_F(WidevineKeySourceTest, HttpFetchFailure) {
|
||||
std::string expected_message = base::StringPrintf(
|
||||
kExpectedRequestMessageFormat, Base64Encode(kContentId).c_str(), kPolicy);
|
||||
EXPECT_CALL(*mock_request_signer_, GenerateSignature(expected_message, _))
|
||||
EXPECT_CALL(*mock_request_signer_,
|
||||
GenerateSignature(StrEq(expected_message), _))
|
||||
.WillOnce(DoAll(SetArgPointee<1>(kMockSignature), Return(true)));
|
||||
|
||||
std::string expected_post_data =
|
||||
|
@ -258,29 +267,43 @@ TEST_F(WidevineKeySourceTest, LicenseStatusCencNotOK) {
|
|||
}
|
||||
|
||||
TEST_F(WidevineKeySourceTest, LicenseStatusCencWithPsshDataOK) {
|
||||
std::string expected_message =
|
||||
base::StringPrintf(kExpectedRequestMessageWithPsshFormat,
|
||||
Base64Encode(kRequestPsshData).c_str());
|
||||
EXPECT_CALL(*mock_request_signer_,
|
||||
GenerateSignature(StrEq(expected_message), _))
|
||||
.WillOnce(DoAll(SetArgPointee<1>(kMockSignature), Return(true)));
|
||||
|
||||
std::string mock_response = base::StringPrintf(
|
||||
kHttpResponseFormat, Base64Encode(GenerateMockLicenseResponse()).c_str());
|
||||
|
||||
EXPECT_CALL(*mock_key_fetcher_, FetchKeys(_, _, _))
|
||||
.WillOnce(DoAll(SetArgPointee<2>(mock_response), Return(Status::OK)));
|
||||
|
||||
CreateWidevineKeySource();
|
||||
widevine_key_source_->set_signer(mock_request_signer_.Pass());
|
||||
std::vector<uint8_t> pssh_data(
|
||||
reinterpret_cast<const uint8_t*>(kRequestPsshData),
|
||||
reinterpret_cast<const uint8_t*>(kRequestPsshData) + strlen(kContentId));
|
||||
reinterpret_cast<const uint8_t*>(kRequestPsshData) +
|
||||
strlen(kRequestPsshData));
|
||||
ASSERT_OK(widevine_key_source_->FetchKeys(pssh_data));
|
||||
VerifyKeys(false);
|
||||
}
|
||||
|
||||
TEST_F(WidevineKeySourceTest, LicenseStatusClassicOK) {
|
||||
std::string expected_message = base::StringPrintf(
|
||||
kExpectedRequestMessageWithAssetIdFormat, kClassicAssetId);
|
||||
EXPECT_CALL(*mock_request_signer_,
|
||||
GenerateSignature(StrEq(expected_message), _))
|
||||
.WillOnce(DoAll(SetArgPointee<1>(kMockSignature), Return(true)));
|
||||
|
||||
std::string mock_response = base::StringPrintf(
|
||||
kHttpResponseFormat, Base64Encode(
|
||||
GenerateMockClassicLicenseResponse()).c_str());
|
||||
|
||||
EXPECT_CALL(*mock_key_fetcher_, FetchKeys(_, _, _))
|
||||
.WillOnce(DoAll(SetArgPointee<2>(mock_response), Return(Status::OK)));
|
||||
|
||||
CreateWidevineKeySource();
|
||||
widevine_key_source_->set_signer(mock_request_signer_.Pass());
|
||||
ASSERT_OK(widevine_key_source_->FetchKeys(kClassicAssetId));
|
||||
VerifyKeys(true);
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue