1 /* 2 * Copyright (c) 2023 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 #ifndef NATIVE_DRM_OBJECT_H 17 #define NATIVE_DRM_OBJECT_H 18 19 #include <stdint.h> 20 #include <stdio.h> 21 #include "native_drm_err.h" 22 #include "native_drm_base.h" 23 #include "native_drm_common.h" 24 25 #include "key_session_impl.h" 26 #include "media_key_system_impl.h" 27 #include "media_key_system_factory_impl.h" 28 #include "native_mediakeysystem.h" 29 #include "native_mediakeysession.h" 30 31 namespace OHOS { 32 namespace DrmStandard { 33 class MediaKeySystemCallbackCapi; 34 class MediaKeySessionCallbackCapi; 35 36 struct MediaKeySystemObject : public MediaKeySystem { MediaKeySystemObjectMediaKeySystemObject37 explicit MediaKeySystemObject(const OHOS::sptr<OHOS::DrmStandard::MediaKeySystemImpl> &impl) : systemImpl_(impl) {} 38 ~MediaKeySystemObject() = default; 39 40 const OHOS::sptr<OHOS::DrmStandard::MediaKeySystemImpl> systemImpl_ = nullptr; 41 OHOS::sptr<OHOS::DrmStandard::MediaKeySystemCallbackCapi> systemCallback_ = nullptr; 42 }; 43 44 struct MediaKeySessionObject : public MediaKeySession { MediaKeySessionObjectMediaKeySessionObject45 explicit MediaKeySessionObject(const OHOS::sptr<OHOS::DrmStandard::MediaKeySessionImpl> &impl) : sessionImpl_(impl) 46 {} 47 ~MediaKeySessionObject() = default; 48 49 const OHOS::sptr<OHOS::DrmStandard::MediaKeySessionImpl> sessionImpl_ = nullptr; 50 OHOS::sptr<MediaKeySessionCallbackCapi> sessionCallback_ = nullptr; 51 }; 52 53 class MediaKeySystemCallbackCapi : public MediaKeySystemImplCallback { 54 public: MediaKeySystemCallbackCapi()55 MediaKeySystemCallbackCapi() 56 { 57 DRM_INFO_LOG("MediaKeySystemCallbackCapi."); 58 InitEventMap(); 59 } 60 InitEventMap()61 void InitEventMap() 62 { 63 eventMap_.insert({ static_cast<std::string>(MediaKeySystemEvent::EVENT_STR_PROVISION_REQUIRED), 64 EVENT_PROVISION_REQUIRED }); 65 } 66 ~MediaKeySystemCallbackCapi()67 virtual ~MediaKeySystemCallbackCapi() 68 { 69 DRM_INFO_LOG("~MediaKeySystemCallbackCapi."); 70 } 71 SetCallbackReference(MediaKeySystem_Callback callback)72 void SetCallbackReference(MediaKeySystem_Callback callback) 73 { 74 DRM_INFO_LOG("MediaKeySystemCallbackCapi SetCallbackReference."); 75 std::lock_guard<std::mutex> lock(mutex_); 76 callback_ = callback; 77 } 78 ClearCallbackReference()79 void ClearCallbackReference() 80 { 81 DRM_INFO_LOG("MediaKeySystemCallbackCapi ClearCallbackReference."); 82 std::lock_guard<std::mutex> lock(mutex_); 83 callback_ = nullptr; 84 } 85 SendEvent(const std::string & event,int32_t extra,const std::vector<uint8_t> & data)86 void SendEvent(const std::string &event, int32_t extra, const std::vector<uint8_t> &data) override 87 { 88 DRM_INFO_LOG("MediaKeySystemCallbackCapi SendEvent."); 89 std::lock_guard<std::mutex> lock(mutex_); 90 if (eventMap_.find(event) == eventMap_.end()) { 91 DRM_ERR_LOG("MediaKeySystemCallbackCapi SendEvent failed, not find this event type."); 92 return; 93 } 94 95 unsigned char *dataInfo = (unsigned char *)malloc(data.size()); 96 DRM_CHECK_AND_RETURN_LOG(dataInfo != nullptr, "malloc faild!"); 97 errno_t ret = memcpy_s(dataInfo, data.size(), data.data(), data.size()); 98 DRM_CHECK_AND_RETURN_LOG(ret == EOK, "memcpy_s faild!"); 99 100 DRM_CHECK_AND_RETURN_LOG(callback_ != nullptr, "callback_ is nullptr"); 101 callback_(eventMap_[event], dataInfo, data.size(), std::to_string(extra).data()); 102 if (dataInfo != nullptr) { 103 free(dataInfo); 104 dataInfo = nullptr; 105 } 106 } 107 108 private: 109 MediaKeySystem_Callback callback_ = nullptr; 110 std::mutex mutex_; 111 std::unordered_map<std::string, DRM_EventType> eventMap_; 112 }; 113 114 class MediaKeySessionCallbackCapi : public MediaKeySessionImplCallback { 115 public: MediaKeySessionCallbackCapi()116 MediaKeySessionCallbackCapi() 117 { 118 DRM_INFO_LOG("MediaKeySessionCallbackCapi."); 119 InitEventMap(); 120 } 121 InitEventMap()122 void InitEventMap() 123 { 124 eventMap_.insert({ static_cast<std::string>(MediaKeySessionEvent::EVENT_STR_EXPIRATION_UPDATED), 125 EVENT_EXPIRATION_UPDATE }); 126 eventMap_.insert( 127 { static_cast<std::string>(MediaKeySessionEvent::EVENT_STR_KEY_EXPIRED), EVENT_KEY_EXPIRED }); 128 eventMap_.insert( 129 { static_cast<std::string>(MediaKeySessionEvent::EVENT_STR_KEY_NEEDED), EVENT_KEY_REQUIRED }); 130 eventMap_.insert( 131 { static_cast<std::string>(MediaKeySessionEvent::EVENT_STR_VENDOR_DEFINED), EVENT_VENDOR_DEFINED }); 132 } 133 ~MediaKeySessionCallbackCapi()134 virtual ~MediaKeySessionCallbackCapi() 135 { 136 DRM_INFO_LOG("~MediaKeySessionCallbackCapi."); 137 } 138 SetCallbackReference(MediaKeySession_Callback callback)139 void SetCallbackReference(MediaKeySession_Callback callback) 140 { 141 DRM_INFO_LOG("MediaKeySessionCallbackCapi SetCallbackReference."); 142 std::lock_guard<std::mutex> lock(mutex_); 143 callback_ = callback; 144 } 145 ClearCallbackReference()146 void ClearCallbackReference() 147 { 148 DRM_INFO_LOG("MediaKeySessionCallbackCapi ClearCallbackReference."); 149 std::lock_guard<std::mutex> lock(mutex_); 150 callback_ = {}; 151 } 152 SendEvent(const std::string & event,int32_t extra,const std::vector<uint8_t> & data)153 void SendEvent(const std::string &event, int32_t extra, const std::vector<uint8_t> &data) override 154 { 155 DRM_INFO_LOG("MediaKeySessionCallbackCapi SendEvent."); 156 std::lock_guard<std::mutex> lock(mutex_); 157 DRM_CHECK_AND_RETURN_LOG(callback_.eventCallback != nullptr, "Callback is nullptr"); 158 if (eventMap_.find(event) == eventMap_.end()) { 159 DRM_ERR_LOG("MediaKeySystemCallbackCapi SendEvent failed, not find this event type."); 160 return; 161 } 162 163 unsigned char *dataInfo = (unsigned char *)malloc(data.size()); 164 DRM_CHECK_AND_RETURN_LOG(dataInfo != nullptr, "malloc faild!"); 165 errno_t ret = memcpy_s(dataInfo, data.size(), data.data(), data.size()); 166 DRM_CHECK_AND_RETURN_LOG(ret == EOK, "memcpy_s faild!"); 167 168 DRM_CHECK_AND_RETURN_LOG(callback_.eventCallback != nullptr, "eventCallback is nullptr"); 169 callback_.eventCallback(eventMap_[event], dataInfo, data.size(), std::to_string(extra).data()); 170 if (dataInfo != nullptr) { 171 free(dataInfo); 172 dataInfo = nullptr; 173 } 174 } 175 SendEventKeyChanged(std::map<std::vector<uint8_t>,MediaKeySessionKeyStatus> statusTable,bool hasNewGoodLicense)176 void SendEventKeyChanged(std::map<std::vector<uint8_t>, MediaKeySessionKeyStatus> statusTable, 177 bool hasNewGoodLicense) override 178 { 179 DRM_INFO_LOG("MediaKeySessionCallbackCapi SendEventKeyChanged."); 180 static std::unordered_map<MediaKeySessionKeyStatus, std::string> KeyStatusStringMap { 181 {MediaKeySessionKeyStatus::MEDIA_KEY_SESSION_KEY_STATUS_USABLE, "USABLE"}, 182 {MediaKeySessionKeyStatus::MEDIA_KEY_SESSION_KEY_STATUS_EXPIRED, "EXPIRED"}, 183 {MediaKeySessionKeyStatus::MEDIA_KEY_SESSION_KEY_STATUS_OUTPUT_NOT_ALLOWED, "OUTPUT_NOT_ALLOWED"}, 184 {MediaKeySessionKeyStatus::MEDIA_KEY_SESSION_KEY_STATUS_PENDING, "PENDING"}, 185 {MediaKeySessionKeyStatus::MEDIA_KEY_SESSION_KEY_STATUS_INTERNAL_ERROR, "INTERNAL_ERROR"}, 186 {MediaKeySessionKeyStatus::MEDIA_KEY_SESSION_KEY_STATUS_USABLE_IN_FUTURE, "USABLE_IN_FUTURE"}, 187 }; 188 189 uint32_t tableCount = statusTable.size(); 190 DRM_CHECK_AND_RETURN_LOG(tableCount <= MAX_KEY_INFO_COUNT, "DRM_KeysInfo has not enough space!"); 191 192 DRM_KeysInfo info; 193 info.keysInfoCount = tableCount; 194 uint32_t index = 0; 195 for (auto &item : statusTable) { 196 uint32_t keyIdSize = item.first.size(); 197 DRM_CHECK_AND_RETURN_LOG(keyIdSize <= MAX_KEY_ID_LEN, "DRM_KeysInfo keyId has not enough space!"); 198 errno_t ret = memset_s(info.keyId[index], MAX_KEY_ID_LEN, 0x00, MAX_KEY_ID_LEN); 199 DRM_CHECK_AND_RETURN_LOG(ret == EOK, "memset_s keyId failed!"); 200 ret = memcpy_s(info.keyId[index], keyIdSize, item.first.data(), keyIdSize); 201 DRM_CHECK_AND_RETURN_LOG(ret == EOK, "memcpy_s keyId failed!"); 202 203 std::string keyStatus = KeyStatusStringMap[item.second]; 204 uint32_t statusSize = keyStatus.size(); 205 DRM_CHECK_AND_RETURN_LOG(statusSize <= MAX_KEY_STATUS_VALUE_LEN, 206 "DRM_KeysInfo statusValue has not enough space!"); 207 ret = memset_s(info.statusValue[index], MAX_KEY_STATUS_VALUE_LEN, 0x00, MAX_KEY_STATUS_VALUE_LEN); 208 DRM_CHECK_AND_RETURN_LOG(ret == EOK, "memset_s statusValue failed!"); 209 ret = memcpy_s(info.statusValue[index], statusSize, keyStatus.data(), statusSize); 210 DRM_CHECK_AND_RETURN_LOG(ret == EOK, "memcpy_s statusValue failed!"); 211 212 index++; 213 } 214 std::lock_guard<std::mutex> lock(mutex_); 215 DRM_CHECK_AND_RETURN_LOG(callback_.keyChangeCallback != nullptr, "keyChangeCallback is nullptr"); 216 callback_.keyChangeCallback(&info, hasNewGoodLicense); 217 } 218 private: 219 struct MediaKeySession_Callback callback_ = {}; 220 std::mutex mutex_; 221 std::unordered_map<std::string, DRM_EventType> eventMap_; 222 }; 223 } // DrmStandard 224 } // OHOS 225 226 #endif // NATIVE_DRM_OBJECT_H