• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022 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 "napi_x509_certificate.h"
17 
18 #include "napi/native_node_api.h"
19 #include "napi/native_api.h"
20 #include "log.h"
21 #include "memory.h"
22 #include "utils.h"
23 #include "object_base.h"
24 #include "result.h"
25 #include "napi_crypto_framework_defines.h"
26 #include "napi_pub_key.h"
27 #include "napi_utils.h"
28 
29 namespace OHOS {
30 namespace CryptoFramework {
31 thread_local napi_ref NapiX509Certificate::classRef_ = nullptr;
32 
33 struct CfCtx {
34     CfAsyncType asyncType = ASYNC_TYPE_CALLBACK;
35     napi_value promise = nullptr;
36     napi_ref callback = nullptr;
37     napi_deferred deferred = nullptr;
38     napi_async_work asyncWork = nullptr;
39 
40     HcfEncodingBlob *encodingBlob = nullptr;
41     NapiX509Certificate *certClass = nullptr;
42     HcfPubKey *pubKey = nullptr;
43 
44     int32_t errCode = 0;
45     const char *errMsg = nullptr;
46     HcfX509Certificate *cert;
47     HcfEncodingBlob *encoded = nullptr;
48 };
49 
NapiX509Certificate(HcfX509Certificate * x509Cert)50 NapiX509Certificate::NapiX509Certificate(HcfX509Certificate *x509Cert)
51 {
52     this->x509Cert_ = x509Cert;
53 }
54 
~NapiX509Certificate()55 NapiX509Certificate::~NapiX509Certificate()
56 {
57     HcfObjDestroy(this->x509Cert_);
58 }
59 
FreeCryptoFwkCtx(napi_env env,CfCtx * context)60 static void FreeCryptoFwkCtx(napi_env env, CfCtx *context)
61 {
62     if (context == nullptr) {
63         return;
64     }
65 
66     if (context->asyncWork != nullptr) {
67         napi_delete_async_work(env, context->asyncWork);
68     }
69 
70     if (context->callback != nullptr) {
71         napi_delete_reference(env, context->callback);
72     }
73 
74     HcfEncodingBlobDataFree(context->encodingBlob);
75     HcfFree(context->encodingBlob);
76     context->encodingBlob = nullptr;
77 
78     HcfEncodingBlobDataFree(context->encoded);
79     HcfFree(context->encoded);
80     context->encoded = nullptr;
81 
82     HcfFree(context);
83 }
84 
ReturnCallbackResult(napi_env env,CfCtx * context,napi_value result)85 static void ReturnCallbackResult(napi_env env, CfCtx *context, napi_value result)
86 {
87     napi_value businessError = nullptr;
88     if (context->errCode != HCF_SUCCESS) {
89         businessError = GenerateBusinessError(env, context->errCode, context->errMsg, true);
90     }
91     napi_value params[ARGS_SIZE_TWO] = { businessError, result };
92 
93     napi_value func = nullptr;
94     napi_get_reference_value(env, context->callback, &func);
95 
96     napi_value recv = nullptr;
97     napi_value callFuncRet = nullptr;
98     napi_get_undefined(env, &recv);
99     napi_call_function(env, recv, func, ARGS_SIZE_TWO, params, &callFuncRet);
100 }
101 
ReturnPromiseResult(napi_env env,CfCtx * context,napi_value result)102 static void ReturnPromiseResult(napi_env env, CfCtx *context, napi_value result)
103 {
104     if (context->errCode == HCF_SUCCESS) {
105         napi_resolve_deferred(env, context->deferred, result);
106     } else {
107         napi_reject_deferred(env, context->deferred,
108             GenerateBusinessError(env, context->errCode, context->errMsg, true));
109     }
110 }
111 
ReturnResult(napi_env env,CfCtx * context,napi_value result)112 static void ReturnResult(napi_env env, CfCtx *context, napi_value result)
113 {
114     if (context->asyncType == ASYNC_TYPE_CALLBACK) {
115         ReturnCallbackResult(env, context, result);
116     } else {
117         ReturnPromiseResult(env, context, result);
118     }
119 }
120 
CreateCallbackAndPromise(napi_env env,CfCtx * context,size_t argc,size_t maxCount,napi_value callbackValue)121 static bool CreateCallbackAndPromise(napi_env env, CfCtx *context, size_t argc,
122     size_t maxCount, napi_value callbackValue)
123 {
124     context->asyncType = (argc == maxCount) ? ASYNC_TYPE_CALLBACK : ASYNC_TYPE_PROMISE;
125     if (context->asyncType == ASYNC_TYPE_CALLBACK) {
126         if (!GetCallbackFromJSParams(env, callbackValue, &context->callback, true)) {
127             LOGE("get callback failed!");
128             return false;
129         }
130     } else {
131         napi_create_promise(env, &context->deferred, &context->promise);
132     }
133     return true;
134 }
135 
VerifyExecute(napi_env env,void * data)136 static void VerifyExecute(napi_env env, void *data)
137 {
138     LOGI("start to verify.");
139     CfCtx *context = static_cast<CfCtx *>(data);
140     HcfX509Certificate *cert = context->certClass->GetX509Cert();
141     context->errCode = cert->base.verify(&(cert->base), context->pubKey);
142     if (context->errCode != HCF_SUCCESS) {
143         LOGE("verify cert failed!");
144         context->errMsg = "verify cert failed";
145     }
146 }
147 
VerifyComplete(napi_env env,napi_status status,void * data)148 static void VerifyComplete(napi_env env, napi_status status, void *data)
149 {
150     CfCtx *context = static_cast<CfCtx *>(data);
151     ReturnResult(env, context, NapiGetNull(env));
152     FreeCryptoFwkCtx(env, context);
153 }
154 
GetEncodedExecute(napi_env env,void * data)155 static void GetEncodedExecute(napi_env env, void *data)
156 {
157     CfCtx *context = static_cast<CfCtx *>(data);
158     HcfX509Certificate *cert = context->certClass->GetX509Cert();
159     HcfEncodingBlob *encodingBlob = static_cast<HcfEncodingBlob *>(HcfMalloc(sizeof(HcfEncodingBlob), 0));
160     if (encodingBlob == nullptr) {
161         LOGE("malloc encoding blob failed!");
162         context->errCode = HCF_ERR_MALLOC;
163         context->errMsg = "malloc encoding blob failed";
164         return;
165     }
166     context->errCode = cert->base.getEncoded(&(cert->base), encodingBlob);
167     if (context->errCode != HCF_SUCCESS) {
168         LOGE("get cert encoded failed!");
169         context->errMsg = "get cert encoded failed";
170     }
171     context->encoded = encodingBlob;
172 }
173 
GetEncodedComplete(napi_env env,napi_status status,void * data)174 static void GetEncodedComplete(napi_env env, napi_status status, void *data)
175 {
176     CfCtx *context = static_cast<CfCtx *>(data);
177     if (context->errCode != HCF_SUCCESS) {
178         ReturnResult(env, context, nullptr);
179         FreeCryptoFwkCtx(env, context);
180         return;
181     }
182     napi_value returnEncodingBlob = ConvertEncodingBlobToNapiValue(env, context->encoded);
183     ReturnResult(env, context, returnEncodingBlob);
184     FreeCryptoFwkCtx(env, context);
185 }
186 
Verify(napi_env env,napi_callback_info info)187 napi_value NapiX509Certificate::Verify(napi_env env, napi_callback_info info)
188 {
189     size_t argc = ARGS_SIZE_TWO;
190     napi_value argv[ARGS_SIZE_TWO] = { nullptr };
191     napi_value thisVar = nullptr;
192     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
193     if (!CheckArgsCount(env, argc, ARGS_SIZE_TWO, false, true)) {
194         return nullptr;
195     }
196 
197     CfCtx *context = static_cast<CfCtx *>(HcfMalloc(sizeof(CfCtx), 0));
198     if (context == nullptr) {
199         LOGE("malloc context failed!");
200         return nullptr;
201     }
202     context->certClass = this;
203 
204     NapiPubKey *pubKey = nullptr;
205     napi_unwrap(env, argv[PARAM0], (void**)&pubKey);
206     if (pubKey == nullptr) {
207         napi_throw(env, GenerateBusinessError(env, HCF_INVALID_PARAMS, "public key is null", true));
208         LOGE("pubKey is null!");
209         FreeCryptoFwkCtx(env, context);
210         return nullptr;
211     }
212     context->pubKey = pubKey->GetPubKey();
213 
214     if (!CreateCallbackAndPromise(env, context, argc, ARGS_SIZE_TWO, argv[PARAM1])) {
215         FreeCryptoFwkCtx(env, context);
216         return nullptr;
217     }
218 
219     napi_create_async_work(
220         env, nullptr, GetResourceName(env, "Verify"),
221         VerifyExecute,
222         VerifyComplete,
223         static_cast<void *>(context),
224         &context->asyncWork);
225 
226     napi_queue_async_work(env, context->asyncWork);
227     if (context->asyncType == ASYNC_TYPE_PROMISE) {
228         return context->promise;
229     } else {
230         return NapiGetNull(env);
231     }
232 }
233 
GetEncoded(napi_env env,napi_callback_info info)234 napi_value NapiX509Certificate::GetEncoded(napi_env env, napi_callback_info info)
235 {
236     size_t argc = ARGS_SIZE_ONE;
237     napi_value argv[ARGS_SIZE_ONE] = { nullptr };
238     napi_value thisVar = nullptr;
239     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
240     if (!CheckArgsCount(env, argc, ARGS_SIZE_ONE, false, true)) {
241         return nullptr;
242     }
243 
244     CfCtx *context = static_cast<CfCtx *>(HcfMalloc(sizeof(CfCtx), 0));
245     if (context == nullptr) {
246         LOGE("malloc context failed!");
247         return nullptr;
248     }
249     context->certClass = this;
250 
251     if (!CreateCallbackAndPromise(env, context, argc, ARGS_SIZE_ONE, argv[PARAM0])) {
252         FreeCryptoFwkCtx(env, context);
253         return nullptr;
254     }
255 
256     napi_create_async_work(
257         env, nullptr, GetResourceName(env, "GetEncoded"),
258         GetEncodedExecute,
259         GetEncodedComplete,
260         static_cast<void *>(context),
261         &context->asyncWork);
262 
263     napi_queue_async_work(env, context->asyncWork);
264     if (context->asyncType == ASYNC_TYPE_PROMISE) {
265         return context->promise;
266     } else {
267         return NapiGetNull(env);
268     }
269 }
270 
GetPublicKey(napi_env env,napi_callback_info info)271 napi_value NapiX509Certificate::GetPublicKey(napi_env env, napi_callback_info info)
272 {
273     HcfX509Certificate *cert = GetX509Cert();
274     HcfPubKey *returnPubKey = nullptr;
275     HcfResult ret = cert->base.getPublicKey(&(cert->base), &returnPubKey);
276     if (ret != HCF_SUCCESS) {
277         napi_throw(env, GenerateBusinessError(env, ret, "get cert public key failed!", true));
278         LOGE("get cert public key failed!");
279         return nullptr;
280     }
281 
282     NapiPubKey *pubKeyClass = new (std::nothrow) NapiPubKey(returnPubKey);
283     if (pubKeyClass == nullptr) {
284         LOGE("create for x509 cert's public key obj failed");
285         HcfObjDestroy(returnPubKey);
286         return nullptr;
287     }
288     napi_value instance = pubKeyClass->ConvertToJsPubKey(env);
289     napi_wrap(
290         env, instance, pubKeyClass,
291         [](napi_env env, void *data, void *hint) {
292             NapiPubKey *pubKeyClass = static_cast<NapiPubKey *>(data);
293             HcfObjDestroy(pubKeyClass->GetPubKey());
294             delete pubKeyClass;
295             return;
296         },
297         nullptr, nullptr);
298     return instance;
299 }
300 
CheckValidityWithDate(napi_env env,napi_callback_info info)301 napi_value NapiX509Certificate::CheckValidityWithDate(napi_env env, napi_callback_info info)
302 {
303     size_t argc = ARGS_SIZE_ONE;
304     napi_value argv[ARGS_SIZE_ONE] = { nullptr };
305     napi_value thisVar = nullptr;
306     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
307     if (!CheckArgsCount(env, argc, ARGS_SIZE_ONE, true, true)) {
308         return nullptr;
309     }
310     std::string date;
311     if (!GetStringFromJSParams(env, argv[PARAM0], date, true)) {
312         LOGE("get date param failed!");
313         return nullptr;
314     }
315     HcfX509Certificate *cert = GetX509Cert();
316     HcfResult ret = cert->checkValidityWithDate(cert, date.c_str());
317     if (ret != HCF_SUCCESS) {
318         napi_throw(env, GenerateBusinessError(env, ret, "check cert validity failed!", true));
319         LOGE("check cert validity failed!");
320     }
321     return nullptr;
322 }
323 
GetVersion(napi_env env,napi_callback_info info)324 napi_value NapiX509Certificate::GetVersion(napi_env env, napi_callback_info info)
325 {
326     HcfX509Certificate *cert = GetX509Cert();
327     int version = cert->getVersion(cert);
328     napi_value result = nullptr;
329     napi_create_int32(env, version, &result);
330     return result;
331 }
332 
333 
GetSerialNumber(napi_env env,napi_callback_info info)334 napi_value NapiX509Certificate::GetSerialNumber(napi_env env, napi_callback_info info)
335 {
336     HcfX509Certificate *cert = GetX509Cert();
337     long serialNumber = cert->getSerialNumber(cert);
338     napi_value result = nullptr;
339     napi_create_int64(env, serialNumber, &result);
340     return result;
341 }
342 
GetIssuerName(napi_env env,napi_callback_info info)343 napi_value NapiX509Certificate::GetIssuerName(napi_env env, napi_callback_info info)
344 {
345     HcfBlob *blob = reinterpret_cast<HcfBlob *>(HcfMalloc(sizeof(HcfBlob), 0));
346     if (blob == nullptr) {
347         LOGE("malloc blob failed!");
348         return nullptr;
349     }
350     HcfX509Certificate *cert = GetX509Cert();
351     HcfResult ret = cert->getIssuerName(cert, blob);
352     if (ret != HCF_SUCCESS) {
353         napi_throw(env, GenerateBusinessError(env, ret, "get issuer name failed", true));
354         LOGE("getIssuerName failed!");
355         HcfFree(blob);
356         blob = nullptr;
357         return nullptr;
358     }
359     napi_value returnValue = ConvertBlobToNapiValue(env, blob);
360     HcfBlobDataFree(blob);
361     HcfFree(blob);
362     blob = nullptr;
363     return returnValue;
364 }
365 
GetSubjectName(napi_env env,napi_callback_info info)366 napi_value NapiX509Certificate::GetSubjectName(napi_env env, napi_callback_info info)
367 {
368     HcfBlob *blob = reinterpret_cast<HcfBlob *>(HcfMalloc(sizeof(HcfBlob), 0));
369     if (blob == nullptr) {
370         LOGE("malloc blob failed!");
371         return nullptr;
372     }
373     HcfX509Certificate *cert = GetX509Cert();
374     HcfResult ret = cert->getSubjectName(cert, blob);
375     if (ret != HCF_SUCCESS) {
376         napi_throw(env, GenerateBusinessError(env, ret, "get subject name failed", true));
377         LOGE("getSubjectName failed!");
378         HcfFree(blob);
379         blob = nullptr;
380         return nullptr;
381     }
382     napi_value returnValue = ConvertBlobToNapiValue(env, blob);
383     HcfBlobDataFree(blob);
384     HcfFree(blob);
385     blob = nullptr;
386     return returnValue;
387 }
388 
GetNotBeforeTime(napi_env env,napi_callback_info info)389 napi_value NapiX509Certificate::GetNotBeforeTime(napi_env env, napi_callback_info info)
390 {
391     HcfBlob *blob = reinterpret_cast<HcfBlob *>(HcfMalloc(sizeof(HcfBlob), 0));
392     if (blob == nullptr) {
393         LOGE("malloc blob failed!");
394         return nullptr;
395     }
396     HcfX509Certificate *cert = GetX509Cert();
397     HcfResult res = cert->getNotBeforeTime(cert, blob);
398     if (res != HCF_SUCCESS) {
399         napi_throw(env, GenerateBusinessError(env, res, "get not before time failed", true));
400         LOGE("getNotBeforeTime failed!");
401         HcfFree(blob);
402         blob = nullptr;
403         return nullptr;
404     }
405     napi_value result = nullptr;
406     napi_create_string_utf8(env, reinterpret_cast<char *>(blob->data), blob->len, &result);
407     HcfBlobDataFree(blob);
408     HcfFree(blob);
409     blob = nullptr;
410     return result;
411 }
412 
GetNotAfterTime(napi_env env,napi_callback_info info)413 napi_value NapiX509Certificate::GetNotAfterTime(napi_env env, napi_callback_info info)
414 {
415     HcfBlob *blob = reinterpret_cast<HcfBlob *>(HcfMalloc(sizeof(HcfBlob), 0));
416     if (blob == nullptr) {
417         LOGE("malloc blob failed!");
418         return nullptr;
419     }
420     HcfX509Certificate *cert = GetX509Cert();
421     HcfResult res = cert->getNotAfterTime(cert, blob);
422     if (res != HCF_SUCCESS) {
423         napi_throw(env, GenerateBusinessError(env, res, "get not after time failed", true));
424         LOGE("getNotAfterTime failed!");
425         HcfFree(blob);
426         blob = nullptr;
427         return nullptr;
428     }
429     napi_value result = nullptr;
430     napi_create_string_utf8(env, reinterpret_cast<char *>(blob->data), blob->len, &result);
431     HcfBlobDataFree(blob);
432     HcfFree(blob);
433     blob = nullptr;
434     return result;
435 }
436 
GetSignature(napi_env env,napi_callback_info info)437 napi_value NapiX509Certificate::GetSignature(napi_env env, napi_callback_info info)
438 {
439     HcfBlob *blob = reinterpret_cast<HcfBlob *>(HcfMalloc(sizeof(HcfBlob), 0));
440     if (blob == nullptr) {
441         LOGE("malloc blob failed!");
442         return nullptr;
443     }
444     HcfX509Certificate *cert = GetX509Cert();
445     HcfResult ret = cert->getSignature(cert, blob);
446     if (ret != HCF_SUCCESS) {
447         napi_throw(env, GenerateBusinessError(env, ret, "get signature failed", true));
448         LOGE("getSignature failed!");
449         HcfFree(blob);
450         blob = nullptr;
451         return nullptr;
452     }
453     napi_value returnValue = ConvertBlobToNapiValue(env, blob);
454     HcfBlobDataFree(blob);
455     HcfFree(blob);
456     blob = nullptr;
457     return returnValue;
458 }
459 
GetSigAlgName(napi_env env,napi_callback_info info)460 napi_value NapiX509Certificate::GetSigAlgName(napi_env env, napi_callback_info info)
461 {
462     HcfBlob *blob = reinterpret_cast<HcfBlob *>(HcfMalloc(sizeof(HcfBlob), 0));
463     if (blob == nullptr) {
464         LOGE("malloc blob failed!");
465         return nullptr;
466     }
467     HcfX509Certificate *cert = GetX509Cert();
468     HcfResult res = cert->getSignatureAlgName(cert, blob);
469     if (res != HCF_SUCCESS) {
470         napi_throw(env, GenerateBusinessError(env, res, "get signature alg name failed", true));
471         LOGE("getSignatureAlgName failed!");
472         HcfFree(blob);
473         blob = nullptr;
474         return nullptr;
475     }
476     napi_value result = nullptr;
477     napi_create_string_utf8(env, reinterpret_cast<char *>(blob->data), blob->len, &result);
478     HcfBlobDataFree(blob);
479     HcfFree(blob);
480     blob = nullptr;
481     return result;
482 }
483 
GetSigAlgOID(napi_env env,napi_callback_info info)484 napi_value NapiX509Certificate::GetSigAlgOID(napi_env env, napi_callback_info info)
485 {
486     HcfBlob *blob = reinterpret_cast<HcfBlob *>(HcfMalloc(sizeof(HcfBlob), 0));
487     if (blob == nullptr) {
488         LOGE("malloc blob failed!");
489         return nullptr;
490     }
491     HcfX509Certificate *cert = GetX509Cert();
492     HcfResult res = cert->getSignatureAlgOid(cert, blob);
493     if (res != HCF_SUCCESS) {
494         napi_throw(env, GenerateBusinessError(env, res, "get signature alg oid failed", true));
495         LOGE("getSignatureAlgOid failed!");
496         HcfFree(blob);
497         blob = nullptr;
498         return nullptr;
499     }
500     napi_value result = nullptr;
501     napi_create_string_utf8(env, reinterpret_cast<char *>(blob->data), blob->len, &result);
502     HcfBlobDataFree(blob);
503     HcfFree(blob);
504     blob = nullptr;
505     return result;
506 }
507 
GetSigAlgParams(napi_env env,napi_callback_info info)508 napi_value NapiX509Certificate::GetSigAlgParams(napi_env env, napi_callback_info info)
509 {
510     HcfBlob *blob = reinterpret_cast<HcfBlob *>(HcfMalloc(sizeof(HcfBlob), 0));
511     if (blob == nullptr) {
512         LOGE("malloc blob failed!");
513         return nullptr;
514     }
515     HcfX509Certificate *cert = GetX509Cert();
516     HcfResult ret = cert->getSignatureAlgParams(cert, blob);
517     if (ret != HCF_SUCCESS) {
518         napi_throw(env, GenerateBusinessError(env, ret, "get signature alg params failed", true));
519         LOGE("getSignatureAlgParams failed!");
520         HcfFree(blob);
521         blob = nullptr;
522         return nullptr;
523     }
524     napi_value returnValue = ConvertBlobToNapiValue(env, blob);
525     HcfBlobDataFree(blob);
526     HcfFree(blob);
527     blob = nullptr;
528     return returnValue;
529 }
530 
GetKeyUsage(napi_env env,napi_callback_info info)531 napi_value NapiX509Certificate::GetKeyUsage(napi_env env, napi_callback_info info)
532 {
533     HcfBlob *blob = reinterpret_cast<HcfBlob *>(HcfMalloc(sizeof(HcfBlob), 0));
534     if (blob == nullptr) {
535         LOGE("malloc blob failed!");
536         return nullptr;
537     }
538     HcfX509Certificate *cert = GetX509Cert();
539     HcfResult ret = cert->getKeyUsage(cert, blob);
540     if (ret != HCF_SUCCESS) {
541         napi_throw(env, GenerateBusinessError(env, ret, "get key usage failed", true));
542         LOGE("getKeyUsage failed!");
543         HcfFree(blob);
544         blob = nullptr;
545         return nullptr;
546     }
547     napi_value returnValue = ConvertBlobToNapiValue(env, blob);
548     HcfBlobDataFree(blob);
549     HcfFree(blob);
550     blob = nullptr;
551     return returnValue;
552 }
553 
GetExtendedKeyUsage(napi_env env,napi_callback_info info)554 napi_value NapiX509Certificate::GetExtendedKeyUsage(napi_env env, napi_callback_info info)
555 {
556     HcfArray *array = reinterpret_cast<HcfArray *>(HcfMalloc(sizeof(HcfArray), 0));
557     if (array == nullptr) {
558         LOGE("malloc array failed!");
559         return nullptr;
560     }
561     HcfX509Certificate *cert = GetX509Cert();
562     HcfResult ret = cert->getExtKeyUsage(cert, array);
563     if (ret != HCF_SUCCESS) {
564         napi_throw(env, GenerateBusinessError(env, ret, "get ext key usage failed", true));
565         LOGE("call getExtKeyUsage failed!");
566         HcfFree(array);
567         array = nullptr;
568         return nullptr;
569     }
570     napi_value returnValue = ConvertArrayToNapiValue(env, array);
571     HcfArrayDataClearAndFree(array);
572     HcfFree(array);
573     array = nullptr;
574     return returnValue;
575 }
576 
577 
GetBasicConstraints(napi_env env,napi_callback_info info)578 napi_value NapiX509Certificate::GetBasicConstraints(napi_env env, napi_callback_info info)
579 {
580     HcfX509Certificate *cert = GetX509Cert();
581     int32_t constrains = cert->getBasicConstraints(cert);
582     napi_value result = nullptr;
583     napi_create_int32(env, constrains, &result);
584     return result;
585 }
586 
GetSubjectAlternativeNames(napi_env env,napi_callback_info info)587 napi_value NapiX509Certificate::GetSubjectAlternativeNames(napi_env env, napi_callback_info info)
588 {
589     HcfArray *array = reinterpret_cast<HcfArray *>(HcfMalloc(sizeof(HcfArray), 0));
590     if (array == nullptr) {
591         LOGE("malloc array failed!");
592         return nullptr;
593     }
594     HcfX509Certificate *cert = GetX509Cert();
595     HcfResult ret = cert->getSubjectAltNames(cert, array);
596     if (ret != HCF_SUCCESS) {
597         napi_throw(env, GenerateBusinessError(env, ret, "get subject alt names failed", true));
598         LOGE("call getSubjectAltNames failed!");
599         HcfFree(array);
600         array = nullptr;
601         return nullptr;
602     }
603     napi_value returnValue = ConvertArrayToNapiValue(env, array);
604     HcfArrayDataClearAndFree(array);
605     HcfFree(array);
606     array = nullptr;
607     return returnValue;
608 }
609 
GetIssuerAlternativeNames(napi_env env,napi_callback_info info)610 napi_value NapiX509Certificate::GetIssuerAlternativeNames(napi_env env, napi_callback_info info)
611 {
612     HcfArray *array = reinterpret_cast<HcfArray *>(HcfMalloc(sizeof(HcfArray), 0));
613     if (array == nullptr) {
614         LOGE("malloc array failed!");
615         return nullptr;
616     }
617     HcfX509Certificate *cert = GetX509Cert();
618     HcfResult ret = cert->getIssuerAltNames(cert, array);
619     if (ret != HCF_SUCCESS) {
620         napi_throw(env, GenerateBusinessError(env, ret, "get issuer alt names failed", true));
621         LOGE("call getIssuerAltNames failed!");
622         HcfFree(array);
623         array = nullptr;
624         return nullptr;
625     }
626     napi_value returnValue = ConvertArrayToNapiValue(env, array);
627     HcfArrayDataClearAndFree(array);
628     HcfFree(array);
629     array = nullptr;
630     return returnValue;
631 }
632 
NapiVerify(napi_env env,napi_callback_info info)633 static napi_value NapiVerify(napi_env env, napi_callback_info info)
634 {
635     napi_value thisVar = nullptr;
636     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
637     NapiX509Certificate *x509Cert = nullptr;
638     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
639     if (x509Cert == nullptr) {
640         LOGE("x509Cert is nullptr!");
641         return nullptr;
642     }
643     return x509Cert->Verify(env, info);
644 }
645 
NapiGetEncoded(napi_env env,napi_callback_info info)646 static napi_value NapiGetEncoded(napi_env env, napi_callback_info info)
647 {
648     napi_value thisVar = nullptr;
649     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
650     NapiX509Certificate *x509Cert = nullptr;
651     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
652     if (x509Cert == nullptr) {
653         LOGE("x509Cert is nullptr!");
654         return nullptr;
655     }
656     return x509Cert->GetEncoded(env, info);
657 }
658 
NapiGetPublicKey(napi_env env,napi_callback_info info)659 static napi_value NapiGetPublicKey(napi_env env, napi_callback_info info)
660 {
661     napi_value thisVar = nullptr;
662     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
663     NapiX509Certificate *x509Cert = nullptr;
664     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
665     if (x509Cert == nullptr) {
666         LOGE("x509Cert is nullptr!");
667         return nullptr;
668     }
669     return x509Cert->GetPublicKey(env, info);
670 }
671 
NapiCheckValidityWithDate(napi_env env,napi_callback_info info)672 static napi_value NapiCheckValidityWithDate(napi_env env, napi_callback_info info)
673 {
674     napi_value thisVar = nullptr;
675     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
676     NapiX509Certificate *x509Cert = nullptr;
677     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
678     if (x509Cert == nullptr) {
679         LOGE("x509Cert is nullptr!");
680         return nullptr;
681     }
682     return x509Cert->CheckValidityWithDate(env, info);
683 }
684 
NapiGetVersion(napi_env env,napi_callback_info info)685 static napi_value NapiGetVersion(napi_env env, napi_callback_info info)
686 {
687     napi_value thisVar = nullptr;
688     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
689     NapiX509Certificate *x509Cert = nullptr;
690     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
691     if (x509Cert == nullptr) {
692         LOGE("x509Cert is nullptr!");
693         return nullptr;
694     }
695     return x509Cert->GetVersion(env, info);
696 }
697 
NapiGetSerialNumber(napi_env env,napi_callback_info info)698 static napi_value NapiGetSerialNumber(napi_env env, napi_callback_info info)
699 {
700     napi_value thisVar = nullptr;
701     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
702     NapiX509Certificate *x509Cert = nullptr;
703     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
704     if (x509Cert == nullptr) {
705         LOGE("x509Cert is nullptr!");
706         return nullptr;
707     }
708     return x509Cert->GetSerialNumber(env, info);
709 }
710 
NapiGetIssuerName(napi_env env,napi_callback_info info)711 static napi_value NapiGetIssuerName(napi_env env, napi_callback_info info)
712 {
713     napi_value thisVar = nullptr;
714     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
715     NapiX509Certificate *x509Cert = nullptr;
716     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
717     if (x509Cert == nullptr) {
718         LOGE("x509Cert is nullptr!");
719         return nullptr;
720     }
721     return x509Cert->GetIssuerName(env, info);
722 }
723 
NapiGetSubjectName(napi_env env,napi_callback_info info)724 static napi_value NapiGetSubjectName(napi_env env, napi_callback_info info)
725 {
726     napi_value thisVar = nullptr;
727     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
728     NapiX509Certificate *x509Cert = nullptr;
729     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
730     if (x509Cert == nullptr) {
731         LOGE("x509Cert is nullptr!");
732         return nullptr;
733     }
734     return x509Cert->GetSubjectName(env, info);
735 }
736 
NapiGetNotBeforeTime(napi_env env,napi_callback_info info)737 static napi_value NapiGetNotBeforeTime(napi_env env, napi_callback_info info)
738 {
739     napi_value thisVar = nullptr;
740     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
741     NapiX509Certificate *x509Cert = nullptr;
742     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
743     if (x509Cert == nullptr) {
744         LOGE("x509Cert is nullptr!");
745         return nullptr;
746     }
747     return x509Cert->GetNotBeforeTime(env, info);
748 }
749 
NapiGetNotAfterTime(napi_env env,napi_callback_info info)750 static napi_value NapiGetNotAfterTime(napi_env env, napi_callback_info info)
751 {
752     napi_value thisVar = nullptr;
753     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
754     NapiX509Certificate *x509Cert = nullptr;
755     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
756     if (x509Cert == nullptr) {
757         LOGE("x509Cert is nullptr!");
758         return nullptr;
759     }
760     return x509Cert->GetNotAfterTime(env, info);
761 }
762 
NapiGetSignature(napi_env env,napi_callback_info info)763 static napi_value NapiGetSignature(napi_env env, napi_callback_info info)
764 {
765     napi_value thisVar = nullptr;
766     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
767     NapiX509Certificate *x509Cert = nullptr;
768     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
769     if (x509Cert == nullptr) {
770         LOGE("x509Cert is nullptr!");
771         return nullptr;
772     }
773     return x509Cert->GetSignature(env, info);
774 }
775 
NapiGetSigAlgName(napi_env env,napi_callback_info info)776 static napi_value NapiGetSigAlgName(napi_env env, napi_callback_info info)
777 {
778     napi_value thisVar = nullptr;
779     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
780     NapiX509Certificate *x509Cert = nullptr;
781     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
782     if (x509Cert == nullptr) {
783         LOGE("x509Cert is nullptr!");
784         return nullptr;
785     }
786     return x509Cert->GetSigAlgName(env, info);
787 }
788 
NapiGetSigAlgOID(napi_env env,napi_callback_info info)789 static napi_value NapiGetSigAlgOID(napi_env env, napi_callback_info info)
790 {
791     napi_value thisVar = nullptr;
792     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
793     NapiX509Certificate *x509Cert = nullptr;
794     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
795     if (x509Cert == nullptr) {
796         LOGE("x509Cert is nullptr!");
797         return nullptr;
798     }
799     return x509Cert->GetSigAlgOID(env, info);
800 }
801 
NapiGetSigAlgParams(napi_env env,napi_callback_info info)802 static napi_value NapiGetSigAlgParams(napi_env env, napi_callback_info info)
803 {
804     napi_value thisVar = nullptr;
805     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
806     NapiX509Certificate *x509Cert = nullptr;
807     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
808     if (x509Cert == nullptr) {
809         LOGE("x509Cert is nullptr!");
810         return nullptr;
811     }
812     return x509Cert->GetSigAlgParams(env, info);
813 }
814 
NapiGetKeyUsage(napi_env env,napi_callback_info info)815 static napi_value NapiGetKeyUsage(napi_env env, napi_callback_info info)
816 {
817     napi_value thisVar = nullptr;
818     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
819     NapiX509Certificate *x509Cert = nullptr;
820     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
821     if (x509Cert == nullptr) {
822         LOGE("x509Cert is nullptr!");
823         return nullptr;
824     }
825     return x509Cert->GetKeyUsage(env, info);
826 }
827 
NapiGetExtendedKeyUsage(napi_env env,napi_callback_info info)828 static napi_value NapiGetExtendedKeyUsage(napi_env env, napi_callback_info info)
829 {
830     napi_value thisVar = nullptr;
831     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
832     NapiX509Certificate *x509Cert = nullptr;
833     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
834     if (x509Cert == nullptr) {
835         LOGE("x509Cert is nullptr!");
836         return nullptr;
837     }
838     return x509Cert->GetExtendedKeyUsage(env, info);
839 }
840 
NapiGetBasicConstraints(napi_env env,napi_callback_info info)841 static napi_value NapiGetBasicConstraints(napi_env env, napi_callback_info info)
842 {
843     napi_value thisVar = nullptr;
844     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
845     NapiX509Certificate *x509Cert = nullptr;
846     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
847     if (x509Cert == nullptr) {
848         LOGE("x509Cert is nullptr!");
849         return nullptr;
850     }
851     return x509Cert->GetBasicConstraints(env, info);
852 }
853 
NapiGetSubjectAlternativeNames(napi_env env,napi_callback_info info)854 static napi_value NapiGetSubjectAlternativeNames(napi_env env, napi_callback_info info)
855 {
856     napi_value thisVar = nullptr;
857     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
858     NapiX509Certificate *x509Cert = nullptr;
859     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
860     if (x509Cert == nullptr) {
861         LOGE("x509Cert is nullptr!");
862         return nullptr;
863     }
864     return x509Cert->GetSubjectAlternativeNames(env, info);
865 }
866 
NapiGetIssuerAlternativeNames(napi_env env,napi_callback_info info)867 static napi_value NapiGetIssuerAlternativeNames(napi_env env, napi_callback_info info)
868 {
869     napi_value thisVar = nullptr;
870     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
871     NapiX509Certificate *x509Cert = nullptr;
872     napi_unwrap(env, thisVar, reinterpret_cast<void **>(&x509Cert));
873     if (x509Cert == nullptr) {
874         LOGE("x509Cert is nullptr!");
875         return nullptr;
876     }
877     return x509Cert->GetIssuerAlternativeNames(env, info);
878 }
879 
CreateX509CertExecute(napi_env env,void * data)880 void NapiX509Certificate::CreateX509CertExecute(napi_env env, void *data)
881 {
882     CfCtx *context = static_cast<CfCtx *>(data);
883     context->errCode = HcfX509CertificateCreate(context->encodingBlob, &context->cert);
884     if (context->errCode != HCF_SUCCESS) {
885         context->errMsg = "create X509Cert failed";
886     }
887 }
888 
CreateX509CertComplete(napi_env env,napi_status status,void * data)889 void NapiX509Certificate::CreateX509CertComplete(napi_env env, napi_status status, void *data)
890 {
891     CfCtx *context = static_cast<CfCtx *>(data);
892     if (context->errCode != HCF_SUCCESS) {
893         LOGE("call create X509Cert failed!");
894         ReturnResult(env, context, nullptr);
895         FreeCryptoFwkCtx(env, context);
896         return;
897     }
898     napi_value instance = CreateX509Cert(env);
899     NapiX509Certificate *x509CertClass = new NapiX509Certificate(context->cert);
900     napi_wrap(
901         env, instance, x509CertClass,
902         [](napi_env env, void *data, void *hint) {
903             NapiX509Certificate *certClass = static_cast<NapiX509Certificate *>(data);
904             delete certClass;
905             return;
906         },
907         nullptr, nullptr);
908     ReturnResult(env, context, instance);
909     FreeCryptoFwkCtx(env, context);
910 }
911 
NapiCreateX509Cert(napi_env env,napi_callback_info info)912 napi_value NapiX509Certificate::NapiCreateX509Cert(napi_env env, napi_callback_info info)
913 {
914     size_t argc = ARGS_SIZE_TWO;
915     napi_value argv[ARGS_SIZE_TWO] = { nullptr };
916     napi_value thisVar = nullptr;
917     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
918     if (!CheckArgsCount(env, argc, ARGS_SIZE_TWO, false, true)) {
919         return nullptr;
920     }
921 
922     CfCtx *context = static_cast<CfCtx *>(HcfMalloc(sizeof(CfCtx), 0));
923     if (context == nullptr) {
924         LOGE("malloc context failed!");
925         return nullptr;
926     }
927     if (!GetEncodingBlobFromValue(env, argv[PARAM0], &context->encodingBlob)) {
928         LOGE("get encoding blob from data failed!");
929         FreeCryptoFwkCtx(env, context);
930         return nullptr;
931     }
932 
933     if (!CreateCallbackAndPromise(env, context, argc, ARGS_SIZE_TWO, argv[PARAM1])) {
934         FreeCryptoFwkCtx(env, context);
935         return nullptr;
936     }
937 
938     napi_create_async_work(
939         env, nullptr, GetResourceName(env, "CreateX509Cert"),
940         CreateX509CertExecute,
941         CreateX509CertComplete,
942         static_cast<void *>(context),
943         &context->asyncWork);
944 
945     napi_queue_async_work(env, context->asyncWork);
946     if (context->asyncType == ASYNC_TYPE_PROMISE) {
947         return context->promise;
948     } else {
949         return NapiGetNull(env);
950     }
951 }
952 
X509CertConstructor(napi_env env,napi_callback_info info)953 static napi_value X509CertConstructor(napi_env env, napi_callback_info info)
954 {
955     napi_value thisVar = nullptr;
956     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
957     return thisVar;
958 }
959 
DefineX509CertJSClass(napi_env env,napi_value exports)960 void NapiX509Certificate::DefineX509CertJSClass(napi_env env, napi_value exports)
961 {
962     napi_property_descriptor desc[] = {
963         DECLARE_NAPI_FUNCTION("createX509Cert", NapiCreateX509Cert),
964     };
965     napi_define_properties(env, exports, sizeof(desc) / sizeof(desc[0]), desc);
966 
967     napi_property_descriptor x509CertDesc[] = {
968         DECLARE_NAPI_FUNCTION("verify", NapiVerify),
969         DECLARE_NAPI_FUNCTION("getEncoded", NapiGetEncoded),
970         DECLARE_NAPI_FUNCTION("getPublicKey", NapiGetPublicKey),
971         DECLARE_NAPI_FUNCTION("checkValidityWithDate", NapiCheckValidityWithDate),
972         DECLARE_NAPI_FUNCTION("getVersion", NapiGetVersion),
973         DECLARE_NAPI_FUNCTION("getSerialNumber", NapiGetSerialNumber),
974         DECLARE_NAPI_FUNCTION("getIssuerName", NapiGetIssuerName),
975         DECLARE_NAPI_FUNCTION("getSubjectName", NapiGetSubjectName),
976         DECLARE_NAPI_FUNCTION("getNotBeforeTime", NapiGetNotBeforeTime),
977         DECLARE_NAPI_FUNCTION("getNotAfterTime", NapiGetNotAfterTime),
978         DECLARE_NAPI_FUNCTION("getSignature", NapiGetSignature),
979         DECLARE_NAPI_FUNCTION("getSignatureAlgName", NapiGetSigAlgName),
980         DECLARE_NAPI_FUNCTION("getSignatureAlgOid", NapiGetSigAlgOID),
981         DECLARE_NAPI_FUNCTION("getSignatureAlgParams", NapiGetSigAlgParams),
982         DECLARE_NAPI_FUNCTION("getKeyUsage", NapiGetKeyUsage),
983         DECLARE_NAPI_FUNCTION("getExtKeyUsage", NapiGetExtendedKeyUsage),
984         DECLARE_NAPI_FUNCTION("getBasicConstraints", NapiGetBasicConstraints),
985         DECLARE_NAPI_FUNCTION("getSubjectAltNames", NapiGetSubjectAlternativeNames),
986         DECLARE_NAPI_FUNCTION("getIssuerAltNames", NapiGetIssuerAlternativeNames),
987     };
988     napi_value constructor = nullptr;
989     napi_define_class(env, "X509Cert", NAPI_AUTO_LENGTH, X509CertConstructor, nullptr,
990         sizeof(x509CertDesc) / sizeof(x509CertDesc[0]), x509CertDesc, &constructor);
991     napi_create_reference(env, constructor, 1, &classRef_);
992 }
993 
CreateX509Cert(napi_env env)994 napi_value NapiX509Certificate::CreateX509Cert(napi_env env)
995 {
996     napi_value constructor = nullptr;
997     napi_value instance = nullptr;
998     napi_get_reference_value(env, classRef_, &constructor);
999     napi_new_instance(env, constructor, 0, nullptr, &instance);
1000     return instance;
1001 }
1002 } // namespace CryptoFramework
1003 } // namespace OHOS
1004