From 169c5b3d10fb443bcde69ff48cecefa6e606816b Mon Sep 17 00:00:00 2001 From: "John W. Bruce" Date: Wed, 15 Jan 2020 16:42:52 -0800 Subject: [PATCH] Revert "Fix IV handling for pattern encryption." (This is a merge of http://go/wvgerrit/92191) This reverts commit 8fe569cc1265021e275a9bccbc362ebd2ba3be5f. The ISO-CENC spec is ambiguous about how to handle the early truncation of the pattern in the 'cens' and 'cbcs' schema. We originally interpreted it to mean "follow the pattern until you run out of full crypto blocks" and shipped the Android and OEMCrypto code accordingly. Later, however, other engineers at Google asserted that it should mean "follow the pattern until you run out of enough crypto blocks to follow the encrypted part of the pattern", which is subtly different when the number of encrypted blocks in the pattern is greater than 1. We made changes to start accommodating this. However, after further discussion, everyone is in agreement that the original behavior was correct. So I am reverting the "fixes" that had already been made. This has no practical effect, since it only affects 'cens' content with a pattern that has more than one encrypted block, and as far as we know, no one has ever generated content like that. Shaka Packager is not capable of generating content like that. Bug: 111001481 Test: No new Android Unit Tests failures Change-Id: I8f0292b1222d6af9a0ae33d6cb91707fd40101f4 --- .../mediacrypto/src/WVCryptoPlugin.cpp | 18 +++++++++++++----- .../mediacrypto/src_hidl/WVCryptoPlugin.cpp | 18 +++++++++++++----- 2 files changed, 26 insertions(+), 10 deletions(-) diff --git a/libwvdrmengine/mediacrypto/src/WVCryptoPlugin.cpp b/libwvdrmengine/mediacrypto/src/WVCryptoPlugin.cpp index ec9005b6..bd23fb61 100644 --- a/libwvdrmengine/mediacrypto/src/WVCryptoPlugin.cpp +++ b/libwvdrmengine/mediacrypto/src/WVCryptoPlugin.cpp @@ -10,6 +10,7 @@ #include "WVCryptoPlugin.h" +#include #include #include #include @@ -234,16 +235,23 @@ ssize_t WVCryptoPlugin::decrypt(bool secure, const uint8_t key[KEY_ID_SIZE], increment = (blockOffset + subSample.mNumBytesOfEncryptedData) / kAESBlockSize; } else { + // The truncation in the integer divisions in this block is + // intentional. const uint64_t numBlocks = subSample.mNumBytesOfEncryptedData / kAESBlockSize; const uint64_t patternLengthInBlocks = pattern.mEncryptBlocks + pattern.mSkipBlocks; + const uint64_t numFullPatternRepetitions = + numBlocks / patternLengthInBlocks; + const uint64_t numDanglingBlocks = + numBlocks % patternLengthInBlocks; + const uint64_t numDanglingEncryptedBlocks = + std::min(static_cast(pattern.mEncryptBlocks), + numDanglingBlocks); + increment = - (numBlocks / patternLengthInBlocks) * pattern.mEncryptBlocks; - // A partial pattern is only encrypted if it is at least - // mEncryptBlocks large. - if (numBlocks % patternLengthInBlocks >= pattern.mEncryptBlocks) - increment += pattern.mEncryptBlocks; + numFullPatternRepetitions * pattern.mEncryptBlocks + + numDanglingEncryptedBlocks; } incrementIV(increment, &ivVector); diff --git a/libwvdrmengine/mediacrypto/src_hidl/WVCryptoPlugin.cpp b/libwvdrmengine/mediacrypto/src_hidl/WVCryptoPlugin.cpp index 6a719f92..239f786c 100644 --- a/libwvdrmengine/mediacrypto/src_hidl/WVCryptoPlugin.cpp +++ b/libwvdrmengine/mediacrypto/src_hidl/WVCryptoPlugin.cpp @@ -10,6 +10,7 @@ #include "WVCryptoPlugin.h" +#include #include #include "HidlTypes.h" @@ -338,16 +339,23 @@ Return WVCryptoPlugin::decrypt_1_2( increment = (blockOffset + subSample.numBytesOfEncryptedData) / kAESBlockSize; } else { + // The truncation in the integer divisions in this block is + // intentional. const uint64_t numBlocks = subSample.numBytesOfEncryptedData / kAESBlockSize; const uint64_t patternLengthInBlocks = pattern.encryptBlocks + pattern.skipBlocks; + const uint64_t numFullPatternRepetitions = + numBlocks / patternLengthInBlocks; + const uint64_t numDanglingBlocks = + numBlocks % patternLengthInBlocks; + const uint64_t numDanglingEncryptedBlocks = + std::min(static_cast(pattern.encryptBlocks), + numDanglingBlocks); + increment = - (numBlocks / patternLengthInBlocks) * pattern.encryptBlocks; - // A partial pattern is only encrypted if it is at least - // mEncryptBlocks large. - if (numBlocks % patternLengthInBlocks >= pattern.encryptBlocks) - increment += pattern.encryptBlocks; + numFullPatternRepetitions * pattern.encryptBlocks + + numDanglingEncryptedBlocks; } incrementIV(increment, &ivVector);