• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 "network_security_config.h"
17 
18 #include <sys/stat.h>
19 #include <fstream>
20 #include <dirent.h>
21 #include <unistd.h>
22 #include <dlfcn.h>
23 #include <securec.h>
24 
25 #include "openssl/evp.h"
26 #include "net_mgr_log_wrapper.h"
27 #include "net_manager_constants.h"
28 #include "net_bundle.h"
29 
30 namespace OHOS {
31 namespace NetManagerStandard {
32 
33 const std::string TAG_NETWORK_SECURITY_CONFIG("network-security-config");
34 const std::string TAG_BASE_CONFIG("base-config");
35 const std::string TAG_DOMAIN_CONFIG("domain-config");
36 const std::string TAG_TRUST_ANCHORS("trust-anchors");
37 const std::string TAG_CERTIFICATES("certificates");
38 const std::string TAG_DOMAINS("domains");
39 const std::string TAG_INCLUDE_SUBDOMAINS("include-subdomains");
40 const std::string TAG_NAME("name");
41 const std::string TAG_PIN_SET("pin-set");
42 const std::string TAG_EXPIRATION("expiration");
43 const std::string TAG_PIN("pin");
44 const std::string TAG_DIGEST_ALGORITHM("digest-algorithm");
45 const std::string TAG_DIGEST("digest");
46 
47 const std::string REHASHD_CA_CERTS_DIR("/data/storage/el2/base/haps/entry/files/rehashed_ca_certs");
48 #ifdef WINDOWS_PLATFORM
49 const char OS_PATH_SEPARATOR = '\\';
50 #else
51 const char OS_PATH_SEPARATOR = '/';
52 #endif
53 
54 #ifdef __LP64__
55 const std::string LIB_LOAD_PATH = "/system/lib64/libnet_bundle_utils.z.so";
56 #else
57 const std::string LIB_LOAD_PATH = "/system/lib/libnet_bundle_utils.z.so";
58 #endif
59 
60 using GetNetBundleClass = INetBundle* (*)();
61 
Endswith(const std::string & str,const std::string & suffix)62 bool Endswith(const std::string &str, const std::string &suffix)
63 {
64     if (str.length() < suffix.length()) {
65         return false;
66     }
67 
68     if (str.rfind(suffix) == (str.length() - suffix.length())) {
69         return true;
70     }
71 
72     return false;
73 }
74 
NetworkSecurityConfig()75 NetworkSecurityConfig::NetworkSecurityConfig()
76 {
77     if (GetConfig() != NETMANAGER_SUCCESS) {
78         NETMGR_LOG_E("Fail to get NetworkSecurityConfig");
79     } else {
80         NETMGR_LOG_D("Succeed to get NetworkSecurityConfig");
81     }
82 }
83 
~NetworkSecurityConfig()84 NetworkSecurityConfig::~NetworkSecurityConfig() {}
85 
GetInstance()86 NetworkSecurityConfig& NetworkSecurityConfig::GetInstance()
87 {
88     static NetworkSecurityConfig gInstance;
89     return gInstance;
90 }
91 
IsCACertFileName(const char * fileName)92 bool NetworkSecurityConfig::IsCACertFileName(const char *fileName)
93 {
94     std::string str;
95     auto ext = strrchr(fileName, '.');
96     if (ext != nullptr) {
97         str = ext + 1;
98     }
99 
100     for (auto &c: str) {
101         c = tolower(c);
102     }
103 
104     return (str == "pem" || str == "crt");
105 }
106 
GetCAFilesFromPath(const std::string caPath,std::vector<std::string> & caFiles)107 void NetworkSecurityConfig::GetCAFilesFromPath(const std::string caPath, std::vector<std::string> &caFiles)
108 {
109     DIR *dir = opendir(caPath.c_str());
110     if (dir == nullptr) {
111         NETMGR_LOG_E("open CA path[%{public}s] fail. [%{public}d]", caPath.c_str(), errno);
112         return;
113     }
114 
115     struct dirent *entry = readdir(dir);
116     while (entry != nullptr) {
117         if (IsCACertFileName(entry->d_name)) {
118             if (caPath.back() != OS_PATH_SEPARATOR) {
119                 caFiles.push_back(caPath + OS_PATH_SEPARATOR + entry->d_name);
120             } else {
121                 caFiles.push_back(caPath + entry->d_name);
122             }
123             NETMGR_LOG_D("Read CA File [%{public}s] from CA Path", entry->d_name);
124         }
125         entry = readdir(dir);
126     }
127 
128     closedir(dir);
129 }
130 
AddSurfixToCACertFileName(const std::string & caPath,std::set<std::string> & allFileNames,std::string & caFile)131 void NetworkSecurityConfig::AddSurfixToCACertFileName(const std::string &caPath,
132     std::set<std::string> &allFileNames, std::string &caFile)
133 {
134     uint32_t count = 0;
135     for (auto &fileName: allFileNames) {
136         if (fileName.find(caFile) != std::string::npos) {
137             count++;
138         }
139     }
140 
141     caFile = caFile + '.' + std::to_string(count);
142     allFileNames.insert(caFile);
143 }
144 
ReadCertFile(const std::string & fileName)145 X509 *NetworkSecurityConfig::ReadCertFile(const std::string &fileName)
146 {
147     std::ifstream certFile(fileName.c_str());
148     if (!certFile.is_open()) {
149         NETMGR_LOG_E("Fail to read cert fail [%{public}s]", fileName.c_str());
150         return nullptr;
151     }
152 
153     std::stringstream certStream;
154     certStream << certFile.rdbuf();
155 
156     const std::string &certData = certStream.str();
157     BIO *bio = BIO_new_mem_buf(certData.c_str(), -1);
158     if (bio == nullptr) {
159         NETMGR_LOG_E("Fail to call BIO_new_mem_buf");
160         return nullptr;
161     }
162 
163     X509 *x509 = PEM_read_bio_X509(bio, nullptr, nullptr, nullptr);
164     if (x509 == nullptr) {
165         NETMGR_LOG_E("Fail to call PEM_read_bio_X509.");
166     }
167 
168     BIO_free(bio);
169     return x509;
170 }
171 
GetRehashedCADirName(const std::string & caPath)172 std::string NetworkSecurityConfig::GetRehashedCADirName(const std::string &caPath)
173 {
174     unsigned char hashedHex[EVP_MAX_MD_SIZE];
175     auto ret = EVP_Digest(reinterpret_cast<const unsigned char *>(caPath.c_str()), caPath.size(),
176                           hashedHex, nullptr, EVP_sha256(), nullptr);
177     if (ret != 1) {
178         return "";
179     }
180 
181     /* Encode the hashed string by base16 */
182     constexpr unsigned int HASHED_DIR_NAME_LEN = 32;
183     constexpr unsigned int BASE16_ELE_SIZE = 2;
184     char hashedStr[HASHED_DIR_NAME_LEN + 1] = {0};
185     for (unsigned int i = 0; i < HASHED_DIR_NAME_LEN / BASE16_ELE_SIZE; i++) {
186         if (sprintf_s(&hashedStr[BASE16_ELE_SIZE * i], sizeof(hashedStr) - BASE16_ELE_SIZE * i, "%02x", hashedHex[i]) <
187             0) {
188             return "";
189         }
190     }
191 
192     return hashedStr;
193 }
194 
BuildRehasedCAPath(const std::string & caPath)195 std::string NetworkSecurityConfig::BuildRehasedCAPath(const std::string &caPath)
196 {
197     if (access(REHASHD_CA_CERTS_DIR.c_str(), F_OK) == -1) {
198         if (mkdir(REHASHD_CA_CERTS_DIR.c_str(), S_IRWXU | S_IRWXG) == -1) {
199             NETMGR_LOG_E("Fail to make a rehased caCerts dir [%{public}d]", errno);
200             return "";
201         }
202     }
203 
204     auto dirName = GetRehashedCADirName(caPath);
205     if (dirName.empty()) {
206         NETMGR_LOG_E("Fail to make a rehased caCerts dir for [%{public}s]", caPath.c_str());
207         return "";
208     }
209 
210     auto rehashedCertpath = REHASHD_CA_CERTS_DIR + OS_PATH_SEPARATOR + dirName;
211     if (access(rehashedCertpath.c_str(), F_OK) == -1) {
212         if (mkdir(rehashedCertpath.c_str(), S_IRWXU | S_IRWXG) == -1) {
213             NETMGR_LOG_E("Fail to make a rehased caCerts dir [%{public}d]", errno);
214             return "";
215         }
216     }
217 
218     NETMGR_LOG_D("Build dir [%{public}s]", rehashedCertpath.c_str());
219     return rehashedCertpath;
220 }
221 
GetRehasedCAPath(const std::string & caPath)222 std::string NetworkSecurityConfig::GetRehasedCAPath(const std::string &caPath)
223 {
224     if (access(REHASHD_CA_CERTS_DIR.c_str(), F_OK) == -1) {
225         return "";
226     }
227 
228     auto dirName = GetRehashedCADirName(caPath);
229     if (dirName.empty()) {
230         return "";
231     }
232 
233     auto rehashedCertpath = REHASHD_CA_CERTS_DIR + OS_PATH_SEPARATOR + dirName;
234     if (access(rehashedCertpath.c_str(), F_OK) == -1) {
235         return "";
236     }
237 
238     return rehashedCertpath;
239 }
240 
ReHashCAPathForX509(const std::string & caPath)241 std::string NetworkSecurityConfig::ReHashCAPathForX509(const std::string &caPath)
242 {
243     std::set<std::string> allFiles;
244     std::vector<std::string> caFiles;
245 
246     GetCAFilesFromPath(caPath, caFiles);
247     if (caFiles.empty()) {
248         NETMGR_LOG_D("No customized CA certs.");
249         return "";
250     }
251 
252     auto rehashedCertpath = BuildRehasedCAPath(caPath);
253     if (rehashedCertpath.empty()) {
254         return rehashedCertpath;
255     }
256 
257     for (auto &caFile: caFiles) {
258         auto x509 = ReadCertFile(caFile);
259         if (x509 == nullptr) {
260             continue;
261         }
262 
263         constexpr int X509_HASH_LEN = 16;
264         char buf[X509_HASH_LEN] = {0};
265         if (sprintf_s(buf, sizeof(buf), "%08lx", X509_subject_name_hash(x509)) < 0) {
266             return "";
267         }
268         X509_free(x509);
269         x509 = nullptr;
270 
271         std::string hashName(buf);
272         AddSurfixToCACertFileName(rehashedCertpath, allFiles, hashName);
273 
274         std::string rehashedCaFile = rehashedCertpath + OS_PATH_SEPARATOR + hashName;
275         if (access(rehashedCaFile.c_str(), F_OK) == 0) {
276             NETMGR_LOG_D("File [%{public}s] exists.", rehashedCaFile.c_str());
277             continue;
278         }
279 
280         std::ifstream src(caFile);
281         std::ofstream dst(rehashedCaFile);
282         if (!src.is_open() || !dst.is_open()) {
283             NETMGR_LOG_E("fail to open cert file.");
284             continue;
285         }
286         dst << src.rdbuf();
287         NETMGR_LOG_D("Rehased cert generated. [%{public}s]", rehashedCaFile.c_str());
288     }
289 
290     return rehashedCertpath;
291 }
292 
CreateRehashedCertFiles()293 int32_t NetworkSecurityConfig::CreateRehashedCertFiles()
294 {
295     for (auto &cert: baseConfig_.trustAnchors_.certs_) {
296             ReHashCAPathForX509(cert);
297         }
298     for (auto &domainConfig: domainConfigs_) {
299         for (auto &cert: domainConfig.trustAnchors_.certs_) {
300             ReHashCAPathForX509(cert);
301         }
302     }
303 
304     return NETMANAGER_SUCCESS;
305 }
306 
ValidateDate(const std::string & dateStr)307 bool NetworkSecurityConfig::ValidateDate(const std::string &dateStr)
308 {
309     return true;
310 }
311 
GetConfig()312 int32_t NetworkSecurityConfig::GetConfig()
313 {
314     std::string json;
315     auto ret = GetJsonFromBundle(json);
316     if (ret != NETMANAGER_SUCCESS) {
317         NETMGR_LOG_E("Failed to get json from bundler manager.");
318         return ret;
319     }
320 
321     ret = ParseJsonConfig(json);
322     if (ret != NETMANAGER_SUCCESS) {
323         return ret;
324     }
325 
326     ret = CreateRehashedCertFiles();
327     if (ret != NETMANAGER_SUCCESS) {
328         return ret;
329     }
330 
331     NETMGR_LOG_D("NetworkSecurityConfig Cached.");
332     return NETMANAGER_SUCCESS;
333 }
334 
GetJsonProfile()335 __attribute__((no_sanitize("cfi"))) std::string NetworkSecurityConfig::GetJsonProfile()
336 {
337     void *handler = dlopen(LIB_LOAD_PATH.c_str(), RTLD_LAZY | RTLD_NODELETE);
338     if (handler == nullptr) {
339         NETMGR_LOG_E("load failed, failed reason : %{public}s", dlerror());
340         return "";
341     }
342     GetNetBundleClass getNetBundle = (GetNetBundleClass)dlsym(handler, "GetNetBundle");
343     if (getNetBundle == nullptr) {
344         NETMGR_LOG_E("GetNetBundle faild, failed reason : %{public}s", dlerror());
345         dlclose(handler);
346         return "";
347     }
348     auto netBundle = getNetBundle();
349     if (netBundle == nullptr) {
350         NETMGR_LOG_E("netBundle is nullptr");
351         dlclose(handler);
352         return "";
353     }
354     std::string jsonProfile;
355     auto ret = netBundle->GetJsonFromBundle(jsonProfile);
356     if (ret != NETMANAGER_SUCCESS) {
357         NETMGR_LOG_E("get profile failed");
358         dlclose(handler);
359         return "";
360     }
361     NETMGR_LOG_D("get profile success");
362     dlclose(handler);
363     return jsonProfile;
364 }
365 
GetJsonFromBundle(std::string & jsonProfile)366 int32_t NetworkSecurityConfig::GetJsonFromBundle(std::string &jsonProfile)
367 {
368     static std::string json = GetJsonProfile();
369     if (json.empty()) {
370         return NETMANAGER_ERR_INTERNAL;
371     }
372     jsonProfile = json;
373     return NETMANAGER_SUCCESS;
374 }
375 
ParseJsonTrustAnchors(const Json::Value & root,TrustAnchors & trustAnchors)376 void NetworkSecurityConfig::ParseJsonTrustAnchors(const Json::Value &root, TrustAnchors &trustAnchors)
377 {
378     if (!root.isArray()) {
379         return;
380     }
381 
382     auto size = root.size();
383     for (uint32_t i = 0; i < size; i++) {
384         if (root[i].isMember(TAG_CERTIFICATES.c_str()) && root[i][TAG_CERTIFICATES.c_str()].isString()) {
385             auto cert_path = root[i][TAG_CERTIFICATES.c_str()].asString();
386             trustAnchors.certs_.push_back(cert_path);
387         }
388     }
389 
390     return;
391 }
392 
ParseJsonDomains(const Json::Value & root,std::vector<Domain> & domains)393 void NetworkSecurityConfig::ParseJsonDomains(const Json::Value &root, std::vector<Domain> &domains)
394 {
395     if (!root.isArray()) {
396         return;
397     }
398 
399     auto size = root.size();
400     for (uint32_t i = 0; i < size; i++) {
401         Domain domain;
402         if (!root[i].isMember(TAG_NAME.c_str()) || !root[i][TAG_NAME.c_str()].isString()) {
403             continue;
404         }
405         domain.domainName_ = root[i][TAG_NAME.c_str()].asString();
406 
407         if (root[i].isMember(TAG_INCLUDE_SUBDOMAINS.c_str()) && root[i][TAG_INCLUDE_SUBDOMAINS.c_str()].isBool()) {
408             domain.includeSubDomains_ = root[i][TAG_INCLUDE_SUBDOMAINS.c_str()].asBool();
409         } else {
410             domain.includeSubDomains_ = true;
411         }
412 
413         domains.push_back(domain);
414     }
415 
416     return;
417 }
418 
ParseJsonPinSet(const Json::Value & root,PinSet & pinSet)419 void NetworkSecurityConfig::ParseJsonPinSet(const Json::Value &root, PinSet &pinSet)
420 {
421     if (root.isNull()) {
422         return;
423     }
424 
425     if (root.isMember(TAG_EXPIRATION.c_str()) && root[TAG_EXPIRATION.c_str()].isString()) {
426         pinSet.expiration_ = root[TAG_EXPIRATION.c_str()].asString();
427     }
428 
429     if (!root.isMember(TAG_PIN.c_str()) || !root[TAG_PIN.c_str()].isArray()) {
430         return;
431     }
432 
433     auto pinRoot = root[TAG_PIN.c_str()];
434     auto size = pinRoot.size();
435     for (uint32_t i = 0; i < size; i++) {
436         if (pinRoot[i].isMember(TAG_DIGEST_ALGORITHM.c_str()) &&
437             pinRoot[i][TAG_DIGEST_ALGORITHM.c_str()].isString() &&
438             pinRoot[i].isMember(TAG_DIGEST.c_str()) &&
439             pinRoot[i][TAG_DIGEST.c_str()].isString()) {
440             Pin pin;
441             pin.digestAlgorithm_ = pinRoot[i][TAG_DIGEST_ALGORITHM.c_str()].asString();
442             pin.digest_ = pinRoot[i][TAG_DIGEST.c_str()].asString();
443             pinSet.pins_.push_back(pin);
444         }
445     }
446 
447     return;
448 }
449 
ParseJsonBaseConfig(const Json::Value & root,BaseConfig & baseConfig)450 void NetworkSecurityConfig::ParseJsonBaseConfig(const Json::Value &root, BaseConfig &baseConfig)
451 {
452     if (root.isNull()) {
453         return;
454     }
455     ParseJsonTrustAnchors(root[TAG_TRUST_ANCHORS.c_str()], baseConfig.trustAnchors_);
456 }
457 
ParseJsonDomainConfigs(const Json::Value & root,std::vector<DomainConfig> & domainConfigs)458 void NetworkSecurityConfig::ParseJsonDomainConfigs(const Json::Value &root, std::vector<DomainConfig> &domainConfigs)
459 {
460     if (!root.isArray()) {
461         return;
462     }
463 
464     auto size = root.size();
465     for (uint32_t i = 0; i < size; i++) {
466         DomainConfig domainConfig;
467         ParseJsonDomains(root[i][TAG_DOMAINS.c_str()], domainConfig.domains_);
468         ParseJsonTrustAnchors(root[i][TAG_TRUST_ANCHORS.c_str()], domainConfig.trustAnchors_);
469         ParseJsonPinSet(root[i][TAG_PIN_SET.c_str()], domainConfig.pinSet_);
470 
471         domainConfigs.push_back(domainConfig);
472     }
473 
474     return;
475 }
476 
ParseJsonConfig(const std::string & content)477 int32_t NetworkSecurityConfig::ParseJsonConfig(const std::string &content)
478 {
479     if (content.empty()) {
480         return NETMANAGER_SUCCESS;
481     }
482 
483     Json::Value root;
484     Json::CharReaderBuilder builder;
485     std::unique_ptr<Json::CharReader> reader(builder.newCharReader());
486     JSONCPP_STRING errs;
487 
488     bool isSuccess = reader->parse(content.c_str(), content.c_str() + content.length(), &root, &errs);
489     if (!isSuccess) {
490         NETMGR_LOG_E("Failed to parse network json profile.");
491         return NETMANAGER_ERR_INTERNAL;
492     }
493 
494     if (root.isNull() || !root.isMember(TAG_NETWORK_SECURITY_CONFIG.c_str())) {
495         return NETMANAGER_SUCCESS;
496     }
497 
498     ParseJsonBaseConfig(root[TAG_NETWORK_SECURITY_CONFIG.c_str()][TAG_BASE_CONFIG.c_str()], baseConfig_);
499 
500     ParseJsonDomainConfigs(root[TAG_NETWORK_SECURITY_CONFIG.c_str()][TAG_DOMAIN_CONFIG.c_str()], domainConfigs_);
501 
502     return NETMANAGER_SUCCESS;
503 }
504 
GetPinSetForHostName(const std::string & hostname,std::string & pins)505 int32_t NetworkSecurityConfig::GetPinSetForHostName(const std::string &hostname, std::string &pins)
506 {
507     if (hostname.empty()) {
508         NETMGR_LOG_E("Failed to get pinset, hostname is empty.");
509         return NETMANAGER_SUCCESS;
510     }
511 
512     PinSet *pPinSet = nullptr;
513     for (auto &domainConfig: domainConfigs_) {
514         for (const auto &domain: domainConfig.domains_) {
515             if (hostname == domain.domainName_) {
516                 pPinSet = &domainConfig.pinSet_;
517                 break;
518             } else if (domain.includeSubDomains_ && Endswith(hostname, domain.domainName_)) {
519                 pPinSet = &domainConfig.pinSet_;
520                 break;
521             }
522         }
523         if (pPinSet != nullptr) {
524             break;
525         }
526     }
527 
528     if (pPinSet == nullptr) {
529         NETMGR_LOG_D("No pinned pubkey configured.");
530         return NETMANAGER_SUCCESS;
531     }
532 
533     if (!ValidateDate(pPinSet->expiration_)) {
534         return NETMANAGER_ERR_PERMISSION_DENIED;
535     }
536 
537     std::stringstream ss;
538     for (const auto &pin: pPinSet->pins_) {
539         NETMGR_LOG_D("Got pinnned pubkey %{public}s", pin.digest_.c_str());
540         ss << pin.digestAlgorithm_ << "//" << pin.digest_ << ";";
541     }
542 
543     pins = ss.str();
544     if (!pins.empty()) {
545         pins.pop_back();
546     }
547 
548     return NETMANAGER_SUCCESS;
549 }
550 
GetTrustAnchorsForHostName(const std::string & hostname,std::vector<std::string> & certs)551 int32_t NetworkSecurityConfig::GetTrustAnchorsForHostName(const std::string &hostname, std::vector<std::string> &certs)
552 {
553     if (hostname.empty()) {
554         NETMGR_LOG_E("Failed to get trust anchors, hostname is empty.");
555         return NETMANAGER_SUCCESS;
556     }
557 
558     TrustAnchors *pTrustAnchors = nullptr;
559     for (auto &domainConfig: domainConfigs_) {
560         for (const auto &domain: domainConfig.domains_) {
561             if (hostname == domain.domainName_) {
562                 pTrustAnchors = &domainConfig.trustAnchors_;
563                 break;
564             } else if (domain.includeSubDomains_ && Endswith(hostname, domain.domainName_)) {
565                 pTrustAnchors = &domainConfig.trustAnchors_;
566                 break;
567             }
568         }
569         if (pTrustAnchors != nullptr) {
570             break;
571         }
572     }
573 
574     if (pTrustAnchors == nullptr) {
575         pTrustAnchors = &baseConfig_.trustAnchors_;
576     }
577 
578     for (auto &certPath: pTrustAnchors->certs_) {
579         auto rehashedCertpath = GetRehasedCAPath(certPath);
580         if (!rehashedCertpath.empty()) {
581             certs.push_back(rehashedCertpath);
582         }
583         NETMGR_LOG_D("Got cert [%{public}s] [%{public}s]", certPath.c_str(), rehashedCertpath.c_str());
584     }
585 
586     if (certs.empty()) {
587         NETMGR_LOG_D("No customized CA certs configured.");
588     }
589 
590     return NETMANAGER_SUCCESS;
591 }
592 
DumpConfigs()593 void NetworkSecurityConfig::DumpConfigs()
594 {
595     NETMGR_LOG_I("DumpConfigs:baseConfig_.trustAnchors_.certs");
596     for (auto &cert: baseConfig_.trustAnchors_.certs_) {
597         NETMGR_LOG_I("[%{public}s]", cert.c_str());
598     }
599 
600     NETMGR_LOG_I("DumpConfigs:domainConfigs_");
601     for (auto &domainConfig: domainConfigs_) {
602         NETMGR_LOG_I("=======================");
603         for (auto &domain: domainConfig.domains_) {
604             NETMGR_LOG_I("domainConfigs_.domains_[%{public}s][%{public}s]",
605                          domain.domainName_.c_str(),
606                          domain.includeSubDomains_ ? "include_subDomain" : "not_include_subDomain");
607         }
608         NETMGR_LOG_I("domainConfigs_.domains_.pinSet_.expiration_[%{public}s]",
609                      domainConfig.pinSet_.expiration_.c_str());
610         for (auto &pin: domainConfig.pinSet_.pins_) {
611             NETMGR_LOG_I("domainConfigs_.domains_.pinSet_.pins[%{public}s][%{public}s]",
612                          pin.digestAlgorithm_.c_str(), pin.digest_.c_str());
613         }
614         for (auto &cert: domainConfig.trustAnchors_.certs_) {
615             NETMGR_LOG_I("domainConfigs_.domains_.trustAnchors_.certs_[%{public}s]", cert.c_str());
616         }
617     }
618 }
619 
620 }
621 }
622