1b1b8bc3fSopenharmony_ci/*
2b1b8bc3fSopenharmony_ci * Copyright (c) 2022-2023 Huawei Device Co., Ltd.
3b1b8bc3fSopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
4b1b8bc3fSopenharmony_ci * you may not use this file except in compliance with the License.
5b1b8bc3fSopenharmony_ci * You may obtain a copy of the License at
6b1b8bc3fSopenharmony_ci *
7b1b8bc3fSopenharmony_ci *     http://www.apache.org/licenses/LICENSE-2.0
8b1b8bc3fSopenharmony_ci *
9b1b8bc3fSopenharmony_ci * Unless required by applicable law or agreed to in writing, software
10b1b8bc3fSopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
11b1b8bc3fSopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12b1b8bc3fSopenharmony_ci * See the License for the specific language governing permissions and
13b1b8bc3fSopenharmony_ci * limitations under the License.
14b1b8bc3fSopenharmony_ci */
15b1b8bc3fSopenharmony_ci
16b1b8bc3fSopenharmony_ci#include <pthread.h>
17b1b8bc3fSopenharmony_ci#include <thread>
18b1b8bc3fSopenharmony_ci
19b1b8bc3fSopenharmony_ci#include "dns_resolv_listen.h"
20b1b8bc3fSopenharmony_ci#include "netmanager_base_common_utils.h"
21b1b8bc3fSopenharmony_ci#include "netnative_log_wrapper.h"
22b1b8bc3fSopenharmony_ci#include "singleton.h"
23b1b8bc3fSopenharmony_ci#include "dns_quality_diag.h"
24b1b8bc3fSopenharmony_ci
25b1b8bc3fSopenharmony_ci#include "dns_manager.h"
26b1b8bc3fSopenharmony_ci#include <netdb.h>
27b1b8bc3fSopenharmony_ci
28b1b8bc3fSopenharmony_cinamespace OHOS {
29b1b8bc3fSopenharmony_cinamespace nmd {
30b1b8bc3fSopenharmony_ciusing namespace OHOS::NetManagerStandard::CommonUtils;
31b1b8bc3fSopenharmony_ci
32b1b8bc3fSopenharmony_civoid StartListen()
33b1b8bc3fSopenharmony_ci{
34b1b8bc3fSopenharmony_ci    NETNATIVE_LOG_D("Enter threadStart");
35b1b8bc3fSopenharmony_ci    DnsResolvListen().StartListen();
36b1b8bc3fSopenharmony_ci}
37b1b8bc3fSopenharmony_ci
38b1b8bc3fSopenharmony_ciDnsManager::DnsManager() : dnsProxyListen_(std::make_shared<DnsProxyListen>())
39b1b8bc3fSopenharmony_ci{
40b1b8bc3fSopenharmony_ci    std::thread t(StartListen);
41b1b8bc3fSopenharmony_ci    std::string threadName = "DnsMgerListen";
42b1b8bc3fSopenharmony_ci    pthread_setname_np(t.native_handle(), threadName.c_str());
43b1b8bc3fSopenharmony_ci    t.detach();
44b1b8bc3fSopenharmony_ci}
45b1b8bc3fSopenharmony_ci
46b1b8bc3fSopenharmony_civoid DnsManager::EnableIpv6(uint16_t netId, std::string &destination, const std::string &nextHop)
47b1b8bc3fSopenharmony_ci{
48b1b8bc3fSopenharmony_ci    auto pos = destination.find("/");
49b1b8bc3fSopenharmony_ci    if (pos != std::string::npos) {
50b1b8bc3fSopenharmony_ci        destination = destination.substr(0, pos);
51b1b8bc3fSopenharmony_ci    }
52b1b8bc3fSopenharmony_ci    if (!(IsValidIPV6(destination) && (IsValidIPV6(nextHop) || nextHop.empty()))) {
53b1b8bc3fSopenharmony_ci        NETNATIVE_LOGE("check IsValidIPV6 faild");
54b1b8bc3fSopenharmony_ci        return;
55b1b8bc3fSopenharmony_ci    }
56b1b8bc3fSopenharmony_ci    DnsParamCache::GetInstance().EnableIpv6(netId);
57b1b8bc3fSopenharmony_ci}
58b1b8bc3fSopenharmony_ci
59b1b8bc3fSopenharmony_ciint32_t DnsManager::SetResolverConfig(uint16_t netId, uint16_t baseTimeoutMillis, uint8_t retryCount,
60b1b8bc3fSopenharmony_ci                                      const std::vector<std::string> &servers, const std::vector<std::string> &domains)
61b1b8bc3fSopenharmony_ci{
62b1b8bc3fSopenharmony_ci    NETNATIVE_LOG_D("manager_SetResolverConfig netId[%{public}d]", netId);
63b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().SetResolverConfig(netId, baseTimeoutMillis, retryCount, servers, domains);
64b1b8bc3fSopenharmony_ci}
65b1b8bc3fSopenharmony_ci
66b1b8bc3fSopenharmony_ciint32_t DnsManager::GetResolverConfig(uint16_t netId, std::vector<std::string> &servers,
67b1b8bc3fSopenharmony_ci                                      std::vector<std::string> &domains, uint16_t &baseTimeoutMillis,
68b1b8bc3fSopenharmony_ci                                      uint8_t &retryCount)
69b1b8bc3fSopenharmony_ci{
70b1b8bc3fSopenharmony_ci    NETNATIVE_LOG_D("manager_GetResolverConfig netId[%{public}d]", netId);
71b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().GetResolverConfig(netId, servers, domains, baseTimeoutMillis, retryCount);
72b1b8bc3fSopenharmony_ci}
73b1b8bc3fSopenharmony_ci
74b1b8bc3fSopenharmony_ciint32_t DnsManager::CreateNetworkCache(uint16_t netId)
75b1b8bc3fSopenharmony_ci{
76b1b8bc3fSopenharmony_ci    NETNATIVE_LOG_D("manager_CreateNetworkCache netId[%{public}d]", netId);
77b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().CreateCacheForNet(netId);
78b1b8bc3fSopenharmony_ci}
79b1b8bc3fSopenharmony_ci
80b1b8bc3fSopenharmony_ciint32_t DnsManager::DestroyNetworkCache(uint16_t netId)
81b1b8bc3fSopenharmony_ci{
82b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().DestroyNetworkCache(netId);
83b1b8bc3fSopenharmony_ci}
84b1b8bc3fSopenharmony_ci
85b1b8bc3fSopenharmony_civoid DnsManager::SetDefaultNetwork(uint16_t netId)
86b1b8bc3fSopenharmony_ci{
87b1b8bc3fSopenharmony_ci    DnsParamCache::GetInstance().SetDefaultNetwork(netId);
88b1b8bc3fSopenharmony_ci}
89b1b8bc3fSopenharmony_ci
90b1b8bc3fSopenharmony_civoid StartProxyListen()
91b1b8bc3fSopenharmony_ci{
92b1b8bc3fSopenharmony_ci    NETNATIVE_LOG_D("begin StartProxyListen");
93b1b8bc3fSopenharmony_ci    DnsProxyListen().StartListen();
94b1b8bc3fSopenharmony_ci}
95b1b8bc3fSopenharmony_ci
96b1b8bc3fSopenharmony_civoid DnsManager::ShareDnsSet(uint16_t netId)
97b1b8bc3fSopenharmony_ci{
98b1b8bc3fSopenharmony_ci    dnsProxyListen_->SetParseNetId(netId);
99b1b8bc3fSopenharmony_ci}
100b1b8bc3fSopenharmony_ci
101b1b8bc3fSopenharmony_civoid DnsManager::StartDnsProxyListen()
102b1b8bc3fSopenharmony_ci{
103b1b8bc3fSopenharmony_ci    dnsProxyListen_->OnListen();
104b1b8bc3fSopenharmony_ci    std::thread t(StartProxyListen);
105b1b8bc3fSopenharmony_ci    std::string threadName = "DnsPxyListen";
106b1b8bc3fSopenharmony_ci    pthread_setname_np(t.native_handle(), threadName.c_str());
107b1b8bc3fSopenharmony_ci    t.detach();
108b1b8bc3fSopenharmony_ci}
109b1b8bc3fSopenharmony_ci
110b1b8bc3fSopenharmony_civoid DnsManager::StopDnsProxyListen()
111b1b8bc3fSopenharmony_ci{
112b1b8bc3fSopenharmony_ci    dnsProxyListen_->OffListen();
113b1b8bc3fSopenharmony_ci}
114b1b8bc3fSopenharmony_ci
115b1b8bc3fSopenharmony_civoid DnsManager::GetDumpInfo(std::string &info)
116b1b8bc3fSopenharmony_ci{
117b1b8bc3fSopenharmony_ci    NETNATIVE_LOG_D("Get dump info");
118b1b8bc3fSopenharmony_ci    DnsParamCache::GetInstance().GetDumpInfo(info);
119b1b8bc3fSopenharmony_ci}
120b1b8bc3fSopenharmony_ci
121b1b8bc3fSopenharmony_ciint32_t DnsManager::GetAddrInfo(const std::string &hostName, const std::string &serverName, const AddrInfo &hints,
122b1b8bc3fSopenharmony_ci                                uint16_t netId, std::vector<AddrInfo> &res)
123b1b8bc3fSopenharmony_ci{
124b1b8bc3fSopenharmony_ci    if (netId == 0) {
125b1b8bc3fSopenharmony_ci        netId = DnsParamCache::GetInstance().GetDefaultNetwork();
126b1b8bc3fSopenharmony_ci        NETNATIVE_LOG_D("DnsManager DnsGetaddrinfo netId == 0 defaultNetId_ : %{public}d", netId);
127b1b8bc3fSopenharmony_ci    }
128b1b8bc3fSopenharmony_ci    struct addrinfo hint = {};
129b1b8bc3fSopenharmony_ci    struct addrinfo *result;
130b1b8bc3fSopenharmony_ci    struct queryparam qparam = {};
131b1b8bc3fSopenharmony_ci
132b1b8bc3fSopenharmony_ci    if ((hostName.size() == 0) && (serverName.size() == 0)) {
133b1b8bc3fSopenharmony_ci        return -1;
134b1b8bc3fSopenharmony_ci    }
135b1b8bc3fSopenharmony_ci
136b1b8bc3fSopenharmony_ci    qparam.qp_netid = netId;
137b1b8bc3fSopenharmony_ci    qparam.qp_type = 1;
138b1b8bc3fSopenharmony_ci
139b1b8bc3fSopenharmony_ci    hint.ai_family = hints.aiFamily;
140b1b8bc3fSopenharmony_ci    hint.ai_flags = hints.aiFlags;
141b1b8bc3fSopenharmony_ci    hint.ai_protocol = hints.aiProtocol;
142b1b8bc3fSopenharmony_ci    hint.ai_socktype = hints.aiSockType;
143b1b8bc3fSopenharmony_ci
144b1b8bc3fSopenharmony_ci    int32_t ret = getaddrinfo_ext(((hostName.size() == 0) ? NULL : hostName.c_str()),
145b1b8bc3fSopenharmony_ci                                  ((serverName.size() == 0) ? NULL : serverName.c_str()),
146b1b8bc3fSopenharmony_ci                                  &hint, &result, &qparam);
147b1b8bc3fSopenharmony_ci    if (ret == 0) {
148b1b8bc3fSopenharmony_ci        ret = FillAddrInfo(res, result);
149b1b8bc3fSopenharmony_ci        freeaddrinfo(result);
150b1b8bc3fSopenharmony_ci    }
151b1b8bc3fSopenharmony_ci
152b1b8bc3fSopenharmony_ci    return ret;
153b1b8bc3fSopenharmony_ci}
154b1b8bc3fSopenharmony_ci
155b1b8bc3fSopenharmony_ciint32_t DnsManager::RegisterDnsResultCallback(const sptr<NetsysNative::INetDnsResultCallback> &callback,
156b1b8bc3fSopenharmony_ci                                              uint32_t timeStep)
157b1b8bc3fSopenharmony_ci{
158b1b8bc3fSopenharmony_ci    return DnsQualityDiag::GetInstance().RegisterResultListener(callback, timeStep);
159b1b8bc3fSopenharmony_ci}
160b1b8bc3fSopenharmony_ci
161b1b8bc3fSopenharmony_ciint32_t DnsManager::UnregisterDnsResultCallback(const sptr<NetsysNative::INetDnsResultCallback> &callback)
162b1b8bc3fSopenharmony_ci{
163b1b8bc3fSopenharmony_ci    return DnsQualityDiag::GetInstance().UnregisterResultListener(callback);
164b1b8bc3fSopenharmony_ci}
165b1b8bc3fSopenharmony_ci
166b1b8bc3fSopenharmony_ciint32_t DnsManager::RegisterDnsHealthCallback(const sptr<NetsysNative::INetDnsHealthCallback> &callback)
167b1b8bc3fSopenharmony_ci{
168b1b8bc3fSopenharmony_ci    return DnsQualityDiag::GetInstance().RegisterHealthListener(callback);
169b1b8bc3fSopenharmony_ci}
170b1b8bc3fSopenharmony_ci
171b1b8bc3fSopenharmony_ciint32_t DnsManager::UnregisterDnsHealthCallback(const sptr<NetsysNative::INetDnsHealthCallback> &callback)
172b1b8bc3fSopenharmony_ci{
173b1b8bc3fSopenharmony_ci    return DnsQualityDiag::GetInstance().UnregisterHealthListener(callback);
174b1b8bc3fSopenharmony_ci}
175b1b8bc3fSopenharmony_ci
176b1b8bc3fSopenharmony_ciint32_t DnsManager::AddUidRange(int32_t netId, const std::vector<NetManagerStandard::UidRange> &uidRanges)
177b1b8bc3fSopenharmony_ci{
178b1b8bc3fSopenharmony_ci    NETNATIVE_LOG_D("DnsManager::AddUidRange");
179b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().AddUidRange(netId, uidRanges);
180b1b8bc3fSopenharmony_ci}
181b1b8bc3fSopenharmony_ci
182b1b8bc3fSopenharmony_ciint32_t DnsManager::DelUidRange(int32_t netId, const std::vector<NetManagerStandard::UidRange> &uidRanges)
183b1b8bc3fSopenharmony_ci{
184b1b8bc3fSopenharmony_ci    NETNATIVE_LOG_D("DnsManager::DelUidRange");
185b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().DelUidRange(netId, uidRanges);
186b1b8bc3fSopenharmony_ci}
187b1b8bc3fSopenharmony_ci
188b1b8bc3fSopenharmony_ciint32_t DnsManager::FillAddrInfo(std::vector<AddrInfo> &addrInfo, addrinfo *res)
189b1b8bc3fSopenharmony_ci{
190b1b8bc3fSopenharmony_ci    int32_t resNum = 0;
191b1b8bc3fSopenharmony_ci    addrinfo *tmp = res;
192b1b8bc3fSopenharmony_ci
193b1b8bc3fSopenharmony_ci    while (tmp) {
194b1b8bc3fSopenharmony_ci        AddrInfo info;
195b1b8bc3fSopenharmony_ci        info.aiFlags = static_cast<int32_t>(tmp->ai_flags);
196b1b8bc3fSopenharmony_ci        info.aiFamily = static_cast<int32_t>(tmp->ai_family);
197b1b8bc3fSopenharmony_ci        info.aiSockType = static_cast<int32_t>(tmp->ai_socktype);
198b1b8bc3fSopenharmony_ci        info.aiProtocol = static_cast<int32_t>(tmp->ai_protocol);
199b1b8bc3fSopenharmony_ci        info.aiAddrLen = tmp->ai_addrlen;
200b1b8bc3fSopenharmony_ci        if (memcpy_s(&info.aiAddr, sizeof(info.aiAddr), tmp->ai_addr, tmp->ai_addrlen) != 0) {
201b1b8bc3fSopenharmony_ci            NETNATIVE_LOGE("memcpy_s failed");
202b1b8bc3fSopenharmony_ci        }
203b1b8bc3fSopenharmony_ci        if (strcpy_s(info.aiCanonName, sizeof(info.aiCanonName), tmp->ai_canonname) != 0) {
204b1b8bc3fSopenharmony_ci            NETNATIVE_LOGE("strcpy_s failed");
205b1b8bc3fSopenharmony_ci        }
206b1b8bc3fSopenharmony_ci
207b1b8bc3fSopenharmony_ci        ++resNum;
208b1b8bc3fSopenharmony_ci        addrInfo.emplace_back(info);
209b1b8bc3fSopenharmony_ci        tmp = tmp->ai_next;
210b1b8bc3fSopenharmony_ci        if (resNum >= MAX_RESULTS) {
211b1b8bc3fSopenharmony_ci            break;
212b1b8bc3fSopenharmony_ci        }
213b1b8bc3fSopenharmony_ci    }
214b1b8bc3fSopenharmony_ci    NETNATIVE_LOGI("FillAddrInfo %{public}d", resNum);
215b1b8bc3fSopenharmony_ci    return 0;
216b1b8bc3fSopenharmony_ci}
217b1b8bc3fSopenharmony_ci
218b1b8bc3fSopenharmony_ci#ifdef FEATURE_NET_FIREWALL_ENABLE
219b1b8bc3fSopenharmony_ciint32_t DnsManager::SetFirewallDefaultAction(FirewallRuleAction inDefault, FirewallRuleAction outDefault)
220b1b8bc3fSopenharmony_ci{
221b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().SetFirewallDefaultAction(inDefault, outDefault);
222b1b8bc3fSopenharmony_ci}
223b1b8bc3fSopenharmony_ci
224b1b8bc3fSopenharmony_ciint32_t DnsManager::SetFirewallCurrentUserId(int32_t userId)
225b1b8bc3fSopenharmony_ci{
226b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().SetFirewallCurrentUserId(userId);
227b1b8bc3fSopenharmony_ci}
228b1b8bc3fSopenharmony_ci
229b1b8bc3fSopenharmony_ciint32_t DnsManager::SetFirewallRules(NetFirewallRuleType type, const std::vector<sptr<NetFirewallBaseRule>> &ruleList,
230b1b8bc3fSopenharmony_ci                                     bool isFinish)
231b1b8bc3fSopenharmony_ci{
232b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().SetFirewallRules(type, ruleList, isFinish);
233b1b8bc3fSopenharmony_ci}
234b1b8bc3fSopenharmony_ci
235b1b8bc3fSopenharmony_ciint32_t DnsManager::ClearFirewallRules(NetFirewallRuleType type)
236b1b8bc3fSopenharmony_ci{
237b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().ClearFirewallRules(type);
238b1b8bc3fSopenharmony_ci}
239b1b8bc3fSopenharmony_ci
240b1b8bc3fSopenharmony_ciint32_t DnsManager::RegisterNetFirewallCallback(const sptr<NetsysNative::INetFirewallCallback> &callback)
241b1b8bc3fSopenharmony_ci{
242b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().RegisterNetFirewallCallback(callback);
243b1b8bc3fSopenharmony_ci}
244b1b8bc3fSopenharmony_ciint32_t DnsManager::UnRegisterNetFirewallCallback(const sptr<NetsysNative::INetFirewallCallback> &callback)
245b1b8bc3fSopenharmony_ci{
246b1b8bc3fSopenharmony_ci    return DnsParamCache::GetInstance().UnRegisterNetFirewallCallback(callback);
247b1b8bc3fSopenharmony_ci}
248b1b8bc3fSopenharmony_ci#endif
249b1b8bc3fSopenharmony_ci} // namespace nmd
250b1b8bc3fSopenharmony_ci} // namespace OHOS
251