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