Source release 18.5.0
This commit is contained in:
@@ -62,7 +62,7 @@ OEMCryptoResult WrapIfNecessary(OEMCryptoResult ret_value) { return ret_value; }
|
||||
}
|
||||
|
||||
#define RETURN_IF_NOT_OPEN(ret_value) \
|
||||
if (!open_) { \
|
||||
if (!IsOpen()) { \
|
||||
LOGE("Crypto session is not open"); \
|
||||
return WrapIfNecessary(ret_value); \
|
||||
}
|
||||
@@ -70,17 +70,8 @@ OEMCryptoResult WrapIfNecessary(OEMCryptoResult ret_value) { return ret_value; }
|
||||
#define CRYPTO_ERROR(cdm_err, oem_err) \
|
||||
CdmResponseType(cdm_err, oem_err, __func__)
|
||||
|
||||
#ifdef HAS_DUAL_KEY
|
||||
/**
|
||||
* Internal only OEMCrypto method. This is called before parsing the license
|
||||
* response to indicate the response uses dual keys. If this isn't called,
|
||||
* it is using single keys.
|
||||
*/
|
||||
extern "C" OEMCryptoResult OEMCrypto_UseSecondaryKey(OEMCrypto_SESSION session,
|
||||
bool dual_key);
|
||||
#endif
|
||||
|
||||
namespace wvcdm {
|
||||
|
||||
namespace {
|
||||
using UsageTableLock = std::unique_lock<std::recursive_mutex>;
|
||||
|
||||
@@ -93,6 +84,8 @@ constexpr size_t kAes128BlockSize = 16;
|
||||
|
||||
constexpr int kMaxTerminateCountDown = 5;
|
||||
|
||||
constexpr char kUnavailableHdcpLevel[] = "<unavailable>";
|
||||
|
||||
const std::string kStringNotAvailable = "NA";
|
||||
|
||||
// TODO(b/174412779): Remove when b/170704368 is fixed.
|
||||
@@ -292,6 +285,37 @@ OEMCryptoCipherMode ToOEMCryptoCipherMode(CdmCipherMode cipher_mode) {
|
||||
: OEMCrypto_CipherMode_CBCS;
|
||||
}
|
||||
|
||||
// static
|
||||
const char* CryptoSession::HdcpCapabilityToString(HdcpCapability hdcp_level) {
|
||||
switch (hdcp_level) {
|
||||
case HDCP_NONE:
|
||||
return "None";
|
||||
case HDCP_V1: // Means v1.x
|
||||
return "v1.x";
|
||||
case HDCP_V2: // Means v2.0
|
||||
return "v2.0";
|
||||
case HDCP_V2_1:
|
||||
return "v2.1";
|
||||
case HDCP_V2_2:
|
||||
return "v2.2";
|
||||
case HDCP_V2_3:
|
||||
return "v2.3";
|
||||
case HDCP_V1_0:
|
||||
return "v1.0";
|
||||
case HDCP_V1_1:
|
||||
return "v1.1";
|
||||
case HDCP_V1_2:
|
||||
return "v1.2";
|
||||
case HDCP_V1_3:
|
||||
return "v1.3";
|
||||
case HDCP_V1_4:
|
||||
return "v1.4";
|
||||
case HDCP_NO_DIGITAL_OUTPUT:
|
||||
return "No-Digital-Output";
|
||||
}
|
||||
return UnknownEnumValueToString(static_cast<int>(hdcp_level));
|
||||
}
|
||||
|
||||
CryptoSession::CryptoSession(metrics::CryptoMetrics* metrics)
|
||||
: metrics_(metrics),
|
||||
system_id_(NULL_SYSTEM_ID),
|
||||
@@ -345,6 +369,9 @@ CdmResponseType CryptoSession::GetProvisioningMethod(
|
||||
case OEMCrypto_BootCertificateChain:
|
||||
type = kClientTokenBootCertChain;
|
||||
break;
|
||||
case OEMCrypto_DrmReprovisioning:
|
||||
type = kClientTokenDrmCertificateReprovisioning;
|
||||
break;
|
||||
case OEMCrypto_ProvisioningError:
|
||||
default:
|
||||
if (static_cast<int>(method) == 0 && needs_keybox_provisioning_) {
|
||||
@@ -661,6 +688,9 @@ CdmResponseType CryptoSession::GetProvisioningToken(
|
||||
} else if (pre_provision_token_type_ == kClientTokenBootCertChain) {
|
||||
status = GetBootCertificateChain(requested_security_level, token,
|
||||
additional_token);
|
||||
} else if (pre_provision_token_type_ ==
|
||||
kClientTokenDrmCertificateReprovisioning) {
|
||||
status = GetTokenFromEmbeddedCertificate(token);
|
||||
}
|
||||
metrics_->crypto_session_get_token_.Increment(status);
|
||||
return status;
|
||||
@@ -1229,6 +1259,7 @@ CdmResponseType CryptoSession::PrepareAndSignProvisioningRequest(
|
||||
}
|
||||
|
||||
OEMCryptoResult sts;
|
||||
// TODO: b/305093063 - Refactor to a switch statement to improve readability
|
||||
if (pre_provision_token_type_ == kClientTokenKeybox) {
|
||||
should_specify_algorithm = false;
|
||||
const CdmResponseType status = GenerateDerivedKeys(message);
|
||||
@@ -1246,6 +1277,11 @@ CdmResponseType CryptoSession::PrepareAndSignProvisioningRequest(
|
||||
should_specify_algorithm = true;
|
||||
// Do nothing here. The key to signing the provisioning 4.0 request for each
|
||||
// stage has been loaded already when it was generated by OEMCrypto.
|
||||
} else if (pre_provision_token_type_ ==
|
||||
kClientTokenDrmCertificateReprovisioning) {
|
||||
should_specify_algorithm = false;
|
||||
// Do nothing here. The baked-in certificate used as the token has already
|
||||
// been loaded when the EncryptedClientId was filled in.
|
||||
} else {
|
||||
LOGE("Unknown method %d", pre_provision_token_type_);
|
||||
return CdmResponseType(UNKNOWN_CLIENT_TOKEN_TYPE);
|
||||
@@ -1417,6 +1453,153 @@ CdmResponseType CryptoSession::GetBootCertificateChain(
|
||||
return CdmResponseType(NO_ERROR);
|
||||
}
|
||||
|
||||
CdmResponseType CryptoSession::GetTokenFromEmbeddedCertificate(
|
||||
std::string* token) {
|
||||
RETURN_IF_UNINITIALIZED(CRYPTO_SESSION_NOT_INITIALIZED);
|
||||
RETURN_IF_NULL(token, PARAMETER_NULL);
|
||||
|
||||
CdmClientTokenType token_type = kClientTokenUninitialized;
|
||||
const CdmResponseType sts =
|
||||
GetProvisioningMethod(requested_security_level_, &token_type);
|
||||
if (sts != NO_ERROR) {
|
||||
LOGE("Failed to get token type");
|
||||
return sts;
|
||||
}
|
||||
if (token_type != kClientTokenDrmCertificateReprovisioning) {
|
||||
token->clear();
|
||||
return CdmResponseType(NO_ERROR);
|
||||
}
|
||||
|
||||
size_t certificate_length = CERTIFICATE_DATA_SIZE;
|
||||
std::string embedded_certificate(certificate_length, '\0');
|
||||
OEMCryptoResult status =
|
||||
WithOecReadLock("GetTokenFromEmbeddedCertificate - attempt 1", [&] {
|
||||
return OEMCrypto_GetEmbeddedDrmCertificate(
|
||||
reinterpret_cast<uint8_t*>(&embedded_certificate.front()),
|
||||
&certificate_length);
|
||||
});
|
||||
|
||||
if (status == OEMCrypto_ERROR_SHORT_BUFFER) {
|
||||
embedded_certificate.assign(certificate_length, '\0');
|
||||
status =
|
||||
WithOecReadLock("GetTokenFromEmbeddedCertificate - attempt 2", [&] {
|
||||
return OEMCrypto_GetEmbeddedDrmCertificate(
|
||||
reinterpret_cast<uint8_t*>(&embedded_certificate.front()),
|
||||
&certificate_length);
|
||||
});
|
||||
}
|
||||
|
||||
if (status == OEMCrypto_SUCCESS) {
|
||||
// TODO: b/312782308 - Store embedded certificate as SignedDrmCertificate
|
||||
video_widevine_client::sdk::HashedFile hashed_file;
|
||||
video_widevine_client::sdk::File file;
|
||||
embedded_certificate.resize(certificate_length);
|
||||
if (hashed_file.ParseFromString(embedded_certificate) &&
|
||||
file.ParseFromString(hashed_file.file())) {
|
||||
*token = file.device_certificate().certificate();
|
||||
return CdmResponseType(NO_ERROR);
|
||||
}
|
||||
}
|
||||
|
||||
token->clear();
|
||||
return MapOEMCryptoResult(status, GET_TOKEN_FROM_EMBEDDED_CERT_ERROR,
|
||||
"GetTokenFromEmbeddedCertificate");
|
||||
}
|
||||
|
||||
CdmResponseType CryptoSession::GetDeviceInformation(
|
||||
RequestedSecurityLevel requested_security_level, std::string* device_info) {
|
||||
RETURN_IF_NULL(device_info, PARAMETER_NULL);
|
||||
RETURN_IF_UNINITIALIZED(CRYPTO_SESSION_NOT_INITIALIZED);
|
||||
if (GetSecurityLevel(requested_security_level) != kSecurityLevelL1) {
|
||||
LOGE("CDM only supports L1 device_info");
|
||||
return CdmResponseType(NOT_IMPLEMENTED_ERROR);
|
||||
}
|
||||
CdmClientTokenType token_type = kClientTokenUninitialized;
|
||||
const CdmResponseType status =
|
||||
GetProvisioningMethod(requested_security_level, &token_type);
|
||||
if (status != NO_ERROR) {
|
||||
LOGE("Failed to get token type");
|
||||
return status;
|
||||
}
|
||||
if (token_type != kClientTokenBootCertChain) {
|
||||
return CdmResponseType(
|
||||
PROVISIONING_TYPE_IS_NOT_BOOT_CERTIFICATE_CHAIN_ERROR);
|
||||
}
|
||||
|
||||
size_t device_info_length = 0;
|
||||
OEMCryptoResult sts = WithOecReadLock("GetDeviceInformation Attempt 1", [&] {
|
||||
return OEMCrypto_GetDeviceInformation(nullptr, &device_info_length);
|
||||
});
|
||||
if (sts == OEMCrypto_ERROR_SHORT_BUFFER) {
|
||||
device_info->resize(device_info_length);
|
||||
sts = WithOecReadLock("GetDeviceInformation Attempt 2", [&] {
|
||||
return OEMCrypto_GetDeviceInformation(
|
||||
MutableStringDataPointer(device_info), &device_info_length);
|
||||
});
|
||||
}
|
||||
if (sts != OEMCrypto_SUCCESS) {
|
||||
LOGE("OEMCrypto_GetDeviceInformation failed: status = %d",
|
||||
static_cast<int>(sts));
|
||||
device_info->clear();
|
||||
return MapOEMCryptoResult(sts, GET_DEVICE_INFORMATION_ERROR,
|
||||
"GetDeviceInformation");
|
||||
}
|
||||
device_info->resize(device_info_length);
|
||||
return CdmResponseType(NO_ERROR);
|
||||
}
|
||||
|
||||
CdmResponseType CryptoSession::GetDeviceSignedCsrPayload(
|
||||
RequestedSecurityLevel requested_security_level,
|
||||
const std::string& challenge, const std::string& device_info,
|
||||
std::string* signed_csr_payload) {
|
||||
RETURN_IF_NULL(signed_csr_payload, PARAMETER_NULL);
|
||||
RETURN_IF_UNINITIALIZED(CRYPTO_SESSION_NOT_INITIALIZED);
|
||||
if (GetSecurityLevel(requested_security_level) != kSecurityLevelL1) {
|
||||
LOGE("CDM only supports L1 CSR payload");
|
||||
return CdmResponseType(NOT_IMPLEMENTED_ERROR);
|
||||
}
|
||||
CdmClientTokenType token_type = kClientTokenUninitialized;
|
||||
const CdmResponseType status =
|
||||
GetProvisioningMethod(requested_security_level, &token_type);
|
||||
if (status != NO_ERROR) {
|
||||
LOGE("Failed to get token type");
|
||||
return status;
|
||||
}
|
||||
if (token_type != kClientTokenBootCertChain) {
|
||||
return CdmResponseType(
|
||||
PROVISIONING_TYPE_IS_NOT_BOOT_CERTIFICATE_CHAIN_ERROR);
|
||||
}
|
||||
|
||||
size_t signed_csr_payload_length = 0;
|
||||
OEMCryptoResult sts =
|
||||
WithOecReadLock("GetDeviceSignedCsrPayload Attempt 1", [&] {
|
||||
return OEMCrypto_GetDeviceSignedCsrPayload(
|
||||
reinterpret_cast<const uint8_t*>(challenge.data()),
|
||||
challenge.size(),
|
||||
reinterpret_cast<const uint8_t*>(device_info.data()),
|
||||
device_info.size(), nullptr, &signed_csr_payload_length);
|
||||
});
|
||||
if (sts == OEMCrypto_ERROR_SHORT_BUFFER) {
|
||||
signed_csr_payload->resize(signed_csr_payload_length);
|
||||
sts = WithOecReadLock("GetDeviceSignedCsrPayload Attempt 2", [&] {
|
||||
return OEMCrypto_GetDeviceSignedCsrPayload(
|
||||
reinterpret_cast<const uint8_t*>(challenge.data()), challenge.size(),
|
||||
reinterpret_cast<const uint8_t*>(device_info.data()),
|
||||
device_info.size(), MutableStringDataPointer(signed_csr_payload),
|
||||
&signed_csr_payload_length);
|
||||
});
|
||||
}
|
||||
if (sts != OEMCrypto_SUCCESS) {
|
||||
LOGE("OEMCrypto_GetDeviceSignedCsrPayload failed: status = %d",
|
||||
static_cast<int>(sts));
|
||||
signed_csr_payload->clear();
|
||||
return MapOEMCryptoResult(sts, GET_DEVICE_SIGNED_CSR_PAYLOAD_ERROR,
|
||||
"GetDeviceSignedCsrPayload");
|
||||
}
|
||||
signed_csr_payload->resize(signed_csr_payload_length);
|
||||
return CdmResponseType(NO_ERROR);
|
||||
}
|
||||
|
||||
CdmResponseType CryptoSession::GenerateCertificateKeyPair(
|
||||
std::string* public_key, std::string* public_key_signature,
|
||||
std::string* wrapped_private_key, CryptoWrappedKey::Type* key_type) {
|
||||
@@ -1513,6 +1696,35 @@ CdmResponseType CryptoSession::SelectKey(const std::string& key_id,
|
||||
return key_session_->SelectKey(key_id, cipher_mode);
|
||||
});
|
||||
|
||||
if (sts != last_select_key_error_) {
|
||||
// Only log errors on first occurrence. Calls to SelectKey from
|
||||
// the app are typically queued. If an error occurs, then it is
|
||||
// expected that multiple failures will occur before the app is
|
||||
// notified and stops queueing calls to the CDM.
|
||||
last_select_key_error_ = sts;
|
||||
if (sts == OEMCrypto_ERROR_INSUFFICIENT_HDCP ||
|
||||
sts == OEMCrypto_WARNING_MIXED_OUTPUT_PROTECTION) {
|
||||
const char* status_message = OemCryptoResultToString(sts);
|
||||
HdcpCapability current_hdcp_level;
|
||||
HdcpCapability max_hdcp_level;
|
||||
const CdmResponseType hdcp_status =
|
||||
GetHdcpCapabilities(¤t_hdcp_level, &max_hdcp_level);
|
||||
const char* current_hdcp_message = kUnavailableHdcpLevel;
|
||||
const char* max_hdcp_message = kUnavailableHdcpLevel;
|
||||
if (hdcp_status == NO_ERROR) {
|
||||
current_hdcp_message = HdcpCapabilityToString(current_hdcp_level);
|
||||
max_hdcp_message = HdcpCapabilityToString(max_hdcp_level);
|
||||
}
|
||||
LOGE(
|
||||
"oec_session_id = %u, security_level = %s, "
|
||||
"status = %s, current_hdcp_level = %s, "
|
||||
"max_hdcp_level = %s",
|
||||
oec_session_id_,
|
||||
RequestedSecurityLevelToString(requested_security_level_),
|
||||
status_message, current_hdcp_message, max_hdcp_message);
|
||||
}
|
||||
}
|
||||
|
||||
switch (sts) {
|
||||
// SelectKey errors.
|
||||
case OEMCrypto_SUCCESS:
|
||||
@@ -1781,8 +1993,8 @@ CdmResponseType CryptoSession::Decrypt(
|
||||
}
|
||||
|
||||
// Perform decrypt
|
||||
const OEMCryptoResult sts =
|
||||
DecryptMultipleSamples(oec_samples, params.cipher_mode, oec_pattern);
|
||||
const OEMCryptoResult sts = DecryptMultipleSamples(
|
||||
oec_samples, params.cipher_mode, oec_pattern, is_any_sample_protected);
|
||||
|
||||
if (sts != OEMCrypto_SUCCESS && last_decrypt_error_ != sts) {
|
||||
// Decrypt errors and warnings are only logged when the error code
|
||||
@@ -1791,11 +2003,26 @@ CdmResponseType CryptoSession::Decrypt(
|
||||
// the next call. The calling application may make several more
|
||||
// decrypt requests before the error is handled by the app.
|
||||
last_decrypt_error_ = sts;
|
||||
if (sts == OEMCrypto_WARNING_MIXED_OUTPUT_PROTECTION) {
|
||||
LOGW(
|
||||
"OEMCrypto_DecryptCENC is warning of mixed HDCP output protection: "
|
||||
"oec_session_id = %u",
|
||||
oec_session_id_);
|
||||
if (sts == OEMCrypto_WARNING_MIXED_OUTPUT_PROTECTION ||
|
||||
sts == OEMCrypto_ERROR_INSUFFICIENT_HDCP) {
|
||||
const char* status_message = OemCryptoResultToString(sts);
|
||||
HdcpCapability current_hdcp_level;
|
||||
HdcpCapability max_hdcp_level;
|
||||
const CdmResponseType hdcp_status =
|
||||
GetHdcpCapabilities(¤t_hdcp_level, &max_hdcp_level);
|
||||
const char* current_hdcp_message = kUnavailableHdcpLevel;
|
||||
const char* max_hdcp_message = kUnavailableHdcpLevel;
|
||||
if (hdcp_status == NO_ERROR) {
|
||||
current_hdcp_message = HdcpCapabilityToString(current_hdcp_level);
|
||||
max_hdcp_message = HdcpCapabilityToString(max_hdcp_level);
|
||||
}
|
||||
LOGE(
|
||||
"OEMCrypto_DecryptCENC failed: oec_session_id = %u, "
|
||||
"security_level = %s, status = %s, current_hdcp_level = %s, "
|
||||
"max_hdcp_level = %s",
|
||||
oec_session_id_,
|
||||
RequestedSecurityLevelToString(requested_security_level_),
|
||||
status_message, current_hdcp_message, max_hdcp_message);
|
||||
} else {
|
||||
LOGE(
|
||||
"OEMCrypto_DecryptCENC failed: oec_session_id = %u, "
|
||||
@@ -2914,22 +3141,24 @@ bool CryptoSession::GetAnalogOutputCapabilities(bool* can_support_output,
|
||||
|
||||
OEMCryptoResult CryptoSession::DecryptMultipleSamples(
|
||||
const std::vector<OEMCrypto_SampleDescription>& samples,
|
||||
CdmCipherMode cipher_mode,
|
||||
const OEMCrypto_CENCEncryptPatternDesc& pattern) {
|
||||
CdmCipherMode cipher_mode, const OEMCrypto_CENCEncryptPatternDesc& pattern,
|
||||
bool is_any_subsample_protected) {
|
||||
OEMCryptoResult sts = OEMCrypto_ERROR_BUFFER_TOO_LARGE;
|
||||
|
||||
// If there's only one sample, automatically fall through to avoid a redundant
|
||||
// roundtrip through OEMCrypto_DecryptCENC()
|
||||
if (samples.size() > 1) {
|
||||
WithOecSessionLock("DecryptMultipleSamples", [&] {
|
||||
sts = key_session_->Decrypt(samples.data(), samples.size(), pattern);
|
||||
sts = key_session_->Decrypt(samples.data(), samples.size(), pattern,
|
||||
is_any_subsample_protected);
|
||||
});
|
||||
}
|
||||
|
||||
if (sts == OEMCrypto_ERROR_BUFFER_TOO_LARGE) {
|
||||
// Fall back to sending each sample individually
|
||||
for (const OEMCrypto_SampleDescription& sample : samples) {
|
||||
sts = DecryptSample(sample, cipher_mode, pattern);
|
||||
sts = DecryptSample(sample, cipher_mode, pattern,
|
||||
is_any_subsample_protected);
|
||||
if (sts != OEMCrypto_SUCCESS) break;
|
||||
}
|
||||
}
|
||||
@@ -2939,7 +3168,8 @@ OEMCryptoResult CryptoSession::DecryptMultipleSamples(
|
||||
|
||||
OEMCryptoResult CryptoSession::DecryptSample(
|
||||
const OEMCrypto_SampleDescription& sample, CdmCipherMode cipher_mode,
|
||||
const OEMCrypto_CENCEncryptPatternDesc& pattern) {
|
||||
const OEMCrypto_CENCEncryptPatternDesc& pattern,
|
||||
bool is_any_subsample_protected) {
|
||||
OEMCryptoResult sts = OEMCrypto_ERROR_BUFFER_TOO_LARGE;
|
||||
|
||||
// If there's only one subsample and it contains only one type of region,
|
||||
@@ -2949,7 +3179,8 @@ OEMCryptoResult CryptoSession::DecryptSample(
|
||||
(sample.subsamples[0].num_bytes_clear > 0 &&
|
||||
sample.subsamples[0].num_bytes_encrypted > 0)) {
|
||||
WithOecSessionLock("DecryptSample", [&] {
|
||||
sts = key_session_->Decrypt(&sample, 1, pattern);
|
||||
sts = key_session_->Decrypt(&sample, 1, pattern,
|
||||
is_any_subsample_protected);
|
||||
});
|
||||
}
|
||||
|
||||
@@ -2981,7 +3212,8 @@ OEMCryptoResult CryptoSession::DecryptSample(
|
||||
fake_sample.subsamples = &clear_subsample;
|
||||
fake_sample.subsamples_length = 1;
|
||||
|
||||
sts = LegacyDecrypt(fake_sample, cipher_mode, pattern);
|
||||
sts = LegacyDecrypt(fake_sample, cipher_mode, pattern,
|
||||
is_any_subsample_protected);
|
||||
if (sts != OEMCrypto_SUCCESS) break;
|
||||
|
||||
fake_sample.buffers.input_data += length;
|
||||
@@ -3007,7 +3239,8 @@ OEMCryptoResult CryptoSession::DecryptSample(
|
||||
fake_sample.subsamples = &encrypted_subsample;
|
||||
fake_sample.subsamples_length = 1;
|
||||
|
||||
sts = LegacyDecrypt(fake_sample, cipher_mode, pattern);
|
||||
sts = LegacyDecrypt(fake_sample, cipher_mode, pattern,
|
||||
is_any_subsample_protected);
|
||||
if (sts != OEMCrypto_SUCCESS) break;
|
||||
|
||||
fake_sample.buffers.input_data += length;
|
||||
@@ -3026,7 +3259,8 @@ OEMCryptoResult CryptoSession::DecryptSample(
|
||||
|
||||
OEMCryptoResult CryptoSession::LegacyDecrypt(
|
||||
const OEMCrypto_SampleDescription& sample, CdmCipherMode cipher_mode,
|
||||
const OEMCrypto_CENCEncryptPatternDesc& pattern) {
|
||||
const OEMCrypto_CENCEncryptPatternDesc& pattern,
|
||||
bool is_any_subsample_protected) {
|
||||
const size_t max_chunk_size = GetMaxSubsampleRegionSize();
|
||||
OEMCryptoResult sts = OEMCrypto_ERROR_NOT_IMPLEMENTED;
|
||||
|
||||
@@ -3056,7 +3290,8 @@ OEMCryptoResult CryptoSession::LegacyDecrypt(
|
||||
}
|
||||
if (is_encrypted || sts == OEMCrypto_ERROR_NOT_IMPLEMENTED) {
|
||||
WithOecSessionLock("LegacyDecrypt() calling key_session_->Decrypt()", [&] {
|
||||
sts = key_session_->Decrypt(&sample, 1, pattern);
|
||||
sts = key_session_->Decrypt(&sample, 1, pattern,
|
||||
is_any_subsample_protected);
|
||||
});
|
||||
|
||||
if (sts == OEMCrypto_ERROR_BUFFER_TOO_LARGE) {
|
||||
@@ -3072,7 +3307,8 @@ OEMCryptoResult CryptoSession::LegacyDecrypt(
|
||||
: max_chunk_size;
|
||||
|
||||
if (sample.buffers.input_data_length > chunk_size) {
|
||||
sts = LegacyDecryptInChunks(sample, cipher_mode, pattern, chunk_size);
|
||||
sts = LegacyDecryptInChunks(sample, cipher_mode, pattern, chunk_size,
|
||||
is_any_subsample_protected);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -3121,7 +3357,8 @@ OEMCryptoResult CryptoSession::LegacyCopyBufferInChunks(
|
||||
|
||||
OEMCryptoResult CryptoSession::LegacyDecryptInChunks(
|
||||
const OEMCrypto_SampleDescription& sample, CdmCipherMode cipher_mode,
|
||||
const OEMCrypto_CENCEncryptPatternDesc& pattern, size_t max_chunk_size) {
|
||||
const OEMCrypto_CENCEncryptPatternDesc& pattern, size_t max_chunk_size,
|
||||
bool is_any_subsample_protected) {
|
||||
const OEMCrypto_SubSampleDescription& subsample = sample.subsamples[0];
|
||||
|
||||
const bool is_protected = (subsample.num_bytes_encrypted > 0);
|
||||
@@ -3155,7 +3392,8 @@ OEMCryptoResult CryptoSession::LegacyDecryptInChunks(
|
||||
// pattern length long, which is also guaranteed to be an exact number
|
||||
// of AES blocks long.
|
||||
WithOecSessionLock("LegacyDecryptInChunks", [&] {
|
||||
sts = key_session_->Decrypt(&fake_sample, 1, pattern);
|
||||
sts = key_session_->Decrypt(&fake_sample, 1, pattern,
|
||||
is_any_subsample_protected);
|
||||
});
|
||||
|
||||
if (sts != OEMCrypto_SUCCESS) break;
|
||||
|
||||
Reference in New Issue
Block a user