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 #include "v1_0/media_decrypt_module_service.h"
17 #include <hdf_base.h>
18 #include <hdf_log.h>
19 #include <memory>
20 #include <chrono>
21 #include <sys/mman.h>
22 #include <unistd.h>
23 #include "openssl/aes.h"
24 #include "openssl/evp.h"
25 #include "openssl/rand.h"
26 #include "session.h"
27 #include "ashmem.h"
28 #include "securec.h"
29 
30 #define HDF_LOG_TAG media_decrypt_module_service
31 
32 namespace OHOS {
33 namespace HDI {
34 namespace Drm {
35 namespace V1_0 {
36 static const size_t BLOCK_SIZE = AES_BLOCK_SIZE;
37 static const size_t BLOCK_BIT_SIZE = BLOCK_SIZE * 8;
38 
MediaDecryptModuleService(sptr<Session> & session)39 MediaDecryptModuleService::MediaDecryptModuleService(sptr<Session> &session)
40 {
41     HDF_LOGI("%{public}s: start", __func__);
42     session_ = session;
43     HDF_LOGI("%{public}s: end", __func__);
44 }
45 
DecryptMediaData(bool secure,const CryptoInfo & cryptoInfo,const DrmBuffer & srcBuffer,const DrmBuffer & destBuffer)46 int32_t MediaDecryptModuleService::DecryptMediaData(bool secure, const CryptoInfo &cryptoInfo,
47     const DrmBuffer &srcBuffer, const DrmBuffer &destBuffer)
48 {
49     HDF_LOGI("%{public}s: start", __func__);
50     auto start = std::chrono::high_resolution_clock::now();
51     ++decryptNumber;
52     int32_t ret = HDF_FAILURE;
53     if (session_ == nullptr || secure == true) {
54         ++errorDecryptNumber;
55         (void)::close(srcBuffer.fd);
56         (void)::close(destBuffer.fd);
57         return HDF_FAILURE;
58     }
59     std::vector<uint8_t> key;
60     ret = session_->getKeyValueByKeyId(cryptoInfo.keyId, key);
61     if (ret != HDF_SUCCESS) {
62         HDF_LOGI("%{public}s: could not find key", __func__);
63     }
64 
65     uint8_t *srcData = nullptr;
66     uint8_t *destData = nullptr;
67     size_t data_size = 0;
68     for (auto &subSample : cryptoInfo.subSamples) {
69         if (subSample.clearHeaderLen > 0) {
70             data_size += subSample.clearHeaderLen;
71         }
72 
73         if (subSample.payLoadLen > 0) {
74             data_size += subSample.payLoadLen;
75         }
76     }
77 
78     srcData = (uint8_t *)mmap(nullptr, data_size, PROT_READ | PROT_WRITE, MAP_SHARED, srcBuffer.fd, 0);
79     if (srcData == nullptr) {
80         HDF_LOGE("%{public}s: invalid src_shared_mem", __func__);
81         ++errorDecryptNumber;
82         (void)::close(srcBuffer.fd);
83         (void)::close(destBuffer.fd);
84         return HDF_FAILURE;
85     }
86 
87     destData = (uint8_t *)mmap(nullptr, data_size, PROT_READ | PROT_WRITE, MAP_SHARED, destBuffer.fd, 0);
88     if (destData == nullptr) {
89         HDF_LOGE("%{public}s: invalid dest_shared_mem", __func__);
90         (void)munmap(srcData, data_size);
91         ++errorDecryptNumber;
92         (void)::close(srcBuffer.fd);
93         (void)::close(destBuffer.fd);
94         return HDF_FAILURE;
95     }
96 
97     switch (cryptoInfo.type) {
98         case ALGTYPE_UNENCRYPTED:
99             ret = CopyBuffer(srcData, destData, cryptoInfo.subSamples);
100             break;
101         case ALGTYPE_AES_WV:
102             ret = DecryptByAesCbc(key, cryptoInfo.iv, srcData, destData, cryptoInfo.subSamples);
103             break;
104         case ALGTYPE_AES_CBC:
105             ret = DecryptByAesCbc(key, cryptoInfo.iv, srcData, destData, cryptoInfo.subSamples);
106             break;
107         case ALGTYPE_AES_CTR:
108         case ALGTYPE_SM4_CBC:
109             ret = DecryptBySM4Cbc(key, cryptoInfo.iv, srcData, destData, cryptoInfo.subSamples);
110             break;
111         default:
112             (void)munmap(srcData, data_size);
113             (void)munmap(destData, data_size);
114             (void)::close(srcBuffer.fd);
115             (void)::close(destBuffer.fd);
116             HDF_LOGE("CryptoAlgorithmType is not supported");
117             ++errorDecryptNumber;
118             return HDF_ERR_INVALID_PARAM;
119     }
120     (void)munmap(srcData, data_size);
121     (void)munmap(destData, data_size);
122     (void)::close(srcBuffer.fd);
123     (void)::close(destBuffer.fd);
124     if (ret != HDF_SUCCESS) {
125         ++errorDecryptNumber;
126         return ret;
127     }
128     auto end = std::chrono::high_resolution_clock::now();
129     auto duration = std::chrono::duration_cast<std::chrono::milliseconds>(end - start);
130     HDF_LOGD("decryption time is %{public}lld", duration.count());
131     decryptTimes.push_back(duration.count());
132     HDF_LOGI("%{public}s: end", __func__);
133     return HDF_SUCCESS;
134 }
135 
DecryptBySM4Cbc(const std::vector<uint8_t> & key,const std::vector<uint8_t> & iv,uint8_t * srcData,uint8_t * destData,const std::vector<SubSample> & subSamples)136 int32_t MediaDecryptModuleService::DecryptBySM4Cbc(const std::vector<uint8_t> &key, const std::vector<uint8_t> &iv,
137     uint8_t *srcData, uint8_t *destData, const std::vector<SubSample> &subSamples)
138 {
139     HDF_LOGI("%{public}s: start", __func__);
140     EVP_CIPHER_CTX *ctx;
141     size_t offset = 0;
142     int len;
143     int32_t ret = HDF_FAILURE;
144     if (key.size() != BLOCK_SIZE || iv.size() != BLOCK_SIZE) {
145         HDF_LOGE("key or iv length error");
146         return HDF_ERR_INVALID_PARAM;
147     }
148     HDF_LOGI("%{public}s: before EVP_DecryptInit_ex", __func__);
149     ctx = EVP_CIPHER_CTX_new();
150     EVP_DecryptInit_ex(ctx, EVP_sm4_cbc(), nullptr, key.data(), iv.data());
151     EVP_CIPHER_CTX_set_padding(ctx, 0);
152     HDF_LOGI("%{public}s: after EVP_DecryptInit_ex", __func__);
153 
154     for (auto &subSample : subSamples) {
155         if (subSample.clearHeaderLen > 0) {
156             HDF_LOGI("%{public}s: before clear header memcpy_s", __func__);
157             ret = memcpy_s(destData + offset, subSample.clearHeaderLen, srcData + offset, subSample.clearHeaderLen);
158             if (ret != 0) {
159                 HDF_LOGI("%{public}s: memcpy_s faild!", __func__);
160                 return ret;
161             }
162             HDF_LOGI("%{public}s: after clear header memcpy_s", __func__);
163             offset += subSample.clearHeaderLen;
164         }
165 
166         if (subSample.payLoadLen > 0) {
167             HDF_LOGI("%{public}s: before EVP_DecryptUpdate", __func__);
168             // Decrypt data
169             EVP_DecryptUpdate(ctx, (unsigned char *)(destData + offset), &len,
170                 (const unsigned char *)(srcData + offset), (int)(subSample.payLoadLen));
171             // End decryption process
172             EVP_DecryptFinal_ex(ctx, (unsigned char *)(destData + offset + len), &len);
173             HDF_LOGI("%{public}s: after EVP_DecryptFinal_ex", __func__);
174             offset += subSample.payLoadLen;
175         }
176     }
177     // release context
178     EVP_CIPHER_CTX_free(ctx);
179     HDF_LOGI("%{public}s: end", __func__);
180     return HDF_SUCCESS;
181 }
182 
DecryptByAesCbc(const std::vector<uint8_t> & key,const std::vector<uint8_t> & iv,uint8_t * srcData,uint8_t * destData,const std::vector<SubSample> & subSamples)183 int32_t MediaDecryptModuleService::DecryptByAesCbc(const std::vector<uint8_t> &key, const std::vector<uint8_t> &iv,
184     uint8_t *srcData, uint8_t *destData, const std::vector<SubSample> &subSamples)
185 {
186     HDF_LOGI("%{public}s: start", __func__);
187     size_t offset = 0;
188     AES_KEY opensslKey;
189     int32_t ret = HDF_FAILURE;
190     if (key.size() != BLOCK_SIZE || iv.size() != BLOCK_SIZE) {
191         HDF_LOGE("key or iv length error");
192         return HDF_ERR_INVALID_PARAM;
193     }
194     HDF_LOGI("%{public}s: before AES_set_decrypt_key", __func__);
195     AES_set_decrypt_key((unsigned char *)key.data(), BLOCK_BIT_SIZE, &opensslKey);
196     HDF_LOGI("%{public}s: after AES_set_decrypt_key", __func__);
197 
198     for (auto &subSample : subSamples) {
199         if (subSample.clearHeaderLen > 0) {
200             HDF_LOGI("%{public}s: before clear header memcpy_s", __func__);
201             ret = memcpy_s(destData + offset, subSample.clearHeaderLen, srcData + offset, subSample.clearHeaderLen);
202             if (ret != 0) {
203                 HDF_LOGE("%{public}s: memcpy_s faild", __func__);
204                 return ret;
205             }
206             HDF_LOGI("%{public}s: after clear header memcpy_s", __func__);
207             offset += subSample.clearHeaderLen;
208         }
209 
210         if (subSample.payLoadLen > 0) {
211             HDF_LOGI("%{public}s: before AES_cbc_encrypt", __func__);
212             AES_cbc_encrypt((uint8_t *)srcData + offset, (uint8_t *)destData + offset, subSample.payLoadLen,
213                 &opensslKey, (unsigned char *)iv.data(), AES_DECRYPT);
214             HDF_LOGI("%{public}s: after AES_cbc_encrypt", __func__);
215             offset += subSample.payLoadLen;
216         }
217     }
218     HDF_LOGI("%{public}s: end", __func__);
219     return HDF_SUCCESS;
220 }
221 
CopyBuffer(uint8_t * srcBuffer,uint8_t * destBuffer,const std::vector<SubSample> & subSamples)222 int32_t MediaDecryptModuleService::CopyBuffer(uint8_t *srcBuffer, uint8_t *destBuffer,
223     const std::vector<SubSample> &subSamples)
224 {
225     HDF_LOGI("%{public}s: start", __func__);
226     size_t offset = 0;
227     int32_t ret = HDF_FAILURE;
228     for (auto &subSample : subSamples) {
229         if (subSample.clearHeaderLen > 0) {
230             ret = memcpy_s(destBuffer + offset, subSample.clearHeaderLen, srcBuffer + offset, subSample.clearHeaderLen);
231             if (ret != 0) {
232                 HDF_LOGE("%{public}s: memcpy_s faild", __func__);
233                 return ret;
234             }
235             offset += subSample.clearHeaderLen;
236         }
237 
238         if (subSample.payLoadLen > 0) {
239             ret = memcpy_s(destBuffer + offset, subSample.clearHeaderLen, srcBuffer + offset, subSample.payLoadLen);
240             if (ret != 0) {
241                 HDF_LOGE("%{public}s: memcpy_s faild", __func__);
242                 return ret;
243             }
244             offset += subSample.payLoadLen;
245         }
246     }
247     HDF_LOGI("%{public}s: end", __func__);
248     return HDF_SUCCESS;
249 }
250 
GetDecryptNumber()251 int32_t MediaDecryptModuleService::GetDecryptNumber()
252 {
253     HDF_LOGI("%{public}s: start", __func__);
254     HDF_LOGI("%{public}s: end", __func__);
255     return decryptNumber;
256 }
257 
GetDecryptTimes(std::vector<double> & times)258 int32_t MediaDecryptModuleService::GetDecryptTimes(std::vector<double> &times)
259 {
260     HDF_LOGI("%{public}s: start", __func__);
261     times.assign(decryptTimes.begin(), decryptTimes.end());
262     HDF_LOGI("%{public}s: end", __func__);
263     return HDF_SUCCESS;
264 }
265 
GetErrorDecryptNumber()266 int32_t MediaDecryptModuleService::GetErrorDecryptNumber()
267 {
268     HDF_LOGI("%{public}s: start", __func__);
269     HDF_LOGI("%{public}s: end", __func__);
270     return errorDecryptNumber;
271 }
272 
Release()273 int32_t MediaDecryptModuleService::Release()
274 {
275     HDF_LOGI("%{public}s: start", __func__);
276     HDF_LOGI("%{public}s: end", __func__);
277     return HDF_SUCCESS;
278 }
279 } // V1_0
280 } // Drm
281 } // HDI
282 } // OHOS
283