Improve query performance

[ Merge of http://go/wvgerrit/15780 ]

Android mediaDrm allows callers to serially query status information through a
property API. CDM however retrieves all status information in a map and
filters out all but the relevent one. This leads to delays in Netflix app
startup. Rewriting the CDM interface to return only the queried value.

b/24181894

Change-Id: Ie9ed6288524e3a7e03b83aa55ef3531dd52a0dfb
This commit is contained in:
Rahul Frias
2015-10-05 15:22:20 -07:00
parent dfe644da56
commit e5dfb83e03
7 changed files with 270 additions and 217 deletions

View File

@@ -405,91 +405,115 @@ CdmResponseType CdmEngine::RenewKey(const CdmSessionId& session_id,
}
CdmResponseType CdmEngine::QueryStatus(SecurityLevel security_level,
CdmQueryMap* key_info) {
const std::string& key,
std::string* value) {
LOGI("CdmEngine::QueryStatus");
CryptoSession crypto_session;
if (security_level == kLevel3) {
CdmResponseType status = crypto_session.Open(kLevel3);
if (NO_ERROR != status) return INVALID_QUERY_STATUS;
}
switch (crypto_session.GetSecurityLevel()) {
case kSecurityLevelL1:
(*key_info)[QUERY_KEY_SECURITY_LEVEL] = QUERY_VALUE_SECURITY_LEVEL_L1;
break;
case kSecurityLevelL2:
(*key_info)[QUERY_KEY_SECURITY_LEVEL] = QUERY_VALUE_SECURITY_LEVEL_L2;
break;
case kSecurityLevelL3:
(*key_info)[QUERY_KEY_SECURITY_LEVEL] = QUERY_VALUE_SECURITY_LEVEL_L3;
break;
case kSecurityLevelUninitialized:
case kSecurityLevelUnknown:
(*key_info)[QUERY_KEY_SECURITY_LEVEL] =
QUERY_VALUE_SECURITY_LEVEL_UNKNOWN;
break;
default:
return INVALID_QUERY_KEY;
}
std::string deviceId;
bool success = crypto_session.GetDeviceUniqueId(&deviceId);
if (success) {
(*key_info)[QUERY_KEY_DEVICE_ID] = deviceId;
}
if (key == QUERY_KEY_SECURITY_LEVEL) {
CdmSecurityLevel security_level = crypto_session.GetSecurityLevel();
switch (security_level) {
case kSecurityLevelL1:
*value = QUERY_VALUE_SECURITY_LEVEL_L1;
break;
case kSecurityLevelL2:
*value = QUERY_VALUE_SECURITY_LEVEL_L2;
break;
case kSecurityLevelL3:
*value = QUERY_VALUE_SECURITY_LEVEL_L3;
break;
case kSecurityLevelUninitialized:
case kSecurityLevelUnknown:
*value = QUERY_VALUE_SECURITY_LEVEL_UNKNOWN;
break;
default:
LOGW("CdmEngine::QueryStatus: Unknown security level: %d",
security_level);
return UNKNOWN_ERROR;
}
} else if (key == QUERY_KEY_DEVICE_ID) {
std::string deviceId;
if (!crypto_session.GetDeviceUniqueId(&deviceId)) {
LOGW("CdmEngine::QueryStatus: GetDeviceUniqueId failed");
return UNKNOWN_ERROR;
}
*value = deviceId;
} else if (key == QUERY_KEY_SYSTEM_ID) {
uint32_t system_id;
if (!crypto_session.GetSystemId(&system_id)) {
LOGW("CdmEngine::QueryStatus: GetSystemId failed");
return UNKNOWN_ERROR;
}
uint32_t system_id;
success = crypto_session.GetSystemId(&system_id);
if (success) {
std::ostringstream system_id_stream;
system_id_stream << system_id;
(*key_info)[QUERY_KEY_SYSTEM_ID] = system_id_stream.str();
}
*value = system_id_stream.str();
} else if (key == QUERY_KEY_PROVISIONING_ID) {
std::string provisioning_id;
if (!crypto_session.GetProvisioningId(&provisioning_id)) {
LOGW("CdmEngine::QueryStatus: GetProvisioningId failed");
return UNKNOWN_ERROR;
}
std::string provisioning_id;
success = crypto_session.GetProvisioningId(&provisioning_id);
if (success) {
(*key_info)[QUERY_KEY_PROVISIONING_ID] = provisioning_id;
}
*value = provisioning_id;
} else if (key == QUERY_KEY_CURRENT_HDCP_LEVEL ||
key == QUERY_KEY_MAX_HDCP_LEVEL) {
CryptoSession::HdcpCapability current_hdcp;
CryptoSession::HdcpCapability max_hdcp;
if (!crypto_session.GetHdcpCapabilities(&current_hdcp, &max_hdcp)) {
LOGW("CdmEngine::QueryStatus: GetHdcpCapabilities failed");
return UNKNOWN_ERROR;
}
CryptoSession::HdcpCapability current_hdcp;
CryptoSession::HdcpCapability max_hdcp;
success = crypto_session.GetHdcpCapabilities(&current_hdcp, &max_hdcp);
if (success) {
(*key_info)[QUERY_KEY_CURRENT_HDCP_LEVEL] = MapHdcpVersion(current_hdcp);
(*key_info)[QUERY_KEY_MAX_HDCP_LEVEL] = MapHdcpVersion(max_hdcp);
}
*value = MapHdcpVersion(key == QUERY_KEY_CURRENT_HDCP_LEVEL ? current_hdcp
: max_hdcp);
} else if (key == QUERY_KEY_USAGE_SUPPORT) {
bool supports_usage_reporting;
if (!crypto_session.UsageInformationSupport(&supports_usage_reporting)) {
LOGW("CdmEngine::QueryStatus: UsageInformationSupport failed");
return UNKNOWN_ERROR;
}
bool supports_usage_reporting;
success = crypto_session.UsageInformationSupport(&supports_usage_reporting);
if (success) {
(*key_info)[QUERY_KEY_USAGE_SUPPORT] =
supports_usage_reporting ? QUERY_VALUE_TRUE : QUERY_VALUE_FALSE;
}
*value = supports_usage_reporting ? QUERY_VALUE_TRUE : QUERY_VALUE_FALSE;
} else if (key == QUERY_KEY_NUMBER_OF_OPEN_SESSIONS) {
size_t number_of_open_sessions;
if (!crypto_session.GetNumberOfOpenSessions(&number_of_open_sessions)) {
LOGW("CdmEngine::QueryStatus: GetNumberOfOpenSessions failed");
return UNKNOWN_ERROR;
}
size_t number_of_open_sessions;
success = crypto_session.GetNumberOfOpenSessions(&number_of_open_sessions);
if (success) {
std::ostringstream open_sessions_stream;
open_sessions_stream << number_of_open_sessions;
(*key_info)[QUERY_KEY_NUMBER_OF_OPEN_SESSIONS] =
open_sessions_stream.str();
}
*value = open_sessions_stream.str();
} else if (key == QUERY_KEY_MAX_NUMBER_OF_SESSIONS) {
size_t maximum_number_of_sessions;
if (!crypto_session.GetMaxNumberOfSessions(&maximum_number_of_sessions)) {
LOGW("CdmEngine::QueryStatus: GetMaxNumberOfOpenSessions failed");
return UNKNOWN_ERROR;
}
size_t maximum_number_of_sessions;
success = crypto_session.GetMaxNumberOfSessions(&maximum_number_of_sessions);
if (success) {
std::ostringstream max_sessions_stream;
max_sessions_stream << maximum_number_of_sessions;
(*key_info)[QUERY_KEY_MAX_NUMBER_OF_SESSIONS] =
max_sessions_stream.str();
}
*value = max_sessions_stream.str();
} else if (key == QUERY_KEY_OEMCRYPTO_API_VERSION) {
uint32_t api_version;
if (!crypto_session.GetApiVersion(&api_version)) {
LOGW("CdmEngine::QueryStatus: GetApiVersion failed");
return UNKNOWN_ERROR;
}
uint32_t api_version;
success = crypto_session.GetApiVersion(&api_version);
if (success) {
std::ostringstream api_version_stream;
api_version_stream << api_version;
(*key_info)[QUERY_KEY_OEMCRYPTO_API_VERSION] = api_version_stream.str();
*value = api_version_stream.str();
} else {
LOGW("CdmEngine::QueryStatus: Unknown status requested, key = %s",
key.c_str());
return INVALID_QUERY_KEY;
}
return NO_ERROR;