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

@@ -100,7 +100,8 @@ class CdmEngine {
// Query system information
virtual CdmResponseType QueryStatus(SecurityLevel security_level,
CdmQueryMap* info);
const std::string& key,
std::string* value);
// Query session information
virtual CdmResponseType QuerySessionStatus(const CdmSessionId& session_id,

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;

View File

@@ -62,8 +62,8 @@ class WvContentDecryptionModule : public android::RefBase, public TimerHandler {
// Query system information
virtual CdmResponseType QueryStatus(SecurityLevel security_level,
CdmQueryMap* key_info);
const std::string& key,
std::string* value);
// Query session information
virtual CdmResponseType QuerySessionStatus(const CdmSessionId& session_id,
CdmQueryMap* key_info);

View File

@@ -121,8 +121,9 @@ CdmResponseType WvContentDecryptionModule::RemoveKeys(
CdmResponseType WvContentDecryptionModule::QueryStatus(
SecurityLevel security_level,
CdmQueryMap* key_info) {
return cdm_engine_->QueryStatus(security_level, key_info);
const std::string& key,
std::string* value) {
return cdm_engine_->QueryStatus(security_level, key, value);
}
CdmResponseType WvContentDecryptionModule::QuerySessionStatus(

View File

@@ -2051,14 +2051,12 @@ TEST_F(WvCdmRequestLicenseTest, UsageReleaseAllTest) {
TEST_F(WvCdmRequestLicenseTest, QueryUnmodifiedSessionStatus) {
// Test that the global value is returned when no properties are modifying it.
CdmQueryMap system_query_info;
CdmQueryMap::iterator system_itr;
std::string security_level;
ASSERT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevelDefault, &system_query_info));
system_itr = system_query_info.find(wvcdm::QUERY_KEY_SECURITY_LEVEL);
ASSERT_TRUE(system_itr != system_query_info.end());
EXPECT_EQ(system_itr->second, GetSecurityLevel(NULL));
decryptor_.QueryStatus(kLevelDefault,
wvcdm::QUERY_KEY_SECURITY_LEVEL,
&security_level));
EXPECT_EQ(GetSecurityLevel(NULL), security_level);
}
TEST_F(WvCdmRequestLicenseTest, QueryModifiedSessionStatus) {
@@ -2121,68 +2119,72 @@ TEST_F(WvCdmRequestLicenseTest, QueryKeyStatus) {
}
TEST_F(WvCdmRequestLicenseTest, QueryStatus) {
CdmQueryMap query_info;
CdmQueryMap::iterator itr;
std::string value;
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevelDefault, &query_info));
decryptor_.QueryStatus(kLevelDefault,
wvcdm::QUERY_KEY_SECURITY_LEVEL, &value));
itr = query_info.find(wvcdm::QUERY_KEY_SECURITY_LEVEL);
ASSERT_TRUE(itr != query_info.end());
EXPECT_EQ(2u, itr->second.size());
EXPECT_EQ(wvcdm::QUERY_VALUE_SECURITY_LEVEL_L3.at(0), itr->second.at(0));
EXPECT_EQ(2u, value.size());
EXPECT_TRUE(wvcdm::QUERY_VALUE_SECURITY_LEVEL_L3 == value ||
wvcdm::QUERY_VALUE_SECURITY_LEVEL_L1 == value);
itr = query_info.find(wvcdm::QUERY_KEY_DEVICE_ID);
ASSERT_TRUE(itr != query_info.end());
EXPECT_GT(itr->second.size(), 0u);
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevelDefault, wvcdm::QUERY_KEY_DEVICE_ID,
&value));
EXPECT_LT(0u, value.size());
itr = query_info.find(wvcdm::QUERY_KEY_SYSTEM_ID);
ASSERT_TRUE(itr != query_info.end());
std::istringstream ss(itr->second);
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevelDefault, wvcdm::QUERY_KEY_SYSTEM_ID,
&value));
std::istringstream ss(value);
uint32_t system_id;
ss >> system_id;
ASSERT_FALSE(ss.fail());
EXPECT_TRUE(ss.eof());
itr = query_info.find(wvcdm::QUERY_KEY_PROVISIONING_ID);
ASSERT_TRUE(itr != query_info.end());
EXPECT_EQ(16u, itr->second.size());
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevelDefault,
wvcdm::QUERY_KEY_PROVISIONING_ID, &value));
EXPECT_EQ(16u, value.size());
itr = query_info.find(QUERY_KEY_CURRENT_HDCP_LEVEL);
ASSERT_TRUE(itr != query_info.end());
EXPECT_TRUE(itr->second == QUERY_VALUE_UNPROTECTED ||
itr->second == QUERY_VALUE_HDCP_V1 ||
itr->second == QUERY_VALUE_HDCP_V2_0 ||
itr->second == QUERY_VALUE_HDCP_V2_1 ||
itr->second == QUERY_VALUE_HDCP_V2_2 ||
itr->second == QUERY_VALUE_DISCONNECTED);
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(
kLevelDefault, wvcdm::QUERY_KEY_CURRENT_HDCP_LEVEL, &value));
EXPECT_TRUE(
value == QUERY_VALUE_UNPROTECTED || value == QUERY_VALUE_HDCP_V1 ||
value == QUERY_VALUE_HDCP_V2_0 || value == QUERY_VALUE_HDCP_V2_1 ||
value == QUERY_VALUE_HDCP_V2_2 || value == QUERY_VALUE_DISCONNECTED);
itr = query_info.find(QUERY_KEY_MAX_HDCP_LEVEL);
ASSERT_TRUE(itr != query_info.end());
EXPECT_TRUE(itr->second == QUERY_VALUE_UNPROTECTED ||
itr->second == QUERY_VALUE_HDCP_V1 ||
itr->second == QUERY_VALUE_HDCP_V2_0 ||
itr->second == QUERY_VALUE_HDCP_V2_1 ||
itr->second == QUERY_VALUE_HDCP_V2_2 ||
itr->second == QUERY_VALUE_DISCONNECTED);
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevelDefault,
wvcdm::QUERY_KEY_MAX_HDCP_LEVEL, &value));
EXPECT_TRUE(
value == QUERY_VALUE_UNPROTECTED || value == QUERY_VALUE_HDCP_V1 ||
value == QUERY_VALUE_HDCP_V2_0 || value == QUERY_VALUE_HDCP_V2_1 ||
value == QUERY_VALUE_HDCP_V2_2 || value == QUERY_VALUE_DISCONNECTED);
itr = query_info.find(QUERY_KEY_USAGE_SUPPORT);
ASSERT_TRUE(itr != query_info.end());
EXPECT_TRUE(itr->second == QUERY_VALUE_TRUE ||
itr->second == QUERY_VALUE_FALSE);
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevelDefault,
wvcdm::QUERY_KEY_USAGE_SUPPORT, &value));
EXPECT_TRUE(value == QUERY_VALUE_TRUE || value == QUERY_VALUE_FALSE);
itr = query_info.find(QUERY_KEY_NUMBER_OF_OPEN_SESSIONS);
ASSERT_TRUE(itr != query_info.end());
EXPECT_EQ(
wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevelDefault,
wvcdm::QUERY_KEY_NUMBER_OF_OPEN_SESSIONS, &value));
ss.clear();
ss.str(itr->second);
ss.str(value);
uint32_t open_sessions;
ss >> open_sessions;
ASSERT_FALSE(ss.fail());
EXPECT_TRUE(ss.eof());
itr = query_info.find(QUERY_KEY_MAX_NUMBER_OF_SESSIONS);
ASSERT_TRUE(itr != query_info.end());
EXPECT_EQ(
wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevelDefault,
wvcdm::QUERY_KEY_MAX_NUMBER_OF_SESSIONS, &value));
ss.clear();
ss.str(itr->second);
ss.str(value);
uint32_t max_sessions;
ss >> max_sessions;
ASSERT_FALSE(ss.fail());
@@ -2190,10 +2192,11 @@ TEST_F(WvCdmRequestLicenseTest, QueryStatus) {
EXPECT_LE(open_sessions, max_sessions);
EXPECT_LE(8u, max_sessions);
itr = query_info.find(QUERY_KEY_OEMCRYPTO_API_VERSION);
ASSERT_TRUE(itr != query_info.end());
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(
kLevelDefault, wvcdm::QUERY_KEY_OEMCRYPTO_API_VERSION, &value));
ss.clear();
ss.str(itr->second);
ss.str(value);
uint32_t api_version;
ss >> api_version;
ASSERT_FALSE(ss.fail());
@@ -2202,50 +2205,94 @@ TEST_F(WvCdmRequestLicenseTest, QueryStatus) {
}
TEST_F(WvCdmRequestLicenseTest, QueryStatusL3) {
CdmQueryMap query_info, query_info_default;
CdmQueryMap::iterator itr;
std::string value;
EXPECT_EQ(
wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevel3, wvcdm::QUERY_KEY_SECURITY_LEVEL, &value));
EXPECT_EQ(wvcdm::QUERY_VALUE_SECURITY_LEVEL_L3, value);
EXPECT_EQ(wvcdm::NO_ERROR, decryptor_.QueryStatus(
kLevel3, wvcdm::QUERY_KEY_DEVICE_ID, &value));
EXPECT_LT(0u, value.size());
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevel3, &query_info));
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevelDefault, &query_info_default));
decryptor_.QueryStatus(kLevelDefault, wvcdm::QUERY_KEY_SYSTEM_ID,
&value));
std::istringstream ss(value);
uint32_t default_system_id;
ss >> default_system_id;
ASSERT_FALSE(ss.fail());
EXPECT_TRUE(ss.eof());
EXPECT_THAT(query_info, Contains(Pair(wvcdm::QUERY_KEY_SECURITY_LEVEL,
wvcdm::QUERY_VALUE_SECURITY_LEVEL_L3)));
itr = query_info.find(wvcdm::QUERY_KEY_DEVICE_ID);
ASSERT_TRUE(itr != query_info.end());
EXPECT_GT(itr->second.size(), 0u);
itr = query_info.find(wvcdm::QUERY_KEY_SYSTEM_ID);
ASSERT_TRUE(itr != query_info.end());
std::istringstream ss(itr->second);
EXPECT_EQ(wvcdm::NO_ERROR, decryptor_.QueryStatus(
kLevel3, wvcdm::QUERY_KEY_SYSTEM_ID, &value));
ss.clear();
ss.str(value);
uint32_t system_id;
ss >> system_id;
ASSERT_FALSE(ss.fail());
EXPECT_TRUE(ss.eof());
EXPECT_NE(default_system_id, system_id);
itr = query_info.find(wvcdm::QUERY_KEY_PROVISIONING_ID);
ASSERT_TRUE(itr != query_info.end());
EXPECT_EQ(16u, itr->second.size());
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevel3, wvcdm::QUERY_KEY_PROVISIONING_ID,
&value));
EXPECT_EQ(16u, value.size());
itr = query_info_default.find(wvcdm::QUERY_KEY_SECURITY_LEVEL);
ASSERT_TRUE(itr != query_info_default.end());
EXPECT_EQ(2u, itr->second.size());
EXPECT_EQ(wvcdm::QUERY_VALUE_SECURITY_LEVEL_L3.at(0), itr->second.at(0));
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevel3, wvcdm::QUERY_KEY_CURRENT_HDCP_LEVEL,
&value));
EXPECT_TRUE(
value == QUERY_VALUE_UNPROTECTED || value == QUERY_VALUE_HDCP_V1 ||
value == QUERY_VALUE_HDCP_V2_0 || value == QUERY_VALUE_HDCP_V2_1 ||
value == QUERY_VALUE_HDCP_V2_2 || value == QUERY_VALUE_DISCONNECTED);
if (wvcdm::QUERY_VALUE_SECURITY_LEVEL_L3.compare(itr->second) != 0) {
itr = query_info_default.find(wvcdm::QUERY_KEY_SYSTEM_ID);
ASSERT_TRUE(itr != query_info_default.end());
std::istringstream ss(itr->second);
uint32_t default_system_id;
ss >> system_id;
ASSERT_FALSE(ss.fail());
EXPECT_TRUE(ss.eof());
EXPECT_NE(system_id, default_system_id);
}
EXPECT_EQ(
wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevel3, wvcdm::QUERY_KEY_MAX_HDCP_LEVEL, &value));
EXPECT_TRUE(
value == QUERY_VALUE_UNPROTECTED || value == QUERY_VALUE_HDCP_V1 ||
value == QUERY_VALUE_HDCP_V2_0 || value == QUERY_VALUE_HDCP_V2_1 ||
value == QUERY_VALUE_HDCP_V2_2 || value == QUERY_VALUE_DISCONNECTED);
EXPECT_EQ(
wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevel3, wvcdm::QUERY_KEY_USAGE_SUPPORT, &value));
EXPECT_TRUE(value == QUERY_VALUE_TRUE || value == QUERY_VALUE_FALSE);
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(
kLevel3, wvcdm::QUERY_KEY_NUMBER_OF_OPEN_SESSIONS, &value));
ss.clear();
ss.str(value);
uint32_t open_sessions;
ss >> open_sessions;
ASSERT_FALSE(ss.fail());
EXPECT_TRUE(ss.eof());
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(
kLevel3, wvcdm::QUERY_KEY_MAX_NUMBER_OF_SESSIONS, &value));
ss.clear();
ss.str(value);
uint32_t max_sessions;
ss >> max_sessions;
ASSERT_FALSE(ss.fail());
EXPECT_TRUE(ss.eof());
EXPECT_LE(open_sessions, max_sessions);
EXPECT_LE(8u, max_sessions);
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(
kLevel3, wvcdm::QUERY_KEY_OEMCRYPTO_API_VERSION, &value));
ss.clear();
ss.str(value);
uint32_t api_version;
ss >> api_version;
ASSERT_FALSE(ss.fail());
EXPECT_TRUE(ss.eof());
EXPECT_LE(10u, api_version);
}
TEST_F(WvCdmRequestLicenseTest, QueryKeyControlInfo) {
Unprovision();
Provision(kLevelDefault);
@@ -2280,18 +2327,16 @@ TEST_F(WvCdmRequestLicenseTest, SecurityLevelPathBackwardCompatibility) {
GetOfflineConfiguration(&key_id, &client_auth);
CdmQueryMap query_info;
CdmQueryMap::iterator itr;
std::string level;
EXPECT_EQ(wvcdm::NO_ERROR,
decryptor_.QueryStatus(kLevelDefault, &query_info));
itr = query_info.find(wvcdm::QUERY_KEY_SECURITY_LEVEL);
ASSERT_TRUE(itr != query_info.end());
EXPECT_EQ(2u, itr->second.size());
EXPECT_TRUE(itr->second.compare(wvcdm::QUERY_VALUE_SECURITY_LEVEL_L3) == 0 ||
itr->second.compare(wvcdm::QUERY_VALUE_SECURITY_LEVEL_L1) == 0);
decryptor_.QueryStatus(kLevelDefault,
wvcdm::QUERY_KEY_SECURITY_LEVEL,
&level));
EXPECT_TRUE(wvcdm::QUERY_VALUE_SECURITY_LEVEL_L3 == level ||
wvcdm::QUERY_VALUE_SECURITY_LEVEL_L1 == level);
CdmSecurityLevel security_level =
(itr->second.compare(wvcdm::QUERY_VALUE_SECURITY_LEVEL_L1) == 0)
wvcdm::QUERY_VALUE_SECURITY_LEVEL_L1 == level
? kSecurityLevelL1
: kSecurityLevelL3;

View File

@@ -880,18 +880,13 @@ status_t WVDrmPlugin::queryProperty(const std::string& property,
status_t WVDrmPlugin::queryProperty(SecurityLevel securityLevel,
const std::string& property,
std::string& stringValue) const {
CdmQueryMap status;
CdmResponseType res = mCDM->QueryStatus(securityLevel, &status);
CdmResponseType res =
mCDM->QueryStatus(securityLevel, property, &stringValue);
if (res != wvcdm::NO_ERROR) {
ALOGE("Error querying CDM status: %u", res);
return mapCdmResponseType(res);
} else if (!status.count(property)) {
ALOGE("CDM did not report %s", property.c_str());
return kErrorCDMGeneric;
}
stringValue = status[property];
return android::OK;
return mapCdmResponseType(res);
}
status_t WVDrmPlugin::queryProperty(const std::string& property,

View File

@@ -60,7 +60,8 @@ class MockCDM : public WvContentDecryptionModule {
MOCK_METHOD2(RestoreKey, CdmResponseType(const CdmSessionId&,
const CdmKeySetId&));
MOCK_METHOD2(QueryStatus, CdmResponseType(SecurityLevel, CdmQueryMap*));
MOCK_METHOD3(QueryStatus, CdmResponseType(SecurityLevel, const std::string&,
std::string*));
MOCK_METHOD2(QueryKeyStatus, CdmResponseType(const CdmSessionId&,
CdmQueryMap*));
@@ -808,45 +809,40 @@ TEST_F(WVDrmPluginTest, ReturnsExpectedPropertyValues) {
l3Map[QUERY_KEY_SECURITY_LEVEL] = QUERY_VALUE_SECURITY_LEVEL_L3;
static const string uniqueId = "The Universe";
CdmQueryMap deviceIDMap;
deviceIDMap[QUERY_KEY_DEVICE_ID] = uniqueId;
static const string systemId = "42";
CdmQueryMap systemIDMap;
systemIDMap[QUERY_KEY_SYSTEM_ID] = systemId;
static const string provisioningId("Life\0&Everything", 16);
CdmQueryMap provisioningIDMap;
provisioningIDMap[QUERY_KEY_PROVISIONING_ID] = provisioningId;
static const string openSessions = "15";
CdmQueryMap openSessionsMap;
openSessionsMap[QUERY_KEY_NUMBER_OF_OPEN_SESSIONS] = openSessions;
static const string maxSessions = "18";
CdmQueryMap maxSessionsMap;
maxSessionsMap[QUERY_KEY_MAX_NUMBER_OF_SESSIONS] = maxSessions;
static const string oemCryptoApiVersion = "10";
CdmQueryMap oemCryptoApiVersionMap;
oemCryptoApiVersionMap[QUERY_KEY_OEMCRYPTO_API_VERSION] = oemCryptoApiVersion;
EXPECT_CALL(*cdm, QueryStatus(_, _))
.WillOnce(DoAll(SetArgPointee<1>(l1Map),
EXPECT_CALL(*cdm, QueryStatus(_, QUERY_KEY_SECURITY_LEVEL, _))
.WillOnce(DoAll(SetArgPointee<2>(QUERY_VALUE_SECURITY_LEVEL_L1),
Return(wvcdm::NO_ERROR)))
.WillOnce(DoAll(SetArgPointee<1>(l3Map),
Return(wvcdm::NO_ERROR)))
.WillOnce(DoAll(SetArgPointee<1>(deviceIDMap),
Return(wvcdm::NO_ERROR)))
.WillOnce(DoAll(SetArgPointee<1>(systemIDMap),
Return(wvcdm::NO_ERROR)))
.WillOnce(DoAll(SetArgPointee<1>(provisioningIDMap),
Return(wvcdm::NO_ERROR)))
.WillOnce(DoAll(SetArgPointee<1>(openSessionsMap),
Return(wvcdm::NO_ERROR)))
.WillOnce(DoAll(SetArgPointee<1>(maxSessionsMap),
Return(wvcdm::NO_ERROR)))
.WillOnce(DoAll(SetArgPointee<1>(oemCryptoApiVersionMap),
.WillOnce(DoAll(SetArgPointee<2>(QUERY_VALUE_SECURITY_LEVEL_L3),
Return(wvcdm::NO_ERROR)));
EXPECT_CALL(*cdm, QueryStatus(_, QUERY_KEY_DEVICE_ID, _))
.WillOnce(DoAll(SetArgPointee<2>(uniqueId),
Return(wvcdm::NO_ERROR)));
EXPECT_CALL(*cdm, QueryStatus(_, QUERY_KEY_SYSTEM_ID, _))
.WillOnce(DoAll(SetArgPointee<2>(systemId),
Return(wvcdm::NO_ERROR)));
EXPECT_CALL(*cdm, QueryStatus(_, QUERY_KEY_PROVISIONING_ID, _))
.WillOnce(DoAll(SetArgPointee<2>(provisioningId),
Return(wvcdm::NO_ERROR)));
EXPECT_CALL(*cdm, QueryStatus(_, QUERY_KEY_NUMBER_OF_OPEN_SESSIONS, _))
.WillOnce(DoAll(SetArgPointee<2>(openSessions),
Return(wvcdm::NO_ERROR)));
EXPECT_CALL(*cdm, QueryStatus(_, QUERY_KEY_MAX_NUMBER_OF_SESSIONS, _))
.WillOnce(DoAll(SetArgPointee<2>(maxSessions),
Return(wvcdm::NO_ERROR)));
EXPECT_CALL(*cdm, QueryStatus(_, QUERY_KEY_OEMCRYPTO_API_VERSION, _))
.WillOnce(DoAll(SetArgPointee<2>(oemCryptoApiVersion),
Return(wvcdm::NO_ERROR)));
String8 stringResult;
@@ -1475,9 +1471,6 @@ TEST_F(WVDrmPluginTest, CanSetAppId) {
const CdmClientPropertySet* propertySet = NULL;
CdmQueryMap l3Map;
l3Map[QUERY_KEY_SECURITY_LEVEL] = QUERY_VALUE_SECURITY_LEVEL_L3;
// Provide expected mock behavior
{
// Provide expected behavior in response to OpenSession and store the
@@ -1488,8 +1481,8 @@ TEST_F(WVDrmPluginTest, CanSetAppId) {
Return(wvcdm::NO_ERROR)));
// Provide expected behavior when plugin queries for the security level
EXPECT_CALL(*cdm, QueryStatus(_, _))
.WillRepeatedly(DoAll(SetArgPointee<1>(l3Map),
EXPECT_CALL(*cdm, QueryStatus(_, QUERY_KEY_SECURITY_LEVEL, _))
.WillRepeatedly(DoAll(SetArgPointee<2>(QUERY_VALUE_SECURITY_LEVEL_L3),
Return(wvcdm::NO_ERROR)));
// Provide expected behavior when plugin requests session control info
@@ -1564,16 +1557,10 @@ TEST_F(WVDrmPluginTest, CanSetSecurityLevel) {
const CdmClientPropertySet* propertySet = NULL;
CdmQueryMap l1Map;
l1Map[QUERY_KEY_SECURITY_LEVEL] = QUERY_VALUE_SECURITY_LEVEL_L1;
CdmQueryMap l3Map;
l3Map[QUERY_KEY_SECURITY_LEVEL] = QUERY_VALUE_SECURITY_LEVEL_L3;
EXPECT_CALL(*cdm, QueryStatus(_, _))
.WillOnce(DoAll(SetArgPointee<1>(l3Map),
EXPECT_CALL(*cdm, QueryStatus(_, QUERY_KEY_SECURITY_LEVEL, _))
.WillOnce(DoAll(SetArgPointee<2>(QUERY_VALUE_SECURITY_LEVEL_L3),
Return(wvcdm::NO_ERROR)))
.WillOnce(DoAll(SetArgPointee<1>(l1Map),
.WillOnce(DoAll(SetArgPointee<2>(QUERY_VALUE_SECURITY_LEVEL_L1),
Return(wvcdm::NO_ERROR)));
// Provide expected mock behavior