• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2022 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #include "chre_host/wifi_ext_hal_handler.h"
18 
19 namespace android {
20 namespace chre {
21 
~WifiExtHalHandler()22 WifiExtHalHandler::~WifiExtHalHandler() {
23   notifyThreadToExit();
24   mThread.join();
25 }
26 
WifiExtHalHandler(const std::function<void (bool)> & statusChangeCallback)27 WifiExtHalHandler::WifiExtHalHandler(
28     const std::function<void(bool)> &statusChangeCallback) {
29   mEnableConfig.reset();
30   mThread = std::thread(&WifiExtHalHandler::wifiExtHandlerThreadEntry, this);
31   mDeathRecipient =
32       AIBinder_DeathRecipient_new(WifiExtHalHandler::onWifiExtHalServiceDeath);
33   mCallback = ndk::SharedRefBase::make<WifiExtCallback>(statusChangeCallback);
34 }
35 
handleConfigurationRequest(bool enable)36 void WifiExtHalHandler::handleConfigurationRequest(bool enable) {
37   std::lock_guard<std::mutex> lock(mMutex);
38   mEnableConfig = enable;
39   mCondVar.notify_one();
40 }
41 
dispatchConfigurationRequest(bool enable)42 void WifiExtHalHandler::dispatchConfigurationRequest(bool enable) {
43   if (checkWifiExtHalConnected()) {
44     auto result = mService->requestWifiChreNanRtt(enable);
45     if (!result.isOk()) {
46       LOGE("wifi ext hal config request for %s failed with code: %d",
47            (enable == true) ? "Enable" : "Disable",
48            result.getServiceSpecificError());
49     }
50     mCallback->onStatusChanged(result.isOk());
51   }
52 }
53 
checkWifiExtHalConnected()54 bool WifiExtHalHandler::checkWifiExtHalConnected() {
55   bool success = false;
56   if (mService == nullptr) {
57     auto serviceName = std::string() + IWifiExt::descriptor + "/default";
58     mService = IWifiExt::fromBinder(
59         ndk::SpAIBinder(AServiceManager_waitForService(serviceName.c_str())));
60     if (mService != nullptr) {
61       LOGD("Connected to Wifi Ext HAL service");
62       AIBinder_linkToDeath(mService->asBinder().get(), mDeathRecipient,
63                            reinterpret_cast<void *>(&mService) /* cookie */);
64       auto result = mService->registerChreCallback(mCallback);
65       if (!result.isOk()) {
66         LOGE("Failed to register CHRE callback with WifiExt, code: %d",
67              result.getServiceSpecificError());
68       } else {
69         success = true;
70       }
71     } else {
72       LOGE("Failed to connect to Wifi Ext HAL service");
73     }
74   }
75   return success;
76 }
77 
onWifiExtHalServiceDeath(void * cookie)78 void WifiExtHalHandler::onWifiExtHalServiceDeath(void *cookie) {
79   LOGI("WiFi Ext HAL service died");
80   // Cookie is expected to be a pointer to mService.
81   *((std::shared_ptr<IWifiExt> *)cookie) = nullptr;
82   // TODO(b/204226580): Figure out if wifi ext HAL is stateful and if it
83   // isn't, notify CHRE of a NAN disabled status change to enable nanoapps
84   // to not expect NAN data until the service is back up, and expect it to
85   // do a re-enable when needed. Or we could store the current status of
86   // enablement, and do a re-enable/disable when the service is back up.
87 }
88 
wifiExtHandlerThreadEntry()89 void WifiExtHalHandler::wifiExtHandlerThreadEntry() {
90   while (mThreadRunning) {
91     std::unique_lock<std::mutex> lock(mMutex);
92     mCondVar.wait(
93         lock, [this] { return mEnableConfig.has_value() || !mThreadRunning; });
94 
95     if (mThreadRunning) {
96       dispatchConfigurationRequest(mEnableConfig.value());
97       mEnableConfig.reset();
98     }
99   }
100 }
101 
notifyThreadToExit()102 void WifiExtHalHandler::notifyThreadToExit() {
103   std::lock_guard<std::mutex> lock(mMutex);
104   mThreadRunning = false;
105   mCondVar.notify_one();
106 }
107 
108 }  // namespace chre
109 }  // namespace android
110