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 "networkvpn_client.h"
17
18 #include <thread>
19
20 #include "fwmark_client.h"
21 #include "iservice_registry.h"
22 #include "net_manager_constants.h"
23 #include "netmgr_ext_log_wrapper.h"
24 #include "system_ability_definition.h"
25
26 namespace OHOS {
27 namespace NetManagerStandard {
28
29 static constexpr uint32_t WAIT_FOR_SERVICE_TIME_MS = 500;
30 static constexpr uint32_t MAX_GET_SERVICE_COUNT = 10;
31
OnVpnMultiUserSetUp()32 void VpnSetUpEventCallback::OnVpnMultiUserSetUp()
33 {
34 NETMGR_EXT_LOG_I("vpn multiple user setup event.");
35 NetworkVpnClient::GetInstance().multiUserSetUpEvent();
36 }
37
GetInstance()38 NetworkVpnClient &NetworkVpnClient::GetInstance()
39 {
40 static NetworkVpnClient instance;
41 return instance;
42 }
43
Prepare(bool & isExistVpn,bool & isRun,std::string & pkg)44 int32_t NetworkVpnClient::Prepare(bool &isExistVpn, bool &isRun, std::string &pkg)
45 {
46 sptr<INetworkVpnService> proxy = GetProxy();
47 if (proxy == nullptr) {
48 NETMGR_EXT_LOG_E("Prepare proxy is nullptr");
49 return NETMANAGER_EXT_ERR_GET_PROXY_FAIL;
50 }
51 return proxy->Prepare(isExistVpn, isRun, pkg);
52 }
53
Protect(int32_t socketFd,bool isVpnExtCall)54 int32_t NetworkVpnClient::Protect(int32_t socketFd, bool isVpnExtCall)
55 {
56 if (socketFd <= 0) {
57 NETMGR_EXT_LOG_E("Invalid socket file discriptor");
58 return NETWORKVPN_ERROR_INVALID_FD;
59 }
60
61 sptr<INetworkVpnService> proxy = GetProxy();
62 if (proxy == nullptr) {
63 NETMGR_EXT_LOG_E("Protect proxy is nullptr");
64 return NETMANAGER_EXT_ERR_GET_PROXY_FAIL;
65 }
66 int32_t result = proxy->Protect(isVpnExtCall);
67 if (result != NETMANAGER_EXT_SUCCESS) {
68 return result;
69 }
70 nmd::FwmarkClient fwmarkClient;
71 return fwmarkClient.ProtectFromVpn(socketFd);
72 }
73
SetUpVpn(sptr<VpnConfig> config,int32_t & tunFd,bool isVpnExtCall)74 int32_t NetworkVpnClient::SetUpVpn(sptr<VpnConfig> config, int32_t &tunFd, bool isVpnExtCall)
75 {
76 if (config == nullptr) {
77 NETMGR_EXT_LOG_E("SetUpVpn param config is nullptr");
78 return NETMANAGER_EXT_ERR_PARAMETER_ERROR;
79 }
80
81 sptr<INetworkVpnService> proxy = GetProxy();
82 if (proxy == nullptr) {
83 NETMGR_EXT_LOG_E("SetUpVpn proxy is nullptr");
84 return NETMANAGER_EXT_ERR_GET_PROXY_FAIL;
85 }
86 NETMGR_EXT_LOG_I("enter SetUpVpn 1, %{public}d", isVpnExtCall);
87 int32_t result = proxy->SetUpVpn(config, isVpnExtCall);
88 if (result != NETMANAGER_EXT_SUCCESS) {
89 tunFd = 0;
90 return result;
91 }
92
93 tunFd = vpnInterface_.GetVpnInterfaceFd();
94 if (tunFd <= 0) {
95 return NETMANAGER_EXT_ERR_INTERNAL;
96 }
97
98 if (vpnEventCallback_ != nullptr) {
99 UnregisterVpnEvent(vpnEventCallback_);
100 }
101 vpnEventCallback_ = new (std::nothrow) VpnSetUpEventCallback();
102 if (vpnEventCallback_ == nullptr) {
103 NETMGR_EXT_LOG_E("vpnEventCallback_ is nullptr");
104 return NETMANAGER_EXT_ERR_INTERNAL;
105 }
106 RegisterVpnEvent(vpnEventCallback_);
107 return NETMANAGER_EXT_SUCCESS;
108 }
109
DestroyVpn(bool isVpnExtCall)110 int32_t NetworkVpnClient::DestroyVpn(bool isVpnExtCall)
111 {
112 vpnInterface_.CloseVpnInterfaceFd();
113 if (vpnEventCallback_ != nullptr) {
114 UnregisterVpnEvent(vpnEventCallback_);
115 vpnEventCallback_ = nullptr;
116 }
117
118 sptr<INetworkVpnService> proxy = GetProxy();
119 if (proxy == nullptr) {
120 NETMGR_EXT_LOG_E("DestroyVpn proxy is nullptr");
121 return NETMANAGER_EXT_ERR_GET_PROXY_FAIL;
122 }
123 return proxy->DestroyVpn(isVpnExtCall);
124 }
125
RegisterVpnEvent(sptr<IVpnEventCallback> callback)126 int32_t NetworkVpnClient::RegisterVpnEvent(sptr<IVpnEventCallback> callback)
127 {
128 if (callback == nullptr) {
129 NETMGR_EXT_LOG_E("RegisterVpnEvent callback is null.");
130 return NETMANAGER_EXT_ERR_PARAMETER_ERROR;
131 }
132 sptr<INetworkVpnService> proxy = GetProxy();
133 if (proxy == nullptr) {
134 NETMGR_EXT_LOG_E("RegisterVpnEvent proxy is nullptr");
135 return NETMANAGER_EXT_ERR_GET_PROXY_FAIL;
136 }
137 return proxy->RegisterVpnEvent(callback);
138 }
139
UnregisterVpnEvent(sptr<IVpnEventCallback> callback)140 int32_t NetworkVpnClient::UnregisterVpnEvent(sptr<IVpnEventCallback> callback)
141 {
142 if (callback == nullptr) {
143 NETMGR_EXT_LOG_E("UnregisterVpnEvent callback is null.");
144 return NETMANAGER_EXT_ERR_PARAMETER_ERROR;
145 }
146 sptr<INetworkVpnService> proxy = GetProxy();
147 if (proxy == nullptr) {
148 NETMGR_EXT_LOG_E("UnregisterVpnEvent proxy is nullptr");
149 return NETMANAGER_EXT_ERR_GET_PROXY_FAIL;
150 }
151 return proxy->UnregisterVpnEvent(callback);
152 }
153
CreateVpnConnection(bool isVpnExtCall)154 int32_t NetworkVpnClient::CreateVpnConnection(bool isVpnExtCall)
155 {
156 sptr<INetworkVpnService> proxy = GetProxy();
157 if (proxy == nullptr) {
158 NETMGR_EXT_LOG_E("CreateVpnConnection proxy is nullptr");
159 return NETMANAGER_EXT_ERR_GET_PROXY_FAIL;
160 }
161 return proxy->CreateVpnConnection(isVpnExtCall);
162 }
163
GetProxy()164 sptr<INetworkVpnService> NetworkVpnClient::GetProxy()
165 {
166 std::lock_guard lock(mutex_);
167 if (networkVpnService_ != nullptr) {
168 return networkVpnService_;
169 }
170 sptr<ISystemAbilityManager> sam = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
171 if (sam == nullptr) {
172 NETMGR_EXT_LOG_E("get SystemAbilityManager failed");
173 return nullptr;
174 }
175 sptr<IRemoteObject> remote = sam->CheckSystemAbility(COMM_VPN_MANAGER_SYS_ABILITY_ID);
176 if (remote == nullptr) {
177 NETMGR_EXT_LOG_E("get Remote vpn service failed");
178 return nullptr;
179 }
180 deathRecipient_ = new (std::nothrow) MonitorVpnServiceDead(*this);
181 if (deathRecipient_ == nullptr) {
182 NETMGR_EXT_LOG_E("deathRecipient_ is nullptr");
183 return nullptr;
184 }
185 if ((remote->IsProxyObject()) && (!remote->AddDeathRecipient(deathRecipient_))) {
186 NETMGR_EXT_LOG_E("add death recipient failed");
187 return nullptr;
188 }
189 networkVpnService_ = iface_cast<INetworkVpnService>(remote);
190 if (networkVpnService_ == nullptr) {
191 NETMGR_EXT_LOG_E("get Remote service proxy failed");
192 return nullptr;
193 }
194 return networkVpnService_;
195 }
196
RecoverCallback()197 void NetworkVpnClient::RecoverCallback()
198 {
199 uint32_t count = 0;
200 while (GetProxy() == nullptr && count < MAX_GET_SERVICE_COUNT) {
201 std::this_thread::sleep_for(std::chrono::milliseconds(WAIT_FOR_SERVICE_TIME_MS));
202 count++;
203 }
204 auto proxy = GetProxy();
205 NETMGR_EXT_LOG_D("Get proxy %{public}s, count: %{public}u", proxy == nullptr ? "failed" : "success", count);
206 if (proxy != nullptr && vpnEventCallback_ != nullptr) {
207 int32_t ret = proxy->RegisterVpnEvent(vpnEventCallback_);
208 NETMGR_EXT_LOG_D("Register result %{public}d", ret);
209 }
210 }
211
OnRemoteDied(const wptr<IRemoteObject> & remote)212 void NetworkVpnClient::OnRemoteDied(const wptr<IRemoteObject> &remote)
213 {
214 if (remote == nullptr) {
215 NETMGR_EXT_LOG_E("remote object is nullptr");
216 return;
217 }
218 std::lock_guard lock(mutex_);
219 if (networkVpnService_ == nullptr) {
220 NETMGR_EXT_LOG_E("networkVpnService_ is nullptr");
221 return;
222 }
223 sptr<IRemoteObject> local = networkVpnService_->AsObject();
224 if (local != remote.promote()) {
225 NETMGR_EXT_LOG_E("proxy and stub is not same remote object");
226 return;
227 }
228 local->RemoveDeathRecipient(deathRecipient_);
229 networkVpnService_ = nullptr;
230
231 if (vpnEventCallback_ != nullptr) {
232 NETMGR_EXT_LOG_D("on remote died recover callback");
233 std::thread t([this]() {
234 RecoverCallback();
235 });
236 std::string threadName = "networkvpnRecoverCallback";
237 pthread_setname_np(t.native_handle(), threadName.c_str());
238 t.detach();
239 }
240 }
241
multiUserSetUpEvent()242 void NetworkVpnClient::multiUserSetUpEvent()
243 {
244 vpnInterface_.CloseVpnInterfaceFd();
245 if (vpnEventCallback_ != nullptr) {
246 UnregisterVpnEvent(vpnEventCallback_);
247 vpnEventCallback_ = nullptr;
248 }
249 }
250 } // namespace NetManagerStandard
251 } // namespace OHOS
252