1 /*
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
17 #include <android-base/logging.h>
18
19 #include "hidl_return_util.h"
20 #include "hidl_struct_util.h"
21 #include "wifi_chip.h"
22 #include "wifi_feature_flags.h"
23 #include "wifi_status_util.h"
24
25 namespace {
26 using android::sp;
27 using android::hardware::hidl_vec;
28 using android::hardware::hidl_string;
29 using android::hardware::wifi::V1_0::ChipModeId;
30 using android::hardware::wifi::V1_0::IWifiChip;
31 using android::hardware::wifi::V1_0::IfaceType;
32
33 constexpr ChipModeId kStaChipModeId = 0;
34 constexpr ChipModeId kApChipModeId = 1;
35 constexpr ChipModeId kInvalidModeId = UINT32_MAX;
36
37 template <typename Iface>
invalidateAndClear(sp<Iface> & iface)38 void invalidateAndClear(sp<Iface>& iface) {
39 if (iface.get()) {
40 iface->invalidate();
41 iface.clear();
42 }
43 }
44 } // namepsace
45
46 namespace android {
47 namespace hardware {
48 namespace wifi {
49 namespace V1_1 {
50 namespace implementation {
51 using hidl_return_util::validateAndCall;
52
WifiChip(ChipId chip_id,const std::weak_ptr<legacy_hal::WifiLegacyHal> legacy_hal,const std::weak_ptr<mode_controller::WifiModeController> mode_controller)53 WifiChip::WifiChip(
54 ChipId chip_id,
55 const std::weak_ptr<legacy_hal::WifiLegacyHal> legacy_hal,
56 const std::weak_ptr<mode_controller::WifiModeController> mode_controller)
57 : chip_id_(chip_id),
58 legacy_hal_(legacy_hal),
59 mode_controller_(mode_controller),
60 is_valid_(true),
61 current_mode_id_(kInvalidModeId),
62 debug_ring_buffer_cb_registered_(false) {}
63
invalidate()64 void WifiChip::invalidate() {
65 invalidateAndRemoveAllIfaces();
66 legacy_hal_.reset();
67 event_cb_handler_.invalidate();
68 is_valid_ = false;
69 }
70
isValid()71 bool WifiChip::isValid() {
72 return is_valid_;
73 }
74
getEventCallbacks()75 std::set<sp<IWifiChipEventCallback>> WifiChip::getEventCallbacks() {
76 return event_cb_handler_.getCallbacks();
77 }
78
getId(getId_cb hidl_status_cb)79 Return<void> WifiChip::getId(getId_cb hidl_status_cb) {
80 return validateAndCall(this,
81 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
82 &WifiChip::getIdInternal,
83 hidl_status_cb);
84 }
85
registerEventCallback(const sp<IWifiChipEventCallback> & event_callback,registerEventCallback_cb hidl_status_cb)86 Return<void> WifiChip::registerEventCallback(
87 const sp<IWifiChipEventCallback>& event_callback,
88 registerEventCallback_cb hidl_status_cb) {
89 return validateAndCall(this,
90 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
91 &WifiChip::registerEventCallbackInternal,
92 hidl_status_cb,
93 event_callback);
94 }
95
getCapabilities(getCapabilities_cb hidl_status_cb)96 Return<void> WifiChip::getCapabilities(getCapabilities_cb hidl_status_cb) {
97 return validateAndCall(this,
98 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
99 &WifiChip::getCapabilitiesInternal,
100 hidl_status_cb);
101 }
102
getAvailableModes(getAvailableModes_cb hidl_status_cb)103 Return<void> WifiChip::getAvailableModes(getAvailableModes_cb hidl_status_cb) {
104 return validateAndCall(this,
105 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
106 &WifiChip::getAvailableModesInternal,
107 hidl_status_cb);
108 }
109
configureChip(ChipModeId mode_id,configureChip_cb hidl_status_cb)110 Return<void> WifiChip::configureChip(ChipModeId mode_id,
111 configureChip_cb hidl_status_cb) {
112 return validateAndCall(this,
113 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
114 &WifiChip::configureChipInternal,
115 hidl_status_cb,
116 mode_id);
117 }
118
getMode(getMode_cb hidl_status_cb)119 Return<void> WifiChip::getMode(getMode_cb hidl_status_cb) {
120 return validateAndCall(this,
121 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
122 &WifiChip::getModeInternal,
123 hidl_status_cb);
124 }
125
requestChipDebugInfo(requestChipDebugInfo_cb hidl_status_cb)126 Return<void> WifiChip::requestChipDebugInfo(
127 requestChipDebugInfo_cb hidl_status_cb) {
128 return validateAndCall(this,
129 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
130 &WifiChip::requestChipDebugInfoInternal,
131 hidl_status_cb);
132 }
133
requestDriverDebugDump(requestDriverDebugDump_cb hidl_status_cb)134 Return<void> WifiChip::requestDriverDebugDump(
135 requestDriverDebugDump_cb hidl_status_cb) {
136 return validateAndCall(this,
137 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
138 &WifiChip::requestDriverDebugDumpInternal,
139 hidl_status_cb);
140 }
141
requestFirmwareDebugDump(requestFirmwareDebugDump_cb hidl_status_cb)142 Return<void> WifiChip::requestFirmwareDebugDump(
143 requestFirmwareDebugDump_cb hidl_status_cb) {
144 return validateAndCall(this,
145 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
146 &WifiChip::requestFirmwareDebugDumpInternal,
147 hidl_status_cb);
148 }
149
createApIface(createApIface_cb hidl_status_cb)150 Return<void> WifiChip::createApIface(createApIface_cb hidl_status_cb) {
151 return validateAndCall(this,
152 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
153 &WifiChip::createApIfaceInternal,
154 hidl_status_cb);
155 }
156
getApIfaceNames(getApIfaceNames_cb hidl_status_cb)157 Return<void> WifiChip::getApIfaceNames(getApIfaceNames_cb hidl_status_cb) {
158 return validateAndCall(this,
159 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
160 &WifiChip::getApIfaceNamesInternal,
161 hidl_status_cb);
162 }
163
getApIface(const hidl_string & ifname,getApIface_cb hidl_status_cb)164 Return<void> WifiChip::getApIface(const hidl_string& ifname,
165 getApIface_cb hidl_status_cb) {
166 return validateAndCall(this,
167 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
168 &WifiChip::getApIfaceInternal,
169 hidl_status_cb,
170 ifname);
171 }
172
removeApIface(const hidl_string & ifname,removeApIface_cb hidl_status_cb)173 Return<void> WifiChip::removeApIface(const hidl_string& ifname,
174 removeApIface_cb hidl_status_cb) {
175 return validateAndCall(this,
176 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
177 &WifiChip::removeApIfaceInternal,
178 hidl_status_cb,
179 ifname);
180 }
181
createNanIface(createNanIface_cb hidl_status_cb)182 Return<void> WifiChip::createNanIface(createNanIface_cb hidl_status_cb) {
183 return validateAndCall(this,
184 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
185 &WifiChip::createNanIfaceInternal,
186 hidl_status_cb);
187 }
188
getNanIfaceNames(getNanIfaceNames_cb hidl_status_cb)189 Return<void> WifiChip::getNanIfaceNames(getNanIfaceNames_cb hidl_status_cb) {
190 return validateAndCall(this,
191 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
192 &WifiChip::getNanIfaceNamesInternal,
193 hidl_status_cb);
194 }
195
getNanIface(const hidl_string & ifname,getNanIface_cb hidl_status_cb)196 Return<void> WifiChip::getNanIface(const hidl_string& ifname,
197 getNanIface_cb hidl_status_cb) {
198 return validateAndCall(this,
199 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
200 &WifiChip::getNanIfaceInternal,
201 hidl_status_cb,
202 ifname);
203 }
204
removeNanIface(const hidl_string & ifname,removeNanIface_cb hidl_status_cb)205 Return<void> WifiChip::removeNanIface(const hidl_string& ifname,
206 removeNanIface_cb hidl_status_cb) {
207 return validateAndCall(this,
208 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
209 &WifiChip::removeNanIfaceInternal,
210 hidl_status_cb,
211 ifname);
212 }
213
createP2pIface(createP2pIface_cb hidl_status_cb)214 Return<void> WifiChip::createP2pIface(createP2pIface_cb hidl_status_cb) {
215 return validateAndCall(this,
216 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
217 &WifiChip::createP2pIfaceInternal,
218 hidl_status_cb);
219 }
220
getP2pIfaceNames(getP2pIfaceNames_cb hidl_status_cb)221 Return<void> WifiChip::getP2pIfaceNames(getP2pIfaceNames_cb hidl_status_cb) {
222 return validateAndCall(this,
223 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
224 &WifiChip::getP2pIfaceNamesInternal,
225 hidl_status_cb);
226 }
227
getP2pIface(const hidl_string & ifname,getP2pIface_cb hidl_status_cb)228 Return<void> WifiChip::getP2pIface(const hidl_string& ifname,
229 getP2pIface_cb hidl_status_cb) {
230 return validateAndCall(this,
231 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
232 &WifiChip::getP2pIfaceInternal,
233 hidl_status_cb,
234 ifname);
235 }
236
removeP2pIface(const hidl_string & ifname,removeP2pIface_cb hidl_status_cb)237 Return<void> WifiChip::removeP2pIface(const hidl_string& ifname,
238 removeP2pIface_cb hidl_status_cb) {
239 return validateAndCall(this,
240 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
241 &WifiChip::removeP2pIfaceInternal,
242 hidl_status_cb,
243 ifname);
244 }
245
createStaIface(createStaIface_cb hidl_status_cb)246 Return<void> WifiChip::createStaIface(createStaIface_cb hidl_status_cb) {
247 return validateAndCall(this,
248 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
249 &WifiChip::createStaIfaceInternal,
250 hidl_status_cb);
251 }
252
getStaIfaceNames(getStaIfaceNames_cb hidl_status_cb)253 Return<void> WifiChip::getStaIfaceNames(getStaIfaceNames_cb hidl_status_cb) {
254 return validateAndCall(this,
255 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
256 &WifiChip::getStaIfaceNamesInternal,
257 hidl_status_cb);
258 }
259
getStaIface(const hidl_string & ifname,getStaIface_cb hidl_status_cb)260 Return<void> WifiChip::getStaIface(const hidl_string& ifname,
261 getStaIface_cb hidl_status_cb) {
262 return validateAndCall(this,
263 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
264 &WifiChip::getStaIfaceInternal,
265 hidl_status_cb,
266 ifname);
267 }
268
removeStaIface(const hidl_string & ifname,removeStaIface_cb hidl_status_cb)269 Return<void> WifiChip::removeStaIface(const hidl_string& ifname,
270 removeStaIface_cb hidl_status_cb) {
271 return validateAndCall(this,
272 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
273 &WifiChip::removeStaIfaceInternal,
274 hidl_status_cb,
275 ifname);
276 }
277
createRttController(const sp<IWifiIface> & bound_iface,createRttController_cb hidl_status_cb)278 Return<void> WifiChip::createRttController(
279 const sp<IWifiIface>& bound_iface, createRttController_cb hidl_status_cb) {
280 return validateAndCall(this,
281 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
282 &WifiChip::createRttControllerInternal,
283 hidl_status_cb,
284 bound_iface);
285 }
286
getDebugRingBuffersStatus(getDebugRingBuffersStatus_cb hidl_status_cb)287 Return<void> WifiChip::getDebugRingBuffersStatus(
288 getDebugRingBuffersStatus_cb hidl_status_cb) {
289 return validateAndCall(this,
290 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
291 &WifiChip::getDebugRingBuffersStatusInternal,
292 hidl_status_cb);
293 }
294
startLoggingToDebugRingBuffer(const hidl_string & ring_name,WifiDebugRingBufferVerboseLevel verbose_level,uint32_t max_interval_in_sec,uint32_t min_data_size_in_bytes,startLoggingToDebugRingBuffer_cb hidl_status_cb)295 Return<void> WifiChip::startLoggingToDebugRingBuffer(
296 const hidl_string& ring_name,
297 WifiDebugRingBufferVerboseLevel verbose_level,
298 uint32_t max_interval_in_sec,
299 uint32_t min_data_size_in_bytes,
300 startLoggingToDebugRingBuffer_cb hidl_status_cb) {
301 return validateAndCall(this,
302 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
303 &WifiChip::startLoggingToDebugRingBufferInternal,
304 hidl_status_cb,
305 ring_name,
306 verbose_level,
307 max_interval_in_sec,
308 min_data_size_in_bytes);
309 }
310
forceDumpToDebugRingBuffer(const hidl_string & ring_name,forceDumpToDebugRingBuffer_cb hidl_status_cb)311 Return<void> WifiChip::forceDumpToDebugRingBuffer(
312 const hidl_string& ring_name,
313 forceDumpToDebugRingBuffer_cb hidl_status_cb) {
314 return validateAndCall(this,
315 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
316 &WifiChip::forceDumpToDebugRingBufferInternal,
317 hidl_status_cb,
318 ring_name);
319 }
320
stopLoggingToDebugRingBuffer(stopLoggingToDebugRingBuffer_cb hidl_status_cb)321 Return<void> WifiChip::stopLoggingToDebugRingBuffer(
322 stopLoggingToDebugRingBuffer_cb hidl_status_cb) {
323 return validateAndCall(this,
324 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
325 &WifiChip::stopLoggingToDebugRingBufferInternal,
326 hidl_status_cb);
327 }
328
getDebugHostWakeReasonStats(getDebugHostWakeReasonStats_cb hidl_status_cb)329 Return<void> WifiChip::getDebugHostWakeReasonStats(
330 getDebugHostWakeReasonStats_cb hidl_status_cb) {
331 return validateAndCall(this,
332 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
333 &WifiChip::getDebugHostWakeReasonStatsInternal,
334 hidl_status_cb);
335 }
336
enableDebugErrorAlerts(bool enable,enableDebugErrorAlerts_cb hidl_status_cb)337 Return<void> WifiChip::enableDebugErrorAlerts(
338 bool enable, enableDebugErrorAlerts_cb hidl_status_cb) {
339 return validateAndCall(this,
340 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
341 &WifiChip::enableDebugErrorAlertsInternal,
342 hidl_status_cb,
343 enable);
344 }
345
selectTxPowerScenario(TxPowerScenario scenario,selectTxPowerScenario_cb hidl_status_cb)346 Return<void> WifiChip::selectTxPowerScenario(
347 TxPowerScenario scenario, selectTxPowerScenario_cb hidl_status_cb) {
348 return validateAndCall(this,
349 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
350 &WifiChip::selectTxPowerScenarioInternal,
351 hidl_status_cb,
352 scenario);
353 }
354
resetTxPowerScenario(resetTxPowerScenario_cb hidl_status_cb)355 Return<void> WifiChip::resetTxPowerScenario(
356 resetTxPowerScenario_cb hidl_status_cb) {
357 return validateAndCall(this,
358 WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
359 &WifiChip::resetTxPowerScenarioInternal,
360 hidl_status_cb);
361 }
362
invalidateAndRemoveAllIfaces()363 void WifiChip::invalidateAndRemoveAllIfaces() {
364 invalidateAndClear(ap_iface_);
365 invalidateAndClear(nan_iface_);
366 invalidateAndClear(p2p_iface_);
367 invalidateAndClear(sta_iface_);
368 // Since all the ifaces are invalid now, all RTT controller objects
369 // using those ifaces also need to be invalidated.
370 for (const auto& rtt : rtt_controllers_) {
371 rtt->invalidate();
372 }
373 rtt_controllers_.clear();
374 }
375
getIdInternal()376 std::pair<WifiStatus, ChipId> WifiChip::getIdInternal() {
377 return {createWifiStatus(WifiStatusCode::SUCCESS), chip_id_};
378 }
379
registerEventCallbackInternal(const sp<IWifiChipEventCallback> & event_callback)380 WifiStatus WifiChip::registerEventCallbackInternal(
381 const sp<IWifiChipEventCallback>& event_callback) {
382 if (!event_cb_handler_.addCallback(event_callback)) {
383 return createWifiStatus(WifiStatusCode::ERROR_UNKNOWN);
384 }
385 return createWifiStatus(WifiStatusCode::SUCCESS);
386 }
387
getCapabilitiesInternal()388 std::pair<WifiStatus, uint32_t> WifiChip::getCapabilitiesInternal() {
389 legacy_hal::wifi_error legacy_status;
390 uint32_t legacy_feature_set;
391 uint32_t legacy_logger_feature_set;
392 std::tie(legacy_status, legacy_feature_set) =
393 legacy_hal_.lock()->getSupportedFeatureSet();
394 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
395 return {createWifiStatusFromLegacyError(legacy_status), 0};
396 }
397 std::tie(legacy_status, legacy_logger_feature_set) =
398 legacy_hal_.lock()->getLoggerSupportedFeatureSet();
399 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
400 return {createWifiStatusFromLegacyError(legacy_status), 0};
401 }
402 uint32_t hidl_caps;
403 if (!hidl_struct_util::convertLegacyFeaturesToHidlChipCapabilities(
404 legacy_feature_set, legacy_logger_feature_set, &hidl_caps)) {
405 return {createWifiStatus(WifiStatusCode::ERROR_UNKNOWN), 0};
406 }
407 return {createWifiStatus(WifiStatusCode::SUCCESS), hidl_caps};
408 }
409
410 std::pair<WifiStatus, std::vector<IWifiChip::ChipMode>>
getAvailableModesInternal()411 WifiChip::getAvailableModesInternal() {
412 // The chip combination supported for current devices is fixed for now with
413 // 2 separate modes of operation:
414 // Mode 1 (STA mode): Will support 1 STA and 1 P2P or NAN iface operations
415 // concurrently [NAN conditional on wifiHidlFeatureAware]
416 // Mode 2 (AP mode): Will support 1 AP iface operations.
417 // TODO (b/32997844): Read this from some device specific flags in the
418 // makefile.
419 // STA mode iface combinations.
420 const IWifiChip::ChipIfaceCombinationLimit
421 sta_chip_iface_combination_limit_1 = {{IfaceType::STA}, 1};
422 IWifiChip::ChipIfaceCombinationLimit sta_chip_iface_combination_limit_2;
423 if (WifiFeatureFlags::wifiHidlFeatureAware) {
424 sta_chip_iface_combination_limit_2 = {{IfaceType::P2P, IfaceType::NAN},
425 1};
426 } else {
427 sta_chip_iface_combination_limit_2 = {{IfaceType::P2P},
428 1};
429 }
430 const IWifiChip::ChipIfaceCombination sta_chip_iface_combination = {
431 {sta_chip_iface_combination_limit_1, sta_chip_iface_combination_limit_2}};
432 const IWifiChip::ChipMode sta_chip_mode = {kStaChipModeId,
433 {sta_chip_iface_combination}};
434 // AP mode iface combinations.
435 const IWifiChip::ChipIfaceCombinationLimit ap_chip_iface_combination_limit = {
436 {IfaceType::AP}, 1};
437 const IWifiChip::ChipIfaceCombination ap_chip_iface_combination = {
438 {ap_chip_iface_combination_limit}};
439 const IWifiChip::ChipMode ap_chip_mode = {kApChipModeId,
440 {ap_chip_iface_combination}};
441 return {createWifiStatus(WifiStatusCode::SUCCESS),
442 {sta_chip_mode, ap_chip_mode}};
443 }
444
configureChipInternal(ChipModeId mode_id)445 WifiStatus WifiChip::configureChipInternal(ChipModeId mode_id) {
446 if (mode_id != kStaChipModeId && mode_id != kApChipModeId) {
447 return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
448 }
449 if (mode_id == current_mode_id_) {
450 LOG(DEBUG) << "Already in the specified mode " << mode_id;
451 return createWifiStatus(WifiStatusCode::SUCCESS);
452 }
453 WifiStatus status = handleChipConfiguration(mode_id);
454 if (status.code != WifiStatusCode::SUCCESS) {
455 for (const auto& callback : event_cb_handler_.getCallbacks()) {
456 if (!callback->onChipReconfigureFailure(status).isOk()) {
457 LOG(ERROR) << "Failed to invoke onChipReconfigureFailure callback";
458 }
459 }
460 return status;
461 }
462 for (const auto& callback : event_cb_handler_.getCallbacks()) {
463 if (!callback->onChipReconfigured(mode_id).isOk()) {
464 LOG(ERROR) << "Failed to invoke onChipReconfigured callback";
465 }
466 }
467 current_mode_id_ = mode_id;
468 return status;
469 }
470
getModeInternal()471 std::pair<WifiStatus, uint32_t> WifiChip::getModeInternal() {
472 if (current_mode_id_ == kInvalidModeId) {
473 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE),
474 current_mode_id_};
475 }
476 return {createWifiStatus(WifiStatusCode::SUCCESS), current_mode_id_};
477 }
478
479 std::pair<WifiStatus, IWifiChip::ChipDebugInfo>
requestChipDebugInfoInternal()480 WifiChip::requestChipDebugInfoInternal() {
481 IWifiChip::ChipDebugInfo result;
482 legacy_hal::wifi_error legacy_status;
483 std::string driver_desc;
484 std::tie(legacy_status, driver_desc) = legacy_hal_.lock()->getDriverVersion();
485 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
486 LOG(ERROR) << "Failed to get driver version: "
487 << legacyErrorToString(legacy_status);
488 WifiStatus status = createWifiStatusFromLegacyError(
489 legacy_status, "failed to get driver version");
490 return {status, result};
491 }
492 result.driverDescription = driver_desc.c_str();
493
494 std::string firmware_desc;
495 std::tie(legacy_status, firmware_desc) =
496 legacy_hal_.lock()->getFirmwareVersion();
497 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
498 LOG(ERROR) << "Failed to get firmware version: "
499 << legacyErrorToString(legacy_status);
500 WifiStatus status = createWifiStatusFromLegacyError(
501 legacy_status, "failed to get firmware version");
502 return {status, result};
503 }
504 result.firmwareDescription = firmware_desc.c_str();
505
506 return {createWifiStatus(WifiStatusCode::SUCCESS), result};
507 }
508
509 std::pair<WifiStatus, std::vector<uint8_t>>
requestDriverDebugDumpInternal()510 WifiChip::requestDriverDebugDumpInternal() {
511 legacy_hal::wifi_error legacy_status;
512 std::vector<uint8_t> driver_dump;
513 std::tie(legacy_status, driver_dump) =
514 legacy_hal_.lock()->requestDriverMemoryDump();
515 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
516 LOG(ERROR) << "Failed to get driver debug dump: "
517 << legacyErrorToString(legacy_status);
518 return {createWifiStatusFromLegacyError(legacy_status),
519 std::vector<uint8_t>()};
520 }
521 return {createWifiStatus(WifiStatusCode::SUCCESS), driver_dump};
522 }
523
524 std::pair<WifiStatus, std::vector<uint8_t>>
requestFirmwareDebugDumpInternal()525 WifiChip::requestFirmwareDebugDumpInternal() {
526 legacy_hal::wifi_error legacy_status;
527 std::vector<uint8_t> firmware_dump;
528 std::tie(legacy_status, firmware_dump) =
529 legacy_hal_.lock()->requestFirmwareMemoryDump();
530 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
531 LOG(ERROR) << "Failed to get firmware debug dump: "
532 << legacyErrorToString(legacy_status);
533 return {createWifiStatusFromLegacyError(legacy_status), {}};
534 }
535 return {createWifiStatus(WifiStatusCode::SUCCESS), firmware_dump};
536 }
537
createApIfaceInternal()538 std::pair<WifiStatus, sp<IWifiApIface>> WifiChip::createApIfaceInternal() {
539 if (current_mode_id_ != kApChipModeId || ap_iface_.get()) {
540 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE), {}};
541 }
542 std::string ifname = legacy_hal_.lock()->getApIfaceName();
543 ap_iface_ = new WifiApIface(ifname, legacy_hal_);
544 for (const auto& callback : event_cb_handler_.getCallbacks()) {
545 if (!callback->onIfaceAdded(IfaceType::AP, ifname).isOk()) {
546 LOG(ERROR) << "Failed to invoke onIfaceAdded callback";
547 }
548 }
549 return {createWifiStatus(WifiStatusCode::SUCCESS), ap_iface_};
550 }
551
552 std::pair<WifiStatus, std::vector<hidl_string>>
getApIfaceNamesInternal()553 WifiChip::getApIfaceNamesInternal() {
554 if (!ap_iface_.get()) {
555 return {createWifiStatus(WifiStatusCode::SUCCESS), {}};
556 }
557 return {createWifiStatus(WifiStatusCode::SUCCESS),
558 {legacy_hal_.lock()->getApIfaceName()}};
559 }
560
getApIfaceInternal(const std::string & ifname)561 std::pair<WifiStatus, sp<IWifiApIface>> WifiChip::getApIfaceInternal(
562 const std::string& ifname) {
563 if (!ap_iface_.get() || (ifname != legacy_hal_.lock()->getApIfaceName())) {
564 return {createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS), nullptr};
565 }
566 return {createWifiStatus(WifiStatusCode::SUCCESS), ap_iface_};
567 }
568
removeApIfaceInternal(const std::string & ifname)569 WifiStatus WifiChip::removeApIfaceInternal(const std::string& ifname) {
570 if (!ap_iface_.get() || (ifname != legacy_hal_.lock()->getApIfaceName())) {
571 return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
572 }
573 invalidateAndClear(ap_iface_);
574 for (const auto& callback : event_cb_handler_.getCallbacks()) {
575 if (!callback->onIfaceRemoved(IfaceType::AP, ifname).isOk()) {
576 LOG(ERROR) << "Failed to invoke onIfaceRemoved callback";
577 }
578 }
579 return createWifiStatus(WifiStatusCode::SUCCESS);
580 }
581
createNanIfaceInternal()582 std::pair<WifiStatus, sp<IWifiNanIface>> WifiChip::createNanIfaceInternal() {
583 // Only 1 of NAN or P2P iface can be active at a time.
584 if (WifiFeatureFlags::wifiHidlFeatureAware) {
585 if (current_mode_id_ != kStaChipModeId || nan_iface_.get() ||
586 p2p_iface_.get()) {
587 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE), {}};
588 }
589 std::string ifname = legacy_hal_.lock()->getNanIfaceName();
590 nan_iface_ = new WifiNanIface(ifname, legacy_hal_);
591 for (const auto& callback : event_cb_handler_.getCallbacks()) {
592 if (!callback->onIfaceAdded(IfaceType::NAN, ifname).isOk()) {
593 LOG(ERROR) << "Failed to invoke onIfaceAdded callback";
594 }
595 }
596 return {createWifiStatus(WifiStatusCode::SUCCESS), nan_iface_};
597 } else {
598 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE), {}};
599 }
600 }
601
602 std::pair<WifiStatus, std::vector<hidl_string>>
getNanIfaceNamesInternal()603 WifiChip::getNanIfaceNamesInternal() {
604 if (!nan_iface_.get()) {
605 return {createWifiStatus(WifiStatusCode::SUCCESS), {}};
606 }
607 return {createWifiStatus(WifiStatusCode::SUCCESS),
608 {legacy_hal_.lock()->getNanIfaceName()}};
609 }
610
getNanIfaceInternal(const std::string & ifname)611 std::pair<WifiStatus, sp<IWifiNanIface>> WifiChip::getNanIfaceInternal(
612 const std::string& ifname) {
613 if (!nan_iface_.get() || (ifname != legacy_hal_.lock()->getNanIfaceName())) {
614 return {createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS), nullptr};
615 }
616 return {createWifiStatus(WifiStatusCode::SUCCESS), nan_iface_};
617 }
618
removeNanIfaceInternal(const std::string & ifname)619 WifiStatus WifiChip::removeNanIfaceInternal(const std::string& ifname) {
620 if (!nan_iface_.get() || (ifname != legacy_hal_.lock()->getNanIfaceName())) {
621 return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
622 }
623 invalidateAndClear(nan_iface_);
624 for (const auto& callback : event_cb_handler_.getCallbacks()) {
625 if (!callback->onIfaceRemoved(IfaceType::NAN, ifname).isOk()) {
626 LOG(ERROR) << "Failed to invoke onIfaceAdded callback";
627 }
628 }
629 return createWifiStatus(WifiStatusCode::SUCCESS);
630 }
631
createP2pIfaceInternal()632 std::pair<WifiStatus, sp<IWifiP2pIface>> WifiChip::createP2pIfaceInternal() {
633 // Only 1 of NAN or P2P iface can be active at a time.
634 if (current_mode_id_ != kStaChipModeId || p2p_iface_.get() ||
635 nan_iface_.get()) {
636 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE), {}};
637 }
638 std::string ifname = legacy_hal_.lock()->getP2pIfaceName();
639 p2p_iface_ = new WifiP2pIface(ifname, legacy_hal_);
640 for (const auto& callback : event_cb_handler_.getCallbacks()) {
641 if (!callback->onIfaceAdded(IfaceType::P2P, ifname).isOk()) {
642 LOG(ERROR) << "Failed to invoke onIfaceAdded callback";
643 }
644 }
645 return {createWifiStatus(WifiStatusCode::SUCCESS), p2p_iface_};
646 }
647
648 std::pair<WifiStatus, std::vector<hidl_string>>
getP2pIfaceNamesInternal()649 WifiChip::getP2pIfaceNamesInternal() {
650 if (!p2p_iface_.get()) {
651 return {createWifiStatus(WifiStatusCode::SUCCESS), {}};
652 }
653 return {createWifiStatus(WifiStatusCode::SUCCESS),
654 {legacy_hal_.lock()->getP2pIfaceName()}};
655 }
656
getP2pIfaceInternal(const std::string & ifname)657 std::pair<WifiStatus, sp<IWifiP2pIface>> WifiChip::getP2pIfaceInternal(
658 const std::string& ifname) {
659 if (!p2p_iface_.get() || (ifname != legacy_hal_.lock()->getP2pIfaceName())) {
660 return {createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS), nullptr};
661 }
662 return {createWifiStatus(WifiStatusCode::SUCCESS), p2p_iface_};
663 }
664
removeP2pIfaceInternal(const std::string & ifname)665 WifiStatus WifiChip::removeP2pIfaceInternal(const std::string& ifname) {
666 if (!p2p_iface_.get() || (ifname != legacy_hal_.lock()->getP2pIfaceName())) {
667 return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
668 }
669 invalidateAndClear(p2p_iface_);
670 for (const auto& callback : event_cb_handler_.getCallbacks()) {
671 if (!callback->onIfaceRemoved(IfaceType::P2P, ifname).isOk()) {
672 LOG(ERROR) << "Failed to invoke onIfaceRemoved callback";
673 }
674 }
675 return createWifiStatus(WifiStatusCode::SUCCESS);
676 }
677
createStaIfaceInternal()678 std::pair<WifiStatus, sp<IWifiStaIface>> WifiChip::createStaIfaceInternal() {
679 if (current_mode_id_ != kStaChipModeId || sta_iface_.get()) {
680 return {createWifiStatus(WifiStatusCode::ERROR_NOT_AVAILABLE), {}};
681 }
682 std::string ifname = legacy_hal_.lock()->getStaIfaceName();
683 sta_iface_ = new WifiStaIface(ifname, legacy_hal_);
684 for (const auto& callback : event_cb_handler_.getCallbacks()) {
685 if (!callback->onIfaceAdded(IfaceType::STA, ifname).isOk()) {
686 LOG(ERROR) << "Failed to invoke onIfaceAdded callback";
687 }
688 }
689 return {createWifiStatus(WifiStatusCode::SUCCESS), sta_iface_};
690 }
691
692 std::pair<WifiStatus, std::vector<hidl_string>>
getStaIfaceNamesInternal()693 WifiChip::getStaIfaceNamesInternal() {
694 if (!sta_iface_.get()) {
695 return {createWifiStatus(WifiStatusCode::SUCCESS), {}};
696 }
697 return {createWifiStatus(WifiStatusCode::SUCCESS),
698 {legacy_hal_.lock()->getStaIfaceName()}};
699 }
700
getStaIfaceInternal(const std::string & ifname)701 std::pair<WifiStatus, sp<IWifiStaIface>> WifiChip::getStaIfaceInternal(
702 const std::string& ifname) {
703 if (!sta_iface_.get() || (ifname != legacy_hal_.lock()->getStaIfaceName())) {
704 return {createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS), nullptr};
705 }
706 return {createWifiStatus(WifiStatusCode::SUCCESS), sta_iface_};
707 }
708
removeStaIfaceInternal(const std::string & ifname)709 WifiStatus WifiChip::removeStaIfaceInternal(const std::string& ifname) {
710 if (!sta_iface_.get() || (ifname != legacy_hal_.lock()->getStaIfaceName())) {
711 return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
712 }
713 invalidateAndClear(sta_iface_);
714 for (const auto& callback : event_cb_handler_.getCallbacks()) {
715 if (!callback->onIfaceRemoved(IfaceType::STA, ifname).isOk()) {
716 LOG(ERROR) << "Failed to invoke onIfaceRemoved callback";
717 }
718 }
719 return createWifiStatus(WifiStatusCode::SUCCESS);
720 }
721
722 std::pair<WifiStatus, sp<IWifiRttController>>
createRttControllerInternal(const sp<IWifiIface> & bound_iface)723 WifiChip::createRttControllerInternal(const sp<IWifiIface>& bound_iface) {
724 sp<WifiRttController> rtt = new WifiRttController(bound_iface, legacy_hal_);
725 rtt_controllers_.emplace_back(rtt);
726 return {createWifiStatus(WifiStatusCode::SUCCESS), rtt};
727 }
728
729 std::pair<WifiStatus, std::vector<WifiDebugRingBufferStatus>>
getDebugRingBuffersStatusInternal()730 WifiChip::getDebugRingBuffersStatusInternal() {
731 legacy_hal::wifi_error legacy_status;
732 std::vector<legacy_hal::wifi_ring_buffer_status>
733 legacy_ring_buffer_status_vec;
734 std::tie(legacy_status, legacy_ring_buffer_status_vec) =
735 legacy_hal_.lock()->getRingBuffersStatus();
736 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
737 return {createWifiStatusFromLegacyError(legacy_status), {}};
738 }
739 std::vector<WifiDebugRingBufferStatus> hidl_ring_buffer_status_vec;
740 if (!hidl_struct_util::convertLegacyVectorOfDebugRingBufferStatusToHidl(
741 legacy_ring_buffer_status_vec, &hidl_ring_buffer_status_vec)) {
742 return {createWifiStatus(WifiStatusCode::ERROR_UNKNOWN), {}};
743 }
744 return {createWifiStatus(WifiStatusCode::SUCCESS),
745 hidl_ring_buffer_status_vec};
746 }
747
startLoggingToDebugRingBufferInternal(const hidl_string & ring_name,WifiDebugRingBufferVerboseLevel verbose_level,uint32_t max_interval_in_sec,uint32_t min_data_size_in_bytes)748 WifiStatus WifiChip::startLoggingToDebugRingBufferInternal(
749 const hidl_string& ring_name,
750 WifiDebugRingBufferVerboseLevel verbose_level,
751 uint32_t max_interval_in_sec,
752 uint32_t min_data_size_in_bytes) {
753 WifiStatus status = registerDebugRingBufferCallback();
754 if (status.code != WifiStatusCode::SUCCESS) {
755 return status;
756 }
757 legacy_hal::wifi_error legacy_status =
758 legacy_hal_.lock()->startRingBufferLogging(
759 ring_name,
760 static_cast<
761 std::underlying_type<WifiDebugRingBufferVerboseLevel>::type>(
762 verbose_level),
763 max_interval_in_sec,
764 min_data_size_in_bytes);
765 return createWifiStatusFromLegacyError(legacy_status);
766 }
767
forceDumpToDebugRingBufferInternal(const hidl_string & ring_name)768 WifiStatus WifiChip::forceDumpToDebugRingBufferInternal(
769 const hidl_string& ring_name) {
770 WifiStatus status = registerDebugRingBufferCallback();
771 if (status.code != WifiStatusCode::SUCCESS) {
772 return status;
773 }
774 legacy_hal::wifi_error legacy_status =
775 legacy_hal_.lock()->getRingBufferData(ring_name);
776 return createWifiStatusFromLegacyError(legacy_status);
777 }
778
stopLoggingToDebugRingBufferInternal()779 WifiStatus WifiChip::stopLoggingToDebugRingBufferInternal() {
780 legacy_hal::wifi_error legacy_status =
781 legacy_hal_.lock()->deregisterRingBufferCallbackHandler();
782 return createWifiStatusFromLegacyError(legacy_status);
783 }
784
785 std::pair<WifiStatus, WifiDebugHostWakeReasonStats>
getDebugHostWakeReasonStatsInternal()786 WifiChip::getDebugHostWakeReasonStatsInternal() {
787 legacy_hal::wifi_error legacy_status;
788 legacy_hal::WakeReasonStats legacy_stats;
789 std::tie(legacy_status, legacy_stats) =
790 legacy_hal_.lock()->getWakeReasonStats();
791 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
792 return {createWifiStatusFromLegacyError(legacy_status), {}};
793 }
794 WifiDebugHostWakeReasonStats hidl_stats;
795 if (!hidl_struct_util::convertLegacyWakeReasonStatsToHidl(legacy_stats,
796 &hidl_stats)) {
797 return {createWifiStatus(WifiStatusCode::ERROR_UNKNOWN), {}};
798 }
799 return {createWifiStatus(WifiStatusCode::SUCCESS), hidl_stats};
800 }
801
enableDebugErrorAlertsInternal(bool enable)802 WifiStatus WifiChip::enableDebugErrorAlertsInternal(bool enable) {
803 legacy_hal::wifi_error legacy_status;
804 if (enable) {
805 android::wp<WifiChip> weak_ptr_this(this);
806 const auto& on_alert_callback = [weak_ptr_this](
807 int32_t error_code, std::vector<uint8_t> debug_data) {
808 const auto shared_ptr_this = weak_ptr_this.promote();
809 if (!shared_ptr_this.get() || !shared_ptr_this->isValid()) {
810 LOG(ERROR) << "Callback invoked on an invalid object";
811 return;
812 }
813 for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
814 if (!callback->onDebugErrorAlert(error_code, debug_data).isOk()) {
815 LOG(ERROR) << "Failed to invoke onDebugErrorAlert callback";
816 }
817 }
818 };
819 legacy_status = legacy_hal_.lock()->registerErrorAlertCallbackHandler(
820 on_alert_callback);
821 } else {
822 legacy_status = legacy_hal_.lock()->deregisterErrorAlertCallbackHandler();
823 }
824 return createWifiStatusFromLegacyError(legacy_status);
825 }
826
selectTxPowerScenarioInternal(TxPowerScenario scenario)827 WifiStatus WifiChip::selectTxPowerScenarioInternal(TxPowerScenario scenario) {
828 auto legacy_status = legacy_hal_.lock()->selectTxPowerScenario(
829 hidl_struct_util::convertHidlTxPowerScenarioToLegacy(scenario));
830 return createWifiStatusFromLegacyError(legacy_status);
831 }
832
resetTxPowerScenarioInternal()833 WifiStatus WifiChip::resetTxPowerScenarioInternal() {
834 auto legacy_status = legacy_hal_.lock()->resetTxPowerScenario();
835 return createWifiStatusFromLegacyError(legacy_status);
836 }
837
handleChipConfiguration(ChipModeId mode_id)838 WifiStatus WifiChip::handleChipConfiguration(ChipModeId mode_id) {
839 // If the chip is already configured in a different mode, stop
840 // the legacy HAL and then start it after firmware mode change.
841 // Currently the underlying implementation has a deadlock issue.
842 // We should return ERROR_NOT_SUPPORTED if chip is already configured in
843 // a different mode.
844 if (current_mode_id_ != kInvalidModeId) {
845 // TODO(b/37446050): Fix the deadlock.
846 return createWifiStatus(WifiStatusCode::ERROR_NOT_SUPPORTED);
847 }
848 bool success;
849 if (mode_id == kStaChipModeId) {
850 success = mode_controller_.lock()->changeFirmwareMode(IfaceType::STA);
851 } else {
852 success = mode_controller_.lock()->changeFirmwareMode(IfaceType::AP);
853 }
854 if (!success) {
855 return createWifiStatus(WifiStatusCode::ERROR_UNKNOWN);
856 }
857 legacy_hal::wifi_error legacy_status = legacy_hal_.lock()->start();
858 if (legacy_status != legacy_hal::WIFI_SUCCESS) {
859 LOG(ERROR) << "Failed to start legacy HAL: "
860 << legacyErrorToString(legacy_status);
861 return createWifiStatusFromLegacyError(legacy_status);
862 }
863 return createWifiStatus(WifiStatusCode::SUCCESS);
864 }
865
registerDebugRingBufferCallback()866 WifiStatus WifiChip::registerDebugRingBufferCallback() {
867 if (debug_ring_buffer_cb_registered_) {
868 return createWifiStatus(WifiStatusCode::SUCCESS);
869 }
870
871 android::wp<WifiChip> weak_ptr_this(this);
872 const auto& on_ring_buffer_data_callback = [weak_ptr_this](
873 const std::string& /* name */,
874 const std::vector<uint8_t>& data,
875 const legacy_hal::wifi_ring_buffer_status& status) {
876 const auto shared_ptr_this = weak_ptr_this.promote();
877 if (!shared_ptr_this.get() || !shared_ptr_this->isValid()) {
878 LOG(ERROR) << "Callback invoked on an invalid object";
879 return;
880 }
881 WifiDebugRingBufferStatus hidl_status;
882 if (!hidl_struct_util::convertLegacyDebugRingBufferStatusToHidl(
883 status, &hidl_status)) {
884 LOG(ERROR) << "Error converting ring buffer status";
885 return;
886 }
887 for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
888 if (!callback->onDebugRingBufferDataAvailable(hidl_status, data).isOk()) {
889 LOG(ERROR) << "Failed to invoke onDebugRingBufferDataAvailable"
890 << " callback on: " << toString(callback);
891
892 }
893 }
894 };
895 legacy_hal::wifi_error legacy_status =
896 legacy_hal_.lock()->registerRingBufferCallbackHandler(
897 on_ring_buffer_data_callback);
898
899 if (legacy_status == legacy_hal::WIFI_SUCCESS) {
900 debug_ring_buffer_cb_registered_ = true;
901 }
902 return createWifiStatusFromLegacyError(legacy_status);
903 }
904
905 } // namespace implementation
906 } // namespace V1_1
907 } // namespace wifi
908 } // namespace hardware
909 } // namespace android
910