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
17 #include <string>
18 #include <refbase.h>
19 #include <securec.h>
20 #include "drm_log.h"
21 #include "http.h"
22 #include "native_drm_common.h"
23 #include "native_drm_base.h"
24 #include "native_drm_object.h"
25 #include "native_mediakeysession.h"
26 #include "mediakeydecryptndk_fuzzer.h"
27 #include "media_decrypt_module_service_proxy.h"
28
29 #define OFFRESPONSE \
30 { \
31 0x31, 0x64, 0x6E, 0x5A, 0x32, 0x4E, 0x57, 0x74, 0x76, 0x4D, 0x47, 0x34, 0x34, 0x4E, 0x6A, 0x42, 0x30, 0x4D, \
32 0x32, 0x77, 0x33, 0x4E, 0x67, 0x3D, 0x3D, 0x3A, 0x59, 0x7A, 0x56, 0x78, 0x63, 0x48, 0x64, 0x70, 0x61, \
33 0x6D, 0x30, 0x34, 0x59, 0x57, 0x45, 0x34, 0x5A, 0x48, 0x6B, 0x79, 0x4D, 0x67, 0x3D, 0x3D \
34 }
35 #define REQUESTINFODATA \
36 { \
37 0x00, 0x00, 0x00, 0x8B, 0x70, 0x73, 0x73, 0x68, 0x00, 0x00, 0x00, 0x00, 0x3D, 0x5E, 0x6D, 0x35, 0x9B, 0x9A, \
38 0x41, 0xE8, 0xB8, 0x43, 0xDD, 0x3C, 0x6E, 0x72, 0xC4, 0x2C, 0x00, 0x00, 0x00, 0x6B, 0x7B, 0x22, 0x76, \
39 0x65, 0x72, 0x73, 0x69, 0x6F, 0x6E, 0x22, 0x3A, 0x22, 0x56, 0x31, 0x2E, 0x30, 0x22, 0x2C, 0x22, 0x63, \
40 0x6F, 0x6E, 0x74, 0x65, 0x6E, 0x74, 0x49, 0x44, 0x22, 0x3A, 0x22, 0x64, 0x48, 0x4D, 0x74, 0x4D, 0x6A, \
41 0x59, 0x30, 0x4C, 0x54, 0x45, 0x77, 0x4F, 0x44, 0x41, 0x74, 0x59, 0x57, 0x56, 0x7A, 0x22, 0x2C, 0x22, \
42 0x6B, 0x69, 0x64, 0x73, 0x22, 0x3A, 0x5B, 0x22, 0x47, 0x2B, 0x45, 0x6B, 0x2F, 0x2B, 0x58, 0x6D, 0x55, \
43 0x6B, 0x70, 0x42, 0x48, 0x51, 0x67, 0x58, 0x59, 0x57, 0x51, 0x51, 0x49, 0x67, 0x3D, 0x3D, 0x22, 0x5D, \
44 0x2C, 0x22, 0x65, 0x6E, 0x73, 0x63, 0x68, 0x65, 0x6D, 0x61, 0x22, 0x3A, 0x22, 0x63, 0x62, 0x63, 0x31, \
45 0x22, 0x7D \
46 }
47 #define PROVISION_URL "https://drmkit.hwcloudtest.cn:8080/provision/v1/wiseplay"
48 #define LICENSE_URL "http://license.dev.trustdta.com:8080/drmproxy/v3/getLicense"
49 #define HTTPOUTTIME 10
50 using namespace std;
51 using namespace OHOS;
52 using namespace DrmStandard;
53 const int32_t MEMMAXSIZE = 128;
54 const int32_t OFFRESPONSELEN = 50;
55 const int32_t DATAMAXSIZE = 12288;
56 namespace OHOS {
57 namespace DrmStandard {
TestsessionEventCallBack(DRM_EventType eventType,unsigned char * info,int32_t infoLen,char * extra)58 Drm_ErrCode TestsessionEventCallBack(DRM_EventType eventType, unsigned char *info, int32_t infoLen, char *extra)
59 {
60 DRM_INFO_LOG("TestsessionEventCallBack ok");
61 return DRM_ERR_OK;
62 }
63
TestSessoinEventCallBack(DRM_EventType eventType,unsigned char * info,int32_t infoLen,char * extra)64 Drm_ErrCode TestSessoinEventCallBack(DRM_EventType eventType, unsigned char *info, int32_t infoLen, char *extra)
65 {
66 DRM_INFO_LOG("TestSessoinEventCallBack ok");
67 return DRM_ERR_OK;
68 }
69
TestSessoinKeyChangeCallBack(DRM_KeysInfo * keysInfo,bool hasNewGoodKeys)70 Drm_ErrCode TestSessoinKeyChangeCallBack(DRM_KeysInfo *keysInfo, bool hasNewGoodKeys)
71 {
72 DRM_INFO_LOG("TestSessoinKeyChangeCallBack ok");
73 return DRM_ERR_OK;
74 }
75
MediadecryptNdkFuzzer()76 MediadecryptNdkFuzzer::MediadecryptNdkFuzzer() {}
77
~MediadecryptNdkFuzzer()78 MediadecryptNdkFuzzer::~MediadecryptNdkFuzzer() {}
79
GetUuid()80 void MediadecryptNdkFuzzer::GetUuid()
81 {
82 if (OH_MediaKeySystem_IsSupported("com.clearplay.drm")) {
83 uuid = "com.clearplay.drm";
84 } else if (OH_MediaKeySystem_IsSupported("com.wiseplay.drm")) {
85 uuid = "com.wiseplay.drm";
86 }
87 }
88
IsWisePlay()89 void MediadecryptNdkFuzzer::IsWisePlay()
90 {
91 if (OH_MediaKeySystem_IsSupported("com.wiseplay.drm")) {
92 wisePlay = true;
93 }
94 }
95
GenerateDeviceCertificate()96 void MediadecryptNdkFuzzer::GenerateDeviceCertificate()
97 {
98 DRM_INFO_LOG("MediadecryptNdkFuzzer::GenerateDeviceCertificate start");
99 unsigned char request[12288] = { 0 }; // 12288:request len
100 int32_t requestLen = 12288; // 12288:request len
101 char defaultUrl[2048] = { 0 }; // 2048:url len
102 int32_t defaultUrlLen = 2048; // 2048:url len
103 OH_MediaKeySystem_GenerateKeySystemRequest(mediaKeySystem, request, &requestLen, defaultUrl, defaultUrlLen);
104 uint8_t Response[12288] = OFFRESPONSE;
105 int32_t ResponseLen = sizeof(Response);
106 if (wisePlay == true) {
107 HttpPost(PROVISION_URL, request, requestLen, Response, &ResponseLen, HTTPOUTTIME);
108 }
109 OH_MediaKeySystem_ProcessKeySystemResponse(mediaKeySystem, Response, ResponseLen);
110 DRM_INFO_LOG("MediadecryptNdkFuzzer::GenerateDeviceCertificate end");
111 }
112
GenerateLicense()113 void MediadecryptNdkFuzzer::GenerateLicense()
114 {
115 DRM_INFO_LOG("MediaKeysessionNdkFuzzer::GenerateLicense start");
116 DRM_MediaKeyRequest mediaKeyRequest;
117 DRM_MediaKeyRequestInfo info;
118 unsigned char testData[139] = REQUESTINFODATA;
119 memset_s(&info, sizeof(DRM_MediaKeyRequestInfo), 0, sizeof(DRM_MediaKeyRequestInfo));
120 info.initDataLen = sizeof(testData);
121 info.type = MEDIA_KEY_TYPE_ONLINE;
122 memcpy_s(info.mimeType, sizeof("video/mp4"), "video/mp4", sizeof("video/mp4"));
123 memcpy_s(info.initData, sizeof(testData), testData, sizeof(testData));
124 int ret = memcpy_s(info.optionName[0], sizeof("optionalDataName"), "optionalDataName", sizeof("optionalDataName"));
125 if (ret != 0) {
126 DRM_INFO_LOG("memcpy_s faild!");
127 }
128 ret = memcpy_s(info.optionData[0], sizeof("optionalDataValue"), "optionalDataValue", sizeof("optionalDataValue"));
129 if (ret != 0) {
130 DRM_INFO_LOG("memcpy_s faild!");
131 }
132 info.optionsCount = 1;
133 OH_MediaKeySession_GenerateMediaKeyRequest(mediaKeySession, &info, &mediaKeyRequest);
134 DRM_INFO_LOG("MediaKeysessionNdkFuzzer::GenerateLicense end");
135 unsigned char keySessionResponse[12288] = OFFRESPONSE;
136 int32_t keySessionResponseLen = sizeof(keySessionResponse);
137 if (wisePlay) {
138 HttpPost(LICENSE_URL, mediaKeyRequest.data, (uint32_t)mediaKeyRequest.dataLen, keySessionResponse,
139 &keySessionResponseLen, HTTPOUTTIME);
140 } else {
141 keySessionResponseLen = OFFRESPONSELEN;
142 }
143 uint8_t mediaKeyId[64] = { 0 }; // 64:OFFLINE_MEDIA_KEY_ID_LEN
144 int32_t mediaKeyIdLen = 64; // 64:OFFLINE_MEDIA_KEY_ID_LEN
145 OH_MediaKeySession_ProcessMediaKeyResponse(mediaKeySession, keySessionResponse, keySessionResponseLen,
146 mediaKeyId, &mediaKeyIdLen);
147 }
148
149
Init()150 void MediadecryptNdkFuzzer::Init()
151 {
152 DRM_INFO_LOG("MediadecryptNdkFuzzer::Init start");
153 GetUuid();
154 IsWisePlay();
155 DRM_INFO_LOG("uuid = %{public}s", uuid.c_str());
156 DRM_INFO_LOG("wisePlay = %{public}d", wisePlay);
157 OH_MediaKeySystem_Create((const char *)uuid.c_str(), &mediaKeySystem);
158 DRM_INFO_LOG("MediadecryptNdkFuzzer::Init end");
159 }
160
Deinitialize()161 void MediadecryptNdkFuzzer::Deinitialize()
162 {
163 DRM_INFO_LOG("MediadecryptNdkFuzzer::Deinitialize start");
164 if (mediaKeySystem != nullptr) {
165 OH_MediaKeySystem_Destroy(mediaKeySystem);
166 mediaKeySystem = nullptr;
167 }
168 DRM_INFO_LOG("MediadecryptNdkFuzzer::Deinitialize end");
169 }
170
FuzzTestMediaKeyDecryptNdk(uint8_t * rawData,size_t size)171 bool MediadecryptNdkFuzzer::FuzzTestMediaKeyDecryptNdk(uint8_t *rawData, size_t size)
172 {
173 if (rawData == nullptr || size < sizeof(int32_t)) {
174 return false;
175 }
176 Init();
177 GenerateDeviceCertificate();
178 OH_MediaKeySystem_CreateMediaKeySession(mediaKeySystem, &ContentProtectionLevel, &mediaKeySession);
179 GenerateLicense();
180 if (mediaKeySession) {
181 MediaKeySessionObject *sessionObject = reinterpret_cast<MediaKeySessionObject *>(mediaKeySession);
182 sptr<IMediaKeySessionService> SessionServiceProxy =
183 sessionObject->sessionImpl_->GetMediaKeySessionServiceProxy();
184 sptr<IMediaDecryptModuleService> decryptModule;
185 SessionServiceProxy->GetMediaDecryptModule(decryptModule);
186 IMediaDecryptModuleService::DrmBuffer srcBuffer;
187 IMediaDecryptModuleService::DrmBuffer dstBuffer;
188 bool secureDecodrtState = false;
189 IMediaDecryptModuleService::CryptInfo cryptInfo;
190 decryptModule->Release();
191 sptr<MediaKeySessionImplCallback> callback = sessionObject->sessionImpl_->GetApplicationCallback();
192 callback->~MediaKeySessionImplCallback();
193 }
194 if (mediaKeySession != nullptr) {
195 OH_MediaKeySession_Destroy(mediaKeySession);
196 mediaKeySession = nullptr;
197 }
198 Deinitialize();
199 DRM_INFO_LOG("MediadecryptNdkFuzzer::FuzzTestMediaKeysessionConfigurationNdk end");
200 return true;
201 }
202 } // namespace DrmStandard
203
FuzzMediaKeysessionNdk(uint8_t * data,size_t size)204 bool FuzzMediaKeysessionNdk(uint8_t *data, size_t size)
205 {
206 if (data == nullptr) {
207 return true;
208 }
209 MediadecryptNdkFuzzer testMediasession;
210 testMediasession.FuzzTestMediaKeyDecryptNdk(data, size);
211 return true;
212 }
213 } // namesapce OHOS
214
215 /* Fuzzer entry point */
LLVMFuzzerTestOneInput(uint8_t * data,size_t size)216 extern "C" int LLVMFuzzerTestOneInput(uint8_t *data, size_t size)
217 {
218 /* Run your code on data */
219 uint8_t rawData[DATAMAXSIZE] = { 0 };
220 int32_t ret = memcpy_s(rawData, DATAMAXSIZE - 1, data, size);
221 if (ret != 0) {
222 return -1;
223 }
224 OHOS::FuzzMediaKeysessionNdk(rawData, size);
225 return 0;
226 }
227