1 /*
2 * Copyright (C) 2022-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 "signature.h"
17
18 #include <securec.h>
19
20 #include "config.h"
21 #include "ecdsa_openssl.h"
22 #include "log.h"
23 #include "memory.h"
24 #include "params_parser.h"
25 #include "signature_spi.h"
26 #include "signature_rsa_openssl.h"
27 #include "utils.h"
28
29 typedef HcfResult (*HcfSignSpiCreateFunc)(HcfSignatureParams *, HcfSignSpi **);
30 typedef HcfResult (*HcfVerifySpiCreateFunc)(HcfSignatureParams *, HcfVerifySpi **);
31
32 typedef struct {
33 HcfSign base;
34
35 HcfSignSpi *spiObj;
36
37 char algoName[HCF_MAX_ALGO_NAME_LEN];
38 } HcfSignImpl;
39
40 typedef struct {
41 HcfVerify base;
42
43 HcfVerifySpi *spiObj;
44
45 char algoName[HCF_MAX_ALGO_NAME_LEN];
46 } HcfVerifyImpl;
47
48 typedef struct {
49 HCF_ALG_VALUE algo;
50
51 HcfSignSpiCreateFunc createFunc;
52 } HcfSignGenAbility;
53
54 typedef struct {
55 HCF_ALG_VALUE algo;
56
57 HcfVerifySpiCreateFunc createFunc;
58 } HcfVerifyGenAbility;
59
60 static const HcfSignGenAbility SIGN_GEN_ABILITY_SET[] = {
61 { HCF_ALG_ECC, HcfSignSpiEcdsaCreate },
62 { HCF_ALG_RSA, HcfSignSpiRsaCreate }
63 };
64
65 static const HcfVerifyGenAbility VERIFY_GEN_ABILITY_SET[] = {
66 { HCF_ALG_ECC, HcfVerifySpiEcdsaCreate },
67 { HCF_ALG_RSA, HcfVerifySpiRsaCreate }
68 };
69
FindSignAbility(HcfSignatureParams * params)70 static HcfSignSpiCreateFunc FindSignAbility(HcfSignatureParams *params)
71 {
72 for (uint32_t i = 0; i < sizeof(SIGN_GEN_ABILITY_SET) / sizeof(SIGN_GEN_ABILITY_SET[0]); i++) {
73 if (SIGN_GEN_ABILITY_SET[i].algo == params->algo) {
74 return SIGN_GEN_ABILITY_SET[i].createFunc;
75 }
76 }
77 LOGE("Algo not support! [Algo]: %d", params->algo);
78 return NULL;
79 }
80
FindVerifyAbility(HcfSignatureParams * params)81 static HcfVerifySpiCreateFunc FindVerifyAbility(HcfSignatureParams *params)
82 {
83 for (uint32_t i = 0; i < sizeof(VERIFY_GEN_ABILITY_SET) / sizeof(VERIFY_GEN_ABILITY_SET[0]); i++) {
84 if (VERIFY_GEN_ABILITY_SET[i].algo == params->algo) {
85 return VERIFY_GEN_ABILITY_SET[i].createFunc;
86 }
87 }
88 LOGE("Algo not support! [Algo]: %d", params->algo);
89 return NULL;
90 }
91
SetKeyType(HCF_ALG_PARA_VALUE value,HcfSignatureParams * paramsObj)92 static void SetKeyType(HCF_ALG_PARA_VALUE value, HcfSignatureParams *paramsObj)
93 {
94 switch (value) {
95 case HCF_ALG_ECC_224:
96 case HCF_ALG_ECC_256:
97 case HCF_ALG_ECC_384:
98 case HCF_ALG_ECC_521:
99 paramsObj->keyLen = value;
100 paramsObj->algo = HCF_ALG_ECC;
101 break;
102 case HCF_OPENSSL_RSA_512:
103 case HCF_OPENSSL_RSA_768:
104 case HCF_OPENSSL_RSA_1024:
105 case HCF_OPENSSL_RSA_2048:
106 case HCF_OPENSSL_RSA_3072:
107 case HCF_OPENSSL_RSA_4096:
108 case HCF_OPENSSL_RSA_8192:
109 paramsObj->algo = HCF_ALG_RSA;
110 break;
111 default:
112 LOGE("there is not matched algorithm.");
113 break;
114 }
115 }
116
ParseSignatureParams(const HcfParaConfig * config,void * params)117 static HcfResult ParseSignatureParams(const HcfParaConfig* config, void *params)
118 {
119 if (config == NULL || params == NULL) {
120 return HCF_INVALID_PARAMS;
121 }
122 HcfResult ret = HCF_SUCCESS;
123 HcfSignatureParams *paramsObj = (HcfSignatureParams *)params;
124 LOGI("Set Parameter: %s", config->tag);
125 switch (config->paraType) {
126 case HCF_ALG_KEY_TYPE:
127 SetKeyType(config->paraValue, paramsObj);
128 break;
129 case HCF_ALG_DIGEST:
130 paramsObj->md = config->paraValue;
131 break;
132 case HCF_ALG_PADDING_TYPE:
133 paramsObj->padding = config->paraValue;
134 break;
135 case HCF_ALG_MGF1_DIGEST:
136 paramsObj->mgf1md = config->paraValue;
137 break;
138 default:
139 ret = HCF_INVALID_PARAMS;
140 break;
141 }
142 return ret;
143 }
144
GetSignClass(void)145 static const char *GetSignClass(void)
146 {
147 return "HcfSign";
148 }
149
GetVerifyClass(void)150 static const char *GetVerifyClass(void)
151 {
152 return "HcfVerify";
153 }
154
GetSignAlgoName(HcfSign * self)155 static const char *GetSignAlgoName(HcfSign *self)
156 {
157 if (self == NULL) {
158 LOGE("The input self ptr is NULL!");
159 return NULL;
160 }
161 if (!IsClassMatch((HcfObjectBase *)self, GetSignClass())) {
162 return NULL;
163 }
164 return ((HcfSignImpl *)self)->algoName;
165 }
166
GetVerifyAlgoName(HcfVerify * self)167 static const char *GetVerifyAlgoName(HcfVerify *self)
168 {
169 if (self == NULL) {
170 LOGE("The input self ptr is NULL!");
171 return NULL;
172 }
173 if (!IsClassMatch((HcfObjectBase *)self, GetVerifyClass())) {
174 return NULL;
175 }
176 return ((HcfVerifyImpl *)self)->algoName;
177 }
178
DestroySign(HcfObjectBase * self)179 static void DestroySign(HcfObjectBase *self)
180 {
181 if (self == NULL) {
182 return;
183 }
184 if (!IsClassMatch(self, GetSignClass())) {
185 return;
186 }
187 HcfSignImpl *impl = (HcfSignImpl *)self;
188 HcfObjDestroy(impl->spiObj);
189 impl->spiObj = NULL;
190 HcfFree(impl);
191 }
192
DestroyVerify(HcfObjectBase * self)193 static void DestroyVerify(HcfObjectBase *self)
194 {
195 if (self == NULL) {
196 return;
197 }
198 if (!IsClassMatch(self, GetVerifyClass())) {
199 return;
200 }
201 HcfVerifyImpl *impl = (HcfVerifyImpl *)self;
202 HcfObjDestroy(impl->spiObj);
203 impl->spiObj = NULL;
204 HcfFree(impl);
205 }
206
SignInit(HcfSign * self,HcfParamsSpec * params,HcfPriKey * privateKey)207 static HcfResult SignInit(HcfSign *self, HcfParamsSpec *params, HcfPriKey *privateKey)
208 {
209 if (self == NULL) {
210 LOGE("Invalid input parameter.");
211 return HCF_INVALID_PARAMS;
212 }
213
214 if (!IsClassMatch((HcfObjectBase *)self, GetSignClass())) {
215 return HCF_INVALID_PARAMS;
216 }
217 return ((HcfSignImpl *)self)->spiObj->engineInit(((HcfSignImpl *)self)->spiObj, params, privateKey);
218 }
219
SignUpdate(HcfSign * self,HcfBlob * data)220 static HcfResult SignUpdate(HcfSign *self, HcfBlob *data)
221 {
222 if (self == NULL) {
223 LOGE("Invalid input parameter.");
224 return HCF_INVALID_PARAMS;
225 }
226
227 if (!IsClassMatch((HcfObjectBase *)self, GetSignClass())) {
228 return HCF_INVALID_PARAMS;
229 }
230 return ((HcfSignImpl *)self)->spiObj->engineUpdate(((HcfSignImpl *)self)->spiObj, data);
231 }
232
SignDoFinal(HcfSign * self,HcfBlob * data,HcfBlob * returnSignatureData)233 static HcfResult SignDoFinal(HcfSign *self, HcfBlob *data, HcfBlob *returnSignatureData)
234 {
235 if (self == NULL) {
236 LOGE("Invalid input parameter.");
237 return HCF_INVALID_PARAMS;
238 }
239
240 if (!IsClassMatch((HcfObjectBase *)self, GetSignClass())) {
241 return HCF_INVALID_PARAMS;
242 }
243 return ((HcfSignImpl *)self)->spiObj->engineSign(((HcfSignImpl *)self)->spiObj, data, returnSignatureData);
244 }
245
VerifyInit(HcfVerify * self,HcfParamsSpec * params,HcfPubKey * publicKey)246 static HcfResult VerifyInit(HcfVerify *self, HcfParamsSpec *params, HcfPubKey *publicKey)
247 {
248 if (self == NULL) {
249 LOGE("Invalid input parameter.");
250 return HCF_INVALID_PARAMS;
251 }
252
253 if (!IsClassMatch((HcfObjectBase *)self, GetVerifyClass())) {
254 return HCF_INVALID_PARAMS;
255 }
256 return ((HcfVerifyImpl *)self)->spiObj->engineInit(((HcfVerifyImpl *)self)->spiObj, params, publicKey);
257 }
258
VerifyUpdate(HcfVerify * self,HcfBlob * data)259 static HcfResult VerifyUpdate(HcfVerify *self, HcfBlob *data)
260 {
261 if (self == NULL) {
262 LOGE("Invalid input parameter.");
263 return HCF_INVALID_PARAMS;
264 }
265
266 if (!IsClassMatch((HcfObjectBase *)self, GetVerifyClass())) {
267 return HCF_INVALID_PARAMS;
268 }
269 return ((HcfVerifyImpl *)self)->spiObj->engineUpdate(((HcfVerifyImpl *)self)->spiObj, data);
270 }
271
VerifyDoFinal(HcfVerify * self,HcfBlob * data,HcfBlob * signatureData)272 static bool VerifyDoFinal(HcfVerify *self, HcfBlob *data, HcfBlob *signatureData)
273 {
274 if (self == NULL) {
275 LOGE("Invalid input parameter.");
276 return false;
277 }
278 if (!IsClassMatch((HcfObjectBase *)self, GetVerifyClass())) {
279 return false;
280 }
281 return ((HcfVerifyImpl *)self)->spiObj->engineVerify(((HcfVerifyImpl *)self)->spiObj, data, signatureData);
282 }
283
HcfSignCreate(const char * algoName,HcfSign ** returnObj)284 HcfResult HcfSignCreate(const char *algoName, HcfSign **returnObj)
285 {
286 LOGI("HcfSignCreate start");
287 if ((!IsStrValid(algoName, HCF_MAX_ALGO_NAME_LEN)) || (returnObj == NULL)) {
288 return HCF_INVALID_PARAMS;
289 }
290
291 HcfSignatureParams params = { 0 };
292 if (ParseAndSetParameter(algoName, ¶ms, ParseSignatureParams) != HCF_SUCCESS) {
293 LOGE("Failed to parser parmas!");
294 return HCF_INVALID_PARAMS;
295 }
296
297 HcfSignSpiCreateFunc createSpifunc = FindSignAbility(¶ms);
298 if (createSpifunc == NULL) {
299 LOGE("Can not find ability.");
300 return HCF_NOT_SUPPORT;
301 }
302
303 HcfSignImpl *returnSign = (HcfSignImpl *)HcfMalloc(sizeof(HcfSignImpl), 0);
304 if (returnSign == NULL) {
305 LOGE("Failed to allocate returnSign memory!");
306 return HCF_ERR_MALLOC;
307 }
308 if (strcpy_s(returnSign->algoName, HCF_MAX_ALGO_NAME_LEN, algoName) != EOK) {
309 LOGE("Failed to copy algoName!");
310 HcfFree(returnSign);
311 return HCF_ERR_COPY;
312 }
313 HcfSignSpi *spiObj = NULL;
314 int32_t res = createSpifunc(¶ms, &spiObj);
315 if (res != HCF_SUCCESS) {
316 LOGE("Failed to create spi object!");
317 HcfFree(returnSign);
318 return res;
319 }
320 returnSign->base.base.destroy = DestroySign;
321 returnSign->base.base.getClass = GetSignClass;
322 returnSign->base.getAlgoName = GetSignAlgoName;
323 returnSign->base.init = SignInit;
324 returnSign->base.update = SignUpdate;
325 returnSign->base.sign = SignDoFinal;
326 returnSign->spiObj = spiObj;
327
328 *returnObj = (HcfSign *)returnSign;
329 LOGI("HcfSignCreate end");
330 return HCF_SUCCESS;
331 }
332
HcfVerifyCreate(const char * algoName,HcfVerify ** returnObj)333 HcfResult HcfVerifyCreate(const char *algoName, HcfVerify **returnObj)
334 {
335 LOGI("HcfVerifyCreate start");
336 if ((!IsStrValid(algoName, HCF_MAX_ALGO_NAME_LEN)) || (returnObj == NULL)) {
337 return HCF_INVALID_PARAMS;
338 }
339 HcfSignatureParams params = {0};
340 if (ParseAndSetParameter(algoName, ¶ms, ParseSignatureParams) != HCF_SUCCESS) {
341 LOGE("Failed to parser parmas!");
342 return HCF_INVALID_PARAMS;
343 }
344
345 HcfVerifySpiCreateFunc createSpifunc = FindVerifyAbility(¶ms);
346 if (createSpifunc == NULL) {
347 return HCF_NOT_SUPPORT;
348 }
349
350 HcfVerifyImpl *returnVerify = (HcfVerifyImpl *)HcfMalloc(sizeof(HcfVerifyImpl), 0);
351 if (returnVerify == NULL) {
352 LOGE("Failed to allocate returnVerify memory!");
353 return HCF_ERR_MALLOC;
354 }
355 if (strcpy_s(returnVerify->algoName, HCF_MAX_ALGO_NAME_LEN, algoName) != EOK) {
356 LOGE("Failed to copy algoName!");
357 HcfFree(returnVerify);
358 return HCF_ERR_COPY;
359 }
360 HcfVerifySpi *spiObj = NULL;
361 int32_t res = createSpifunc(¶ms, &spiObj);
362 if (res != HCF_SUCCESS) {
363 LOGE("Failed to create spi object!");
364 HcfFree(returnVerify);
365 return res;
366 }
367 returnVerify->base.base.destroy = DestroyVerify;
368 returnVerify->base.base.getClass = GetVerifyClass;
369 returnVerify->base.getAlgoName = GetVerifyAlgoName;
370 returnVerify->base.init = VerifyInit;
371 returnVerify->base.update = VerifyUpdate;
372 returnVerify->base.verify = VerifyDoFinal;
373 returnVerify->spiObj = spiObj;
374 *returnObj = (HcfVerify *)returnVerify;
375 LOGI("HcfVerifyCreate end");
376 return HCF_SUCCESS;
377 }
378