// Copyright 2019 Google LLC. All Rights Reserved. This file and proprietary // source code may only be used and distributed under the Widevine Master // License Agreement. #include "certificate_provisioning.h" #include #include #include #include "crypto_session.h" #include "metrics_collections.h" #include "test_base.h" #include "wv_cdm_types.h" namespace { const std::string kSignedDeviceCertificate = wvcdm::a2bs_hex( "0A350802121B7769646576696E655F746573745F73657269616C5F6E756D62657228D2093A" "11746573742E7769646576696E652E636F6D12097369676E6174757265"); const std::string kSignedDeviceCertificateInvalid = wvcdm::a2bs_hex( "76340802121B7769646576696E655F746573745F73657269616C5F6E756D62657228D2093A" "11746573742E7769646576696E652E636F6D12097369676E6174757265"); const std::string kSignedDeviceCertificateNoDrmCertificate = wvcdm::a2bs_hex("12097369676E6174757265"); const std::string kSignedDeviceCertificateInvalidCertificateType = wvcdm::a2bs_hex( "0A350801121B7769646576696E655F746573745F73657269616C5F6E756D62657228D2" "093A11746573742E7769646576696E652E636F6D12097369676E6174757265"); const std::string kSerialNumber = "widevine_test_serial_number"; const uint32_t kSystemId = 1234; } // unnamed namespace namespace wvcdm { class MockCryptoSession : public TestCryptoSession { public: MockCryptoSession(metrics::CryptoMetrics* metrics) : TestCryptoSession(metrics) {} MOCK_METHOD1(Open, CdmResponseType(SecurityLevel)); MOCK_METHOD1(LoadUsageTableHeader, CdmResponseType(const CdmUsageTableHeader&)); MOCK_METHOD1(CreateUsageTableHeader, CdmResponseType(CdmUsageTableHeader*)); MOCK_METHOD1(CreateUsageEntry, CdmResponseType(uint32_t*)); MOCK_METHOD2(LoadUsageEntry, CdmResponseType(uint32_t, const CdmUsageEntry&)); MOCK_METHOD2(UpdateUsageEntry, CdmResponseType(CdmUsageTableHeader*, CdmUsageEntry*)); MOCK_METHOD1(MoveUsageEntry, CdmResponseType(uint32_t)); MOCK_METHOD2(ShrinkUsageTableHeader, CdmResponseType(uint32_t, CdmUsageTableHeader*)); }; class TestStubCryptoSessionFactory : public CryptoSessionFactory { CryptoSession* MakeCryptoSession(metrics::CryptoMetrics* crypto_metrics) { return new MockCryptoSession(crypto_metrics); } }; // gmock methods using ::testing::_; class CertificateProvisioningTest : public WvCdmTestBase { public: protected: void SetUp() override { WvCdmTestBase::SetUp(); CryptoSession::SetCryptoSessionFactory(new TestStubCryptoSessionFactory()); certificate_provisioning_.reset( new CertificateProvisioning(new metrics::CryptoMetrics())); } void TearDown() override {} std::unique_ptr certificate_provisioning_; }; // Tests ExtractDeviceInfo failure scenarios // * invalid output parmeters // * invalid signed drm device certificate // * signed drm device certificate contains no drm certificate // * drm certificate has an invalid certificate type TEST_F(CertificateProvisioningTest, ExtractDeviceInfo_InvalidInput) { std::string serial_number; uint32_t system_id; EXPECT_FALSE(certificate_provisioning_->ExtractDeviceInfo( kSignedDeviceCertificate, nullptr, nullptr)); EXPECT_FALSE(certificate_provisioning_->ExtractDeviceInfo( kSignedDeviceCertificateInvalid, &serial_number, &system_id)); EXPECT_FALSE(certificate_provisioning_->ExtractDeviceInfo( kSignedDeviceCertificateNoDrmCertificate, &serial_number, &system_id)); EXPECT_FALSE(certificate_provisioning_->ExtractDeviceInfo( kSignedDeviceCertificateInvalidCertificateType, &serial_number, &system_id)); } // Tests ExtractDeviceInfo success scenarios // * able to extract both |serial_number| and |system_id| // * able to extract only |serial_number| // * able to extract only |system_id| TEST_F(CertificateProvisioningTest, ExtractDeviceInfo) { std::string serial_number; uint32_t system_id; EXPECT_TRUE(certificate_provisioning_->ExtractDeviceInfo( kSignedDeviceCertificate, &serial_number, &system_id)); EXPECT_EQ(kSerialNumber, serial_number); EXPECT_EQ(kSystemId, system_id); EXPECT_TRUE(certificate_provisioning_->ExtractDeviceInfo( kSignedDeviceCertificate, nullptr, &system_id)); EXPECT_EQ(kSystemId, system_id); EXPECT_TRUE(certificate_provisioning_->ExtractDeviceInfo( kSignedDeviceCertificate, &serial_number, nullptr)); EXPECT_EQ(kSerialNumber, serial_number); } } // namespace wvcdm