1 /*
2  * Copyright (C) 2023-2024 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 "dh_asy_key_generator_openssl.h"
17 #include <string.h>
18 
19 #include "dh_openssl_common.h"
20 #include "detailed_dh_key_params.h"
21 #include "log.h"
22 #include "memory.h"
23 #include "openssl_adapter.h"
24 #include "openssl_class.h"
25 #include "openssl_common.h"
26 
27 #define OPENSSL_DH_GENERATOR_CLASS "OPENSSL.DH.KEYGENERATOR"
28 #define OPENSSL_DH_PUBKEY_FORMAT "X.509"
29 #define OPENSSL_DH_PRIKEY_FORMAT "PKCS#8"
30 #define ALGORITHM_NAME_DH "DH"
31 #define PARAMS_NUM_TWO 2
32 #define BIT8 8
33 
34 typedef struct {
35     HcfAsyKeyGeneratorSpi base;
36 
37     int32_t pBits;
38 } HcfAsyKeyGeneratorSpiDhOpensslImpl;
39 
FreeCtx(EVP_PKEY_CTX * paramsCtx,EVP_PKEY * paramsPkey,EVP_PKEY_CTX * pkeyCtx)40 static void FreeCtx(EVP_PKEY_CTX *paramsCtx, EVP_PKEY *paramsPkey, EVP_PKEY_CTX *pkeyCtx)
41 {
42     if (paramsCtx != NULL) {
43         OpensslEvpPkeyCtxFree(paramsCtx);
44     }
45     if (paramsPkey != NULL) {
46         OpensslEvpPkeyFree(paramsPkey);
47     }
48     if (pkeyCtx != NULL) {
49         OpensslEvpPkeyCtxFree(pkeyCtx);
50     }
51 }
52 
FreeCommSpecBn(BIGNUM * p,BIGNUM * g)53 static void FreeCommSpecBn(BIGNUM *p, BIGNUM *g)
54 {
55     if (p != NULL) {
56         OpensslBnFree(p);
57     }
58     if (g != NULL) {
59         OpensslBnFree(g);
60     }
61 }
62 
GetDhKeyGeneratorSpiClass(void)63 static const char *GetDhKeyGeneratorSpiClass(void)
64 {
65     return OPENSSL_DH_GENERATOR_CLASS;
66 }
67 
GetDhKeyPairClass(void)68 static const char *GetDhKeyPairClass(void)
69 {
70     return OPENSSL_DH_KEYPAIR_CLASS;
71 }
72 
GetDhPubKeyClass(void)73 static const char *GetDhPubKeyClass(void)
74 {
75     return OPENSSL_DH_PUBKEY_CLASS;
76 }
77 
GetDhPriKeyClass(void)78 static const char *GetDhPriKeyClass(void)
79 {
80     return OPENSSL_DH_PRIKEY_CLASS;
81 }
82 
DestroyDhKeyGeneratorSpiImpl(HcfObjectBase * self)83 static void DestroyDhKeyGeneratorSpiImpl(HcfObjectBase *self)
84 {
85     if (self == NULL) {
86         LOGE("Class is null.");
87         return;
88     }
89     if (!HcfIsClassMatch(self, GetDhKeyGeneratorSpiClass())) {
90         LOGE("Class not match.");
91         return;
92     }
93     HcfFree(self);
94 }
95 
DestroyDhPubKey(HcfObjectBase * self)96 static void DestroyDhPubKey(HcfObjectBase *self)
97 {
98     if (self == NULL) {
99         LOGE("Class is null.");
100         return;
101     }
102     if (!HcfIsClassMatch(self, GetDhPubKeyClass())) {
103         LOGE("Class not match.");
104         return;
105     }
106     HcfOpensslDhPubKey *impl = (HcfOpensslDhPubKey *)self;
107     OpensslDhFree(impl->pk);
108     impl->pk = NULL;
109     HcfFree(impl);
110 }
111 
DestroyDhPriKey(HcfObjectBase * self)112 static void DestroyDhPriKey(HcfObjectBase *self)
113 {
114     if (self == NULL) {
115         LOGE("Class is null.");
116         return;
117     }
118     if (!HcfIsClassMatch(self, GetDhPriKeyClass())) {
119         LOGE("Class not match.");
120         return;
121     }
122     HcfOpensslDhPriKey *impl = (HcfOpensslDhPriKey *)self;
123     OpensslDhFree(impl->sk);
124     impl->sk = NULL;
125     HcfFree(impl);
126 }
127 
DestroyDhKeyPair(HcfObjectBase * self)128 static void DestroyDhKeyPair(HcfObjectBase *self)
129 {
130     if (self == NULL) {
131         LOGE("Class is null.");
132         return;
133     }
134     if (!HcfIsClassMatch(self, GetDhKeyPairClass())) {
135         LOGE("Class not match.");
136         return;
137     }
138     HcfOpensslDhKeyPair *impl = (HcfOpensslDhKeyPair *)self;
139     DestroyDhPubKey((HcfObjectBase *)impl->base.pubKey);
140     impl->base.pubKey = NULL;
141     DestroyDhPriKey((HcfObjectBase *)impl->base.priKey);
142     impl->base.priKey = NULL;
143     HcfFree(self);
144 }
145 
GetDhPubKeyAlgorithm(HcfKey * self)146 static const char *GetDhPubKeyAlgorithm(HcfKey *self)
147 {
148     if (self == NULL) {
149         LOGE("Invalid input parameter.");
150         return NULL;
151     }
152     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhPubKeyClass())) {
153         LOGE("Class not match.");
154         return NULL;
155     }
156     return ALGORITHM_NAME_DH;
157 }
158 
GetDhPriKeyAlgorithm(HcfKey * self)159 static const char *GetDhPriKeyAlgorithm(HcfKey *self)
160 {
161     if (self == NULL) {
162         LOGE("Invalid input parameter.");
163         return NULL;
164     }
165     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhPriKeyClass())) {
166         LOGE("Class not match.");
167         return NULL;
168     }
169     return ALGORITHM_NAME_DH;
170 }
171 
GetDhPubKeyEncoded(HcfKey * self,HcfBlob * returnBlob)172 static HcfResult GetDhPubKeyEncoded(HcfKey *self, HcfBlob *returnBlob)
173 {
174     if ((self == NULL) || (returnBlob == NULL)) {
175         LOGE("Invalid input parameter.");
176         return HCF_INVALID_PARAMS;
177     }
178     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhPubKeyClass())) {
179         LOGE("Class not match.");
180         return HCF_INVALID_PARAMS;
181     }
182     HcfOpensslDhPubKey *impl = (HcfOpensslDhPubKey *)self;
183     unsigned char *returnData = NULL;
184     EVP_PKEY *pKey = NewEvpPkeyByDh(impl->pk, true);
185     if (pKey == NULL) {
186         LOGD("[error] New pKey by dh fail.");
187         return HCF_ERR_CRYPTO_OPERATION;
188     }
189     int len = OpensslI2dPubKey(pKey, &returnData);
190     if (len <= 0) {
191         LOGD("[error] Call i2d_PUBKEY failed");
192         HcfPrintOpensslError();
193         OpensslEvpPkeyFree(pKey);
194         return HCF_ERR_CRYPTO_OPERATION;
195     }
196     returnBlob->data = returnData;
197     returnBlob->len = len;
198     OpensslEvpPkeyFree(pKey);
199     return HCF_SUCCESS;
200 }
201 
GetDhPubKeyEncodedPem(HcfKey * self,const char * format,char ** returnString)202 static HcfResult GetDhPubKeyEncodedPem(HcfKey *self, const char *format, char **returnString)
203 {
204     (void)self;
205     (void)format;
206     (void)returnString;
207     return HCF_INVALID_PARAMS;
208 }
209 
GetDhPriKeyEncoded(HcfKey * self,HcfBlob * returnBlob)210 static HcfResult GetDhPriKeyEncoded(HcfKey *self, HcfBlob *returnBlob)
211 {
212     if ((self == NULL) || (returnBlob == NULL)) {
213         LOGE("Invalid input parameter.");
214         return HCF_INVALID_PARAMS;
215     }
216     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhPriKeyClass())) {
217         LOGE("Class not match.");
218         return HCF_INVALID_PARAMS;
219     }
220     HcfOpensslDhPriKey *impl = (HcfOpensslDhPriKey *)self;
221     unsigned char *returnData = NULL;
222     EVP_PKEY *pKey = NewEvpPkeyByDh(impl->sk, true);
223     if (pKey == NULL) {
224         LOGD("[error] New pKey by dh fail.");
225         HcfPrintOpensslError();
226         return HCF_ERR_CRYPTO_OPERATION;
227     }
228     int len = OpensslI2dPrivateKey(pKey, &returnData);
229     if (len <= 0) {
230         LOGD("[error] Call i2d_PrivateKey failed.");
231         HcfPrintOpensslError();
232         OpensslEvpPkeyFree(pKey);
233         return HCF_ERR_CRYPTO_OPERATION;
234     }
235     returnBlob->data = returnData;
236     returnBlob->len = len;
237     OpensslEvpPkeyFree(pKey);
238     return HCF_SUCCESS;
239 }
240 
GetDhPriKeyEncodedPem(HcfKey * self,const char * format,char ** returnString)241 static HcfResult GetDhPriKeyEncodedPem(HcfKey *self, const char *format, char **returnString)
242 {
243     (void)self;
244     (void)format;
245     (void)returnString;
246     return HCF_INVALID_PARAMS;
247 }
248 
GetDhPubKeyFormat(HcfKey * self)249 static const char *GetDhPubKeyFormat(HcfKey *self)
250 {
251     if (self == NULL) {
252         LOGE("Invalid input parameter.");
253         return NULL;
254     }
255     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhPubKeyClass())) {
256         LOGE("Class not match.");
257         return NULL;
258     }
259     return OPENSSL_DH_PUBKEY_FORMAT;
260 }
261 
GetDhPriKeyFormat(HcfKey * self)262 static const char *GetDhPriKeyFormat(HcfKey *self)
263 {
264     if (self == NULL) {
265         LOGE("Invalid input parameter.");
266         return NULL;
267     }
268     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhPriKeyClass())) {
269         LOGE("Class not match.");
270         return NULL;
271     }
272     return OPENSSL_DH_PRIKEY_FORMAT;
273 }
274 
GetBigIntegerSpec(const HcfPubKey * pubSelf,const HcfPriKey * priSelf,const AsyKeySpecItem item,HcfBigInteger * returnBigInteger)275 static HcfResult GetBigIntegerSpec(const HcfPubKey *pubSelf, const HcfPriKey *priSelf, const AsyKeySpecItem item,
276     HcfBigInteger *returnBigInteger)
277 {
278     DH *dh = NULL;
279     if (pubSelf != NULL) {
280         if (item == DH_SK_BN) {
281             LOGE("Invalid item.");
282             return HCF_INVALID_PARAMS;
283         }
284         HcfOpensslDhPubKey *impl = (HcfOpensslDhPubKey *)pubSelf;
285         dh = impl->pk;
286     } else {
287         if (item == DH_PK_BN) {
288             LOGE("Invalid item.");
289             return HCF_INVALID_PARAMS;
290         }
291         HcfOpensslDhPriKey *impl = (HcfOpensslDhPriKey *)priSelf;
292         dh = impl->sk;
293     }
294     if (dh == NULL) {
295         LOGE("Dh is null.");
296         return HCF_INVALID_PARAMS;
297     }
298     HcfResult ret = HCF_SUCCESS;
299     switch (item) {
300         case DH_P_BN:
301             ret = BigNumToBigInteger(OpensslDhGet0P(dh), returnBigInteger);
302             break;
303         case DH_G_BN:
304             ret = BigNumToBigInteger(OpensslDhGet0G(dh), returnBigInteger);
305             break;
306         case DH_PK_BN:
307             ret = BigNumToBigInteger(OpensslDhGet0PubKey(dh), returnBigInteger);
308             break;
309         case DH_SK_BN:
310             ret = BigNumToBigInteger(OpensslDhGet0PrivKey(dh), returnBigInteger);
311             break;
312         default:
313             LOGE("Input item [%d] is invalid", item);
314             ret = HCF_INVALID_PARAMS;
315             break;
316     }
317     return ret;
318 }
319 
GetBigIntegerSpecFromDhPubKey(const HcfPubKey * self,const AsyKeySpecItem item,HcfBigInteger * returnBigInteger)320 static HcfResult GetBigIntegerSpecFromDhPubKey(const HcfPubKey *self, const AsyKeySpecItem item,
321     HcfBigInteger *returnBigInteger)
322 {
323     if (self ==  NULL || returnBigInteger == NULL) {
324         LOGE("Invalid input parameter.");
325         return HCF_INVALID_PARAMS;
326     }
327     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhPubKeyClass())) {
328         LOGE("Invalid class of self.");
329         return HCF_INVALID_PARAMS;
330     }
331     HcfResult ret = GetBigIntegerSpec(self, NULL, item, returnBigInteger);
332     if (ret != HCF_SUCCESS) {
333         LOGE("Get big integer failed.");
334     }
335     return ret;
336 }
337 
GetBigIntegerSpecFromDhPriKey(const HcfPriKey * self,const AsyKeySpecItem item,HcfBigInteger * returnBigInteger)338 static HcfResult GetBigIntegerSpecFromDhPriKey(const HcfPriKey *self, const AsyKeySpecItem item,
339     HcfBigInteger *returnBigInteger)
340 {
341     if (self ==  NULL || returnBigInteger == NULL) {
342         LOGE("Invalid input parameter.");
343         return HCF_INVALID_PARAMS;
344     }
345     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhPriKeyClass())) {
346         LOGE("Invalid class of self.");
347         return HCF_INVALID_PARAMS;
348     }
349     HcfResult ret = GetBigIntegerSpec(NULL, self, item, returnBigInteger);
350     if (ret != HCF_SUCCESS) {
351         LOGE("Get big integer failed.");
352     }
353     return ret;
354 }
355 
GetIntSpecFromDhPubKey(const HcfPubKey * self,const AsyKeySpecItem item,int * returnInt)356 static HcfResult GetIntSpecFromDhPubKey(const HcfPubKey *self, const AsyKeySpecItem item, int *returnInt)
357 {
358     (void)self;
359     (void)returnInt;
360     return HCF_NOT_SUPPORT;
361 }
362 
GetIntSpecFromDhPriKey(const HcfPriKey * self,const AsyKeySpecItem item,int * returnInt)363 static HcfResult GetIntSpecFromDhPriKey(const HcfPriKey *self, const AsyKeySpecItem item, int *returnInt)
364 {
365     if (self ==  NULL || returnInt == NULL) {
366         LOGE("Invalid input parameter.");
367         return HCF_INVALID_PARAMS;
368     }
369     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhPriKeyClass())) {
370         LOGE("Invalid class of self.");
371         return HCF_INVALID_PARAMS;
372     }
373     if (item != DH_L_NUM) {
374         LOGE("Invalid input item.");
375         return HCF_INVALID_PARAMS;
376     }
377     HcfOpensslDhPriKey *impl = (HcfOpensslDhPriKey *)self;
378     DH *dh = impl->sk;
379     if (dh == NULL) {
380         LOGE("Dh is null.");
381         return HCF_INVALID_PARAMS;
382     }
383 
384     *returnInt = (int)OpensslDhGetLength(dh);
385     return HCF_SUCCESS;
386 }
387 
GetStrSpecFromDhPubKey(const HcfPubKey * self,const AsyKeySpecItem item,char ** returnString)388 static HcfResult GetStrSpecFromDhPubKey(const HcfPubKey *self, const AsyKeySpecItem item, char **returnString)
389 {
390     (void)self;
391     (void)returnString;
392     return HCF_NOT_SUPPORT;
393 }
394 
GetStrSpecFromDhPriKey(const HcfPriKey * self,const AsyKeySpecItem item,char ** returnString)395 static HcfResult GetStrSpecFromDhPriKey(const HcfPriKey *self, const AsyKeySpecItem item, char **returnString)
396 {
397     (void)self;
398     (void)returnString;
399     return HCF_NOT_SUPPORT;
400 }
401 
GetDhPriKeyEncodedDer(const HcfPriKey * self,const char * format,HcfBlob * returnBlob)402 static HcfResult GetDhPriKeyEncodedDer(const HcfPriKey *self, const char *format, HcfBlob *returnBlob)
403 {
404     (void)self;
405     (void)format;
406     (void)returnBlob;
407     return HCF_INVALID_PARAMS;
408 }
409 
ClearDhPriKeyMem(HcfPriKey * self)410 static void ClearDhPriKeyMem(HcfPriKey *self)
411 {
412     if (self == NULL) {
413         LOGE("Class is null.");
414         return;
415     }
416     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhPriKeyClass())) {
417         LOGE("Class not match.");
418         return;
419     }
420     HcfOpensslDhPriKey *impl = (HcfOpensslDhPriKey *)self;
421     OpensslDhFree(impl->sk);
422     impl->sk = NULL;
423 }
424 
ConstructDhOsslParamsAndGenPkey(int32_t dhId,EVP_PKEY_CTX * paramsCtx)425 static EVP_PKEY *ConstructDhOsslParamsAndGenPkey(int32_t dhId, EVP_PKEY_CTX *paramsCtx)
426 {
427     EVP_PKEY *paramsPkey = NULL;
428     OSSL_PARAM params[PARAMS_NUM_TWO];
429     char *nidName = GetNidNameByDhId(dhId);
430     if (nidName == NULL) {
431         LOGE("Get nid name failed.");
432         return NULL;
433     }
434     params[0] = OpensslOsslParamConstructUtf8String("group", nidName, 0);
435     params[1] = OpensslOsslParamConstructEnd();
436     if (OpensslEvpPkeyKeyGenInit(paramsCtx) != HCF_OPENSSL_SUCCESS) {
437         LOGD("[error] ParamsCtx generate init failed.");
438         return NULL;
439     }
440     if (OpensslEvpPkeyCtxSetParams(paramsCtx, params) != HCF_OPENSSL_SUCCESS) {
441         LOGD("[error] ParamsCtx set failed.");
442         return NULL;
443     }
444     if (OpensslEvpPkeyGenerate(paramsCtx, &paramsPkey) != HCF_OPENSSL_SUCCESS) {
445         LOGD("[error] Create generate failed.");
446         return NULL;
447     }
448     return paramsPkey;
449 }
450 
GenerateDhEvpKey(int32_t dhId,EVP_PKEY ** ppkey)451 static HcfResult GenerateDhEvpKey(int32_t dhId, EVP_PKEY **ppkey)
452 {
453     HcfResult ret = HCF_SUCCESS;
454     EVP_PKEY *paramsPkey = NULL;
455     EVP_PKEY_CTX *pkeyCtx = NULL;
456     EVP_PKEY_CTX *paramsCtx = NULL;
457 
458     do {
459         paramsCtx = OpensslEvpPkeyCtxNewFromName(NULL, "DH", NULL);
460         if (paramsCtx == NULL) {
461             LOGD("[error] New paramsCtx from name failed.");
462             ret = HCF_ERR_CRYPTO_OPERATION;
463             break;
464         }
465         paramsPkey = ConstructDhOsslParamsAndGenPkey(dhId, paramsCtx);
466         if (paramsPkey == NULL) {
467             LOGD("[error] Construct dh params and generate pkey failed.");
468             ret = HCF_ERR_CRYPTO_OPERATION;
469             break;
470         }
471         pkeyCtx = OpensslEvpPkeyCtxNew(paramsPkey, NULL);
472         if (pkeyCtx == NULL) {
473             LOGD("[error] Create pkey ctx failed.");
474             ret = HCF_ERR_CRYPTO_OPERATION;
475             break;
476         }
477         if (OpensslEvpPkeyKeyGenInit(pkeyCtx) != HCF_OPENSSL_SUCCESS) {
478             LOGD("[error] Key ctx generate init failed.");
479             ret = HCF_ERR_CRYPTO_OPERATION;
480             break;
481         }
482         if (OpensslEvpPkeyKeyGen(pkeyCtx, ppkey) != HCF_OPENSSL_SUCCESS) {
483             LOGD("[error] Generate pkey failed.");
484             ret = HCF_ERR_CRYPTO_OPERATION;
485             break;
486         }
487         if (OpensslEvpPkeyCheck(pkeyCtx) != HCF_OPENSSL_SUCCESS) {
488             LOGD("[error] Check pkey fail.");
489             OpensslEvpPkeyFree(*ppkey);
490             *ppkey = NULL;
491             ret = HCF_ERR_CRYPTO_OPERATION;
492             break;
493         }
494     } while (0);
495     FreeCtx(paramsCtx, paramsPkey, pkeyCtx);
496     return ret;
497 }
498 
GetDhPubKeyEncodedDer(const HcfPubKey * self,const char * format,HcfBlob * returnBlob)499 static HcfResult GetDhPubKeyEncodedDer(const HcfPubKey *self, const char *format, HcfBlob *returnBlob)
500 {
501     (void)self;
502     (void)format;
503     (void)returnBlob;
504     return HCF_INVALID_PARAMS;
505 }
506 
FillOpensslDhPubKeyFunc(HcfOpensslDhPubKey * pk)507 static void FillOpensslDhPubKeyFunc(HcfOpensslDhPubKey *pk)
508 {
509     pk->base.base.base.destroy = DestroyDhPubKey;
510     pk->base.base.base.getClass = GetDhPubKeyClass;
511     pk->base.base.getAlgorithm = GetDhPubKeyAlgorithm;
512     pk->base.base.getEncoded = GetDhPubKeyEncoded;
513     pk->base.base.getEncodedPem = GetDhPubKeyEncodedPem;
514     pk->base.base.getFormat = GetDhPubKeyFormat;
515     pk->base.getAsyKeySpecBigInteger = GetBigIntegerSpecFromDhPubKey;
516     pk->base.getAsyKeySpecInt = GetIntSpecFromDhPubKey;
517     pk->base.getAsyKeySpecString = GetStrSpecFromDhPubKey;
518     pk->base.getEncodedDer = GetDhPubKeyEncodedDer;
519 }
520 
FillOpensslDhPriKeyFunc(HcfOpensslDhPriKey * sk)521 static void FillOpensslDhPriKeyFunc(HcfOpensslDhPriKey *sk)
522 {
523     sk->base.base.base.destroy = DestroyDhPriKey;
524     sk->base.base.base.getClass = GetDhPriKeyClass;
525     sk->base.base.getAlgorithm = GetDhPriKeyAlgorithm;
526     sk->base.base.getEncoded = GetDhPriKeyEncoded;
527     sk->base.base.getEncodedPem = GetDhPriKeyEncodedPem;
528     sk->base.base.getFormat = GetDhPriKeyFormat;
529     sk->base.getAsyKeySpecBigInteger = GetBigIntegerSpecFromDhPriKey;
530     sk->base.getAsyKeySpecInt = GetIntSpecFromDhPriKey;
531     sk->base.getAsyKeySpecString = GetStrSpecFromDhPriKey;
532     sk->base.getEncodedDer = GetDhPriKeyEncodedDer;
533     sk->base.clearMem = ClearDhPriKeyMem;
534 }
535 
CreateDhPubKey(DH * pk,HcfOpensslDhPubKey ** returnPubKey)536 static HcfResult CreateDhPubKey(DH *pk, HcfOpensslDhPubKey **returnPubKey)
537 {
538     HcfOpensslDhPubKey *dhPubKey = (HcfOpensslDhPubKey *)HcfMalloc(sizeof(HcfOpensslDhPubKey), 0);
539     if (dhPubKey == NULL) {
540         LOGE("Failed to allocate DH public key memory.");
541         return HCF_ERR_MALLOC;
542     }
543     FillOpensslDhPubKeyFunc(dhPubKey);
544     dhPubKey->pk = pk;
545 
546     *returnPubKey = dhPubKey;
547     return HCF_SUCCESS;
548 }
549 
CreateDhPriKey(DH * sk,HcfOpensslDhPriKey ** returnPriKey)550 static HcfResult CreateDhPriKey(DH *sk, HcfOpensslDhPriKey **returnPriKey)
551 {
552     HcfOpensslDhPriKey *dhPriKey = (HcfOpensslDhPriKey *)HcfMalloc(sizeof(HcfOpensslDhPriKey), 0);
553     if (dhPriKey == NULL) {
554         LOGE("Failed to allocate Dh private key memory.");
555         return HCF_ERR_MALLOC;
556     }
557     FillOpensslDhPriKeyFunc(dhPriKey);
558     dhPriKey->sk = sk;
559 
560     *returnPriKey = dhPriKey;
561     return HCF_SUCCESS;
562 }
563 
CreateDhKeyPair(const HcfOpensslDhPubKey * pubKey,const HcfOpensslDhPriKey * priKey,HcfKeyPair ** returnKeyPair)564 static HcfResult CreateDhKeyPair(const HcfOpensslDhPubKey *pubKey, const HcfOpensslDhPriKey *priKey,
565     HcfKeyPair **returnKeyPair)
566 {
567     HcfOpensslDhKeyPair *keyPair = (HcfOpensslDhKeyPair *)HcfMalloc(sizeof(HcfOpensslDhKeyPair), 0);
568     if (keyPair == NULL) {
569         LOGE("Failed to allocate keyPair memory.");
570         return HCF_ERR_MALLOC;
571     }
572     keyPair->base.base.getClass = GetDhKeyPairClass;
573     keyPair->base.base.destroy = DestroyDhKeyPair;
574     keyPair->base.pubKey = (HcfPubKey *)pubKey;
575     keyPair->base.priKey = (HcfPriKey *)priKey;
576 
577     *returnKeyPair = (HcfKeyPair *)keyPair;
578     return HCF_SUCCESS;
579 }
580 
GeneratePubKeyByPkey(EVP_PKEY * pkey,HcfOpensslDhPubKey ** returnPubKey)581 static HcfResult GeneratePubKeyByPkey(EVP_PKEY *pkey, HcfOpensslDhPubKey **returnPubKey)
582 {
583     DH *pk = OpensslEvpPkeyGet1Dh(pkey);
584     if (pk == NULL) {
585         LOGD("[error] Get dh public key from pkey failed");
586         HcfPrintOpensslError();
587         return HCF_ERR_CRYPTO_OPERATION;
588     }
589     HcfResult ret = CreateDhPubKey(pk, returnPubKey);
590     if (ret != HCF_SUCCESS) {
591         LOGD("[error] Create DH public key failed");
592         OpensslDhFree(pk);
593     }
594     return ret;
595 }
596 
GeneratePriKeyByPkey(EVP_PKEY * pkey,HcfOpensslDhPriKey ** returnPriKey)597 static HcfResult GeneratePriKeyByPkey(EVP_PKEY *pkey, HcfOpensslDhPriKey **returnPriKey)
598 {
599     DH *sk = OpensslEvpPkeyGet1Dh(pkey);
600     if (sk == NULL) {
601         LOGD("[error] Get DH private key from pkey failed");
602         HcfPrintOpensslError();
603         return HCF_ERR_CRYPTO_OPERATION;
604     }
605     HcfResult ret = CreateDhPriKey(sk, returnPriKey);
606     if (ret != HCF_SUCCESS) {
607         LOGD("[error] Create DH private key failed");
608         OpensslDhFree(sk);
609     }
610     return ret;
611 }
612 
GenerateDhPubAndPriKey(int32_t dhId,HcfOpensslDhPubKey ** returnPubKey,HcfOpensslDhPriKey ** returnPriKey)613 static HcfResult GenerateDhPubAndPriKey(int32_t dhId, HcfOpensslDhPubKey **returnPubKey,
614     HcfOpensslDhPriKey **returnPriKey)
615 {
616     EVP_PKEY *pkey = NULL;
617     HcfResult ret = GenerateDhEvpKey(dhId, &pkey);
618     if (ret != HCF_SUCCESS) {
619         LOGE("Generate DH EVP_PKEY failed.");
620         return ret;
621     }
622 
623     ret = GeneratePubKeyByPkey(pkey, returnPubKey);
624     if (ret != HCF_SUCCESS) {
625         OpensslEvpPkeyFree(pkey);
626         LOGE("Generate public key failed.");
627         return ret;
628     }
629 
630     ret = GeneratePriKeyByPkey(pkey, returnPriKey);
631     if (ret != HCF_SUCCESS) {
632         HcfObjDestroy(*returnPubKey);
633         *returnPubKey = NULL;
634         OpensslEvpPkeyFree(pkey);
635         LOGE("Generate private key failed.");
636         return ret;
637     }
638 
639     OpensslEvpPkeyFree(pkey);
640     return ret;
641 }
642 
ConvertCommSpec2Bn(const HcfDhCommParamsSpec * paramsSpec,BIGNUM ** p,BIGNUM ** g)643 static HcfResult ConvertCommSpec2Bn(const HcfDhCommParamsSpec *paramsSpec, BIGNUM **p, BIGNUM **g)
644 {
645     if (BigIntegerToBigNum(&(paramsSpec->p), p) != HCF_SUCCESS) {
646         LOGD("[error] Get openssl BN p failed");
647         return HCF_ERR_CRYPTO_OPERATION;
648     }
649     if (BigIntegerToBigNum(&(paramsSpec->g), g) != HCF_SUCCESS) {
650         LOGD("[error] Get openssl BN g failed");
651         OpensslBnFree(*p);
652         *p = NULL;
653         return HCF_ERR_CRYPTO_OPERATION;
654     }
655     return HCF_SUCCESS;
656 }
657 
CreateOpensslDhKey(const HcfDhCommParamsSpec * paramsSpec,BIGNUM * pk,BIGNUM * sk,DH ** returnDh)658 static HcfResult CreateOpensslDhKey(const HcfDhCommParamsSpec *paramsSpec, BIGNUM *pk, BIGNUM *sk, DH **returnDh)
659 {
660     BIGNUM *p = NULL;
661     BIGNUM *g = NULL;
662     if (ConvertCommSpec2Bn(paramsSpec, &p, &g)!= HCF_SUCCESS) {
663         LOGD("[error] Get openssl BN p q failed");
664         return HCF_ERR_CRYPTO_OPERATION;
665     }
666     DH *dh = OpensslDhNew();
667     if (dh == NULL) {
668         FreeCommSpecBn(p, g);
669         LOGD("[error] Openssl dh new failed");
670         HcfPrintOpensslError();
671         return HCF_ERR_CRYPTO_OPERATION;
672     }
673     if (OpensslDhSet0Pqg(dh, p, NULL, g) != HCF_OPENSSL_SUCCESS) {
674         LOGD("[error] Openssl dh set pqg failed");
675         HcfPrintOpensslError();
676         FreeCommSpecBn(p, g);
677         OpensslDhFree(dh);
678         return HCF_ERR_CRYPTO_OPERATION;
679     }
680     if (paramsSpec->length > 0) {
681         if (OpensslDhSetLength(dh, paramsSpec->length) != HCF_OPENSSL_SUCCESS) {
682             LOGD("[error] Openssl dh set length failed");
683             HcfPrintOpensslError();
684             OpensslDhFree(dh);
685             return HCF_ERR_CRYPTO_OPERATION;
686         }
687     }
688     if ((pk == NULL) && (sk == NULL)) {
689         *returnDh = dh;
690         return HCF_SUCCESS;
691     }
692     if (OpensslDhSet0Key(dh, pk, sk) != HCF_OPENSSL_SUCCESS) {
693         LOGD("[error] Openssl DH set key failed");
694         HcfPrintOpensslError();
695         OpensslDhFree(dh);
696         return HCF_ERR_CRYPTO_OPERATION;
697     }
698     *returnDh = dh;
699     return HCF_SUCCESS;
700 }
701 
GenerateOpensslDhKeyByCommSpec(const HcfDhCommParamsSpec * paramsSpec,DH ** returnDh)702 static HcfResult GenerateOpensslDhKeyByCommSpec(const HcfDhCommParamsSpec *paramsSpec, DH **returnDh)
703 {
704     if (CreateOpensslDhKey(paramsSpec, NULL, NULL, returnDh) != HCF_SUCCESS) {
705         LOGD("[error] Create openssl dh key failed");
706         return HCF_ERR_CRYPTO_OPERATION;
707     }
708 
709     if (OpensslDhGenerateKey(*returnDh) != HCF_OPENSSL_SUCCESS) {
710         LOGD("[error] Openssl DH generate key failed");
711         HcfPrintOpensslError();
712         OpensslDhFree(*returnDh);
713         *returnDh = NULL;
714         return HCF_ERR_CRYPTO_OPERATION;
715     }
716     return HCF_SUCCESS;
717 }
718 
GenerateOpensslDhKeyByPubKeySpec(const HcfDhPubKeyParamsSpec * paramsSpec,DH ** returnDh)719 static HcfResult GenerateOpensslDhKeyByPubKeySpec(const HcfDhPubKeyParamsSpec *paramsSpec, DH **returnDh)
720 {
721     BIGNUM *pubKey = NULL;
722     if (BigIntegerToBigNum(&(paramsSpec->pk), &pubKey) != HCF_SUCCESS) {
723         LOGD("[error] Get openssl BN pk failed");
724         return HCF_ERR_CRYPTO_OPERATION;
725     }
726 
727     if (CreateOpensslDhKey(&(paramsSpec->base), pubKey, NULL, returnDh) != HCF_SUCCESS) {
728         LOGD("[error] Create dh key failed.");
729         OpensslBnFree(pubKey);
730         return HCF_ERR_CRYPTO_OPERATION;
731     }
732     return HCF_SUCCESS;
733 }
734 
GenerateOpensslDhKeyByPriKeySpec(const HcfDhPriKeyParamsSpec * paramsSpec,DH ** returnDh)735 static HcfResult GenerateOpensslDhKeyByPriKeySpec(const HcfDhPriKeyParamsSpec *paramsSpec, DH **returnDh)
736 {
737     BIGNUM *priKey = NULL;
738     if (BigIntegerToBigNum(&(paramsSpec->sk), &priKey) != HCF_SUCCESS) {
739         LOGD("[error] Get openssl BN pk failed");
740         return HCF_ERR_CRYPTO_OPERATION;
741     }
742 
743     if (CreateOpensslDhKey(&(paramsSpec->base), NULL, priKey, returnDh) != HCF_SUCCESS) {
744         LOGD("[error] Create dh key failed.");
745         OpensslBnFree(priKey);
746         return HCF_ERR_CRYPTO_OPERATION;
747     }
748     return HCF_SUCCESS;
749 }
750 
GenerateOpensslDhKeyByKeyPairSpec(const HcfDhKeyPairParamsSpec * paramsSpec,DH ** returnDh)751 static HcfResult GenerateOpensslDhKeyByKeyPairSpec(const HcfDhKeyPairParamsSpec *paramsSpec, DH **returnDh)
752 {
753     BIGNUM *pubKey = NULL;
754     BIGNUM *priKey = NULL;
755     if (BigIntegerToBigNum(&(paramsSpec->pk), &pubKey) != HCF_SUCCESS) {
756         LOGD("[error] Get openssl BN pk failed");
757         return HCF_ERR_CRYPTO_OPERATION;
758     }
759     if (BigIntegerToBigNum(&(paramsSpec->sk), &priKey) != HCF_SUCCESS) {
760         LOGD("[error] Get openssl BN sk failed");
761         OpensslBnFree(pubKey);
762         return HCF_ERR_CRYPTO_OPERATION;
763     }
764     if (CreateOpensslDhKey(&(paramsSpec->base), pubKey, priKey, returnDh) != HCF_SUCCESS) {
765         LOGD("[error] Create dh key failed.");
766         OpensslBnFree(pubKey);
767         OpensslBnFree(priKey);
768         return HCF_ERR_CRYPTO_OPERATION;
769     }
770     return HCF_SUCCESS;
771 }
772 
CreateDhKeyPairByCommSpec(const HcfDhCommParamsSpec * paramsSpec,HcfKeyPair ** returnKeyPair)773 static HcfResult CreateDhKeyPairByCommSpec(const HcfDhCommParamsSpec *paramsSpec, HcfKeyPair **returnKeyPair)
774 {
775     DH *dh = NULL;
776     if (GenerateOpensslDhKeyByCommSpec(paramsSpec, &dh) != HCF_SUCCESS) {
777         LOGD("[error] Generate openssl dh key by commSpec failed.");
778         return HCF_ERR_CRYPTO_OPERATION;
779     }
780     HcfOpensslDhPubKey *pubKey = NULL;
781     if (CreateDhPubKey(dh, &pubKey) != HCF_SUCCESS) {
782         LOGE("Create dh pubKey failed.");
783         OpensslDhFree(dh);
784         return HCF_ERR_MALLOC;
785     }
786 
787     if (OpensslDhUpRef(dh) != HCF_OPENSSL_SUCCESS) {
788         LOGD("[error] DH_up_ref failed.");
789         HcfPrintOpensslError();
790         HcfObjDestroy(pubKey);
791         return HCF_ERR_CRYPTO_OPERATION;
792     }
793 
794     HcfOpensslDhPriKey *priKey = NULL;
795     if (CreateDhPriKey(dh, &priKey) != HCF_SUCCESS) {
796         LOGE("Create dh priKey failed.");
797         OpensslDhFree(dh);
798         HcfObjDestroy(pubKey);
799         return HCF_ERR_MALLOC;
800     }
801 
802     if (CreateDhKeyPair(pubKey, priKey, returnKeyPair) != HCF_SUCCESS) {
803         LOGE("Create dh keyPair failed.");
804         HcfObjDestroy(pubKey);
805         HcfObjDestroy(priKey);
806         return HCF_ERR_MALLOC;
807     }
808     return HCF_SUCCESS;
809 }
810 
CreateDhPubKeyByKeyPairSpec(const HcfDhKeyPairParamsSpec * paramsSpec,HcfOpensslDhPubKey ** returnPubKey)811 static HcfResult CreateDhPubKeyByKeyPairSpec(const HcfDhKeyPairParamsSpec *paramsSpec,
812     HcfOpensslDhPubKey **returnPubKey)
813 {
814     DH *dh = NULL;
815     if (GenerateOpensslDhKeyByKeyPairSpec(paramsSpec, &dh) != HCF_SUCCESS) {
816         LOGD("[error] Generate openssl dh key by keyPairSpec failed.");
817         return HCF_ERR_CRYPTO_OPERATION;
818     }
819     if (CreateDhPubKey(dh, returnPubKey) != HCF_SUCCESS) {
820         LOGE("Create dh pubKey failed.");
821         OpensslDhFree(dh);
822         return HCF_ERR_MALLOC;
823     }
824     return HCF_SUCCESS;
825 }
826 
CreateDhPriKeyByKeyPairSpec(const HcfDhKeyPairParamsSpec * paramsSpec,HcfOpensslDhPriKey ** returnPriKey)827 static HcfResult CreateDhPriKeyByKeyPairSpec(const HcfDhKeyPairParamsSpec *paramsSpec,
828     HcfOpensslDhPriKey **returnPriKey)
829 {
830     DH *dh = NULL;
831     if (GenerateOpensslDhKeyByKeyPairSpec(paramsSpec, &dh) != HCF_SUCCESS) {
832         LOGD("[error] Generate openssl dh key by keyPairSpec failed.");
833         return HCF_ERR_CRYPTO_OPERATION;
834     }
835     if (CreateDhPriKey(dh, returnPriKey) != HCF_SUCCESS) {
836         LOGE("Create dh priKey failed.");
837         OpensslDhFree(dh);
838         return HCF_ERR_MALLOC;
839     }
840     return HCF_SUCCESS;
841 }
842 
CreateDhKeyPairByKeyPairSpec(const HcfDhKeyPairParamsSpec * paramsSpec,HcfKeyPair ** returnKeyPair)843 static HcfResult CreateDhKeyPairByKeyPairSpec(const HcfDhKeyPairParamsSpec *paramsSpec, HcfKeyPair **returnKeyPair)
844 {
845     HcfOpensslDhPubKey *pubKey = NULL;
846     HcfResult ret = CreateDhPubKeyByKeyPairSpec(paramsSpec, &pubKey);
847     if (ret != HCF_SUCCESS) {
848         LOGD("[error] Create dh pubKey by keyPairSpec failed.");
849         return ret;
850     }
851 
852     HcfOpensslDhPriKey *priKey = NULL;
853     ret = CreateDhPriKeyByKeyPairSpec(paramsSpec, &priKey);
854     if (ret != HCF_SUCCESS) {
855         LOGD("[error] Create dh priKey by keyPairSpec failed.");
856         HcfObjDestroy(pubKey);
857         return ret;
858     }
859     ret = CreateDhKeyPair(pubKey, priKey, returnKeyPair);
860     if (ret != HCF_SUCCESS) {
861         LOGD("[error] Create dh keyPair failed.");
862         HcfObjDestroy(pubKey);
863         HcfObjDestroy(priKey);
864         return ret;
865     }
866     return HCF_SUCCESS;
867 }
868 
CreateDhKeyPairBySpec(const HcfAsyKeyParamsSpec * paramsSpec,HcfKeyPair ** returnKeyPair)869 static HcfResult CreateDhKeyPairBySpec(const HcfAsyKeyParamsSpec *paramsSpec, HcfKeyPair **returnKeyPair)
870 {
871     if (paramsSpec->specType == HCF_COMMON_PARAMS_SPEC) {
872         return CreateDhKeyPairByCommSpec((const HcfDhCommParamsSpec *)paramsSpec, returnKeyPair);
873     } else {
874         return CreateDhKeyPairByKeyPairSpec((const HcfDhKeyPairParamsSpec*)paramsSpec, returnKeyPair);
875     }
876 }
877 
CreateDhPubKeyBySpec(const HcfDhPubKeyParamsSpec * paramsSpec,HcfPubKey ** returnPubKey)878 static HcfResult CreateDhPubKeyBySpec(const HcfDhPubKeyParamsSpec *paramsSpec, HcfPubKey **returnPubKey)
879 {
880     DH *dh = NULL;
881     if (GenerateOpensslDhKeyByPubKeySpec(paramsSpec, &dh) != HCF_SUCCESS) {
882         LOGD("[error] Generate openssl dh key by pubKeySpec failed.");
883         return HCF_ERR_CRYPTO_OPERATION;
884     }
885 
886     HcfOpensslDhPubKey *pubKey = NULL;
887     if (CreateDhPubKey(dh, &pubKey) != HCF_SUCCESS) {
888         LOGE("Create dh pubKey failed.");
889         OpensslDhFree(dh);
890         return HCF_ERR_MALLOC;
891     }
892     *returnPubKey = (HcfPubKey *)pubKey;
893     return HCF_SUCCESS;
894 }
895 
CreateDhPriKeyBySpec(const HcfDhPriKeyParamsSpec * paramsSpec,HcfPriKey ** returnPriKey)896 static HcfResult CreateDhPriKeyBySpec(const HcfDhPriKeyParamsSpec *paramsSpec, HcfPriKey **returnPriKey)
897 {
898     DH *dh = NULL;
899     if (GenerateOpensslDhKeyByPriKeySpec(paramsSpec, &dh) != HCF_SUCCESS) {
900         LOGD("[error] Generate openssl dh key by priKeySpec failed.");
901         return HCF_ERR_CRYPTO_OPERATION;
902     }
903 
904     HcfOpensslDhPriKey *priKey = NULL;
905     if (CreateDhPriKey(dh, &priKey) != HCF_SUCCESS) {
906         LOGE("Create dh priKey failed.");
907         OpensslDhFree(dh);
908         return HCF_ERR_MALLOC;
909     }
910     *returnPriKey = (HcfPriKey *)priKey;
911     return HCF_SUCCESS;
912 }
913 
ConvertDhPubKey(const HcfBlob * pubKeyBlob,HcfOpensslDhPubKey ** returnPubKey)914 static HcfResult ConvertDhPubKey(const HcfBlob *pubKeyBlob, HcfOpensslDhPubKey **returnPubKey)
915 {
916     const unsigned char *temp = (const unsigned char *)pubKeyBlob->data;
917     EVP_PKEY *pKey = OpensslD2iPubKey(NULL, &temp, pubKeyBlob->len);
918     if (pKey == NULL) {
919         LOGD("[error] Call d2i_PUBKEY failed.");
920         HcfPrintOpensslError();
921         return HCF_ERR_CRYPTO_OPERATION;
922     }
923     DH *dh = OpensslEvpPkeyGet1Dh(pKey);
924     if (dh == NULL) {
925         LOGD("[error] EVP_PKEY_get1_DH failed");
926         HcfPrintOpensslError();
927         OpensslEvpPkeyFree(pKey);
928         return HCF_ERR_CRYPTO_OPERATION;
929     }
930     OpensslEvpPkeyFree(pKey);
931     HcfResult ret = CreateDhPubKey(dh, returnPubKey);
932     if (ret != HCF_SUCCESS) {
933         LOGE("Create dh public key failed");
934         OpensslDhFree(dh);
935     }
936     return ret;
937 }
938 
ConvertDhPriKey(const HcfBlob * priKeyBlob,HcfOpensslDhPriKey ** returnPriKey)939 static HcfResult ConvertDhPriKey(const HcfBlob *priKeyBlob, HcfOpensslDhPriKey **returnPriKey)
940 {
941     const unsigned char *temp = (const unsigned char *)priKeyBlob->data;
942     EVP_PKEY *pKey = OpensslD2iPrivateKey(EVP_PKEY_DH, NULL, &temp, priKeyBlob->len);
943     if (pKey == NULL) {
944         LOGD("[error] Call d2i_PrivateKey failed.");
945         HcfPrintOpensslError();
946         return HCF_ERR_CRYPTO_OPERATION;
947     }
948     DH *dh = OpensslEvpPkeyGet1Dh(pKey);
949     if (dh == NULL) {
950         LOGD("[error] EVP_PKEY_get1_DH failed");
951         HcfPrintOpensslError();
952         OpensslEvpPkeyFree(pKey);
953         return HCF_ERR_CRYPTO_OPERATION;
954     }
955     OpensslEvpPkeyFree(pKey);
956     HcfResult ret = CreateDhPriKey(dh, returnPriKey);
957     if (ret != HCF_SUCCESS) {
958         LOGE("Create DH private key failed");
959         OpensslDhFree(dh);
960     }
961     return ret;
962 }
963 
ConvertDhPubAndPriKey(const HcfBlob * pubKeyBlob,const HcfBlob * priKeyBlob,HcfOpensslDhPubKey ** returnPubKey,HcfOpensslDhPriKey ** returnPriKey)964 static HcfResult ConvertDhPubAndPriKey(const HcfBlob *pubKeyBlob, const HcfBlob *priKeyBlob,
965     HcfOpensslDhPubKey **returnPubKey, HcfOpensslDhPriKey **returnPriKey)
966 {
967     if (pubKeyBlob != NULL) {
968         if (ConvertDhPubKey(pubKeyBlob, returnPubKey) != HCF_SUCCESS) {
969             LOGD("[error] Convert DH public key failed.");
970             return HCF_ERR_CRYPTO_OPERATION;
971         }
972     }
973     if (priKeyBlob != NULL) {
974         if (ConvertDhPriKey(priKeyBlob, returnPriKey) != HCF_SUCCESS) {
975             LOGD("[error] Convert DH private key failed.");
976             HcfObjDestroy(*returnPubKey);
977             *returnPubKey = NULL;
978             return HCF_ERR_CRYPTO_OPERATION;
979         }
980     }
981     return HCF_SUCCESS;
982 }
983 
EngineGenerateDhKeyPair(HcfAsyKeyGeneratorSpi * self,HcfKeyPair ** returnKeyPair)984 static HcfResult EngineGenerateDhKeyPair(HcfAsyKeyGeneratorSpi *self, HcfKeyPair **returnKeyPair)
985 {
986     if (self == NULL || returnKeyPair == NULL) {
987         LOGE("Invalid params.");
988         return HCF_INVALID_PARAMS;
989     }
990     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhKeyGeneratorSpiClass())) {
991         LOGE("Class not match.");
992         return HCF_INVALID_PARAMS;
993     }
994     HcfAsyKeyGeneratorSpiDhOpensslImpl *impl = (HcfAsyKeyGeneratorSpiDhOpensslImpl *)self;
995 
996     HcfOpensslDhPubKey *pubKey = NULL;
997     HcfOpensslDhPriKey *priKey = NULL;
998     HcfResult ret = GenerateDhPubAndPriKey(impl->pBits, &pubKey, &priKey);
999     if (ret != HCF_SUCCESS) {
1000         LOGE("Generate DH pk and sk by openssl failed.");
1001         return ret;
1002     }
1003     ret = CreateDhKeyPair(pubKey, priKey, returnKeyPair);
1004     if (ret != HCF_SUCCESS) {
1005         LOGE("Create dh keyPair failed.");
1006         HcfObjDestroy(pubKey);
1007         HcfObjDestroy(priKey);
1008         return ret;
1009     }
1010     return HCF_SUCCESS;
1011 }
1012 
EngineConvertDhKey(HcfAsyKeyGeneratorSpi * self,HcfParamsSpec * params,HcfBlob * pubKeyBlob,HcfBlob * priKeyBlob,HcfKeyPair ** returnKeyPair)1013 static HcfResult EngineConvertDhKey(HcfAsyKeyGeneratorSpi *self, HcfParamsSpec *params, HcfBlob *pubKeyBlob,
1014     HcfBlob *priKeyBlob, HcfKeyPair **returnKeyPair)
1015 {
1016     (void)params;
1017     if ((self == NULL) || (returnKeyPair == NULL)) {
1018         LOGE("Invalid input parameter.");
1019         return HCF_INVALID_PARAMS;
1020     }
1021     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhKeyGeneratorSpiClass())) {
1022         LOGE("Class not match.");
1023         return HCF_INVALID_PARAMS;
1024     }
1025     bool pubKeyValid = HcfIsBlobValid(pubKeyBlob);
1026     bool priKeyValid = HcfIsBlobValid(priKeyBlob);
1027     if ((!pubKeyValid) && (!priKeyValid)) {
1028         LOGE("The private key and public key cannot both be NULL.");
1029         return HCF_INVALID_PARAMS;
1030     }
1031 
1032     HcfOpensslDhPubKey *pubKey = NULL;
1033     HcfOpensslDhPriKey *priKey = NULL;
1034     HcfBlob *inputPk = pubKeyValid ? pubKeyBlob : NULL;
1035     HcfBlob *inputSk = priKeyValid ? priKeyBlob : NULL;
1036     HcfResult ret = ConvertDhPubAndPriKey(inputPk, inputSk, &pubKey, &priKey);
1037     if (ret != HCF_SUCCESS) {
1038         LOGE("Convert dh pubKey and priKey failed.");
1039         return ret;
1040     }
1041     ret = CreateDhKeyPair(pubKey, priKey, returnKeyPair);
1042     if (ret != HCF_SUCCESS) {
1043         LOGE("Create dh keyPair failed.");
1044         HcfObjDestroy(pubKey);
1045         HcfObjDestroy(priKey);
1046     }
1047     return ret;
1048 }
1049 
EngineGenerateDhKeyPairBySpec(const HcfAsyKeyGeneratorSpi * self,const HcfAsyKeyParamsSpec * paramsSpec,HcfKeyPair ** returnKeyPair)1050 static HcfResult EngineGenerateDhKeyPairBySpec(const HcfAsyKeyGeneratorSpi *self,
1051     const HcfAsyKeyParamsSpec *paramsSpec, HcfKeyPair **returnKeyPair)
1052 {
1053     if ((self == NULL) || (paramsSpec == NULL) || (paramsSpec->algName == NULL) || (returnKeyPair == NULL)) {
1054         LOGE("Invalid input parameter.");
1055         return HCF_INVALID_PARAMS;
1056     }
1057 
1058     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhKeyGeneratorSpiClass())) {
1059         LOGE("Class not match.");
1060         return HCF_INVALID_PARAMS;
1061     }
1062 
1063     if ((strcmp(paramsSpec->algName, ALGORITHM_NAME_DH) != 0) ||
1064         ((paramsSpec->specType != HCF_COMMON_PARAMS_SPEC) && (paramsSpec->specType != HCF_KEY_PAIR_SPEC))) {
1065         LOGE("Invalid params spec.");
1066         return HCF_INVALID_PARAMS;
1067     }
1068     HcfResult ret = CreateDhKeyPairBySpec(paramsSpec, returnKeyPair);
1069     if (ret != HCF_SUCCESS) {
1070         LOGE("Create DH key pair by spec failed.");
1071     }
1072     return ret;
1073 }
1074 
EngineGenerateDhPubKeyBySpec(const HcfAsyKeyGeneratorSpi * self,const HcfAsyKeyParamsSpec * paramsSpec,HcfPubKey ** returnPubKey)1075 static HcfResult EngineGenerateDhPubKeyBySpec(const HcfAsyKeyGeneratorSpi *self,
1076     const HcfAsyKeyParamsSpec *paramsSpec, HcfPubKey **returnPubKey)
1077 {
1078     if ((self == NULL) || (paramsSpec == NULL) || (paramsSpec->algName == NULL) || (returnPubKey == NULL)) {
1079         LOGE("Invalid input parameter.");
1080         return HCF_INVALID_PARAMS;
1081     }
1082 
1083     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhKeyGeneratorSpiClass())) {
1084         LOGE("Class not match.");
1085         return HCF_INVALID_PARAMS;
1086     }
1087 
1088     if ((strcmp(paramsSpec->algName, ALGORITHM_NAME_DH) != 0) ||
1089         ((paramsSpec->specType != HCF_PUBLIC_KEY_SPEC) && (paramsSpec->specType != HCF_KEY_PAIR_SPEC))) {
1090         LOGE("Invalid params spec.");
1091         return HCF_INVALID_PARAMS;
1092     }
1093 
1094     HcfResult ret = CreateDhPubKeyBySpec((const HcfDhPubKeyParamsSpec *)paramsSpec, returnPubKey);
1095     if (ret != HCF_SUCCESS) {
1096         LOGE("Create DH public key by spec failed.");
1097     }
1098     return ret;
1099 }
1100 
EngineGenerateDhPriKeyBySpec(const HcfAsyKeyGeneratorSpi * self,const HcfAsyKeyParamsSpec * paramsSpec,HcfPriKey ** returnPriKey)1101 static HcfResult EngineGenerateDhPriKeyBySpec(const HcfAsyKeyGeneratorSpi *self,
1102     const HcfAsyKeyParamsSpec *paramsSpec, HcfPriKey **returnPriKey)
1103 {
1104     if ((self == NULL) || (paramsSpec == NULL) || (paramsSpec->algName == NULL) || (returnPriKey == NULL)) {
1105         LOGE("Invalid input parameter.");
1106         return HCF_INVALID_PARAMS;
1107     }
1108     if (!HcfIsClassMatch((HcfObjectBase *)self, GetDhKeyGeneratorSpiClass())) {
1109         LOGE("Class not match.");
1110         return HCF_INVALID_PARAMS;
1111     }
1112     if ((strcmp(paramsSpec->algName, ALGORITHM_NAME_DH) != 0) ||
1113         ((paramsSpec->specType != HCF_PRIVATE_KEY_SPEC) && (paramsSpec->specType != HCF_KEY_PAIR_SPEC))) {
1114         LOGE("Invalid params spec.");
1115         return HCF_INVALID_PARAMS;
1116     }
1117 
1118     HcfResult ret = CreateDhPriKeyBySpec((const HcfDhPriKeyParamsSpec *)paramsSpec, returnPriKey);
1119     if (ret != HCF_SUCCESS) {
1120         LOGE("Create DH private key by spec failed.");
1121     }
1122     return ret;
1123 }
1124 
HcfAsyKeyGeneratorSpiDhCreate(HcfAsyKeyGenParams * params,HcfAsyKeyGeneratorSpi ** generator)1125 HcfResult HcfAsyKeyGeneratorSpiDhCreate(HcfAsyKeyGenParams *params, HcfAsyKeyGeneratorSpi **generator)
1126 {
1127     if (params == NULL || generator == NULL) {
1128         LOGE("Invalid input parameter.");
1129         return HCF_INVALID_PARAMS;
1130     }
1131     HcfAsyKeyGeneratorSpiDhOpensslImpl *impl = (HcfAsyKeyGeneratorSpiDhOpensslImpl *)HcfMalloc(
1132         sizeof(HcfAsyKeyGeneratorSpiDhOpensslImpl), 0);
1133     if (impl == NULL) {
1134         LOGE("Failed to allocate generator impl memroy.");
1135         return HCF_ERR_MALLOC;
1136     }
1137     impl->pBits = params->bits;
1138     impl->base.base.getClass = GetDhKeyGeneratorSpiClass;
1139     impl->base.base.destroy = DestroyDhKeyGeneratorSpiImpl;
1140     impl->base.engineGenerateKeyPair = EngineGenerateDhKeyPair;
1141     impl->base.engineConvertKey = EngineConvertDhKey;
1142     impl->base.engineGenerateKeyPairBySpec = EngineGenerateDhKeyPairBySpec;
1143     impl->base.engineGeneratePubKeyBySpec = EngineGenerateDhPubKeyBySpec;
1144     impl->base.engineGeneratePriKeyBySpec = EngineGenerateDhPriKeyBySpec;
1145 
1146     *generator = (HcfAsyKeyGeneratorSpi *)impl;
1147     return HCF_SUCCESS;
1148 }