blob: 79fdfdcf921e140417d7bfc73c29cd4ee410ff89 [file] [log] [blame]
Roshan Pius3c4e8a32016-10-03 14:53:58 -07001/*
2 * Copyright (C) 2016 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
Roshan Pius3c4e8a32016-10-03 14:53:58 -070017#include <android-base/logging.h>
Roshan Pius9377a0d2017-10-06 13:18:54 -070018#include <cutils/properties.h>
Roshan Pius3c4e8a32016-10-03 14:53:58 -070019
Roshan Pius3c868522016-10-27 12:43:49 -070020#include "hidl_return_util.h"
Roshan Piuse2d0ab52016-12-05 15:24:20 -080021#include "hidl_struct_util.h"
Roshan Pius3c868522016-10-27 12:43:49 -070022#include "wifi_chip.h"
Etan Cohenc5700402017-03-08 16:43:38 -080023#include "wifi_feature_flags.h"
Roshan Pius5c055462016-10-11 08:27:27 -070024#include "wifi_status_util.h"
Roshan Pius3c4e8a32016-10-03 14:53:58 -070025
Roshan Pius35d958c2016-10-06 16:47:38 -070026namespace {
Roshan Pius35d958c2016-10-06 16:47:38 -070027using android::hardware::hidl_string;
Roshan Piusabcf78f2017-10-06 16:30:38 -070028using android::hardware::hidl_vec;
Roshan Pius2c06a3f2016-12-15 17:51:40 -080029using android::hardware::wifi::V1_0::ChipModeId;
Roshan Pius52947fb2016-11-18 11:38:07 -080030using android::hardware::wifi::V1_0::IWifiChip;
31using android::hardware::wifi::V1_0::IfaceType;
Roshan Piusabcf78f2017-10-06 16:30:38 -070032using android::sp;
Roshan Pius52947fb2016-11-18 11:38:07 -080033
Roshan Pius2c06a3f2016-12-15 17:51:40 -080034constexpr ChipModeId kStaChipModeId = 0;
35constexpr ChipModeId kApChipModeId = 1;
36constexpr ChipModeId kInvalidModeId = UINT32_MAX;
Roshan Pius35d958c2016-10-06 16:47:38 -070037
Roshan Pius35d958c2016-10-06 16:47:38 -070038template <typename Iface>
39void invalidateAndClear(sp<Iface>& iface) {
Roshan Piusabcf78f2017-10-06 16:30:38 -070040 if (iface.get()) {
41 iface->invalidate();
42 iface.clear();
43 }
Roshan Pius35d958c2016-10-06 16:47:38 -070044}
Roshan Pius9377a0d2017-10-06 13:18:54 -070045
46std::string getWlan0IfaceName() {
Roshan Piusabcf78f2017-10-06 16:30:38 -070047 std::array<char, PROPERTY_VALUE_MAX> buffer;
48 property_get("wifi.interface", buffer.data(), "wlan0");
49 return buffer.data();
Roshan Pius9377a0d2017-10-06 13:18:54 -070050}
51
52/** Not used yet.
53std::string getWlan1IfaceName() {
54 std::array<char, PROPERTY_VALUE_MAX> buffer;
55 property_get("wifi.concurrent.interface", buffer.data(), "wlan1");
56 return buffer.data();
57}
58*/
59
60std::string getP2pIfaceName() {
Roshan Piusabcf78f2017-10-06 16:30:38 -070061 std::array<char, PROPERTY_VALUE_MAX> buffer;
62 property_get("wifi.direct.interface", buffer.data(), "p2p0");
63 return buffer.data();
Roshan Pius9377a0d2017-10-06 13:18:54 -070064}
65
Roshan Piusabcf78f2017-10-06 16:30:38 -070066} // namespace
Roshan Pius35d958c2016-10-06 16:47:38 -070067
Roshan Pius3c4e8a32016-10-03 14:53:58 -070068namespace android {
69namespace hardware {
70namespace wifi {
Etan Cohen6ce50902017-09-14 07:30:57 -070071namespace V1_2 {
Roshan Pius79a99752016-10-04 13:03:58 -070072namespace implementation {
Roshan Pius3c868522016-10-27 12:43:49 -070073using hidl_return_util::validateAndCall;
Roshan Pius3c4e8a32016-10-03 14:53:58 -070074
Roshan Pius52947fb2016-11-18 11:38:07 -080075WifiChip::WifiChip(
Roshan Piusabcf78f2017-10-06 16:30:38 -070076 ChipId chip_id, const std::weak_ptr<legacy_hal::WifiLegacyHal> legacy_hal,
Roshan Pius52947fb2016-11-18 11:38:07 -080077 const std::weak_ptr<mode_controller::WifiModeController> mode_controller)
78 : chip_id_(chip_id),
79 legacy_hal_(legacy_hal),
80 mode_controller_(mode_controller),
81 is_valid_(true),
Roshan Pius48185b22016-12-15 19:10:30 -080082 current_mode_id_(kInvalidModeId),
83 debug_ring_buffer_cb_registered_(false) {}
Roshan Pius3c4e8a32016-10-03 14:53:58 -070084
Roshan Piusaabe5752016-09-29 09:03:59 -070085void WifiChip::invalidate() {
Roshan Piusabcf78f2017-10-06 16:30:38 -070086 invalidateAndRemoveAllIfaces();
87 legacy_hal_.reset();
88 event_cb_handler_.invalidate();
89 is_valid_ = false;
Roshan Pius3c4e8a32016-10-03 14:53:58 -070090}
91
Roshan Piusabcf78f2017-10-06 16:30:38 -070092bool WifiChip::isValid() { return is_valid_; }
Roshan Pius3c868522016-10-27 12:43:49 -070093
Roshan Piusd37341f2017-01-31 13:13:28 -080094std::set<sp<IWifiChipEventCallback>> WifiChip::getEventCallbacks() {
Roshan Piusabcf78f2017-10-06 16:30:38 -070095 return event_cb_handler_.getCallbacks();
Roshan Pius203cb032016-12-14 17:41:20 -080096}
97
Roshan Pius5c055462016-10-11 08:27:27 -070098Return<void> WifiChip::getId(getId_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -070099 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
100 &WifiChip::getIdInternal, hidl_status_cb);
Roshan Piuscd566bd2016-10-10 08:03:42 -0700101}
102
Roshan Pius3c4e8a32016-10-03 14:53:58 -0700103Return<void> WifiChip::registerEventCallback(
Roshan Pius5c055462016-10-11 08:27:27 -0700104 const sp<IWifiChipEventCallback>& event_callback,
105 registerEventCallback_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700106 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
107 &WifiChip::registerEventCallbackInternal,
108 hidl_status_cb, event_callback);
Roshan Pius3c4e8a32016-10-03 14:53:58 -0700109}
110
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700111Return<void> WifiChip::getCapabilities(getCapabilities_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700112 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
113 &WifiChip::getCapabilitiesInternal, hidl_status_cb);
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700114}
115
Roshan Pius5c055462016-10-11 08:27:27 -0700116Return<void> WifiChip::getAvailableModes(getAvailableModes_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700117 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
118 &WifiChip::getAvailableModesInternal,
119 hidl_status_cb);
Roshan Pius3c4e8a32016-10-03 14:53:58 -0700120}
121
Roshan Pius2c06a3f2016-12-15 17:51:40 -0800122Return<void> WifiChip::configureChip(ChipModeId mode_id,
Roshan Pius5c055462016-10-11 08:27:27 -0700123 configureChip_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700124 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
125 &WifiChip::configureChipInternal, hidl_status_cb,
126 mode_id);
Roshan Pius3c4e8a32016-10-03 14:53:58 -0700127}
128
Roshan Pius5c055462016-10-11 08:27:27 -0700129Return<void> WifiChip::getMode(getMode_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700130 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
131 &WifiChip::getModeInternal, hidl_status_cb);
Roshan Pius3c4e8a32016-10-03 14:53:58 -0700132}
133
Roshan Pius5c055462016-10-11 08:27:27 -0700134Return<void> WifiChip::requestChipDebugInfo(
135 requestChipDebugInfo_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700136 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
137 &WifiChip::requestChipDebugInfoInternal,
138 hidl_status_cb);
Roshan Pius5c055462016-10-11 08:27:27 -0700139}
140
141Return<void> WifiChip::requestDriverDebugDump(
142 requestDriverDebugDump_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700143 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
144 &WifiChip::requestDriverDebugDumpInternal,
145 hidl_status_cb);
Roshan Pius3c4e8a32016-10-03 14:53:58 -0700146}
147
Roshan Pius5c055462016-10-11 08:27:27 -0700148Return<void> WifiChip::requestFirmwareDebugDump(
149 requestFirmwareDebugDump_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700150 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
151 &WifiChip::requestFirmwareDebugDumpInternal,
152 hidl_status_cb);
Roshan Pius3c4e8a32016-10-03 14:53:58 -0700153}
154
Roshan Pius5c055462016-10-11 08:27:27 -0700155Return<void> WifiChip::createApIface(createApIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700156 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
157 &WifiChip::createApIfaceInternal, hidl_status_cb);
Roshan Pius35d958c2016-10-06 16:47:38 -0700158}
159
Roshan Pius5c055462016-10-11 08:27:27 -0700160Return<void> WifiChip::getApIfaceNames(getApIfaceNames_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700161 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
162 &WifiChip::getApIfaceNamesInternal, hidl_status_cb);
Roshan Pius35d958c2016-10-06 16:47:38 -0700163}
164
Roshan Pius5c055462016-10-11 08:27:27 -0700165Return<void> WifiChip::getApIface(const hidl_string& ifname,
166 getApIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700167 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
168 &WifiChip::getApIfaceInternal, hidl_status_cb,
169 ifname);
Roshan Pius35d958c2016-10-06 16:47:38 -0700170}
171
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800172Return<void> WifiChip::removeApIface(const hidl_string& ifname,
173 removeApIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700174 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
175 &WifiChip::removeApIfaceInternal, hidl_status_cb,
176 ifname);
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800177}
178
Roshan Pius5c055462016-10-11 08:27:27 -0700179Return<void> WifiChip::createNanIface(createNanIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700180 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
181 &WifiChip::createNanIfaceInternal, hidl_status_cb);
Roshan Pius35d958c2016-10-06 16:47:38 -0700182}
183
Roshan Pius5c055462016-10-11 08:27:27 -0700184Return<void> WifiChip::getNanIfaceNames(getNanIfaceNames_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700185 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
186 &WifiChip::getNanIfaceNamesInternal, hidl_status_cb);
Roshan Pius35d958c2016-10-06 16:47:38 -0700187}
188
189Return<void> WifiChip::getNanIface(const hidl_string& ifname,
Roshan Pius5c055462016-10-11 08:27:27 -0700190 getNanIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700191 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
192 &WifiChip::getNanIfaceInternal, hidl_status_cb,
193 ifname);
Roshan Pius35d958c2016-10-06 16:47:38 -0700194}
195
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800196Return<void> WifiChip::removeNanIface(const hidl_string& ifname,
197 removeNanIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700198 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
199 &WifiChip::removeNanIfaceInternal, hidl_status_cb,
200 ifname);
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800201}
202
Roshan Pius5c055462016-10-11 08:27:27 -0700203Return<void> WifiChip::createP2pIface(createP2pIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700204 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
205 &WifiChip::createP2pIfaceInternal, hidl_status_cb);
Roshan Pius35d958c2016-10-06 16:47:38 -0700206}
207
Roshan Pius5c055462016-10-11 08:27:27 -0700208Return<void> WifiChip::getP2pIfaceNames(getP2pIfaceNames_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700209 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
210 &WifiChip::getP2pIfaceNamesInternal, hidl_status_cb);
Roshan Pius35d958c2016-10-06 16:47:38 -0700211}
212
213Return<void> WifiChip::getP2pIface(const hidl_string& ifname,
Roshan Pius5c055462016-10-11 08:27:27 -0700214 getP2pIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700215 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
216 &WifiChip::getP2pIfaceInternal, hidl_status_cb,
217 ifname);
Roshan Pius35d958c2016-10-06 16:47:38 -0700218}
219
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800220Return<void> WifiChip::removeP2pIface(const hidl_string& ifname,
221 removeP2pIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700222 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
223 &WifiChip::removeP2pIfaceInternal, hidl_status_cb,
224 ifname);
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800225}
226
Roshan Pius5c055462016-10-11 08:27:27 -0700227Return<void> WifiChip::createStaIface(createStaIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700228 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
229 &WifiChip::createStaIfaceInternal, hidl_status_cb);
Roshan Pius35d958c2016-10-06 16:47:38 -0700230}
231
Roshan Pius5c055462016-10-11 08:27:27 -0700232Return<void> WifiChip::getStaIfaceNames(getStaIfaceNames_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700233 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
234 &WifiChip::getStaIfaceNamesInternal, hidl_status_cb);
Roshan Pius35d958c2016-10-06 16:47:38 -0700235}
236
237Return<void> WifiChip::getStaIface(const hidl_string& ifname,
Roshan Pius5c055462016-10-11 08:27:27 -0700238 getStaIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700239 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
240 &WifiChip::getStaIfaceInternal, hidl_status_cb,
241 ifname);
Roshan Pius35d958c2016-10-06 16:47:38 -0700242}
243
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800244Return<void> WifiChip::removeStaIface(const hidl_string& ifname,
245 removeStaIface_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700246 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
247 &WifiChip::removeStaIfaceInternal, hidl_status_cb,
248 ifname);
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800249}
250
Roshan Pius5c055462016-10-11 08:27:27 -0700251Return<void> WifiChip::createRttController(
252 const sp<IWifiIface>& bound_iface, createRttController_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700253 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
254 &WifiChip::createRttControllerInternal,
255 hidl_status_cb, bound_iface);
Roshan Pius59268282016-10-06 20:23:47 -0700256}
257
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700258Return<void> WifiChip::getDebugRingBuffersStatus(
259 getDebugRingBuffersStatus_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700260 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
261 &WifiChip::getDebugRingBuffersStatusInternal,
262 hidl_status_cb);
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700263}
264
265Return<void> WifiChip::startLoggingToDebugRingBuffer(
Roshan Piusabcf78f2017-10-06 16:30:38 -0700266 const hidl_string& ring_name, WifiDebugRingBufferVerboseLevel verbose_level,
267 uint32_t max_interval_in_sec, uint32_t min_data_size_in_bytes,
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700268 startLoggingToDebugRingBuffer_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700269 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
270 &WifiChip::startLoggingToDebugRingBufferInternal,
271 hidl_status_cb, ring_name, verbose_level,
272 max_interval_in_sec, min_data_size_in_bytes);
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700273}
274
275Return<void> WifiChip::forceDumpToDebugRingBuffer(
276 const hidl_string& ring_name,
277 forceDumpToDebugRingBuffer_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700278 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
279 &WifiChip::forceDumpToDebugRingBufferInternal,
280 hidl_status_cb, ring_name);
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700281}
282
Roshan Pius8c0c8e92017-02-24 08:07:42 -0800283Return<void> WifiChip::stopLoggingToDebugRingBuffer(
284 stopLoggingToDebugRingBuffer_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700285 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
286 &WifiChip::stopLoggingToDebugRingBufferInternal,
287 hidl_status_cb);
Roshan Pius8c0c8e92017-02-24 08:07:42 -0800288}
289
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700290Return<void> WifiChip::getDebugHostWakeReasonStats(
291 getDebugHostWakeReasonStats_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700292 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
293 &WifiChip::getDebugHostWakeReasonStatsInternal,
294 hidl_status_cb);
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700295}
296
Roshan Pius203cb032016-12-14 17:41:20 -0800297Return<void> WifiChip::enableDebugErrorAlerts(
298 bool enable, enableDebugErrorAlerts_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700299 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
300 &WifiChip::enableDebugErrorAlertsInternal,
301 hidl_status_cb, enable);
Roshan Pius203cb032016-12-14 17:41:20 -0800302}
303
Roshan Pius735ff432017-07-25 08:48:08 -0700304Return<void> WifiChip::selectTxPowerScenario(
305 TxPowerScenario scenario, selectTxPowerScenario_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700306 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
307 &WifiChip::selectTxPowerScenarioInternal,
308 hidl_status_cb, scenario);
Roshan Piusdbd83ef2017-06-20 12:05:40 -0700309}
310
Roshan Pius735ff432017-07-25 08:48:08 -0700311Return<void> WifiChip::resetTxPowerScenario(
312 resetTxPowerScenario_cb hidl_status_cb) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700313 return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
314 &WifiChip::resetTxPowerScenarioInternal,
315 hidl_status_cb);
Roshan Piusdbd83ef2017-06-20 12:05:40 -0700316}
317
Roshan Pius35d958c2016-10-06 16:47:38 -0700318void WifiChip::invalidateAndRemoveAllIfaces() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700319 invalidateAndClear(ap_iface_);
320 invalidateAndClear(nan_iface_);
321 invalidateAndClear(p2p_iface_);
322 invalidateAndClear(sta_iface_);
323 // Since all the ifaces are invalid now, all RTT controller objects
324 // using those ifaces also need to be invalidated.
325 for (const auto& rtt : rtt_controllers_) {
326 rtt->invalidate();
327 }
328 rtt_controllers_.clear();
Roshan Pius35d958c2016-10-06 16:47:38 -0700329}
330
Roshan Pius3c868522016-10-27 12:43:49 -0700331std::pair<WifiStatus, ChipId> WifiChip::getIdInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700332 return {createWifiStatus(WifiStatusCode::SUCCESS), chip_id_};
Roshan Pius3c868522016-10-27 12:43:49 -0700333}
334
335WifiStatus WifiChip::registerEventCallbackInternal(
336 const sp<IWifiChipEventCallback>& event_callback) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700337 if (!event_cb_handler_.addCallback(event_callback)) {
338 return createWifiStatus(WifiStatusCode::ERROR_UNKNOWN);
339 }
340 return createWifiStatus(WifiStatusCode::SUCCESS);
Roshan Pius3c868522016-10-27 12:43:49 -0700341}
342
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700343std::pair<WifiStatus, uint32_t> WifiChip::getCapabilitiesInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700344 legacy_hal::wifi_error legacy_status;
345 uint32_t legacy_feature_set;
346 uint32_t legacy_logger_feature_set;
347 std::tie(legacy_status, legacy_feature_set) =
348 legacy_hal_.lock()->getSupportedFeatureSet(getWlan0IfaceName());
349 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
350 return {createWifiStatusFromLegacyError(legacy_status), 0};
351 }
352 std::tie(legacy_status, legacy_logger_feature_set) =
353 legacy_hal_.lock()->getLoggerSupportedFeatureSet(getWlan0IfaceName());
354 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
355 return {createWifiStatusFromLegacyError(legacy_status), 0};
356 }
357 uint32_t hidl_caps;
358 if (!hidl_struct_util::convertLegacyFeaturesToHidlChipCapabilities(
359 legacy_feature_set, legacy_logger_feature_set, &hidl_caps)) {
360 return {createWifiStatus(WifiStatusCode::ERROR_UNKNOWN), 0};
361 }
362 return {createWifiStatus(WifiStatusCode::SUCCESS), hidl_caps};
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700363}
364
Roshan Pius3c868522016-10-27 12:43:49 -0700365std::pair<WifiStatus, std::vector<IWifiChip::ChipMode>>
366WifiChip::getAvailableModesInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700367 // The chip combination supported for current devices is fixed for now with
368 // 2 separate modes of operation:
369 // Mode 1 (STA mode): Will support 1 STA and 1 P2P or NAN iface operations
370 // concurrently [NAN conditional on wifiHidlFeatureAware]
371 // Mode 2 (AP mode): Will support 1 AP iface operations.
372 // TODO (b/32997844): Read this from some device specific flags in the
373 // makefile.
374 // STA mode iface combinations.
375 const IWifiChip::ChipIfaceCombinationLimit
376 sta_chip_iface_combination_limit_1 = {{IfaceType::STA}, 1};
377 IWifiChip::ChipIfaceCombinationLimit sta_chip_iface_combination_limit_2;
378 if (WifiFeatureFlags::wifiHidlFeatureAware) {
379 sta_chip_iface_combination_limit_2 = {{IfaceType::P2P, IfaceType::NAN},
380 1};
381 } else {
382 sta_chip_iface_combination_limit_2 = {{IfaceType::P2P}, 1};
383 }
384 const IWifiChip::ChipIfaceCombination sta_chip_iface_combination = {
385 {sta_chip_iface_combination_limit_1,
386 sta_chip_iface_combination_limit_2}};
387 const IWifiChip::ChipMode sta_chip_mode = {kStaChipModeId,
388 {sta_chip_iface_combination}};
389 // AP mode iface combinations.
390 const IWifiChip::ChipIfaceCombinationLimit ap_chip_iface_combination_limit =
391 {{IfaceType::AP}, 1};
392 const IWifiChip::ChipIfaceCombination ap_chip_iface_combination = {
393 {ap_chip_iface_combination_limit}};
394 const IWifiChip::ChipMode ap_chip_mode = {kApChipModeId,
395 {ap_chip_iface_combination}};
396 return {createWifiStatus(WifiStatusCode::SUCCESS),
397 {sta_chip_mode, ap_chip_mode}};
Roshan Pius3c868522016-10-27 12:43:49 -0700398}
399
Roshan Pius2c06a3f2016-12-15 17:51:40 -0800400WifiStatus WifiChip::configureChipInternal(ChipModeId mode_id) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700401 if (mode_id != kStaChipModeId && mode_id != kApChipModeId) {
402 return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
403 }
404 if (mode_id == current_mode_id_) {
405 LOG(DEBUG) << "Already in the specified mode " << mode_id;
406 return createWifiStatus(WifiStatusCode::SUCCESS);
407 }
408 WifiStatus status = handleChipConfiguration(mode_id);
409 if (status.code != WifiStatusCode::SUCCESS) {
410 for (const auto& callback : event_cb_handler_.getCallbacks()) {
411 if (!callback->onChipReconfigureFailure(status).isOk()) {
412 LOG(ERROR)
413 << "Failed to invoke onChipReconfigureFailure callback";
414 }
415 }
416 return status;
417 }
Roshan Piusd37341f2017-01-31 13:13:28 -0800418 for (const auto& callback : event_cb_handler_.getCallbacks()) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700419 if (!callback->onChipReconfigured(mode_id).isOk()) {
420 LOG(ERROR) << "Failed to invoke onChipReconfigured callback";
421 }
Roshan Pius52947fb2016-11-18 11:38:07 -0800422 }
Roshan Piusabcf78f2017-10-06 16:30:38 -0700423 current_mode_id_ = mode_id;
Roshan Pius2c06a3f2016-12-15 17:51:40 -0800424 return status;
Roshan Pius3c868522016-10-27 12:43:49 -0700425}
426
427std::pair<WifiStatus, uint32_t> WifiChip::getModeInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700428 if (current_mode_id_ == kInvalidModeId) {
429 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE),
430 current_mode_id_};
431 }
432 return {createWifiStatus(WifiStatusCode::SUCCESS), current_mode_id_};
Roshan Pius3c868522016-10-27 12:43:49 -0700433}
434
435std::pair<WifiStatus, IWifiChip::ChipDebugInfo>
436WifiChip::requestChipDebugInfoInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700437 IWifiChip::ChipDebugInfo result;
438 legacy_hal::wifi_error legacy_status;
439 std::string driver_desc;
440 std::tie(legacy_status, driver_desc) =
441 legacy_hal_.lock()->getDriverVersion(getWlan0IfaceName());
442 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
443 LOG(ERROR) << "Failed to get driver version: "
444 << legacyErrorToString(legacy_status);
445 WifiStatus status = createWifiStatusFromLegacyError(
446 legacy_status, "failed to get driver version");
447 return {status, result};
448 }
449 result.driverDescription = driver_desc.c_str();
Roshan Pius3c868522016-10-27 12:43:49 -0700450
Roshan Piusabcf78f2017-10-06 16:30:38 -0700451 std::string firmware_desc;
452 std::tie(legacy_status, firmware_desc) =
453 legacy_hal_.lock()->getFirmwareVersion(getWlan0IfaceName());
454 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
455 LOG(ERROR) << "Failed to get firmware version: "
456 << legacyErrorToString(legacy_status);
457 WifiStatus status = createWifiStatusFromLegacyError(
458 legacy_status, "failed to get firmware version");
459 return {status, result};
460 }
461 result.firmwareDescription = firmware_desc.c_str();
Roshan Pius3c868522016-10-27 12:43:49 -0700462
Roshan Piusabcf78f2017-10-06 16:30:38 -0700463 return {createWifiStatus(WifiStatusCode::SUCCESS), result};
Roshan Pius3c868522016-10-27 12:43:49 -0700464}
465
466std::pair<WifiStatus, std::vector<uint8_t>>
467WifiChip::requestDriverDebugDumpInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700468 legacy_hal::wifi_error legacy_status;
469 std::vector<uint8_t> driver_dump;
470 std::tie(legacy_status, driver_dump) =
471 legacy_hal_.lock()->requestDriverMemoryDump(getWlan0IfaceName());
472 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
473 LOG(ERROR) << "Failed to get driver debug dump: "
474 << legacyErrorToString(legacy_status);
475 return {createWifiStatusFromLegacyError(legacy_status),
476 std::vector<uint8_t>()};
477 }
478 return {createWifiStatus(WifiStatusCode::SUCCESS), driver_dump};
Roshan Pius3c868522016-10-27 12:43:49 -0700479}
480
481std::pair<WifiStatus, std::vector<uint8_t>>
482WifiChip::requestFirmwareDebugDumpInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700483 legacy_hal::wifi_error legacy_status;
484 std::vector<uint8_t> firmware_dump;
485 std::tie(legacy_status, firmware_dump) =
486 legacy_hal_.lock()->requestFirmwareMemoryDump(getWlan0IfaceName());
487 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
488 LOG(ERROR) << "Failed to get firmware debug dump: "
489 << legacyErrorToString(legacy_status);
490 return {createWifiStatusFromLegacyError(legacy_status), {}};
491 }
492 return {createWifiStatus(WifiStatusCode::SUCCESS), firmware_dump};
Roshan Pius3c868522016-10-27 12:43:49 -0700493}
494
495std::pair<WifiStatus, sp<IWifiApIface>> WifiChip::createApIfaceInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700496 if (current_mode_id_ != kApChipModeId || ap_iface_.get()) {
497 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE), {}};
Roshan Piusbc662202017-01-30 17:07:42 -0800498 }
Roshan Piusabcf78f2017-10-06 16:30:38 -0700499 std::string ifname = getWlan0IfaceName();
500 ap_iface_ = new WifiApIface(ifname, legacy_hal_);
501 for (const auto& callback : event_cb_handler_.getCallbacks()) {
502 if (!callback->onIfaceAdded(IfaceType::AP, ifname).isOk()) {
503 LOG(ERROR) << "Failed to invoke onIfaceAdded callback";
504 }
505 }
506 return {createWifiStatus(WifiStatusCode::SUCCESS), ap_iface_};
Roshan Pius3c868522016-10-27 12:43:49 -0700507}
508
509std::pair<WifiStatus, std::vector<hidl_string>>
510WifiChip::getApIfaceNamesInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700511 if (!ap_iface_.get()) {
512 return {createWifiStatus(WifiStatusCode::SUCCESS), {}};
513 }
514 return {createWifiStatus(WifiStatusCode::SUCCESS), {getWlan0IfaceName()}};
Roshan Pius3c868522016-10-27 12:43:49 -0700515}
516
517std::pair<WifiStatus, sp<IWifiApIface>> WifiChip::getApIfaceInternal(
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800518 const std::string& ifname) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700519 if (!ap_iface_.get() || (ifname != getWlan0IfaceName())) {
520 return {createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS), nullptr};
521 }
522 return {createWifiStatus(WifiStatusCode::SUCCESS), ap_iface_};
Roshan Pius3c868522016-10-27 12:43:49 -0700523}
524
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800525WifiStatus WifiChip::removeApIfaceInternal(const std::string& ifname) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700526 if (!ap_iface_.get() || (ifname != getWlan0IfaceName())) {
527 return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
Roshan Piusbc662202017-01-30 17:07:42 -0800528 }
Roshan Piusabcf78f2017-10-06 16:30:38 -0700529 invalidateAndClear(ap_iface_);
530 for (const auto& callback : event_cb_handler_.getCallbacks()) {
531 if (!callback->onIfaceRemoved(IfaceType::AP, ifname).isOk()) {
532 LOG(ERROR) << "Failed to invoke onIfaceRemoved callback";
533 }
534 }
535 return createWifiStatus(WifiStatusCode::SUCCESS);
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800536}
537
Roshan Pius3c868522016-10-27 12:43:49 -0700538std::pair<WifiStatus, sp<IWifiNanIface>> WifiChip::createNanIfaceInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700539 // Only 1 of NAN or P2P iface can be active at a time.
540 if (WifiFeatureFlags::wifiHidlFeatureAware) {
541 if (current_mode_id_ != kStaChipModeId || nan_iface_.get() ||
542 p2p_iface_.get()) {
543 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE), {}};
544 }
545 std::string ifname = getWlan0IfaceName();
546 nan_iface_ = new WifiNanIface(ifname, legacy_hal_);
547 for (const auto& callback : event_cb_handler_.getCallbacks()) {
548 if (!callback->onIfaceAdded(IfaceType::NAN, ifname).isOk()) {
549 LOG(ERROR) << "Failed to invoke onIfaceAdded callback";
550 }
551 }
552 return {createWifiStatus(WifiStatusCode::SUCCESS), nan_iface_};
553 } else {
554 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE), {}};
Etan Cohenc5700402017-03-08 16:43:38 -0800555 }
Roshan Pius3c868522016-10-27 12:43:49 -0700556}
557
558std::pair<WifiStatus, std::vector<hidl_string>>
559WifiChip::getNanIfaceNamesInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700560 if (!nan_iface_.get()) {
561 return {createWifiStatus(WifiStatusCode::SUCCESS), {}};
562 }
563 return {createWifiStatus(WifiStatusCode::SUCCESS), {getWlan0IfaceName()}};
Roshan Pius3c868522016-10-27 12:43:49 -0700564}
565
566std::pair<WifiStatus, sp<IWifiNanIface>> WifiChip::getNanIfaceInternal(
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800567 const std::string& ifname) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700568 if (!nan_iface_.get() || (ifname != getWlan0IfaceName())) {
569 return {createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS), nullptr};
570 }
571 return {createWifiStatus(WifiStatusCode::SUCCESS), nan_iface_};
Roshan Pius3c868522016-10-27 12:43:49 -0700572}
573
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800574WifiStatus WifiChip::removeNanIfaceInternal(const std::string& ifname) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700575 if (!nan_iface_.get() || (ifname != getWlan0IfaceName())) {
576 return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
Roshan Piusbc662202017-01-30 17:07:42 -0800577 }
Roshan Piusabcf78f2017-10-06 16:30:38 -0700578 invalidateAndClear(nan_iface_);
579 for (const auto& callback : event_cb_handler_.getCallbacks()) {
580 if (!callback->onIfaceRemoved(IfaceType::NAN, ifname).isOk()) {
581 LOG(ERROR) << "Failed to invoke onIfaceAdded callback";
582 }
583 }
584 return createWifiStatus(WifiStatusCode::SUCCESS);
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800585}
586
Roshan Pius3c868522016-10-27 12:43:49 -0700587std::pair<WifiStatus, sp<IWifiP2pIface>> WifiChip::createP2pIfaceInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700588 // Only 1 of NAN or P2P iface can be active at a time.
589 if (current_mode_id_ != kStaChipModeId || p2p_iface_.get() ||
590 nan_iface_.get()) {
591 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE), {}};
Roshan Piusbc662202017-01-30 17:07:42 -0800592 }
Roshan Piusabcf78f2017-10-06 16:30:38 -0700593 std::string ifname = getP2pIfaceName();
594 p2p_iface_ = new WifiP2pIface(ifname, legacy_hal_);
595 for (const auto& callback : event_cb_handler_.getCallbacks()) {
596 if (!callback->onIfaceAdded(IfaceType::P2P, ifname).isOk()) {
597 LOG(ERROR) << "Failed to invoke onIfaceAdded callback";
598 }
599 }
600 return {createWifiStatus(WifiStatusCode::SUCCESS), p2p_iface_};
Roshan Pius3c868522016-10-27 12:43:49 -0700601}
602
603std::pair<WifiStatus, std::vector<hidl_string>>
604WifiChip::getP2pIfaceNamesInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700605 if (!p2p_iface_.get()) {
606 return {createWifiStatus(WifiStatusCode::SUCCESS), {}};
607 }
608 return {createWifiStatus(WifiStatusCode::SUCCESS), {getP2pIfaceName()}};
Roshan Pius3c868522016-10-27 12:43:49 -0700609}
610
611std::pair<WifiStatus, sp<IWifiP2pIface>> WifiChip::getP2pIfaceInternal(
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800612 const std::string& ifname) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700613 if (!p2p_iface_.get() || (ifname != getP2pIfaceName())) {
614 return {createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS), nullptr};
615 }
616 return {createWifiStatus(WifiStatusCode::SUCCESS), p2p_iface_};
Roshan Pius3c868522016-10-27 12:43:49 -0700617}
618
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800619WifiStatus WifiChip::removeP2pIfaceInternal(const std::string& ifname) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700620 if (!p2p_iface_.get() || (ifname != getP2pIfaceName())) {
621 return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
Roshan Piusbc662202017-01-30 17:07:42 -0800622 }
Roshan Piusabcf78f2017-10-06 16:30:38 -0700623 invalidateAndClear(p2p_iface_);
624 for (const auto& callback : event_cb_handler_.getCallbacks()) {
625 if (!callback->onIfaceRemoved(IfaceType::P2P, ifname).isOk()) {
626 LOG(ERROR) << "Failed to invoke onIfaceRemoved callback";
627 }
628 }
629 return createWifiStatus(WifiStatusCode::SUCCESS);
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800630}
631
Roshan Pius3c868522016-10-27 12:43:49 -0700632std::pair<WifiStatus, sp<IWifiStaIface>> WifiChip::createStaIfaceInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700633 if (current_mode_id_ != kStaChipModeId || sta_iface_.get()) {
634 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE), {}};
Roshan Piusbc662202017-01-30 17:07:42 -0800635 }
Roshan Piusabcf78f2017-10-06 16:30:38 -0700636 std::string ifname = getWlan0IfaceName();
637 sta_iface_ = new WifiStaIface(ifname, legacy_hal_);
638 for (const auto& callback : event_cb_handler_.getCallbacks()) {
639 if (!callback->onIfaceAdded(IfaceType::STA, ifname).isOk()) {
640 LOG(ERROR) << "Failed to invoke onIfaceAdded callback";
641 }
642 }
643 return {createWifiStatus(WifiStatusCode::SUCCESS), sta_iface_};
Roshan Pius3c868522016-10-27 12:43:49 -0700644}
645
646std::pair<WifiStatus, std::vector<hidl_string>>
647WifiChip::getStaIfaceNamesInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700648 if (!sta_iface_.get()) {
649 return {createWifiStatus(WifiStatusCode::SUCCESS), {}};
650 }
651 return {createWifiStatus(WifiStatusCode::SUCCESS), {getWlan0IfaceName()}};
Roshan Pius3c868522016-10-27 12:43:49 -0700652}
653
654std::pair<WifiStatus, sp<IWifiStaIface>> WifiChip::getStaIfaceInternal(
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800655 const std::string& ifname) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700656 if (!sta_iface_.get() || (ifname != getWlan0IfaceName())) {
657 return {createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS), nullptr};
658 }
659 return {createWifiStatus(WifiStatusCode::SUCCESS), sta_iface_};
Roshan Pius3c868522016-10-27 12:43:49 -0700660}
661
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800662WifiStatus WifiChip::removeStaIfaceInternal(const std::string& ifname) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700663 if (!sta_iface_.get() || (ifname != getWlan0IfaceName())) {
664 return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
Roshan Piusbc662202017-01-30 17:07:42 -0800665 }
Roshan Piusabcf78f2017-10-06 16:30:38 -0700666 invalidateAndClear(sta_iface_);
667 for (const auto& callback : event_cb_handler_.getCallbacks()) {
668 if (!callback->onIfaceRemoved(IfaceType::STA, ifname).isOk()) {
669 LOG(ERROR) << "Failed to invoke onIfaceRemoved callback";
670 }
671 }
672 return createWifiStatus(WifiStatusCode::SUCCESS);
Roshan Pius8b55e6f2016-12-09 12:05:12 -0800673}
674
Roshan Pius3c868522016-10-27 12:43:49 -0700675std::pair<WifiStatus, sp<IWifiRttController>>
676WifiChip::createRttControllerInternal(const sp<IWifiIface>& bound_iface) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700677 sp<WifiRttController> rtt =
678 new WifiRttController(getWlan0IfaceName(), bound_iface, legacy_hal_);
679 rtt_controllers_.emplace_back(rtt);
680 return {createWifiStatus(WifiStatusCode::SUCCESS), rtt};
Roshan Pius3c868522016-10-27 12:43:49 -0700681}
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700682
683std::pair<WifiStatus, std::vector<WifiDebugRingBufferStatus>>
684WifiChip::getDebugRingBuffersStatusInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700685 legacy_hal::wifi_error legacy_status;
686 std::vector<legacy_hal::wifi_ring_buffer_status>
687 legacy_ring_buffer_status_vec;
688 std::tie(legacy_status, legacy_ring_buffer_status_vec) =
689 legacy_hal_.lock()->getRingBuffersStatus(getWlan0IfaceName());
690 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
691 return {createWifiStatusFromLegacyError(legacy_status), {}};
692 }
693 std::vector<WifiDebugRingBufferStatus> hidl_ring_buffer_status_vec;
694 if (!hidl_struct_util::convertLegacyVectorOfDebugRingBufferStatusToHidl(
695 legacy_ring_buffer_status_vec, &hidl_ring_buffer_status_vec)) {
696 return {createWifiStatus(WifiStatusCode::ERROR_UNKNOWN), {}};
697 }
698 return {createWifiStatus(WifiStatusCode::SUCCESS),
699 hidl_ring_buffer_status_vec};
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700700}
701
702WifiStatus WifiChip::startLoggingToDebugRingBufferInternal(
Roshan Piusabcf78f2017-10-06 16:30:38 -0700703 const hidl_string& ring_name, WifiDebugRingBufferVerboseLevel verbose_level,
704 uint32_t max_interval_in_sec, uint32_t min_data_size_in_bytes) {
705 WifiStatus status = registerDebugRingBufferCallback();
706 if (status.code != WifiStatusCode::SUCCESS) {
707 return status;
708 }
709 legacy_hal::wifi_error legacy_status =
710 legacy_hal_.lock()->startRingBufferLogging(
711 getWlan0IfaceName(), ring_name,
712 static_cast<
713 std::underlying_type<WifiDebugRingBufferVerboseLevel>::type>(
714 verbose_level),
715 max_interval_in_sec, min_data_size_in_bytes);
716 return createWifiStatusFromLegacyError(legacy_status);
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700717}
718
719WifiStatus WifiChip::forceDumpToDebugRingBufferInternal(
Roshan Piuse2d0ab52016-12-05 15:24:20 -0800720 const hidl_string& ring_name) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700721 WifiStatus status = registerDebugRingBufferCallback();
722 if (status.code != WifiStatusCode::SUCCESS) {
723 return status;
724 }
725 legacy_hal::wifi_error legacy_status =
726 legacy_hal_.lock()->getRingBufferData(getWlan0IfaceName(), ring_name);
727 return createWifiStatusFromLegacyError(legacy_status);
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700728}
729
Roshan Pius8c0c8e92017-02-24 08:07:42 -0800730WifiStatus WifiChip::stopLoggingToDebugRingBufferInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700731 legacy_hal::wifi_error legacy_status =
732 legacy_hal_.lock()->deregisterRingBufferCallbackHandler(
733 getWlan0IfaceName());
734 return createWifiStatusFromLegacyError(legacy_status);
Roshan Pius8c0c8e92017-02-24 08:07:42 -0800735}
736
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700737std::pair<WifiStatus, WifiDebugHostWakeReasonStats>
738WifiChip::getDebugHostWakeReasonStatsInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700739 legacy_hal::wifi_error legacy_status;
740 legacy_hal::WakeReasonStats legacy_stats;
741 std::tie(legacy_status, legacy_stats) =
742 legacy_hal_.lock()->getWakeReasonStats(getWlan0IfaceName());
743 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
744 return {createWifiStatusFromLegacyError(legacy_status), {}};
745 }
746 WifiDebugHostWakeReasonStats hidl_stats;
747 if (!hidl_struct_util::convertLegacyWakeReasonStatsToHidl(legacy_stats,
748 &hidl_stats)) {
749 return {createWifiStatus(WifiStatusCode::ERROR_UNKNOWN), {}};
750 }
751 return {createWifiStatus(WifiStatusCode::SUCCESS), hidl_stats};
Roshan Pius7d08d7a2016-10-27 14:35:05 -0700752}
753
Roshan Pius203cb032016-12-14 17:41:20 -0800754WifiStatus WifiChip::enableDebugErrorAlertsInternal(bool enable) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700755 legacy_hal::wifi_error legacy_status;
756 if (enable) {
757 android::wp<WifiChip> weak_ptr_this(this);
758 const auto& on_alert_callback = [weak_ptr_this](
759 int32_t error_code,
760 std::vector<uint8_t> debug_data) {
761 const auto shared_ptr_this = weak_ptr_this.promote();
762 if (!shared_ptr_this.get() || !shared_ptr_this->isValid()) {
763 LOG(ERROR) << "Callback invoked on an invalid object";
764 return;
765 }
766 for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
767 if (!callback->onDebugErrorAlert(error_code, debug_data)
768 .isOk()) {
769 LOG(ERROR) << "Failed to invoke onDebugErrorAlert callback";
770 }
771 }
772 };
773 legacy_status = legacy_hal_.lock()->registerErrorAlertCallbackHandler(
Roshan Piusacededb2017-10-06 14:59:26 -0700774 getWlan0IfaceName(), on_alert_callback);
Roshan Piusabcf78f2017-10-06 16:30:38 -0700775 } else {
776 legacy_status = legacy_hal_.lock()->deregisterErrorAlertCallbackHandler(
Roshan Piusacededb2017-10-06 14:59:26 -0700777 getWlan0IfaceName());
Roshan Piusabcf78f2017-10-06 16:30:38 -0700778 }
779 return createWifiStatusFromLegacyError(legacy_status);
Roshan Pius203cb032016-12-14 17:41:20 -0800780}
Roshan Pius2c06a3f2016-12-15 17:51:40 -0800781
Roshan Pius735ff432017-07-25 08:48:08 -0700782WifiStatus WifiChip::selectTxPowerScenarioInternal(TxPowerScenario scenario) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700783 auto legacy_status = legacy_hal_.lock()->selectTxPowerScenario(
784 getWlan0IfaceName(),
785 hidl_struct_util::convertHidlTxPowerScenarioToLegacy(scenario));
786 return createWifiStatusFromLegacyError(legacy_status);
Roshan Piusdbd83ef2017-06-20 12:05:40 -0700787}
788
Roshan Pius735ff432017-07-25 08:48:08 -0700789WifiStatus WifiChip::resetTxPowerScenarioInternal() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700790 auto legacy_status =
791 legacy_hal_.lock()->resetTxPowerScenario(getWlan0IfaceName());
792 return createWifiStatusFromLegacyError(legacy_status);
Roshan Piusdbd83ef2017-06-20 12:05:40 -0700793}
794
Roshan Pius2c06a3f2016-12-15 17:51:40 -0800795WifiStatus WifiChip::handleChipConfiguration(ChipModeId mode_id) {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700796 // If the chip is already configured in a different mode, stop
797 // the legacy HAL and then start it after firmware mode change.
798 // Currently the underlying implementation has a deadlock issue.
799 // We should return ERROR_NOT_SUPPORTED if chip is already configured in
800 // a different mode.
801 if (current_mode_id_ != kInvalidModeId) {
802 // TODO(b/37446050): Fix the deadlock.
803 return createWifiStatus(WifiStatusCode::ERROR_NOT_SUPPORTED);
804 }
805 bool success;
806 if (mode_id == kStaChipModeId) {
807 success = mode_controller_.lock()->changeFirmwareMode(IfaceType::STA);
808 } else {
809 success = mode_controller_.lock()->changeFirmwareMode(IfaceType::AP);
810 }
811 if (!success) {
812 return createWifiStatus(WifiStatusCode::ERROR_UNKNOWN);
813 }
814 legacy_hal::wifi_error legacy_status = legacy_hal_.lock()->start();
815 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
816 LOG(ERROR) << "Failed to start legacy HAL: "
817 << legacyErrorToString(legacy_status);
818 return createWifiStatusFromLegacyError(legacy_status);
819 }
820 return createWifiStatus(WifiStatusCode::SUCCESS);
Roshan Pius2c06a3f2016-12-15 17:51:40 -0800821}
Roshan Pius48185b22016-12-15 19:10:30 -0800822
823WifiStatus WifiChip::registerDebugRingBufferCallback() {
Roshan Piusabcf78f2017-10-06 16:30:38 -0700824 if (debug_ring_buffer_cb_registered_) {
825 return createWifiStatus(WifiStatusCode::SUCCESS);
Roshan Pius48185b22016-12-15 19:10:30 -0800826 }
Roshan Pius3797e182017-03-30 18:01:54 -0700827
Roshan Piusabcf78f2017-10-06 16:30:38 -0700828 android::wp<WifiChip> weak_ptr_this(this);
829 const auto& on_ring_buffer_data_callback =
830 [weak_ptr_this](const std::string& /* name */,
831 const std::vector<uint8_t>& data,
832 const legacy_hal::wifi_ring_buffer_status& status) {
833 const auto shared_ptr_this = weak_ptr_this.promote();
834 if (!shared_ptr_this.get() || !shared_ptr_this->isValid()) {
835 LOG(ERROR) << "Callback invoked on an invalid object";
836 return;
837 }
838 WifiDebugRingBufferStatus hidl_status;
839 if (!hidl_struct_util::convertLegacyDebugRingBufferStatusToHidl(
840 status, &hidl_status)) {
841 LOG(ERROR) << "Error converting ring buffer status";
842 return;
843 }
844 for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
845 if (!callback->onDebugRingBufferDataAvailable(hidl_status, data)
846 .isOk()) {
847 LOG(ERROR)
848 << "Failed to invoke onDebugRingBufferDataAvailable"
849 << " callback on: " << toString(callback);
850 }
851 }
852 };
853 legacy_hal::wifi_error legacy_status =
854 legacy_hal_.lock()->registerRingBufferCallbackHandler(
855 getWlan0IfaceName(), on_ring_buffer_data_callback);
Roshan Pius48185b22016-12-15 19:10:30 -0800856
Roshan Piusabcf78f2017-10-06 16:30:38 -0700857 if (legacy_status == legacy_hal::WIFI_SUCCESS) {
858 debug_ring_buffer_cb_registered_ = true;
859 }
860 return createWifiStatusFromLegacyError(legacy_status);
Roshan Pius48185b22016-12-15 19:10:30 -0800861}
862
Roshan Pius79a99752016-10-04 13:03:58 -0700863} // namespace implementation
Etan Cohen6ce50902017-09-14 07:30:57 -0700864} // namespace V1_2
Roshan Pius3c4e8a32016-10-03 14:53:58 -0700865} // namespace wifi
866} // namespace hardware
867} // namespace android