// Copyright 2016 Google Inc. All Rights Reserved. // // This file contains definitions for metrics being collected throughout the // CDM. #ifndef WVCDM_METRICS_METRICS_GROUP_H_ #define WVCDM_METRICS_METRICS_GROUP_H_ #include #include #include #include "event_metric.h" #include "metrics.pb.h" #include "OEMCryptoCENC.h" #include "wv_cdm_types.h" // This definition indicates that a given metric does not need timing // stats. Example: // // M_RECORD(my_metrics, my_metric_name, NO_TIME); #define NO_TIME 0 // Used to record metric timing and additional information about a specific // event. Assumes that a microsecond timing has been provided. Example: // // long total_time = 0; // long error_code = TimeSomeOperation(&total_time); // M_RECORD(my_metrics, my_metric_name, total_time, error_code); #define M_RECORD(GROUP, METRIC, TIME, ...) \ if ( GROUP ) { \ ( GROUP ) -> METRIC . Record( TIME, ##__VA_ARGS__ ); \ } // This definition automatically times an operation and records the time and // additional information such as error code to the provided metric. // Example: // // OEMCryptoResult sts; // M_TIME( // sts = OEMCrypto_Initialize(), // my_metrics_collection, // oemcrypto_initialize_, // sts); #define M_TIME(CALL, GROUP, METRIC, ...) \ if ( GROUP ) { \ wvcdm::metrics::TimerMetric timer; \ timer.Start(); \ CALL; \ ( GROUP ) -> METRIC . Record(timer.AsUs(), ##__VA_ARGS__ ); \ } else { \ CALL; \ } namespace wvcdm { namespace metrics { // This enum defines the conditions encountered during OEMCrypto Initialization // in oemcrypto_adapter_dynamic. typedef enum OEMCryptoInitializationMode { OEMCrypto_INITIALIZED_USING_IN_APP = 0, OEMCrypto_INITIALIZED_FORCING_L3 = 1, OEMCrypto_INITIALIZED_USING_L3_NO_L1_LIBRARY_PATH = 2, OEMCrypto_INITIALIZED_USING_L3_L1_OPEN_FAILED = 3, OEMCrypto_INITIALIZED_USING_L3_L1_LOAD_FAILED = 4, OEMCrypto_INITIALIZED_USING_L3_COULD_NOT_INITIALIZE_L1 = 5, OEMCrypto_INITIALIZED_USING_L3_WRONG_L1_VERSION = 6, OEMCrypto_INITIALIZED_USING_L1_WITH_KEYBOX = 7, OEMCrypto_INITIALIZED_USING_L1_WITH_CERTIFICATE = 8, OEMCrypto_INITIALIZED_USING_L1_CERTIFICATE_MIX = 9, OEMCrypto_INITIALIZED_USING_L3_BAD_KEYBOX = 10, OEMCrypto_INITIALIZED_USING_L3_COULD_NOT_OPEN_FACTORY_KEYBOX = 11, OEMCrypto_INITIALIZED_USING_L3_COULD_NOT_INSTALL_KEYBOX = 12, OEMCrypto_INITIALIZED_USING_L1_INSTALLED_KEYBOX = 13, OEMCrypto_INITIALIZED_USING_L3_INVALID_L1 = 14, OEMCrypto_INITIALIZED_USING_L1_WITH_PROVISIONING_3_0 = 15, OEMCrypto_INITIALIZED_L3_INITIALIZATION_FAILED = 16 } OEMCryptoInitializationMode; // This class contains metrics for Crypto Session and OEM Crypto. class CryptoMetrics { public: CryptoMetrics(); void Serialize(drm_metrics::MetricsGroup* metrics); /* CRYPTO SESSION */ EventMetric crypto_session_delete_all_usage_reports_; EventMetric crypto_session_delete_multiple_usage_information_; EventMetric crypto_session_generic_decrypt_; EventMetric crypto_session_generic_encrypt_; EventMetric crypto_session_generic_sign_; EventMetric crypto_session_generic_verify_; EventMetric crypto_session_get_device_unique_id_; EventMetric crypto_session_get_security_level_; EventMetric crypto_session_get_system_id_; EventMetric crypto_session_get_token_; EventMetric<> crypto_session_life_span_; EventMetric crypto_session_load_certificate_private_key_; EventMetric crypto_session_open_; EventMetric crypto_session_update_usage_information_; EventMetric crypto_session_usage_information_support_; /* OEMCRYPTO */ EventMetric oemcrypto_api_version_; EventMetric oemcrypto_close_session_; EventMetric oemcrypto_copy_buffer_; EventMetric oemcrypto_deactivate_usage_entry_; EventMetric oemcrypto_decrypt_cenc_; EventMetric oemcrypto_delete_usage_entry_; EventMetric oemcrypto_delete_usage_table_; EventMetric oemcrypto_derive_keys_from_session_key_; EventMetric oemcrypto_force_delete_usage_entry_; EventMetric oemcrypto_generate_derived_keys_; EventMetric oemcrypto_generate_nonce_; EventMetric oemcrypto_generate_rsa_signature_; EventMetric oemcrypto_generate_signature_; EventMetric oemcrypto_generic_decrypt_; EventMetric oemcrypto_generic_encrypt_; EventMetric oemcrypto_generic_sign_; EventMetric oemcrypto_generic_verify_; EventMetric oemcrypto_get_device_id_; EventMetric oemcrypto_get_hdcp_capability_; EventMetric oemcrypto_get_key_data_; EventMetric oemcrypto_get_max_number_of_sessions_; EventMetric oemcrypto_get_number_of_open_sessions_; EventMetric oemcrypto_get_oem_public_certificate_; EventMetric oemcrypto_get_provisioning_method_; EventMetric oemcrypto_get_random_; EventMetric oemcrypto_initialize_; EventMetric oemcrypto_install_keybox_; EventMetric oemcrypto_is_anti_rollback_hw_present_; EventMetric oemcrypto_is_keybox_valid_; EventMetric oemcrypto_load_device_rsa_key_; EventMetric oemcrypto_load_keys_; EventMetric oemcrypto_load_test_keybox_; EventMetric oemcrypto_load_test_rsa_key_; EventMetric oemcrypto_open_session_; EventMetric oemcrypto_refresh_keys_; EventMetric oemcrypto_report_usage_; EventMetric oemcrypto_rewrap_device_rsa_key_; EventMetric oemcrypto_rewrap_device_rsa_key_30_; EventMetric oemcrypto_security_level_; EventMetric oemcrypto_security_patch_level_; EventMetric oemcrypto_select_key_; EventMetric oemcrypto_supports_usage_table_; EventMetric oemcrypto_update_usage_table_; EventMetric oemcrypto_wrap_keybox_; /* Internal OEMCrypto Metrics */ EventMetric oemcrypto_initialization_mode_; EventMetric oemcrypto_l1_api_version_; }; // This class contains session-scoped metrics. All properties and // statistics related to operations within a single session are // recorded here. class SessionMetrics { public: SessionMetrics(); // Sets the session id of the metrics group. This allows the session // id to be captured and reported as part of the collection of metrics. void SetSessionId(const CdmSessionId& session_id) { session_id_ = session_id; } // Returns the session id or an empty session id if it has not been set. const CdmSessionId& GetSessionId() const { return session_id_; } // Marks the metrics object as completed and ready for serialization. void SetCompleted() { completed_ = true; } // Returns true if the object is completed. This is used to determine // when the stats are ready to be published. bool IsCompleted() const { return completed_; } // Returns a pointer to the crypto metrics belonging to the engine instance. // This instance retains ownership of the object. CryptoMetrics* GetCryptoMetrics() { return &crypto_metrics_; } // Metrics collected at the session level. EventMetric<> cdm_session_life_span_; EventMetric cdm_session_renew_key_; EventMetric cdm_session_restore_offline_session_; EventMetric cdm_session_restore_usage_session_; // Serialize the session metrics to the provided |metric_group|. // |metric_group| is owned by the caller and must not be null. void Serialize(drm_metrics::MetricsGroup* metric_group); private: void SerializeSessionMetrics(drm_metrics::MetricsGroup* metric_group); CdmSessionId session_id_; bool completed_; CryptoMetrics crypto_metrics_; }; // This class contains engine-scoped metrics. All properties and // statistics related to operations within the engine, but outside // the scope of a session are recorded here. class EngineMetrics { public: EngineMetrics(); ~EngineMetrics(); // Add a new SessionMetrics instance and return a pointer to the caller. // The new SessionMetrics instance is owned by this EngineMetrics instance // and will exist until RemoveSession is called or this object is deleted. SessionMetrics* AddSession(); // Removes the metrics object for the given session id. This should only // be called when the SessionMetrics instance is no longer in use. void RemoveSession(CdmSessionId session_id); // Returns a pointer to the crypto metrics belonging to the engine instance. // The CryptoMetrics instance is still owned by this object and will exist // until this object is deleted. CryptoMetrics* GetCryptoMetrics() { return &crypto_metrics_; } // Serialize engine and session metrics into a serialized MetricsGroup // instance and output that instance to the provided |metric_group|. // |metric_group| is owned by the caller and must NOT be null. // |completed_only| indicates that this call should only publish // SessionMetrics instances that are marked as completed. // |clear_sessions| indicates that this call should clear sessions metrics // for those sessions that were serialized. This allows atomic // serialization and closing of session-level metrics. void Serialize(drm_metrics::MetricsGroup* metric_group, bool completed_only, bool clear_serialized_sessions); // Metrics recorded at the engine level. EventMetric cdm_engine_add_key_; EventMetric cdm_engine_close_session_; EventMetric cdm_engine_decrypt_; EventMetric cdm_engine_find_session_for_key_; EventMetric cdm_engine_generate_key_request_; EventMetric cdm_engine_get_provisioning_request_; EventMetric cdm_engine_get_usage_info_; EventMetric cdm_engine_handle_provisioning_response_; EventMetric<> cdm_engine_life_span_; EventMetric cdm_engine_open_key_set_session_; EventMetric cdm_engine_open_session_; EventMetric cdm_engine_query_key_status_; EventMetric cdm_engine_release_all_usage_info_; EventMetric cdm_engine_release_usage_info_; EventMetric cdm_engine_remove_keys_; EventMetric cdm_engine_restore_key_; EventMetric cdm_engine_unprovision_; private: Lock session_metrics_lock_; std::vector session_metrics_list_; CryptoMetrics crypto_metrics_; void SerializeEngineMetrics(drm_metrics::MetricsGroup* out); }; } // namespace metrics } // namespace wvcdm #endif