// Copyright 2018 Google LLC. All Rights Reserved. This file and proprietary // source code may only be used and distributed under the Widevine // License Agreement. // // OEMCrypto unit tests - extra tests required for Android platform. // // The Widevine CDM system can be built on many platforms, with different // capabilities. For example, some platforms do not require usage tables, // and some can have a pre-installed certificate and do not need a keybox. // On Android, these features are not optional. This set of unit tests // verify that these features are implemented. // // In the other oemcrypto test files, the unit tests only verify correct // functionality for functions that are implemented. Android devices must pass // unit tests in this file also. #include #include "OEMCryptoCENC.h" #include "oec_device_features.h" #include "oec_test_data.h" namespace wvoec { /// @addtogroup android /// @{ /** These tests are required for LollyPop Android devices.*/ class OEMCryptoAndroidLMPTest : public ::testing::Test { protected: void SetUp() override { OEMCrypto_SetSandbox(kTestSandbox, sizeof(kTestSandbox)); ASSERT_EQ(OEMCrypto_SUCCESS, OEMCrypto_Initialize()); OEMCrypto_SetMaxAPIVersion(kCurrentAPI); OEMCrypto_EnterTestMode(); } void TearDown() override { OEMCrypto_Terminate(); } }; /** Android devices that use Provisioning 2.0 must have a valid keybox. */ TEST_F(OEMCryptoAndroidLMPTest, ValidKeyboxTest) { if (global_features.provisioning_method != OEMCrypto_Keybox) { GTEST_SKIP() << "Test for Prov 2.0 devices only."; } ASSERT_EQ(OEMCrypto_SUCCESS, OEMCrypto_IsKeyboxValid()); } /** Android devices must support remote provisioning. Either Provisioning 2, 3 * or 4. */ TEST_F(OEMCryptoAndroidLMPTest, RewrapDeviceRSAKeyImplemented) { ASSERT_NE(OEMCrypto_ERROR_NOT_IMPLEMENTED, OEMCrypto_LoadProvisioning(0, nullptr, 0, nullptr, 0, 0, nullptr, 0, nullptr, 0)); } /** The Generic Crypto API functions are required for Android. */ TEST_F(OEMCryptoAndroidLMPTest, GenericCryptoImplemented) { ASSERT_NE( OEMCrypto_ERROR_NOT_IMPLEMENTED, OEMCrypto_Generic_Encrypt(nullptr, 0, nullptr, 0, nullptr, OEMCrypto_AES_CBC_128_NO_PADDING, nullptr)); ASSERT_NE( OEMCrypto_ERROR_NOT_IMPLEMENTED, OEMCrypto_Generic_Decrypt(nullptr, 0, nullptr, 0, nullptr, OEMCrypto_AES_CBC_128_NO_PADDING, nullptr)); ASSERT_NE(OEMCrypto_ERROR_NOT_IMPLEMENTED, OEMCrypto_Generic_Sign(nullptr, 0, nullptr, 0, OEMCrypto_HMAC_SHA256, nullptr, nullptr)); ASSERT_NE(OEMCrypto_ERROR_NOT_IMPLEMENTED, OEMCrypto_Generic_Verify(nullptr, 0, nullptr, 0, OEMCrypto_HMAC_SHA256, nullptr, 0)); } /** Android requires support of usage table. The usage table is used for * offline licenses. */ TEST_F(OEMCryptoAndroidLMPTest, SupportsUsageTable) { ASSERT_TRUE(OEMCrypto_SupportsUsageTable()); } /** Most Android GMS devices require L1 OEMCrypto. This is not a hard * requirement for all devices, but is a source of common errors, so we test for * it here. */ TEST_F(OEMCryptoAndroidLMPTest, Level1Required) { OEMCrypto_Security_Level security_level = OEMCrypto_SecurityLevel(); EXPECT_EQ(OEMCrypto_Level1, security_level) << "The security level is " << security_level << ". but we expect L1.\n" << "If you are testing a device that should be L3 or L2, please\n" << "repeat the tests with the flag --gtest_filter=\"*-*Level1Required\""; } /** These tests are required for M Android devices. */ class OEMCryptoAndroidMNCTest : public OEMCryptoAndroidLMPTest {}; /** Android devices using Provisioning 2.0 must be able to load a test keybox. * If they are not using Provisioning 2.0, then they must use Provisioning 3 or * 4. */ TEST_F(OEMCryptoAndroidMNCTest, LoadsTestKeyboxImplemented) { if (global_features.provisioning_method != OEMCrypto_Keybox) { GTEST_SKIP() << "Test for Prov 2.0 devices only."; } ASSERT_EQ( OEMCrypto_SUCCESS, OEMCrypto_LoadTestKeybox(reinterpret_cast(&kTestKeybox), sizeof(kTestKeybox))); } /** Android requires implementation of functions that report how many open * sessions are available. */ TEST_F(OEMCryptoAndroidMNCTest, NumberOfSessionsImplemented) { ASSERT_NE(OEMCrypto_ERROR_NOT_IMPLEMENTED, OEMCrypto_GetNumberOfOpenSessions(nullptr)); ASSERT_NE(OEMCrypto_ERROR_NOT_IMPLEMENTED, OEMCrypto_GetMaxNumberOfSessions(nullptr)); } /** Android requires implementation of `OEMCrypto_QueryKeyControl`. */ TEST_F(OEMCryptoAndroidMNCTest, QueryKeyControlImplemented) { ASSERT_NE(OEMCrypto_ERROR_NOT_IMPLEMENTED, OEMCrypto_QueryKeyControl(0, nullptr, 0, nullptr, nullptr)); } /** These tests are required for R Android devices. */ class OEMCryptoAndroidRVCTest : public OEMCryptoAndroidMNCTest {}; /** Minimum OEMCrypto version 16 is required for all Android R and later * releases. */ TEST_F(OEMCryptoAndroidRVCTest, MinVersionNumber16) { uint32_t version = OEMCrypto_APIVersion(); ASSERT_GE(version, 16u); } /// @} } // namespace wvoec