• 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 "dns_param_cache.h"
17 
18 #include <algorithm>
19 
20 #include "netmanager_base_common_utils.h"
21 
22 namespace OHOS::nmd {
23 using namespace OHOS::NetManagerStandard::CommonUtils;
24 namespace {
GetVectorData(const std::vector<std::string> & data,std::string & result)25 void GetVectorData(const std::vector<std::string> &data, std::string &result)
26 {
27     result.append("{ ");
28     std::for_each(data.begin(), data.end(), [&result](const auto &str) { result.append(ToAnonymousIp(str) + ", "); });
29     result.append("}\n");
30 }
31 constexpr int RES_TIMEOUT = 5000;    // min. milliseconds between retries
32 constexpr int RES_DEFAULT_RETRY = 2; // Default
33 } // namespace
34 
DnsParamCache()35 DnsParamCache::DnsParamCache() : defaultNetId_(0) {}
36 
GetInstance()37 DnsParamCache &DnsParamCache::GetInstance()
38 {
39     static DnsParamCache instance;
40     return instance;
41 }
42 
SelectNameservers(const std::vector<std::string> & servers)43 std::vector<std::string> DnsParamCache::SelectNameservers(const std::vector<std::string> &servers)
44 {
45     std::vector<std::string> res = servers;
46     if (res.size() > MAX_SERVER_NUM) {
47         res.resize(MAX_SERVER_NUM);
48     }
49     return res;
50 }
51 
CreateCacheForNet(uint16_t netId)52 int32_t DnsParamCache::CreateCacheForNet(uint16_t netId)
53 {
54     NETNATIVE_LOG_D("DnsParamCache::CreateCacheForNet, netid:%{public}d,", netId);
55     std::lock_guard<std::mutex> guard(cacheMutex_);
56     auto it = serverConfigMap_.find(netId);
57     if (it != serverConfigMap_.end()) {
58         NETNATIVE_LOGE("DnsParamCache::CreateCacheForNet, netid already exist, no need to create");
59         return -EEXIST;
60     }
61     serverConfigMap_[netId].SetNetId(netId);
62     return 0;
63 }
64 
DestroyNetworkCache(uint16_t netId)65 int32_t DnsParamCache::DestroyNetworkCache(uint16_t netId)
66 {
67     NETNATIVE_LOG_D("DnsParamCache::CreateCacheForNet, netid:%{public}d,", netId);
68     std::lock_guard<std::mutex> guard(cacheMutex_);
69     auto it = serverConfigMap_.find(netId);
70     if (it == serverConfigMap_.end()) {
71         return -ENOENT;
72     }
73     serverConfigMap_.erase(it);
74     if (defaultNetId_ == netId) {
75         defaultNetId_ = 0;
76     }
77     return 0;
78 }
79 
SetResolverConfig(uint16_t netId,uint16_t baseTimeoutMsec,uint8_t retryCount,const std::vector<std::string> & servers,const std::vector<std::string> & domains)80 int32_t DnsParamCache::SetResolverConfig(uint16_t netId, uint16_t baseTimeoutMsec, uint8_t retryCount,
81                                          const std::vector<std::string> &servers,
82                                          const std::vector<std::string> &domains)
83 {
84     std::vector<std::string> nameservers = SelectNameservers(servers);
85     NETNATIVE_LOG_D("DnsParamCache::SetResolverConfig, netid:%{public}d, numServers:%{public}d,", netId,
86                     static_cast<int>(nameservers.size()));
87 
88     std::lock_guard<std::mutex> guard(cacheMutex_);
89 
90     // select_domains
91     auto it = serverConfigMap_.find(netId);
92     if (it == serverConfigMap_.end()) {
93         NETNATIVE_LOGE("DnsParamCache::SetResolverConfig failed, netid is non-existent");
94         return -ENOENT;
95     }
96 
97     auto oldDnsServers = it->second.GetServers();
98     std::sort(oldDnsServers.begin(), oldDnsServers.end());
99 
100     auto newDnsServers = servers;
101     std::sort(newDnsServers.begin(), newDnsServers.end());
102 
103     if (oldDnsServers != newDnsServers) {
104         it->second.GetCache().Clear();
105     }
106 
107     it->second.SetNetId(netId);
108     it->second.SetServers(servers);
109     it->second.SetDomains(domains);
110     if (retryCount == 0) {
111         it->second.SetRetryCount(RES_DEFAULT_RETRY);
112     } else {
113         it->second.SetRetryCount(retryCount);
114     }
115     if (baseTimeoutMsec == 0) {
116         it->second.SetTimeoutMsec(RES_TIMEOUT);
117     } else {
118         it->second.SetTimeoutMsec(baseTimeoutMsec);
119     }
120     return 0;
121 }
122 
SetDefaultNetwork(uint16_t netId)123 void DnsParamCache::SetDefaultNetwork(uint16_t netId)
124 {
125     defaultNetId_ = netId;
126 }
127 
EnableIpv6(uint16_t netId)128 void DnsParamCache::EnableIpv6(uint16_t netId)
129 {
130     std::lock_guard<std::mutex> guard(cacheMutex_);
131     auto it = serverConfigMap_.find(netId);
132     if (it == serverConfigMap_.end()) {
133         DNS_CONFIG_PRINT("get Config failed: netid is not have netid:%{public}d,", netId);
134         return;
135     }
136 
137     it->second.EnableIpv6();
138 }
139 
IsIpv6Enable(uint16_t netId)140 bool DnsParamCache::IsIpv6Enable(uint16_t netId)
141 {
142     if (netId == 0) {
143         netId = defaultNetId_;
144     }
145 
146     std::lock_guard<std::mutex> guard(cacheMutex_);
147     auto it = serverConfigMap_.find(netId);
148     if (it == serverConfigMap_.end()) {
149         DNS_CONFIG_PRINT("get Config failed: netid is not have netid:%{public}d,", netId);
150         return false;
151     }
152 
153     return it->second.IsIpv6Enable();
154 }
155 
GetResolverConfig(uint16_t netId,std::vector<std::string> & servers,std::vector<std::string> & domains,uint16_t & baseTimeoutMsec,uint8_t & retryCount)156 int32_t DnsParamCache::GetResolverConfig(uint16_t netId, std::vector<std::string> &servers,
157                                          std::vector<std::string> &domains, uint16_t &baseTimeoutMsec,
158                                          uint8_t &retryCount)
159 {
160     if (netId == 0) {
161         netId = defaultNetId_;
162     }
163 
164     std::lock_guard<std::mutex> guard(cacheMutex_);
165     auto it = serverConfigMap_.find(netId);
166     if (it == serverConfigMap_.end()) {
167         DNS_CONFIG_PRINT("get Config failed: netid is not have netid:%{public}d,", netId);
168         return -ENOENT;
169     }
170 
171     servers = it->second.GetServers();
172     domains = it->second.GetDomains();
173     baseTimeoutMsec = it->second.GetTimeoutMsec();
174     retryCount = it->second.GetRetryCount();
175 
176     return 0;
177 }
178 
GetDefaultNetwork() const179 int32_t DnsParamCache::GetDefaultNetwork() const
180 {
181     return defaultNetId_;
182 }
183 
SetDnsCache(uint16_t netId,const std::string & hostName,const AddrInfo & addrInfo)184 void DnsParamCache::SetDnsCache(uint16_t netId, const std::string &hostName, const AddrInfo &addrInfo)
185 {
186     if (netId == 0) {
187         netId = defaultNetId_;
188     }
189     std::lock_guard<std::mutex> guard(cacheMutex_);
190     auto it = serverConfigMap_.find(netId);
191     if (it == serverConfigMap_.end()) {
192         DNS_CONFIG_PRINT("SetDnsCache failed: netid is not have netid:%{public}d,", netId);
193         return;
194     }
195 
196     it->second.GetCache().Put(hostName, addrInfo);
197 }
198 
GetDnsCache(uint16_t netId,const std::string & hostName)199 std::vector<AddrInfo> DnsParamCache::GetDnsCache(uint16_t netId, const std::string &hostName)
200 {
201     if (netId == 0) {
202         netId = defaultNetId_;
203     }
204 
205     std::lock_guard<std::mutex> guard(cacheMutex_);
206     auto it = serverConfigMap_.find(netId);
207     if (it == serverConfigMap_.end()) {
208         DNS_CONFIG_PRINT("GetDnsCache failed: netid is not have netid:%{public}d,", netId);
209         return {};
210     }
211 
212     return it->second.GetCache().Get(hostName);
213 }
214 
SetCacheDelayed(uint16_t netId,const std::string & hostName)215 void DnsParamCache::SetCacheDelayed(uint16_t netId, const std::string &hostName)
216 {
217     if (netId == 0) {
218         netId = defaultNetId_;
219     }
220 
221     std::lock_guard<std::mutex> guard(cacheMutex_);
222     auto it = serverConfigMap_.find(netId);
223     if (it == serverConfigMap_.end()) {
224         DNS_CONFIG_PRINT("SetCacheDelayed failed: netid is not have netid:%{public}d,", netId);
225         return;
226     }
227 
228     it->second.SetCacheDelayed(hostName);
229 }
230 
GetDumpInfo(std::string & info)231 void DnsParamCache::GetDumpInfo(std::string &info)
232 {
233     std::string dnsData;
234     static const std::string TAB = "  ";
235     std::for_each(serverConfigMap_.begin(), serverConfigMap_.end(), [&dnsData](const auto &serverConfig) {
236         dnsData.append(TAB + "NetId: " + std::to_string(serverConfig.second.GetNetId()) + "\n");
237         dnsData.append(TAB + "TimeoutMsec: " + std::to_string(serverConfig.second.GetTimeoutMsec()) + "\n");
238         dnsData.append(TAB + "RetryCount: " + std::to_string(serverConfig.second.GetRetryCount()) + "\n");
239         dnsData.append(TAB + "Servers:");
240         GetVectorData(serverConfig.second.GetServers(), dnsData);
241         dnsData.append(TAB + "Domains:");
242         GetVectorData(serverConfig.second.GetDomains(), dnsData);
243     });
244     info.append(dnsData);
245 }
246 } // namespace OHOS::nmd
247