Fix cens Mode in Android CDM am: e0f4942b8f

am: 442099fb15

Change-Id: I978356e4982b83a3f343bb025fbeb5b33daee44f
This commit is contained in:
John "Juce" Bruce
2016-08-29 21:31:34 +00:00
committed by android-build-merger
4 changed files with 9 additions and 26 deletions

View File

@@ -282,11 +282,9 @@ enum CdmCipherMode {
struct CdmCencPatternEncryptionDescriptor { struct CdmCencPatternEncryptionDescriptor {
size_t encrypt_blocks; // number of 16 byte blocks to decrypt size_t encrypt_blocks; // number of 16 byte blocks to decrypt
size_t skip_blocks; // number of 16 byte blocks to leave in clear size_t skip_blocks; // number of 16 byte blocks to leave in clear
size_t offset_blocks; // offset into the pattern for this call, in blocks
CdmCencPatternEncryptionDescriptor() CdmCencPatternEncryptionDescriptor()
: encrypt_blocks(0), : encrypt_blocks(0),
skip_blocks(0), skip_blocks(0) {}
offset_blocks(0) {}
}; };
struct CdmDecryptionParameters { struct CdmDecryptionParameters {

View File

@@ -689,7 +689,7 @@ CdmResponseType CryptoSession::Decrypt(const CdmDecryptionParameters& params) {
OEMCrypto_CENCEncryptPatternDesc pattern_descriptor; OEMCrypto_CENCEncryptPatternDesc pattern_descriptor;
pattern_descriptor.encrypt = params.pattern_descriptor.encrypt_blocks; pattern_descriptor.encrypt = params.pattern_descriptor.encrypt_blocks;
pattern_descriptor.skip = params.pattern_descriptor.skip_blocks; pattern_descriptor.skip = params.pattern_descriptor.skip_blocks;
pattern_descriptor.offset = params.pattern_descriptor.offset_blocks; pattern_descriptor.offset = 0; // Deprecated field
AutoLock auto_lock(crypto_lock_); AutoLock auto_lock(crypto_lock_);
// Check if key needs to be selected // Check if key needs to be selected
if (params.is_encrypted) { if (params.is_encrypted) {

View File

@@ -47,7 +47,7 @@ class WVCryptoPlugin : public android::CryptoPlugin {
wvcdm::CdmSessionId configureTestMode(const void* data, size_t size); wvcdm::CdmSessionId configureTestMode(const void* data, size_t size);
static wvcdm::CdmResponseType countEncryptedBlocksInPatternedRange( static wvcdm::CdmResponseType countEncryptedBlocksInPatternedRange(
size_t range, size_t startingOffset, const Pattern& pattern, size_t range, size_t startingOffset, const Pattern& pattern,
size_t startingPatternOffset, uint64_t* result); uint64_t* result);
static void incrementIV(uint64_t increaseBy, std::vector<uint8_t>* ivPtr); static void incrementIV(uint64_t increaseBy, std::vector<uint8_t>* ivPtr);
}; };

View File

@@ -146,7 +146,6 @@ ssize_t WVCryptoPlugin::decrypt(bool secure, const uint8_t key[KEY_ID_SIZE],
size_t blockOffset = 0; size_t blockOffset = 0;
const size_t patternLengthInBytes = const size_t patternLengthInBytes =
(pattern.mEncryptBlocks + pattern.mSkipBlocks) * kAESBlockSize; (pattern.mEncryptBlocks + pattern.mSkipBlocks) * kAESBlockSize;
size_t patternOffsetInBytes = 0;
for (size_t i = 0; i < numSubSamples; ++i) { for (size_t i = 0; i < numSubSamples; ++i) {
const SubSample& subSample = subSamples[i]; const SubSample& subSample = subSamples[i];
@@ -187,7 +186,6 @@ ssize_t WVCryptoPlugin::decrypt(bool secure, const uint8_t key[KEY_ID_SIZE],
params.encrypt_buffer = source + offset; params.encrypt_buffer = source + offset;
params.encrypt_length = subSample.mNumBytesOfClearData; params.encrypt_length = subSample.mNumBytesOfClearData;
params.block_offset = 0; params.block_offset = 0;
params.pattern_descriptor.offset_blocks = 0;
params.decrypt_buffer_offset = offset; params.decrypt_buffer_offset = offset;
params.subsample_flags = clearFlags; params.subsample_flags = clearFlags;
@@ -238,12 +236,6 @@ ssize_t WVCryptoPlugin::decrypt(bool secure, const uint8_t key[KEY_ID_SIZE],
params.encrypt_buffer = source + offset; params.encrypt_buffer = source + offset;
params.encrypt_length = subSample.mNumBytesOfEncryptedData; params.encrypt_length = subSample.mNumBytesOfEncryptedData;
params.block_offset = blockOffset; params.block_offset = blockOffset;
// Note that the pattern offset calculation relies intentionally on
// integer division's flooring behavior. If we are partway through a
// crypto block, we should return the offset of the pattern block we are
// partway through.
size_t patternOffsetInBlocks = patternOffsetInBytes / kAESBlockSize;
params.pattern_descriptor.offset_blocks = patternOffsetInBlocks;
params.decrypt_buffer_offset = offset; params.decrypt_buffer_offset = offset;
params.subsample_flags = encryptedFlags; params.subsample_flags = encryptedFlags;
@@ -301,7 +293,7 @@ ssize_t WVCryptoPlugin::decrypt(bool secure, const uint8_t key[KEY_ID_SIZE],
} else { } else {
res = countEncryptedBlocksInPatternedRange( res = countEncryptedBlocksInPatternedRange(
subSample.mNumBytesOfEncryptedData, blockOffset, pattern, subSample.mNumBytesOfEncryptedData, blockOffset, pattern,
patternOffsetInBlocks, &increment); &increment);
if (!isCdmResponseTypeSuccess(res)) { if (!isCdmResponseTypeSuccess(res)) {
// Swallow the specifics of the error to obscure decrypt internals. // Swallow the specifics of the error to obscure decrypt internals.
return kErrorCDMGeneric; return kErrorCDMGeneric;
@@ -312,12 +304,6 @@ ssize_t WVCryptoPlugin::decrypt(bool secure, const uint8_t key[KEY_ID_SIZE],
// Update the block offset // Update the block offset
blockOffset = (blockOffset + subSample.mNumBytesOfEncryptedData) % blockOffset = (blockOffset + subSample.mNumBytesOfEncryptedData) %
kAESBlockSize; kAESBlockSize;
if (patternLengthInBytes > 0) {
patternOffsetInBytes =
(patternOffsetInBytes + subSample.mNumBytesOfEncryptedData) %
patternLengthInBytes;
}
} else if (mode == kMode_AES_CBC && patternLengthInBytes == 0) { } else if (mode == kMode_AES_CBC && patternLengthInBytes == 0) {
// If there is no pattern, assume cbc1 mode and update the IV. // If there is no pattern, assume cbc1 mode and update the IV.
@@ -363,14 +349,13 @@ ssize_t WVCryptoPlugin::decrypt(bool secure, const uint8_t key[KEY_ID_SIZE],
CdmResponseType WVCryptoPlugin::countEncryptedBlocksInPatternedRange( CdmResponseType WVCryptoPlugin::countEncryptedBlocksInPatternedRange(
size_t range, size_t startingOffset, const Pattern& pattern, size_t range, size_t startingOffset, const Pattern& pattern,
size_t startingPatternOffset, uint64_t* result) { uint64_t* result) {
uint64_t blocksPassed = 0; uint64_t blocksPassed = 0;
size_t bytesRemaining = range; size_t bytesRemaining = range;
size_t patternOffset = startingPatternOffset; size_t patternPosition = 0;
size_t patternLength = pattern.mEncryptBlocks + pattern.mSkipBlocks; size_t patternLength = pattern.mEncryptBlocks + pattern.mSkipBlocks;
if (result == NULL || startingOffset >= kAESBlockSize || if (result == NULL || startingOffset >= kAESBlockSize) {
startingPatternOffset >= patternLength) {
return wvcdm::UNKNOWN_ERROR; return wvcdm::UNKNOWN_ERROR;
} }
@@ -379,10 +364,10 @@ CdmResponseType WVCryptoPlugin::countEncryptedBlocksInPatternedRange(
size_t bytesNeededToCompleteABlock = kAESBlockSize - startingOffset; size_t bytesNeededToCompleteABlock = kAESBlockSize - startingOffset;
while (bytesRemaining >= bytesNeededToCompleteABlock) { while (bytesRemaining >= bytesNeededToCompleteABlock) {
bytesRemaining -= bytesNeededToCompleteABlock; bytesRemaining -= bytesNeededToCompleteABlock;
if (patternOffset < pattern.mEncryptBlocks) { if (patternPosition < pattern.mEncryptBlocks) {
++blocksPassed; ++blocksPassed;
} }
patternOffset = (patternOffset + 1) % patternLength; patternPosition = (patternPosition + 1) % patternLength;
// After the first block, we only concern ourselves with complete blocks. // After the first block, we only concern ourselves with complete blocks.
bytesNeededToCompleteABlock = kAESBlockSize; bytesNeededToCompleteABlock = kAESBlockSize;