// // Copyright 2017 Google Inc. All Rights Reserved. // #ifndef WV_DRM_PLUGIN_H_ #define WV_DRM_PLUGIN_H_ #include #include #include #include "cdm_client_property_set.h" #include "cdm_identifier.h" #include "OEMCryptoCENC.h" #include "wv_cdm_event_listener.h" #include "wv_content_decryption_module.h" #include "WVGenericCryptoInterface.h" #include "WVTypes.h" namespace wvdrm { namespace hardware { namespace drm { namespace V1_0 { namespace widevine { using ::android::hardware::drm::V1_0::EventType; using ::android::hardware::drm::V1_0::IDrmPlugin; using ::android::hardware::drm::V1_0::IDrmPluginListener; using ::android::hardware::drm::V1_0::KeyRequestType; using ::android::hardware::drm::V1_0::KeyStatus; using ::android::hardware::drm::V1_0::KeyType; using ::android::hardware::drm::V1_0::KeyValue; using ::android::hardware::drm::V1_0::SecureStop; using ::android::hardware::drm::V1_0::Status; using ::android::hardware::hidl_array; using ::android::hardware::hidl_string; using ::android::hardware::hidl_vec; using ::android::hardware::Return; using ::android::sp; using android::status_t; using std::map; using wvcdm::CdmIdentifier; using wvcdm::CdmKeyStatusMap; using wvcdm::CdmSessionId; using wvcdm::CdmResponseType; using wvcdm::WvContentDecryptionModule; const OEMCrypto_Algorithm kInvalidCryptoAlgorithm = static_cast(-1); struct WVDrmPlugin : public IDrmPlugin, IDrmPluginListener, wvcdm::WvCdmEventListener { WVDrmPlugin(const sp& cdm, const std::string& appPackageName, WVGenericCryptoInterface* crypto, bool useSpoid); virtual ~WVDrmPlugin(); Return openSession(openSession_cb _hidl_cb) override; Return closeSession(const hidl_vec& sessionId) override; Return getKeyRequest( const hidl_vec& scope, const hidl_vec& initData, const hidl_string& mimeType, KeyType keyType, const hidl_vec& optionalParameters, getKeyRequest_cb _hidl_cb) override; Return provideKeyResponse( const hidl_vec& scope, const hidl_vec& response, provideKeyResponse_cb _hidl_cb) override; Return removeKeys(const hidl_vec& sessionId) override; Return restoreKeys( const hidl_vec& sessionId, const hidl_vec& keySetId) override; Return queryKeyStatus( const hidl_vec& sessionId, queryKeyStatus_cb _hidl_cb) override; Return getProvisionRequest( const hidl_string& certificateType, const hidl_string& certificateAuthority, getProvisionRequest_cb _hidl_cb) override; Return provideProvisionResponse( const hidl_vec& response, provideProvisionResponse_cb _hidl_cb) override; Return getSecureStops(getSecureStops_cb _hidl_cb) override; Return getSecureStop( const hidl_vec& secureStopId, getSecureStop_cb _hidl_cb) override; Return releaseAllSecureStops() override; Return releaseSecureStop( const hidl_vec& secureStopId) override; Return getPropertyString( const hidl_string& propertyName, getPropertyString_cb _hidl_cb) override; Return getPropertyByteArray( const hidl_string& propertyName, getPropertyByteArray_cb _hidl_cb) override; Return setPropertyString( const hidl_string& propertyName, const hidl_string& value) override; Return setPropertyByteArray( const hidl_string& propertyName, const hidl_vec& value) override; Return setCipherAlgorithm( const hidl_vec& sessionId, const hidl_string& algorithm) override; Return setMacAlgorithm( const hidl_vec& sessionId, const hidl_string& algorithm) override; Return encrypt( const hidl_vec& sessionId, const hidl_vec& keyId, const hidl_vec& input, const hidl_vec& iv, encrypt_cb _hidl_cb) override; Return decrypt( const hidl_vec& sessionId, const hidl_vec& keyId, const hidl_vec& input, const hidl_vec& iv, decrypt_cb _hidl_cb) override; Return sign(const hidl_vec& sessionId, const hidl_vec& keyId, const hidl_vec& message, sign_cb _hidl_cb) override; Return verify( const hidl_vec& sessionId, const hidl_vec& keyId, const hidl_vec& message, const hidl_vec& signature, verify_cb _hidl_cb) override; Return signRSA( const hidl_vec& sessionId, const hidl_string& algorithm, const hidl_vec& message, const hidl_vec& wrappedkey, signRSA_cb _hidl_cb) override; Return setListener(const sp& listener) override; Return sendEvent( EventType eventType, const hidl_vec& sessionId, const hidl_vec& data) override; Return sendExpirationUpdate( const hidl_vec& sessionId, int64_t expiryTimeInMS) override; Return sendKeysChange( const hidl_vec& sessionId, const hidl_vec& keyStatusList, bool hasNewUsableKey) override; // The following methods do not use hidl interface, it is used internally. virtual status_t unprovisionDevice(); virtual void OnSessionRenewalNeeded(const CdmSessionId& cdmSessionId); virtual void OnSessionKeysChange( const CdmSessionId& cdmSessionId, const CdmKeyStatusMap& cdmKeysStatus, bool hasNewUsableKey); virtual void OnExpirationUpdate( const CdmSessionId& cdmSessionId, int64_t newExpiryTimeSeconds); private: WVDRM_DISALLOW_COPY_AND_ASSIGN_AND_NEW(WVDrmPlugin); struct CryptoSession { public: CryptoSession() : mOecSessionId(-1), mCipherAlgorithm(kInvalidCryptoAlgorithm), mMacAlgorithm(kInvalidCryptoAlgorithm) {} CryptoSession(OEMCrypto_SESSION sessionId) : mOecSessionId(sessionId), mCipherAlgorithm(kInvalidCryptoAlgorithm), mMacAlgorithm(kInvalidCryptoAlgorithm) {} OEMCrypto_SESSION oecSessionId() const { return mOecSessionId; } OEMCrypto_Algorithm cipherAlgorithm() const { return mCipherAlgorithm; } void setCipherAlgorithm(OEMCrypto_Algorithm newAlgorithm) { mCipherAlgorithm = newAlgorithm; } OEMCrypto_Algorithm macAlgorithm() const { return mMacAlgorithm; } void setMacAlgorithm(OEMCrypto_Algorithm newAlgorithm) { mMacAlgorithm = newAlgorithm; } private: OEMCrypto_SESSION mOecSessionId; OEMCrypto_Algorithm mCipherAlgorithm; OEMCrypto_Algorithm mMacAlgorithm; }; class WVClientPropertySet : public wvcdm::CdmClientPropertySet { public: WVClientPropertySet() : mUsePrivacyMode(false), mShareKeys(false), mSessionSharingId(0) {} virtual ~WVClientPropertySet() {} virtual const std::string& security_level() const { return mSecurityLevel; } void set_security_level(const std::string& securityLevel) { mSecurityLevel = securityLevel; } virtual bool use_privacy_mode() const { return mUsePrivacyMode; } void set_use_privacy_mode(bool usePrivacyMode) { mUsePrivacyMode = usePrivacyMode; } virtual const std::string& service_certificate() const { return mServiceCertificate; } virtual void set_service_certificate( const std::string& serviceCertificate) { mServiceCertificate = serviceCertificate; } virtual const std::string& device_provisioning_service_certificate() const { // Android does not support service certificates for provisioning. return mEmptyString; } virtual void set_device_provisioning_service_certificate( const std::string& ) { // Ignore. Android does not support service certificates for provisioning } virtual bool is_session_sharing_enabled() const { return mShareKeys; } void set_is_session_sharing_enabled(bool shareKeys) { mShareKeys = shareKeys; } virtual uint32_t session_sharing_id() const { return mSessionSharingId; } virtual void set_session_sharing_id(uint32_t id) { mSessionSharingId = id; } virtual const std::string& app_id() const { return mAppId; } void set_app_id(const std::string& appId) { mAppId = appId; } private: DISALLOW_EVIL_CONSTRUCTORS(WVClientPropertySet); std::string mSecurityLevel; bool mUsePrivacyMode; std::string mServiceCertificate; bool mShareKeys; uint32_t mSessionSharingId; std::string mAppId; const std::string mEmptyString; } mPropertySet; class CdmIdentifierBuilder { public: CdmIdentifierBuilder(bool useSpoid, const std::string& appPackageName); const CdmIdentifier& get_identifier(); const std::string& get_device_unique_id(); bool set_device_id(const std::string& id); const std::string& origin() const { return mCdmIdentifier.origin; } bool set_origin(const std::string& id); private: WVDRM_DISALLOW_COPY_AND_ASSIGN(CdmIdentifierBuilder); CdmIdentifier mCdmIdentifier; bool mIsIdentifierSealed; bool mUseSpoid; std::string mDeviceId; std::string mAppPackageName; void calculateSpoid(); } mCdmIdentifierBuilder; sp const mCDM; WVGenericCryptoInterface* mCrypto; map mCryptoSessions; sp mListener; status_t queryProperty(const std::string& property, std::string& stringValue) const; status_t queryProperty(wvcdm::SecurityLevel securityLevel, const std::string& property, std::string& stringValue) const; status_t queryProperty(const std::string& property, std::vector& vector_value) const; status_t mapAndNotifyOfCdmResponseType(const std::vector& sessionId, CdmResponseType res); status_t mapAndNotifyOfOEMCryptoResult(const std::vector& sessionId, OEMCryptoResult res); status_t mapOEMCryptoResult(OEMCryptoResult res); bool initDataResemblesPSSH(const std::vector& initData); status_t unprovision(const CdmIdentifier& identifier); }; } // namespace widevine } // namespace V1_0 } // namespace drm } // namespace hardware } // namespace wvdrm #endif // WV_DRM_PLUGIN_H_