blob: 5f3e313418206deea809bbcfb24c8e7a22a645cd [file] [log] [blame]
Gabriel Birenf3262f92022-07-15 23:25:39 +00001/*
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 "wifi_legacy_hal.h"
18
19#include <android-base/logging.h>
20#include <cutils/properties.h>
21#include <net/if.h>
22
23#include <array>
24#include <chrono>
25
26#include "aidl_sync_util.h"
27#include "wifi_legacy_hal_stubs.h"
28
29namespace {
30// Constants ported over from the legacy HAL calling code
31// (com_android_server_wifi_WifiNative.cpp). This will all be thrown
32// away when this shim layer is replaced by the real vendor
33// implementation.
34static constexpr uint32_t kMaxVersionStringLength = 256;
35static constexpr uint32_t kMaxCachedGscanResults = 64;
36static constexpr uint32_t kMaxGscanFrequenciesForBand = 64;
37static constexpr uint32_t kLinkLayerStatsDataMpduSizeThreshold = 128;
38static constexpr uint32_t kMaxWakeReasonStatsArraySize = 32;
39static constexpr uint32_t kMaxRingBuffers = 10;
40static constexpr uint32_t kMaxWifiUsableChannels = 256;
41static constexpr uint32_t kMaxSupportedRadioCombinationsMatrixLength = 256;
42// Need a long timeout (1000ms) for chips that unload their driver.
43static constexpr uint32_t kMaxStopCompleteWaitMs = 1000;
44static constexpr char kDriverPropName[] = "wlan.driver.status";
45
46// Helper function to create a non-const char* for legacy Hal API's.
47std::vector<char> makeCharVec(const std::string& str) {
48 std::vector<char> vec(str.size() + 1);
49 vec.assign(str.begin(), str.end());
50 vec.push_back('\0');
51 return vec;
52}
53} // namespace
54
55namespace aidl {
56namespace android {
57namespace hardware {
58namespace wifi {
59namespace legacy_hal {
60
61// Legacy HAL functions accept "C" style function pointers, so use global
62// functions to pass to the legacy HAL function and store the corresponding
63// std::function methods to be invoked.
64//
65// Callback to be invoked once |stop| is complete
66std::function<void(wifi_handle handle)> on_stop_complete_internal_callback;
67void onAsyncStopComplete(wifi_handle handle) {
68 const auto lock = aidl_sync_util::acquireGlobalLock();
69 if (on_stop_complete_internal_callback) {
70 on_stop_complete_internal_callback(handle);
71 // Invalidate this callback since we don't want this firing again.
72 on_stop_complete_internal_callback = nullptr;
73 }
74}
75
76// Callback to be invoked for driver dump.
77std::function<void(char*, int)> on_driver_memory_dump_internal_callback;
78void onSyncDriverMemoryDump(char* buffer, int buffer_size) {
79 if (on_driver_memory_dump_internal_callback) {
80 on_driver_memory_dump_internal_callback(buffer, buffer_size);
81 }
82}
83
84// Callback to be invoked for firmware dump.
85std::function<void(char*, int)> on_firmware_memory_dump_internal_callback;
86void onSyncFirmwareMemoryDump(char* buffer, int buffer_size) {
87 if (on_firmware_memory_dump_internal_callback) {
88 on_firmware_memory_dump_internal_callback(buffer, buffer_size);
89 }
90}
91
92// Callback to be invoked for Gscan events.
93std::function<void(wifi_request_id, wifi_scan_event)> on_gscan_event_internal_callback;
94void onAsyncGscanEvent(wifi_request_id id, wifi_scan_event event) {
95 const auto lock = aidl_sync_util::acquireGlobalLock();
96 if (on_gscan_event_internal_callback) {
97 on_gscan_event_internal_callback(id, event);
98 }
99}
100
101// Callback to be invoked for Gscan full results.
102std::function<void(wifi_request_id, wifi_scan_result*, uint32_t)>
103 on_gscan_full_result_internal_callback;
104void onAsyncGscanFullResult(wifi_request_id id, wifi_scan_result* result,
105 uint32_t buckets_scanned) {
106 const auto lock = aidl_sync_util::acquireGlobalLock();
107 if (on_gscan_full_result_internal_callback) {
108 on_gscan_full_result_internal_callback(id, result, buckets_scanned);
109 }
110}
111
112// Callback to be invoked for link layer stats results.
113std::function<void((wifi_request_id, wifi_iface_stat*, int, wifi_radio_stat*))>
114 on_link_layer_stats_result_internal_callback;
115void onSyncLinkLayerStatsResult(wifi_request_id id, wifi_iface_stat* iface_stat, int num_radios,
116 wifi_radio_stat* radio_stat) {
117 if (on_link_layer_stats_result_internal_callback) {
118 on_link_layer_stats_result_internal_callback(id, iface_stat, num_radios, radio_stat);
119 }
120}
121
Mahesh KKV5f30d332022-10-26 14:07:44 -0700122// Callback to be invoked for Multi link layer stats results.
123std::function<void((wifi_request_id, wifi_iface_ml_stat*, int, wifi_radio_stat*))>
124 on_link_layer_ml_stats_result_internal_callback;
125void onSyncLinkLayerMlStatsResult(wifi_request_id id, wifi_iface_ml_stat* iface_ml_stat,
126 int num_radios, wifi_radio_stat* radio_stat) {
127 if (on_link_layer_ml_stats_result_internal_callback) {
128 on_link_layer_ml_stats_result_internal_callback(id, iface_ml_stat, num_radios, radio_stat);
129 }
130}
131
Gabriel Birenf3262f92022-07-15 23:25:39 +0000132// Callback to be invoked for rssi threshold breach.
133std::function<void((wifi_request_id, uint8_t*, int8_t))>
134 on_rssi_threshold_breached_internal_callback;
135void onAsyncRssiThresholdBreached(wifi_request_id id, uint8_t* bssid, int8_t rssi) {
136 const auto lock = aidl_sync_util::acquireGlobalLock();
137 if (on_rssi_threshold_breached_internal_callback) {
138 on_rssi_threshold_breached_internal_callback(id, bssid, rssi);
139 }
140}
141
142// Callback to be invoked for ring buffer data indication.
143std::function<void(char*, char*, int, wifi_ring_buffer_status*)>
144 on_ring_buffer_data_internal_callback;
145void onAsyncRingBufferData(char* ring_name, char* buffer, int buffer_size,
146 wifi_ring_buffer_status* status) {
147 const auto lock = aidl_sync_util::acquireGlobalLock();
148 if (on_ring_buffer_data_internal_callback) {
149 on_ring_buffer_data_internal_callback(ring_name, buffer, buffer_size, status);
150 }
151}
152
153// Callback to be invoked for error alert indication.
154std::function<void(wifi_request_id, char*, int, int)> on_error_alert_internal_callback;
155void onAsyncErrorAlert(wifi_request_id id, char* buffer, int buffer_size, int err_code) {
156 const auto lock = aidl_sync_util::acquireGlobalLock();
157 if (on_error_alert_internal_callback) {
158 on_error_alert_internal_callback(id, buffer, buffer_size, err_code);
159 }
160}
161
162// Callback to be invoked for radio mode change indication.
163std::function<void(wifi_request_id, uint32_t, wifi_mac_info*)>
164 on_radio_mode_change_internal_callback;
165void onAsyncRadioModeChange(wifi_request_id id, uint32_t num_macs, wifi_mac_info* mac_infos) {
166 const auto lock = aidl_sync_util::acquireGlobalLock();
167 if (on_radio_mode_change_internal_callback) {
168 on_radio_mode_change_internal_callback(id, num_macs, mac_infos);
169 }
170}
171
172// Callback to be invoked to report subsystem restart
173std::function<void(const char*)> on_subsystem_restart_internal_callback;
174void onAsyncSubsystemRestart(const char* error) {
175 const auto lock = aidl_sync_util::acquireGlobalLock();
176 if (on_subsystem_restart_internal_callback) {
177 on_subsystem_restart_internal_callback(error);
178 }
179}
180
181// Callback to be invoked for rtt results results.
182std::function<void(wifi_request_id, unsigned num_results, wifi_rtt_result* rtt_results[])>
183 on_rtt_results_internal_callback;
Sunil Ravif8fc2372022-11-10 18:37:41 +0000184std::function<void(wifi_request_id, unsigned num_results, wifi_rtt_result_v2* rtt_results_v2[])>
185 on_rtt_results_internal_callback_v2;
186
187void invalidateRttResultsCallbacks() {
188 on_rtt_results_internal_callback = nullptr;
189 on_rtt_results_internal_callback_v2 = nullptr;
190};
191
Gabriel Birenf3262f92022-07-15 23:25:39 +0000192void onAsyncRttResults(wifi_request_id id, unsigned num_results, wifi_rtt_result* rtt_results[]) {
193 const auto lock = aidl_sync_util::acquireGlobalLock();
194 if (on_rtt_results_internal_callback) {
195 on_rtt_results_internal_callback(id, num_results, rtt_results);
Sunil Ravif8fc2372022-11-10 18:37:41 +0000196 invalidateRttResultsCallbacks();
197 }
198}
199
200void onAsyncRttResultsV2(wifi_request_id id, unsigned num_results,
201 wifi_rtt_result_v2* rtt_results_v2[]) {
202 const auto lock = aidl_sync_util::acquireGlobalLock();
203 if (on_rtt_results_internal_callback_v2) {
204 on_rtt_results_internal_callback_v2(id, num_results, rtt_results_v2);
205 invalidateRttResultsCallbacks();
Gabriel Birenf3262f92022-07-15 23:25:39 +0000206 }
207}
208
209// Callbacks for the various NAN operations.
210// NOTE: These have very little conversions to perform before invoking the user
211// callbacks.
212// So, handle all of them here directly to avoid adding an unnecessary layer.
213std::function<void(transaction_id, const NanResponseMsg&)> on_nan_notify_response_user_callback;
214void onAsyncNanNotifyResponse(transaction_id id, NanResponseMsg* msg) {
215 const auto lock = aidl_sync_util::acquireGlobalLock();
216 if (on_nan_notify_response_user_callback && msg) {
217 on_nan_notify_response_user_callback(id, *msg);
218 }
219}
220
221std::function<void(const NanPublishRepliedInd&)> on_nan_event_publish_replied_user_callback;
222void onAsyncNanEventPublishReplied(NanPublishRepliedInd* /* event */) {
223 LOG(ERROR) << "onAsyncNanEventPublishReplied triggered";
224}
225
226std::function<void(const NanPublishTerminatedInd&)> on_nan_event_publish_terminated_user_callback;
227void onAsyncNanEventPublishTerminated(NanPublishTerminatedInd* event) {
228 const auto lock = aidl_sync_util::acquireGlobalLock();
229 if (on_nan_event_publish_terminated_user_callback && event) {
230 on_nan_event_publish_terminated_user_callback(*event);
231 }
232}
233
234std::function<void(const NanMatchInd&)> on_nan_event_match_user_callback;
235void onAsyncNanEventMatch(NanMatchInd* event) {
236 const auto lock = aidl_sync_util::acquireGlobalLock();
237 if (on_nan_event_match_user_callback && event) {
238 on_nan_event_match_user_callback(*event);
239 }
240}
241
242std::function<void(const NanMatchExpiredInd&)> on_nan_event_match_expired_user_callback;
243void onAsyncNanEventMatchExpired(NanMatchExpiredInd* event) {
244 const auto lock = aidl_sync_util::acquireGlobalLock();
245 if (on_nan_event_match_expired_user_callback && event) {
246 on_nan_event_match_expired_user_callback(*event);
247 }
248}
249
250std::function<void(const NanSubscribeTerminatedInd&)>
251 on_nan_event_subscribe_terminated_user_callback;
252void onAsyncNanEventSubscribeTerminated(NanSubscribeTerminatedInd* event) {
253 const auto lock = aidl_sync_util::acquireGlobalLock();
254 if (on_nan_event_subscribe_terminated_user_callback && event) {
255 on_nan_event_subscribe_terminated_user_callback(*event);
256 }
257}
258
259std::function<void(const NanFollowupInd&)> on_nan_event_followup_user_callback;
260void onAsyncNanEventFollowup(NanFollowupInd* event) {
261 const auto lock = aidl_sync_util::acquireGlobalLock();
262 if (on_nan_event_followup_user_callback && event) {
263 on_nan_event_followup_user_callback(*event);
264 }
265}
266
267std::function<void(const NanDiscEngEventInd&)> on_nan_event_disc_eng_event_user_callback;
268void onAsyncNanEventDiscEngEvent(NanDiscEngEventInd* event) {
269 const auto lock = aidl_sync_util::acquireGlobalLock();
270 if (on_nan_event_disc_eng_event_user_callback && event) {
271 on_nan_event_disc_eng_event_user_callback(*event);
272 }
273}
274
275std::function<void(const NanDisabledInd&)> on_nan_event_disabled_user_callback;
276void onAsyncNanEventDisabled(NanDisabledInd* event) {
277 const auto lock = aidl_sync_util::acquireGlobalLock();
278 if (on_nan_event_disabled_user_callback && event) {
279 on_nan_event_disabled_user_callback(*event);
280 }
281}
282
283std::function<void(const NanTCAInd&)> on_nan_event_tca_user_callback;
284void onAsyncNanEventTca(NanTCAInd* event) {
285 const auto lock = aidl_sync_util::acquireGlobalLock();
286 if (on_nan_event_tca_user_callback && event) {
287 on_nan_event_tca_user_callback(*event);
288 }
289}
290
291std::function<void(const NanBeaconSdfPayloadInd&)> on_nan_event_beacon_sdf_payload_user_callback;
292void onAsyncNanEventBeaconSdfPayload(NanBeaconSdfPayloadInd* event) {
293 const auto lock = aidl_sync_util::acquireGlobalLock();
294 if (on_nan_event_beacon_sdf_payload_user_callback && event) {
295 on_nan_event_beacon_sdf_payload_user_callback(*event);
296 }
297}
298
299std::function<void(const NanDataPathRequestInd&)> on_nan_event_data_path_request_user_callback;
300void onAsyncNanEventDataPathRequest(NanDataPathRequestInd* event) {
301 const auto lock = aidl_sync_util::acquireGlobalLock();
302 if (on_nan_event_data_path_request_user_callback && event) {
303 on_nan_event_data_path_request_user_callback(*event);
304 }
305}
306std::function<void(const NanDataPathConfirmInd&)> on_nan_event_data_path_confirm_user_callback;
307void onAsyncNanEventDataPathConfirm(NanDataPathConfirmInd* event) {
308 const auto lock = aidl_sync_util::acquireGlobalLock();
309 if (on_nan_event_data_path_confirm_user_callback && event) {
310 on_nan_event_data_path_confirm_user_callback(*event);
311 }
312}
313
314std::function<void(const NanDataPathEndInd&)> on_nan_event_data_path_end_user_callback;
315void onAsyncNanEventDataPathEnd(NanDataPathEndInd* event) {
316 const auto lock = aidl_sync_util::acquireGlobalLock();
317 if (on_nan_event_data_path_end_user_callback && event) {
318 on_nan_event_data_path_end_user_callback(*event);
319 }
320}
321
322std::function<void(const NanTransmitFollowupInd&)> on_nan_event_transmit_follow_up_user_callback;
323void onAsyncNanEventTransmitFollowUp(NanTransmitFollowupInd* event) {
324 const auto lock = aidl_sync_util::acquireGlobalLock();
325 if (on_nan_event_transmit_follow_up_user_callback && event) {
326 on_nan_event_transmit_follow_up_user_callback(*event);
327 }
328}
329
330std::function<void(const NanRangeRequestInd&)> on_nan_event_range_request_user_callback;
331void onAsyncNanEventRangeRequest(NanRangeRequestInd* event) {
332 const auto lock = aidl_sync_util::acquireGlobalLock();
333 if (on_nan_event_range_request_user_callback && event) {
334 on_nan_event_range_request_user_callback(*event);
335 }
336}
337
338std::function<void(const NanRangeReportInd&)> on_nan_event_range_report_user_callback;
339void onAsyncNanEventRangeReport(NanRangeReportInd* event) {
340 const auto lock = aidl_sync_util::acquireGlobalLock();
341 if (on_nan_event_range_report_user_callback && event) {
342 on_nan_event_range_report_user_callback(*event);
343 }
344}
345
346std::function<void(const NanDataPathScheduleUpdateInd&)> on_nan_event_schedule_update_user_callback;
347void onAsyncNanEventScheduleUpdate(NanDataPathScheduleUpdateInd* event) {
348 const auto lock = aidl_sync_util::acquireGlobalLock();
349 if (on_nan_event_schedule_update_user_callback && event) {
350 on_nan_event_schedule_update_user_callback(*event);
351 }
352}
353
Nate Jiangd6cc3312023-02-14 16:37:54 -0800354std::function<void(const NanSuspensionModeChangeInd&)>
355 on_nan_event_suspension_mode_change_user_callback;
356void onAsyncNanEventSuspensionModeChange(NanSuspensionModeChangeInd* event) {
357 const auto lock = aidl_sync_util::acquireGlobalLock();
358 if (on_nan_event_suspension_mode_change_user_callback && event) {
359 on_nan_event_suspension_mode_change_user_callback(*event);
360 }
361}
362
Nate Jiang38e8db52022-12-02 17:30:27 -0800363std::function<void(const NanPairingRequestInd&)> on_nan_event_pairing_request_user_callback;
364void onAsyncNanEventPairingRequest(NanPairingRequestInd* event) {
365 const auto lock = aidl_sync_util::acquireGlobalLock();
366 if (on_nan_event_pairing_request_user_callback && event) {
367 on_nan_event_pairing_request_user_callback(*event);
368 }
369}
370
371std::function<void(const NanPairingConfirmInd&)> on_nan_event_pairing_confirm_user_callback;
372void onAsyncNanEventPairingConfirm(NanPairingConfirmInd* event) {
373 const auto lock = aidl_sync_util::acquireGlobalLock();
374 if (on_nan_event_pairing_confirm_user_callback && event) {
375 on_nan_event_pairing_confirm_user_callback(*event);
376 }
377}
378
379std::function<void(const NanBootstrappingRequestInd&)>
380 on_nan_event_bootstrapping_request_user_callback;
381void onAsyncNanEventBootstrappingRequest(NanBootstrappingRequestInd* event) {
382 const auto lock = aidl_sync_util::acquireGlobalLock();
383 if (on_nan_event_bootstrapping_request_user_callback && event) {
384 on_nan_event_bootstrapping_request_user_callback(*event);
385 }
386}
387
388std::function<void(const NanBootstrappingConfirmInd&)>
389 on_nan_event_bootstrapping_confirm_user_callback;
390void onAsyncNanEventBootstrappingConfirm(NanBootstrappingConfirmInd* event) {
391 const auto lock = aidl_sync_util::acquireGlobalLock();
392 if (on_nan_event_bootstrapping_confirm_user_callback && event) {
393 on_nan_event_bootstrapping_confirm_user_callback(*event);
394 }
395}
396
Gabriel Birenf3262f92022-07-15 23:25:39 +0000397// Callbacks for the various TWT operations.
398std::function<void(const TwtSetupResponse&)> on_twt_event_setup_response_callback;
399void onAsyncTwtEventSetupResponse(TwtSetupResponse* event) {
400 const auto lock = aidl_sync_util::acquireGlobalLock();
401 if (on_twt_event_setup_response_callback && event) {
402 on_twt_event_setup_response_callback(*event);
403 }
404}
405
406std::function<void(const TwtTeardownCompletion&)> on_twt_event_teardown_completion_callback;
407void onAsyncTwtEventTeardownCompletion(TwtTeardownCompletion* event) {
408 const auto lock = aidl_sync_util::acquireGlobalLock();
409 if (on_twt_event_teardown_completion_callback && event) {
410 on_twt_event_teardown_completion_callback(*event);
411 }
412}
413
414std::function<void(const TwtInfoFrameReceived&)> on_twt_event_info_frame_received_callback;
415void onAsyncTwtEventInfoFrameReceived(TwtInfoFrameReceived* event) {
416 const auto lock = aidl_sync_util::acquireGlobalLock();
417 if (on_twt_event_info_frame_received_callback && event) {
418 on_twt_event_info_frame_received_callback(*event);
419 }
420}
421
422std::function<void(const TwtDeviceNotify&)> on_twt_event_device_notify_callback;
423void onAsyncTwtEventDeviceNotify(TwtDeviceNotify* event) {
424 const auto lock = aidl_sync_util::acquireGlobalLock();
425 if (on_twt_event_device_notify_callback && event) {
426 on_twt_event_device_notify_callback(*event);
427 }
428}
429
430// Callback to report current CHRE NAN state
431std::function<void(chre_nan_rtt_state)> on_chre_nan_rtt_internal_callback;
432void onAsyncChreNanRttState(chre_nan_rtt_state state) {
433 const auto lock = aidl_sync_util::acquireGlobalLock();
434 if (on_chre_nan_rtt_internal_callback) {
435 on_chre_nan_rtt_internal_callback(state);
436 }
437}
438
439// Callback to report cached scan results
440std::function<void(wifi_cached_scan_report*)> on_cached_scan_results_internal_callback;
441void onSyncCachedScanResults(wifi_cached_scan_report* cache_report) {
Kai Shi7d0e5e92023-11-20 19:23:36 -0800442 const auto lock = aidl_sync_util::acquireGlobalLock();
Gabriel Birenf3262f92022-07-15 23:25:39 +0000443 if (on_cached_scan_results_internal_callback) {
444 on_cached_scan_results_internal_callback(cache_report);
445 }
446}
447
448// End of the free-standing "C" style callbacks.
449
450WifiLegacyHal::WifiLegacyHal(const std::weak_ptr<::android::wifi_system::InterfaceTool> iface_tool,
451 const wifi_hal_fn& fn, bool is_primary)
452 : global_func_table_(fn),
453 global_handle_(nullptr),
454 awaiting_event_loop_termination_(false),
455 is_started_(false),
456 iface_tool_(iface_tool),
457 is_primary_(is_primary) {}
458
459wifi_error WifiLegacyHal::initialize() {
460 LOG(DEBUG) << "Initialize legacy HAL";
461 // this now does nothing, since HAL function table is provided
462 // to the constructor
463 return WIFI_SUCCESS;
464}
465
466wifi_error WifiLegacyHal::start() {
467 // Ensure that we're starting in a good state.
468 CHECK(global_func_table_.wifi_initialize && !global_handle_ && iface_name_to_handle_.empty() &&
469 !awaiting_event_loop_termination_);
470 if (is_started_) {
471 LOG(DEBUG) << "Legacy HAL already started";
472 return WIFI_SUCCESS;
473 }
474 LOG(DEBUG) << "Waiting for the driver ready";
475 wifi_error status = global_func_table_.wifi_wait_for_driver_ready();
476 if (status == WIFI_ERROR_TIMED_OUT || status == WIFI_ERROR_UNKNOWN) {
477 LOG(ERROR) << "Failed or timed out awaiting driver ready";
478 return status;
479 }
480
481 if (is_primary_) {
482 property_set(kDriverPropName, "ok");
483
484 if (!iface_tool_.lock()->SetWifiUpState(true)) {
485 LOG(ERROR) << "Failed to set WiFi interface up";
486 return WIFI_ERROR_UNKNOWN;
487 }
488 }
489
490 LOG(DEBUG) << "Starting legacy HAL";
491 status = global_func_table_.wifi_initialize(&global_handle_);
492 if (status != WIFI_SUCCESS || !global_handle_) {
493 LOG(ERROR) << "Failed to retrieve global handle";
494 return status;
495 }
496 std::thread(&WifiLegacyHal::runEventLoop, this).detach();
497 status = retrieveIfaceHandles();
498 if (status != WIFI_SUCCESS || iface_name_to_handle_.empty()) {
499 LOG(ERROR) << "Failed to retrieve wlan interface handle";
500 return status;
501 }
502 LOG(DEBUG) << "Legacy HAL start complete";
503 is_started_ = true;
504 return WIFI_SUCCESS;
505}
506
507wifi_error WifiLegacyHal::stop(
508 /* NONNULL */ std::unique_lock<std::recursive_mutex>* lock,
509 const std::function<void()>& on_stop_complete_user_callback) {
510 if (!is_started_) {
511 LOG(DEBUG) << "Legacy HAL already stopped";
512 on_stop_complete_user_callback();
513 return WIFI_SUCCESS;
514 }
515 LOG(DEBUG) << "Stopping legacy HAL";
516 on_stop_complete_internal_callback = [on_stop_complete_user_callback,
517 this](wifi_handle handle) {
518 CHECK_EQ(global_handle_, handle) << "Handle mismatch";
519 LOG(INFO) << "Legacy HAL stop complete callback received";
520 // Invalidate all the internal pointers now that the HAL is
521 // stopped.
522 invalidate();
523 if (is_primary_) iface_tool_.lock()->SetWifiUpState(false);
524 on_stop_complete_user_callback();
525 is_started_ = false;
526 };
527 awaiting_event_loop_termination_ = true;
528 global_func_table_.wifi_cleanup(global_handle_, onAsyncStopComplete);
529 const auto status =
530 stop_wait_cv_.wait_for(*lock, std::chrono::milliseconds(kMaxStopCompleteWaitMs),
531 [this] { return !awaiting_event_loop_termination_; });
532 if (!status) {
533 LOG(ERROR) << "Legacy HAL stop failed or timed out";
534 return WIFI_ERROR_UNKNOWN;
535 }
536 LOG(DEBUG) << "Legacy HAL stop complete";
537 return WIFI_SUCCESS;
538}
539
540bool WifiLegacyHal::isStarted() {
541 return is_started_;
542}
543
544wifi_error WifiLegacyHal::waitForDriverReady() {
545 return global_func_table_.wifi_wait_for_driver_ready();
546}
547
548std::pair<wifi_error, std::string> WifiLegacyHal::getDriverVersion(const std::string& iface_name) {
549 std::array<char, kMaxVersionStringLength> buffer;
550 buffer.fill(0);
551 wifi_error status = global_func_table_.wifi_get_driver_version(getIfaceHandle(iface_name),
552 buffer.data(), buffer.size());
553 return {status, buffer.data()};
554}
555
556std::pair<wifi_error, std::string> WifiLegacyHal::getFirmwareVersion(
557 const std::string& iface_name) {
558 std::array<char, kMaxVersionStringLength> buffer;
559 buffer.fill(0);
560 wifi_error status = global_func_table_.wifi_get_firmware_version(getIfaceHandle(iface_name),
561 buffer.data(), buffer.size());
562 return {status, buffer.data()};
563}
564
565std::pair<wifi_error, std::vector<uint8_t>> WifiLegacyHal::requestDriverMemoryDump(
566 const std::string& iface_name) {
567 std::vector<uint8_t> driver_dump;
568 on_driver_memory_dump_internal_callback = [&driver_dump](char* buffer, int buffer_size) {
569 driver_dump.insert(driver_dump.end(), reinterpret_cast<uint8_t*>(buffer),
570 reinterpret_cast<uint8_t*>(buffer) + buffer_size);
571 };
572 wifi_error status = global_func_table_.wifi_get_driver_memory_dump(getIfaceHandle(iface_name),
573 {onSyncDriverMemoryDump});
574 on_driver_memory_dump_internal_callback = nullptr;
575 return {status, std::move(driver_dump)};
576}
577
578std::pair<wifi_error, std::vector<uint8_t>> WifiLegacyHal::requestFirmwareMemoryDump(
579 const std::string& iface_name) {
580 std::vector<uint8_t> firmware_dump;
581 on_firmware_memory_dump_internal_callback = [&firmware_dump](char* buffer, int buffer_size) {
582 firmware_dump.insert(firmware_dump.end(), reinterpret_cast<uint8_t*>(buffer),
583 reinterpret_cast<uint8_t*>(buffer) + buffer_size);
584 };
585 wifi_error status = global_func_table_.wifi_get_firmware_memory_dump(
586 getIfaceHandle(iface_name), {onSyncFirmwareMemoryDump});
587 on_firmware_memory_dump_internal_callback = nullptr;
588 return {status, std::move(firmware_dump)};
589}
590
591std::pair<wifi_error, uint64_t> WifiLegacyHal::getSupportedFeatureSet(
592 const std::string& iface_name) {
593 feature_set set = 0, chip_set = 0;
594 wifi_error status = WIFI_SUCCESS;
595
596 static_assert(sizeof(set) == sizeof(uint64_t),
597 "Some feature_flags can not be represented in output");
598 wifi_interface_handle iface_handle = getIfaceHandle(iface_name);
599
600 global_func_table_.wifi_get_chip_feature_set(
601 global_handle_, &chip_set); /* ignore error, chip_set will stay 0 */
602
603 if (iface_handle) {
604 status = global_func_table_.wifi_get_supported_feature_set(iface_handle, &set);
605 }
606 return {status, static_cast<uint64_t>(set | chip_set)};
607}
608
609std::pair<wifi_error, PacketFilterCapabilities> WifiLegacyHal::getPacketFilterCapabilities(
610 const std::string& iface_name) {
611 PacketFilterCapabilities caps;
612 wifi_error status = global_func_table_.wifi_get_packet_filter_capabilities(
613 getIfaceHandle(iface_name), &caps.version, &caps.max_len);
614 return {status, caps};
615}
616
617wifi_error WifiLegacyHal::setPacketFilter(const std::string& iface_name,
618 const std::vector<uint8_t>& program) {
619 return global_func_table_.wifi_set_packet_filter(getIfaceHandle(iface_name), program.data(),
620 program.size());
621}
622
623std::pair<wifi_error, std::vector<uint8_t>> WifiLegacyHal::readApfPacketFilterData(
624 const std::string& iface_name) {
625 PacketFilterCapabilities caps;
626 wifi_error status = global_func_table_.wifi_get_packet_filter_capabilities(
627 getIfaceHandle(iface_name), &caps.version, &caps.max_len);
628 if (status != WIFI_SUCCESS) {
629 return {status, {}};
630 }
631
632 // Size the buffer to read the entire program & work memory.
633 std::vector<uint8_t> buffer(caps.max_len);
634
635 status = global_func_table_.wifi_read_packet_filter(
636 getIfaceHandle(iface_name), /*src_offset=*/0, buffer.data(), buffer.size());
637 return {status, std::move(buffer)};
638}
639
640std::pair<wifi_error, wifi_gscan_capabilities> WifiLegacyHal::getGscanCapabilities(
641 const std::string& iface_name) {
642 wifi_gscan_capabilities caps;
643 wifi_error status =
644 global_func_table_.wifi_get_gscan_capabilities(getIfaceHandle(iface_name), &caps);
645 return {status, caps};
646}
647
648wifi_error WifiLegacyHal::startGscan(
649 const std::string& iface_name, wifi_request_id id, const wifi_scan_cmd_params& params,
650 const std::function<void(wifi_request_id)>& on_failure_user_callback,
651 const on_gscan_results_callback& on_results_user_callback,
652 const on_gscan_full_result_callback& on_full_result_user_callback) {
653 // If there is already an ongoing background scan, reject new scan requests.
654 if (on_gscan_event_internal_callback || on_gscan_full_result_internal_callback) {
655 return WIFI_ERROR_NOT_AVAILABLE;
656 }
657
658 // This callback will be used to either trigger |on_results_user_callback|
659 // or |on_failure_user_callback|.
660 on_gscan_event_internal_callback = [iface_name, on_failure_user_callback,
661 on_results_user_callback,
662 this](wifi_request_id id, wifi_scan_event event) {
663 switch (event) {
664 case WIFI_SCAN_RESULTS_AVAILABLE:
665 case WIFI_SCAN_THRESHOLD_NUM_SCANS:
666 case WIFI_SCAN_THRESHOLD_PERCENT: {
667 wifi_error status;
668 std::vector<wifi_cached_scan_results> cached_scan_results;
669 std::tie(status, cached_scan_results) = getGscanCachedResults(iface_name);
670 if (status == WIFI_SUCCESS) {
671 on_results_user_callback(id, cached_scan_results);
672 return;
673 }
674 FALLTHROUGH_INTENDED;
675 }
676 // Fall through if failed. Failure to retrieve cached scan
677 // results should trigger a background scan failure.
678 case WIFI_SCAN_FAILED:
679 on_failure_user_callback(id);
680 on_gscan_event_internal_callback = nullptr;
681 on_gscan_full_result_internal_callback = nullptr;
682 return;
683 }
684 LOG(FATAL) << "Unexpected gscan event received: " << event;
685 };
686
687 on_gscan_full_result_internal_callback = [on_full_result_user_callback](
688 wifi_request_id id, wifi_scan_result* result,
689 uint32_t buckets_scanned) {
690 if (result) {
691 on_full_result_user_callback(id, result, buckets_scanned);
692 }
693 };
694
695 wifi_scan_result_handler handler = {onAsyncGscanFullResult, onAsyncGscanEvent};
696 wifi_error status =
697 global_func_table_.wifi_start_gscan(id, getIfaceHandle(iface_name), params, handler);
698 if (status != WIFI_SUCCESS) {
699 on_gscan_event_internal_callback = nullptr;
700 on_gscan_full_result_internal_callback = nullptr;
701 }
702 return status;
703}
704
705wifi_error WifiLegacyHal::stopGscan(const std::string& iface_name, wifi_request_id id) {
706 // If there is no an ongoing background scan, reject stop requests.
707 // TODO(b/32337212): This needs to be handled by the HIDL object because we
708 // need to return the NOT_STARTED error code.
709 if (!on_gscan_event_internal_callback && !on_gscan_full_result_internal_callback) {
710 return WIFI_ERROR_NOT_AVAILABLE;
711 }
712 wifi_error status = global_func_table_.wifi_stop_gscan(id, getIfaceHandle(iface_name));
713 // If the request Id is wrong, don't stop the ongoing background scan. Any
714 // other error should be treated as the end of background scan.
715 if (status != WIFI_ERROR_INVALID_REQUEST_ID) {
716 on_gscan_event_internal_callback = nullptr;
717 on_gscan_full_result_internal_callback = nullptr;
718 }
719 return status;
720}
721
722std::pair<wifi_error, std::vector<uint32_t>> WifiLegacyHal::getValidFrequenciesForBand(
723 const std::string& iface_name, wifi_band band) {
724 static_assert(sizeof(uint32_t) >= sizeof(wifi_channel),
725 "Wifi Channel cannot be represented in output");
726 std::vector<uint32_t> freqs;
727 freqs.resize(kMaxGscanFrequenciesForBand);
728 int32_t num_freqs = 0;
729 wifi_error status = global_func_table_.wifi_get_valid_channels(
730 getIfaceHandle(iface_name), band, freqs.size(),
731 reinterpret_cast<wifi_channel*>(freqs.data()), &num_freqs);
732 CHECK(num_freqs >= 0 && static_cast<uint32_t>(num_freqs) <= kMaxGscanFrequenciesForBand);
733 freqs.resize(num_freqs);
734 return {status, std::move(freqs)};
735}
736
737wifi_error WifiLegacyHal::setDfsFlag(const std::string& iface_name, bool dfs_on) {
738 return global_func_table_.wifi_set_nodfs_flag(getIfaceHandle(iface_name), dfs_on ? 0 : 1);
739}
740
741wifi_error WifiLegacyHal::enableLinkLayerStats(const std::string& iface_name, bool debug) {
742 wifi_link_layer_params params;
743 params.mpdu_size_threshold = kLinkLayerStatsDataMpduSizeThreshold;
744 params.aggressive_statistics_gathering = debug;
745 return global_func_table_.wifi_set_link_stats(getIfaceHandle(iface_name), params);
746}
747
748wifi_error WifiLegacyHal::disableLinkLayerStats(const std::string& iface_name) {
749 // TODO: Do we care about these responses?
750 uint32_t clear_mask_rsp;
751 uint8_t stop_rsp;
752 return global_func_table_.wifi_clear_link_stats(getIfaceHandle(iface_name), 0xFFFFFFFF,
753 &clear_mask_rsp, 1, &stop_rsp);
754}
755
Mahesh KKV5f30d332022-10-26 14:07:44 -0700756// Copies wifi_peer_info* to vector<WifiPeerInfo> and returns poiner to next element.
757wifi_peer_info* WifiLegacyHal::copyPeerInfo(wifi_peer_info* peer_ptr,
Ye Jiaodec38702023-02-10 11:37:58 +0800758 std::vector<WifiPeerInfo>& peers) {
Mahesh KKV5f30d332022-10-26 14:07:44 -0700759 WifiPeerInfo peer;
760 peer.peer_info = *peer_ptr;
761 if (peer_ptr->num_rate > 0) {
762 // Copy the rate stats.
763 peer.rate_stats.assign(peer_ptr->rate_stats, peer_ptr->rate_stats + peer_ptr->num_rate);
764 }
765 peer.peer_info.num_rate = 0;
766 // Push peer info.
767 peers.push_back(peer);
768 // Return the address of next peer info.
769 return (wifi_peer_info*)((u8*)peer_ptr + sizeof(wifi_peer_info) +
770 (sizeof(wifi_rate_stat) * peer_ptr->num_rate));
771}
772// Copies wifi_link_stat* to vector<LinkStats> and returns poiner to next element.
773wifi_link_stat* WifiLegacyHal::copyLinkStat(wifi_link_stat* stat_ptr,
Ye Jiaodec38702023-02-10 11:37:58 +0800774 std::vector<LinkStats>& stats) {
Mahesh KKV5f30d332022-10-26 14:07:44 -0700775 LinkStats linkStat;
776 linkStat.stat = *stat_ptr;
777 wifi_peer_info* l_peer_info_stats_ptr = stat_ptr->peer_info;
778 for (uint32_t i = 0; i < linkStat.stat.num_peers; i++) {
779 l_peer_info_stats_ptr = copyPeerInfo(l_peer_info_stats_ptr, linkStat.peers);
780 }
781 // Copied all peers to linkStat.peers.
782 linkStat.stat.num_peers = 0;
783 // Push link stat.
784 stats.push_back(linkStat);
785 // Read all peers, return the address of next wifi_link_stat.
786 return (wifi_link_stat*)l_peer_info_stats_ptr;
787}
788
789wifi_error WifiLegacyHal::getLinkLayerStats(const std::string& iface_name,
790 LinkLayerStats& link_stats,
791 LinkLayerMlStats& link_ml_stats) {
Gabriel Birenf3262f92022-07-15 23:25:39 +0000792 LinkLayerStats* link_stats_ptr = &link_stats;
Mahesh KKV5f30d332022-10-26 14:07:44 -0700793 link_stats_ptr->valid = false;
Gabriel Birenf3262f92022-07-15 23:25:39 +0000794
795 on_link_layer_stats_result_internal_callback = [&link_stats_ptr](
796 wifi_request_id /* id */,
797 wifi_iface_stat* iface_stats_ptr,
798 int num_radios,
799 wifi_radio_stat* radio_stats_ptr) {
800 wifi_radio_stat* l_radio_stats_ptr;
801 wifi_peer_info* l_peer_info_stats_ptr;
Mahesh KKV5f30d332022-10-26 14:07:44 -0700802 link_stats_ptr->valid = true;
Gabriel Birenf3262f92022-07-15 23:25:39 +0000803
804 if (iface_stats_ptr != nullptr) {
805 link_stats_ptr->iface = *iface_stats_ptr;
806 l_peer_info_stats_ptr = iface_stats_ptr->peer_info;
807 for (uint32_t i = 0; i < iface_stats_ptr->num_peers; i++) {
808 WifiPeerInfo peer;
809 peer.peer_info = *l_peer_info_stats_ptr;
810 if (l_peer_info_stats_ptr->num_rate > 0) {
811 /* Copy the rate stats */
812 peer.rate_stats.assign(
813 l_peer_info_stats_ptr->rate_stats,
814 l_peer_info_stats_ptr->rate_stats + l_peer_info_stats_ptr->num_rate);
815 }
816 peer.peer_info.num_rate = 0;
817 link_stats_ptr->peers.push_back(peer);
818 l_peer_info_stats_ptr =
819 (wifi_peer_info*)((u8*)l_peer_info_stats_ptr + sizeof(wifi_peer_info) +
820 (sizeof(wifi_rate_stat) *
821 l_peer_info_stats_ptr->num_rate));
822 }
823 link_stats_ptr->iface.num_peers = 0;
824 } else {
825 LOG(ERROR) << "Invalid iface stats in link layer stats";
826 }
827 if (num_radios <= 0 || radio_stats_ptr == nullptr) {
828 LOG(ERROR) << "Invalid radio stats in link layer stats";
829 return;
830 }
831 l_radio_stats_ptr = radio_stats_ptr;
832 for (int i = 0; i < num_radios; i++) {
833 LinkLayerRadioStats radio;
834
835 radio.stats = *l_radio_stats_ptr;
836 // Copy over the tx level array to the separate vector.
837 if (l_radio_stats_ptr->num_tx_levels > 0 &&
838 l_radio_stats_ptr->tx_time_per_levels != nullptr) {
839 radio.tx_time_per_levels.assign(
840 l_radio_stats_ptr->tx_time_per_levels,
841 l_radio_stats_ptr->tx_time_per_levels + l_radio_stats_ptr->num_tx_levels);
842 }
843 radio.stats.num_tx_levels = 0;
844 radio.stats.tx_time_per_levels = nullptr;
845 /* Copy over the channel stat to separate vector */
846 if (l_radio_stats_ptr->num_channels > 0) {
847 /* Copy the channel stats */
848 radio.channel_stats.assign(
849 l_radio_stats_ptr->channels,
850 l_radio_stats_ptr->channels + l_radio_stats_ptr->num_channels);
851 }
852 link_stats_ptr->radios.push_back(radio);
853 l_radio_stats_ptr =
854 (wifi_radio_stat*)((u8*)l_radio_stats_ptr + sizeof(wifi_radio_stat) +
855 (sizeof(wifi_channel_stat) *
856 l_radio_stats_ptr->num_channels));
857 }
858 };
859
Mahesh KKV5f30d332022-10-26 14:07:44 -0700860 LinkLayerMlStats* link_ml_stats_ptr = &link_ml_stats;
861 link_ml_stats_ptr->valid = false;
862
863 on_link_layer_ml_stats_result_internal_callback =
864 [this, &link_ml_stats_ptr](wifi_request_id /* id */,
865 wifi_iface_ml_stat* iface_ml_stats_ptr, int num_radios,
866 wifi_radio_stat* radio_stats_ptr) {
867 wifi_radio_stat* l_radio_stats_ptr;
868 wifi_link_stat* l_link_stat_ptr;
869 link_ml_stats_ptr->valid = true;
870
871 if (iface_ml_stats_ptr != nullptr && iface_ml_stats_ptr->num_links > 0) {
872 // Copy stats from wifi_iface_ml_stat to LinkLayerMlStats,
873 // - num_links * links[] to vector of links.
874 // - num_peers * peer_info[] to vector of links[i].peers.
875 link_ml_stats_ptr->iface = *iface_ml_stats_ptr;
876 l_link_stat_ptr = iface_ml_stats_ptr->links;
877 for (int l = 0; l < iface_ml_stats_ptr->num_links; ++l) {
878 l_link_stat_ptr = copyLinkStat(l_link_stat_ptr, link_ml_stats_ptr->links);
879 }
880 } else {
881 LOG(ERROR) << "Invalid iface stats in link layer stats";
882 }
883 if (num_radios <= 0 || radio_stats_ptr == nullptr) {
884 LOG(ERROR) << "Invalid radio stats in link layer stats";
885 return;
886 }
887 l_radio_stats_ptr = radio_stats_ptr;
888 for (int i = 0; i < num_radios; i++) {
889 LinkLayerRadioStats radio;
890
891 radio.stats = *l_radio_stats_ptr;
892 // Copy over the tx level array to the separate vector.
893 if (l_radio_stats_ptr->num_tx_levels > 0 &&
894 l_radio_stats_ptr->tx_time_per_levels != nullptr) {
895 radio.tx_time_per_levels.assign(l_radio_stats_ptr->tx_time_per_levels,
896 l_radio_stats_ptr->tx_time_per_levels +
897 l_radio_stats_ptr->num_tx_levels);
898 }
899 radio.stats.num_tx_levels = 0;
900 radio.stats.tx_time_per_levels = nullptr;
901 /* Copy over the channel stat to separate vector */
902 if (l_radio_stats_ptr->num_channels > 0) {
903 /* Copy the channel stats */
904 radio.channel_stats.assign(
905 l_radio_stats_ptr->channels,
906 l_radio_stats_ptr->channels + l_radio_stats_ptr->num_channels);
907 }
908 link_ml_stats_ptr->radios.push_back(radio);
909 l_radio_stats_ptr =
910 (wifi_radio_stat*)((u8*)l_radio_stats_ptr + sizeof(wifi_radio_stat) +
911 (sizeof(wifi_channel_stat) *
912 l_radio_stats_ptr->num_channels));
913 }
914 };
915
916 wifi_error status = global_func_table_.wifi_get_link_stats(
917 0, getIfaceHandle(iface_name),
918 {onSyncLinkLayerStatsResult, onSyncLinkLayerMlStatsResult});
Gabriel Birenf3262f92022-07-15 23:25:39 +0000919 on_link_layer_stats_result_internal_callback = nullptr;
Mahesh KKV5f30d332022-10-26 14:07:44 -0700920 on_link_layer_ml_stats_result_internal_callback = nullptr;
921
922 return status;
Gabriel Birenf3262f92022-07-15 23:25:39 +0000923}
924
925wifi_error WifiLegacyHal::startRssiMonitoring(
926 const std::string& iface_name, wifi_request_id id, int8_t max_rssi, int8_t min_rssi,
927 const on_rssi_threshold_breached_callback& on_threshold_breached_user_callback) {
928 if (on_rssi_threshold_breached_internal_callback) {
929 return WIFI_ERROR_NOT_AVAILABLE;
930 }
931 on_rssi_threshold_breached_internal_callback = [on_threshold_breached_user_callback](
932 wifi_request_id id, uint8_t* bssid_ptr,
933 int8_t rssi) {
934 if (!bssid_ptr) {
935 return;
936 }
937 std::array<uint8_t, ETH_ALEN> bssid_arr;
938 // |bssid_ptr| pointer is assumed to have 6 bytes for the mac
939 // address.
940 std::copy(bssid_ptr, bssid_ptr + 6, std::begin(bssid_arr));
941 on_threshold_breached_user_callback(id, bssid_arr, rssi);
942 };
943 wifi_error status = global_func_table_.wifi_start_rssi_monitoring(
944 id, getIfaceHandle(iface_name), max_rssi, min_rssi, {onAsyncRssiThresholdBreached});
945 if (status != WIFI_SUCCESS) {
946 on_rssi_threshold_breached_internal_callback = nullptr;
947 }
948 return status;
949}
950
951wifi_error WifiLegacyHal::stopRssiMonitoring(const std::string& iface_name, wifi_request_id id) {
952 if (!on_rssi_threshold_breached_internal_callback) {
953 return WIFI_ERROR_NOT_AVAILABLE;
954 }
955 wifi_error status =
956 global_func_table_.wifi_stop_rssi_monitoring(id, getIfaceHandle(iface_name));
957 // If the request Id is wrong, don't stop the ongoing rssi monitoring. Any
958 // other error should be treated as the end of background scan.
959 if (status != WIFI_ERROR_INVALID_REQUEST_ID) {
960 on_rssi_threshold_breached_internal_callback = nullptr;
961 }
962 return status;
963}
964
965std::pair<wifi_error, wifi_roaming_capabilities> WifiLegacyHal::getRoamingCapabilities(
966 const std::string& iface_name) {
967 wifi_roaming_capabilities caps;
968 wifi_error status =
969 global_func_table_.wifi_get_roaming_capabilities(getIfaceHandle(iface_name), &caps);
970 return {status, caps};
971}
972
973wifi_error WifiLegacyHal::configureRoaming(const std::string& iface_name,
974 const wifi_roaming_config& config) {
975 wifi_roaming_config config_internal = config;
976 return global_func_table_.wifi_configure_roaming(getIfaceHandle(iface_name), &config_internal);
977}
978
979wifi_error WifiLegacyHal::enableFirmwareRoaming(const std::string& iface_name,
980 fw_roaming_state_t state) {
981 return global_func_table_.wifi_enable_firmware_roaming(getIfaceHandle(iface_name), state);
982}
983
984wifi_error WifiLegacyHal::configureNdOffload(const std::string& iface_name, bool enable) {
985 return global_func_table_.wifi_configure_nd_offload(getIfaceHandle(iface_name), enable);
986}
987
988wifi_error WifiLegacyHal::startSendingOffloadedPacket(const std::string& iface_name, int32_t cmd_id,
989 uint16_t ether_type,
990 const std::vector<uint8_t>& ip_packet_data,
991 const std::array<uint8_t, 6>& src_address,
992 const std::array<uint8_t, 6>& dst_address,
993 int32_t period_in_ms) {
994 std::vector<uint8_t> ip_packet_data_internal(ip_packet_data);
995 std::vector<uint8_t> src_address_internal(src_address.data(),
996 src_address.data() + src_address.size());
997 std::vector<uint8_t> dst_address_internal(dst_address.data(),
998 dst_address.data() + dst_address.size());
999 return global_func_table_.wifi_start_sending_offloaded_packet(
1000 cmd_id, getIfaceHandle(iface_name), ether_type, ip_packet_data_internal.data(),
1001 ip_packet_data_internal.size(), src_address_internal.data(),
1002 dst_address_internal.data(), period_in_ms);
1003}
1004
1005wifi_error WifiLegacyHal::stopSendingOffloadedPacket(const std::string& iface_name,
1006 uint32_t cmd_id) {
1007 return global_func_table_.wifi_stop_sending_offloaded_packet(cmd_id,
1008 getIfaceHandle(iface_name));
1009}
1010
1011wifi_error WifiLegacyHal::selectTxPowerScenario(const std::string& iface_name,
1012 wifi_power_scenario scenario) {
1013 return global_func_table_.wifi_select_tx_power_scenario(getIfaceHandle(iface_name), scenario);
1014}
1015
1016wifi_error WifiLegacyHal::resetTxPowerScenario(const std::string& iface_name) {
1017 return global_func_table_.wifi_reset_tx_power_scenario(getIfaceHandle(iface_name));
1018}
1019
1020wifi_error WifiLegacyHal::setLatencyMode(const std::string& iface_name, wifi_latency_mode mode) {
1021 return global_func_table_.wifi_set_latency_mode(getIfaceHandle(iface_name), mode);
1022}
1023
1024wifi_error WifiLegacyHal::setThermalMitigationMode(wifi_thermal_mode mode,
1025 uint32_t completion_window) {
1026 return global_func_table_.wifi_set_thermal_mitigation_mode(global_handle_, mode,
1027 completion_window);
1028}
1029
1030wifi_error WifiLegacyHal::setDscpToAccessCategoryMapping(uint32_t start, uint32_t end,
1031 uint32_t access_category) {
1032 return global_func_table_.wifi_map_dscp_access_category(global_handle_, start, end,
1033 access_category);
1034}
1035
1036wifi_error WifiLegacyHal::resetDscpToAccessCategoryMapping() {
1037 return global_func_table_.wifi_reset_dscp_mapping(global_handle_);
1038}
1039
1040std::pair<wifi_error, uint32_t> WifiLegacyHal::getLoggerSupportedFeatureSet(
1041 const std::string& iface_name) {
1042 uint32_t supported_feature_flags = 0;
1043 wifi_error status = WIFI_SUCCESS;
1044
1045 wifi_interface_handle iface_handle = getIfaceHandle(iface_name);
1046
1047 if (iface_handle) {
1048 status = global_func_table_.wifi_get_logger_supported_feature_set(iface_handle,
1049 &supported_feature_flags);
1050 }
1051 return {status, supported_feature_flags};
1052}
1053
1054wifi_error WifiLegacyHal::startPktFateMonitoring(const std::string& iface_name) {
1055 return global_func_table_.wifi_start_pkt_fate_monitoring(getIfaceHandle(iface_name));
1056}
1057
1058std::pair<wifi_error, std::vector<wifi_tx_report>> WifiLegacyHal::getTxPktFates(
1059 const std::string& iface_name) {
1060 std::vector<wifi_tx_report> tx_pkt_fates;
1061 tx_pkt_fates.resize(MAX_FATE_LOG_LEN);
1062 size_t num_fates = 0;
1063 wifi_error status = global_func_table_.wifi_get_tx_pkt_fates(
1064 getIfaceHandle(iface_name), tx_pkt_fates.data(), tx_pkt_fates.size(), &num_fates);
1065 CHECK(num_fates <= MAX_FATE_LOG_LEN);
1066 tx_pkt_fates.resize(num_fates);
1067 return {status, std::move(tx_pkt_fates)};
1068}
1069
1070std::pair<wifi_error, std::vector<wifi_rx_report>> WifiLegacyHal::getRxPktFates(
1071 const std::string& iface_name) {
1072 std::vector<wifi_rx_report> rx_pkt_fates;
1073 rx_pkt_fates.resize(MAX_FATE_LOG_LEN);
1074 size_t num_fates = 0;
1075 wifi_error status = global_func_table_.wifi_get_rx_pkt_fates(
1076 getIfaceHandle(iface_name), rx_pkt_fates.data(), rx_pkt_fates.size(), &num_fates);
1077 CHECK(num_fates <= MAX_FATE_LOG_LEN);
1078 rx_pkt_fates.resize(num_fates);
1079 return {status, std::move(rx_pkt_fates)};
1080}
1081
1082std::pair<wifi_error, WakeReasonStats> WifiLegacyHal::getWakeReasonStats(
1083 const std::string& iface_name) {
1084 WakeReasonStats stats;
1085 stats.cmd_event_wake_cnt.resize(kMaxWakeReasonStatsArraySize);
1086 stats.driver_fw_local_wake_cnt.resize(kMaxWakeReasonStatsArraySize);
1087
1088 // This legacy struct needs separate memory to store the variable sized wake
1089 // reason types.
1090 stats.wake_reason_cnt.cmd_event_wake_cnt =
1091 reinterpret_cast<int32_t*>(stats.cmd_event_wake_cnt.data());
1092 stats.wake_reason_cnt.cmd_event_wake_cnt_sz = stats.cmd_event_wake_cnt.size();
1093 stats.wake_reason_cnt.cmd_event_wake_cnt_used = 0;
1094 stats.wake_reason_cnt.driver_fw_local_wake_cnt =
1095 reinterpret_cast<int32_t*>(stats.driver_fw_local_wake_cnt.data());
1096 stats.wake_reason_cnt.driver_fw_local_wake_cnt_sz = stats.driver_fw_local_wake_cnt.size();
1097 stats.wake_reason_cnt.driver_fw_local_wake_cnt_used = 0;
1098
1099 wifi_error status = global_func_table_.wifi_get_wake_reason_stats(getIfaceHandle(iface_name),
1100 &stats.wake_reason_cnt);
1101
1102 CHECK(stats.wake_reason_cnt.cmd_event_wake_cnt_used >= 0 &&
1103 static_cast<uint32_t>(stats.wake_reason_cnt.cmd_event_wake_cnt_used) <=
1104 kMaxWakeReasonStatsArraySize);
1105 stats.cmd_event_wake_cnt.resize(stats.wake_reason_cnt.cmd_event_wake_cnt_used);
1106 stats.wake_reason_cnt.cmd_event_wake_cnt = nullptr;
1107
1108 CHECK(stats.wake_reason_cnt.driver_fw_local_wake_cnt_used >= 0 &&
1109 static_cast<uint32_t>(stats.wake_reason_cnt.driver_fw_local_wake_cnt_used) <=
1110 kMaxWakeReasonStatsArraySize);
1111 stats.driver_fw_local_wake_cnt.resize(stats.wake_reason_cnt.driver_fw_local_wake_cnt_used);
1112 stats.wake_reason_cnt.driver_fw_local_wake_cnt = nullptr;
1113
1114 return {status, stats};
1115}
1116
1117wifi_error WifiLegacyHal::registerRingBufferCallbackHandler(
1118 const std::string& iface_name, const on_ring_buffer_data_callback& on_user_data_callback) {
1119 if (on_ring_buffer_data_internal_callback) {
1120 return WIFI_ERROR_NOT_AVAILABLE;
1121 }
1122 on_ring_buffer_data_internal_callback = [on_user_data_callback](
1123 char* ring_name, char* buffer, int buffer_size,
1124 wifi_ring_buffer_status* status) {
1125 if (status && buffer) {
1126 std::vector<uint8_t> buffer_vector(reinterpret_cast<uint8_t*>(buffer),
1127 reinterpret_cast<uint8_t*>(buffer) + buffer_size);
1128 on_user_data_callback(ring_name, buffer_vector, *status);
1129 }
1130 };
1131 wifi_error status = global_func_table_.wifi_set_log_handler(0, getIfaceHandle(iface_name),
1132 {onAsyncRingBufferData});
1133 if (status != WIFI_SUCCESS) {
1134 on_ring_buffer_data_internal_callback = nullptr;
1135 }
1136 return status;
1137}
1138
1139wifi_error WifiLegacyHal::deregisterRingBufferCallbackHandler(const std::string& iface_name) {
1140 if (!on_ring_buffer_data_internal_callback) {
1141 return WIFI_ERROR_NOT_AVAILABLE;
1142 }
1143 on_ring_buffer_data_internal_callback = nullptr;
1144 return global_func_table_.wifi_reset_log_handler(0, getIfaceHandle(iface_name));
1145}
1146
1147std::pair<wifi_error, std::vector<wifi_ring_buffer_status>> WifiLegacyHal::getRingBuffersStatus(
1148 const std::string& iface_name) {
1149 std::vector<wifi_ring_buffer_status> ring_buffers_status;
1150 ring_buffers_status.resize(kMaxRingBuffers);
1151 uint32_t num_rings = kMaxRingBuffers;
1152 wifi_error status = global_func_table_.wifi_get_ring_buffers_status(
1153 getIfaceHandle(iface_name), &num_rings, ring_buffers_status.data());
1154 CHECK(num_rings <= kMaxRingBuffers);
1155 ring_buffers_status.resize(num_rings);
1156 return {status, std::move(ring_buffers_status)};
1157}
1158
1159wifi_error WifiLegacyHal::startRingBufferLogging(const std::string& iface_name,
1160 const std::string& ring_name,
1161 uint32_t verbose_level, uint32_t max_interval_sec,
1162 uint32_t min_data_size) {
1163 return global_func_table_.wifi_start_logging(getIfaceHandle(iface_name), verbose_level, 0,
1164 max_interval_sec, min_data_size,
1165 makeCharVec(ring_name).data());
1166}
1167
1168wifi_error WifiLegacyHal::getRingBufferData(const std::string& iface_name,
1169 const std::string& ring_name) {
1170 return global_func_table_.wifi_get_ring_data(getIfaceHandle(iface_name),
1171 makeCharVec(ring_name).data());
1172}
1173
1174wifi_error WifiLegacyHal::registerErrorAlertCallbackHandler(
1175 const std::string& iface_name, const on_error_alert_callback& on_user_alert_callback) {
1176 if (on_error_alert_internal_callback) {
1177 return WIFI_ERROR_NOT_AVAILABLE;
1178 }
1179 on_error_alert_internal_callback = [on_user_alert_callback](wifi_request_id id, char* buffer,
1180 int buffer_size, int err_code) {
1181 if (buffer) {
1182 CHECK(id == 0);
1183 on_user_alert_callback(
1184 err_code,
1185 std::vector<uint8_t>(reinterpret_cast<uint8_t*>(buffer),
1186 reinterpret_cast<uint8_t*>(buffer) + buffer_size));
1187 }
1188 };
1189 wifi_error status = global_func_table_.wifi_set_alert_handler(0, getIfaceHandle(iface_name),
1190 {onAsyncErrorAlert});
1191 if (status != WIFI_SUCCESS) {
1192 on_error_alert_internal_callback = nullptr;
1193 }
1194 return status;
1195}
1196
1197wifi_error WifiLegacyHal::deregisterErrorAlertCallbackHandler(const std::string& iface_name) {
1198 if (!on_error_alert_internal_callback) {
1199 return WIFI_ERROR_NOT_AVAILABLE;
1200 }
1201 on_error_alert_internal_callback = nullptr;
1202 return global_func_table_.wifi_reset_alert_handler(0, getIfaceHandle(iface_name));
1203}
1204
1205wifi_error WifiLegacyHal::registerRadioModeChangeCallbackHandler(
1206 const std::string& iface_name,
1207 const on_radio_mode_change_callback& on_user_change_callback) {
1208 if (on_radio_mode_change_internal_callback) {
1209 return WIFI_ERROR_NOT_AVAILABLE;
1210 }
1211 on_radio_mode_change_internal_callback = [on_user_change_callback](
1212 wifi_request_id /* id */, uint32_t num_macs,
1213 wifi_mac_info* mac_infos_arr) {
1214 if (num_macs > 0 && mac_infos_arr) {
1215 std::vector<WifiMacInfo> mac_infos_vec;
1216 for (uint32_t i = 0; i < num_macs; i++) {
1217 WifiMacInfo mac_info;
1218 mac_info.wlan_mac_id = mac_infos_arr[i].wlan_mac_id;
1219 mac_info.mac_band = mac_infos_arr[i].mac_band;
1220 for (int32_t j = 0; j < mac_infos_arr[i].num_iface; j++) {
1221 WifiIfaceInfo iface_info;
1222 iface_info.name = mac_infos_arr[i].iface_info[j].iface_name;
1223 iface_info.channel = mac_infos_arr[i].iface_info[j].channel;
1224 mac_info.iface_infos.push_back(iface_info);
1225 }
1226 mac_infos_vec.push_back(mac_info);
1227 }
1228 on_user_change_callback(mac_infos_vec);
1229 }
1230 };
1231 wifi_error status = global_func_table_.wifi_set_radio_mode_change_handler(
1232 0, getIfaceHandle(iface_name), {onAsyncRadioModeChange});
1233 if (status != WIFI_SUCCESS) {
1234 on_radio_mode_change_internal_callback = nullptr;
1235 }
1236 return status;
1237}
1238
1239wifi_error WifiLegacyHal::registerSubsystemRestartCallbackHandler(
1240 const on_subsystem_restart_callback& on_restart_callback) {
1241 if (on_subsystem_restart_internal_callback) {
1242 return WIFI_ERROR_NOT_AVAILABLE;
1243 }
1244 on_subsystem_restart_internal_callback = [on_restart_callback](const char* error) {
1245 on_restart_callback(error);
1246 };
1247 wifi_error status = global_func_table_.wifi_set_subsystem_restart_handler(
1248 global_handle_, {onAsyncSubsystemRestart});
1249 if (status != WIFI_SUCCESS) {
1250 on_subsystem_restart_internal_callback = nullptr;
1251 }
1252 return status;
1253}
1254
1255wifi_error WifiLegacyHal::startRttRangeRequest(
1256 const std::string& iface_name, wifi_request_id id,
1257 const std::vector<wifi_rtt_config>& rtt_configs,
Sunil Ravif8fc2372022-11-10 18:37:41 +00001258 const on_rtt_results_callback& on_results_user_callback,
1259 const on_rtt_results_callback_v2& on_results_user_callback_v2) {
1260 if (on_rtt_results_internal_callback || on_rtt_results_internal_callback_v2) {
Gabriel Birenf3262f92022-07-15 23:25:39 +00001261 return WIFI_ERROR_NOT_AVAILABLE;
1262 }
1263
1264 on_rtt_results_internal_callback = [on_results_user_callback](wifi_request_id id,
1265 unsigned num_results,
1266 wifi_rtt_result* rtt_results[]) {
1267 if (num_results > 0 && !rtt_results) {
1268 LOG(ERROR) << "Unexpected nullptr in RTT results";
1269 return;
1270 }
1271 std::vector<const wifi_rtt_result*> rtt_results_vec;
1272 std::copy_if(rtt_results, rtt_results + num_results, back_inserter(rtt_results_vec),
1273 [](wifi_rtt_result* rtt_result) { return rtt_result != nullptr; });
1274 on_results_user_callback(id, rtt_results_vec);
1275 };
1276
Sunil Ravif8fc2372022-11-10 18:37:41 +00001277 on_rtt_results_internal_callback_v2 = [on_results_user_callback_v2](
1278 wifi_request_id id, unsigned num_results,
1279 wifi_rtt_result_v2* rtt_results_v2[]) {
1280 if (num_results > 0 && !rtt_results_v2) {
1281 LOG(ERROR) << "Unexpected nullptr in RTT results";
1282 return;
1283 }
1284 std::vector<const wifi_rtt_result_v2*> rtt_results_vec_v2;
1285 std::copy_if(rtt_results_v2, rtt_results_v2 + num_results,
1286 back_inserter(rtt_results_vec_v2),
1287 [](wifi_rtt_result_v2* rtt_result_v2) { return rtt_result_v2 != nullptr; });
1288 on_results_user_callback_v2(id, rtt_results_vec_v2);
1289 };
1290
Gabriel Birenf3262f92022-07-15 23:25:39 +00001291 std::vector<wifi_rtt_config> rtt_configs_internal(rtt_configs);
1292 wifi_error status = global_func_table_.wifi_rtt_range_request(
1293 id, getIfaceHandle(iface_name), rtt_configs.size(), rtt_configs_internal.data(),
Sunil Ravif8fc2372022-11-10 18:37:41 +00001294 {onAsyncRttResults, onAsyncRttResultsV2});
Gabriel Birenf3262f92022-07-15 23:25:39 +00001295 if (status != WIFI_SUCCESS) {
Sunil Ravif8fc2372022-11-10 18:37:41 +00001296 invalidateRttResultsCallbacks();
Gabriel Birenf3262f92022-07-15 23:25:39 +00001297 }
1298 return status;
1299}
1300
1301wifi_error WifiLegacyHal::cancelRttRangeRequest(
1302 const std::string& iface_name, wifi_request_id id,
1303 const std::vector<std::array<uint8_t, ETH_ALEN>>& mac_addrs) {
Sunil Ravif8fc2372022-11-10 18:37:41 +00001304 if (!on_rtt_results_internal_callback && !on_rtt_results_internal_callback_v2) {
Gabriel Birenf3262f92022-07-15 23:25:39 +00001305 return WIFI_ERROR_NOT_AVAILABLE;
1306 }
1307 static_assert(sizeof(mac_addr) == sizeof(std::array<uint8_t, ETH_ALEN>),
1308 "MAC address size mismatch");
1309 // TODO: How do we handle partial cancels (i.e only a subset of enabled mac
1310 // addressed are cancelled).
1311 std::vector<std::array<uint8_t, ETH_ALEN>> mac_addrs_internal(mac_addrs);
1312 wifi_error status = global_func_table_.wifi_rtt_range_cancel(
1313 id, getIfaceHandle(iface_name), mac_addrs.size(),
1314 reinterpret_cast<mac_addr*>(mac_addrs_internal.data()));
1315 // If the request Id is wrong, don't stop the ongoing range request. Any
1316 // other error should be treated as the end of rtt ranging.
1317 if (status != WIFI_ERROR_INVALID_REQUEST_ID) {
Sunil Ravif8fc2372022-11-10 18:37:41 +00001318 invalidateRttResultsCallbacks();
Gabriel Birenf3262f92022-07-15 23:25:39 +00001319 }
1320 return status;
1321}
1322
1323std::pair<wifi_error, wifi_rtt_capabilities> WifiLegacyHal::getRttCapabilities(
1324 const std::string& iface_name) {
1325 wifi_rtt_capabilities rtt_caps;
1326 wifi_error status =
1327 global_func_table_.wifi_get_rtt_capabilities(getIfaceHandle(iface_name), &rtt_caps);
1328 return {status, rtt_caps};
1329}
1330
1331std::pair<wifi_error, wifi_rtt_responder> WifiLegacyHal::getRttResponderInfo(
1332 const std::string& iface_name) {
1333 wifi_rtt_responder rtt_responder;
1334 wifi_error status = global_func_table_.wifi_rtt_get_responder_info(getIfaceHandle(iface_name),
1335 &rtt_responder);
1336 return {status, rtt_responder};
1337}
1338
1339wifi_error WifiLegacyHal::enableRttResponder(const std::string& iface_name, wifi_request_id id,
1340 const wifi_channel_info& channel_hint,
1341 uint32_t max_duration_secs,
1342 const wifi_rtt_responder& info) {
1343 wifi_rtt_responder info_internal(info);
1344 return global_func_table_.wifi_enable_responder(id, getIfaceHandle(iface_name), channel_hint,
1345 max_duration_secs, &info_internal);
1346}
1347
1348wifi_error WifiLegacyHal::disableRttResponder(const std::string& iface_name, wifi_request_id id) {
1349 return global_func_table_.wifi_disable_responder(id, getIfaceHandle(iface_name));
1350}
1351
1352wifi_error WifiLegacyHal::setRttLci(const std::string& iface_name, wifi_request_id id,
1353 const wifi_lci_information& info) {
1354 wifi_lci_information info_internal(info);
1355 return global_func_table_.wifi_set_lci(id, getIfaceHandle(iface_name), &info_internal);
1356}
1357
1358wifi_error WifiLegacyHal::setRttLcr(const std::string& iface_name, wifi_request_id id,
1359 const wifi_lcr_information& info) {
1360 wifi_lcr_information info_internal(info);
1361 return global_func_table_.wifi_set_lcr(id, getIfaceHandle(iface_name), &info_internal);
1362}
1363
1364wifi_error WifiLegacyHal::nanRegisterCallbackHandlers(const std::string& iface_name,
1365 const NanCallbackHandlers& user_callbacks) {
1366 on_nan_notify_response_user_callback = user_callbacks.on_notify_response;
1367 on_nan_event_publish_terminated_user_callback = user_callbacks.on_event_publish_terminated;
1368 on_nan_event_match_user_callback = user_callbacks.on_event_match;
1369 on_nan_event_match_expired_user_callback = user_callbacks.on_event_match_expired;
1370 on_nan_event_subscribe_terminated_user_callback = user_callbacks.on_event_subscribe_terminated;
1371 on_nan_event_followup_user_callback = user_callbacks.on_event_followup;
1372 on_nan_event_disc_eng_event_user_callback = user_callbacks.on_event_disc_eng_event;
1373 on_nan_event_disabled_user_callback = user_callbacks.on_event_disabled;
1374 on_nan_event_tca_user_callback = user_callbacks.on_event_tca;
1375 on_nan_event_beacon_sdf_payload_user_callback = user_callbacks.on_event_beacon_sdf_payload;
1376 on_nan_event_data_path_request_user_callback = user_callbacks.on_event_data_path_request;
Nate Jiang38e8db52022-12-02 17:30:27 -08001377 on_nan_event_pairing_request_user_callback = user_callbacks.on_event_pairing_request;
1378 on_nan_event_pairing_confirm_user_callback = user_callbacks.on_event_pairing_confirm;
1379 on_nan_event_bootstrapping_request_user_callback =
1380 user_callbacks.on_event_bootstrapping_request;
1381 on_nan_event_bootstrapping_confirm_user_callback =
1382 user_callbacks.on_event_bootstrapping_confirm;
Gabriel Birenf3262f92022-07-15 23:25:39 +00001383 on_nan_event_data_path_confirm_user_callback = user_callbacks.on_event_data_path_confirm;
1384 on_nan_event_data_path_end_user_callback = user_callbacks.on_event_data_path_end;
1385 on_nan_event_transmit_follow_up_user_callback = user_callbacks.on_event_transmit_follow_up;
1386 on_nan_event_range_request_user_callback = user_callbacks.on_event_range_request;
1387 on_nan_event_range_report_user_callback = user_callbacks.on_event_range_report;
1388 on_nan_event_schedule_update_user_callback = user_callbacks.on_event_schedule_update;
Nate Jiangd6cc3312023-02-14 16:37:54 -08001389 on_nan_event_suspension_mode_change_user_callback =
1390 user_callbacks.on_event_suspension_mode_change;
Gabriel Birenf3262f92022-07-15 23:25:39 +00001391
Nate Jiang38e8db52022-12-02 17:30:27 -08001392 return global_func_table_.wifi_nan_register_handler(getIfaceHandle(iface_name),
1393 {onAsyncNanNotifyResponse,
1394 onAsyncNanEventPublishReplied,
1395 onAsyncNanEventPublishTerminated,
1396 onAsyncNanEventMatch,
1397 onAsyncNanEventMatchExpired,
1398 onAsyncNanEventSubscribeTerminated,
1399 onAsyncNanEventFollowup,
1400 onAsyncNanEventDiscEngEvent,
1401 onAsyncNanEventDisabled,
1402 onAsyncNanEventTca,
1403 onAsyncNanEventBeaconSdfPayload,
1404 onAsyncNanEventDataPathRequest,
1405 onAsyncNanEventDataPathConfirm,
1406 onAsyncNanEventDataPathEnd,
1407 onAsyncNanEventTransmitFollowUp,
1408 onAsyncNanEventRangeRequest,
1409 onAsyncNanEventRangeReport,
1410 onAsyncNanEventScheduleUpdate,
1411 onAsyncNanEventPairingRequest,
1412 onAsyncNanEventPairingConfirm,
1413 onAsyncNanEventBootstrappingRequest,
Nate Jiangd6cc3312023-02-14 16:37:54 -08001414 onAsyncNanEventBootstrappingConfirm,
1415 onAsyncNanEventSuspensionModeChange});
Gabriel Birenf3262f92022-07-15 23:25:39 +00001416}
1417
1418wifi_error WifiLegacyHal::nanEnableRequest(const std::string& iface_name, transaction_id id,
1419 const NanEnableRequest& msg) {
1420 NanEnableRequest msg_internal(msg);
1421 return global_func_table_.wifi_nan_enable_request(id, getIfaceHandle(iface_name),
1422 &msg_internal);
1423}
1424
1425wifi_error WifiLegacyHal::nanDisableRequest(const std::string& iface_name, transaction_id id) {
1426 return global_func_table_.wifi_nan_disable_request(id, getIfaceHandle(iface_name));
1427}
1428
1429wifi_error WifiLegacyHal::nanPublishRequest(const std::string& iface_name, transaction_id id,
1430 const NanPublishRequest& msg) {
1431 NanPublishRequest msg_internal(msg);
1432 return global_func_table_.wifi_nan_publish_request(id, getIfaceHandle(iface_name),
1433 &msg_internal);
1434}
1435
1436wifi_error WifiLegacyHal::nanPublishCancelRequest(const std::string& iface_name, transaction_id id,
1437 const NanPublishCancelRequest& msg) {
1438 NanPublishCancelRequest msg_internal(msg);
1439 return global_func_table_.wifi_nan_publish_cancel_request(id, getIfaceHandle(iface_name),
1440 &msg_internal);
1441}
1442
1443wifi_error WifiLegacyHal::nanSubscribeRequest(const std::string& iface_name, transaction_id id,
1444 const NanSubscribeRequest& msg) {
1445 NanSubscribeRequest msg_internal(msg);
1446 return global_func_table_.wifi_nan_subscribe_request(id, getIfaceHandle(iface_name),
1447 &msg_internal);
1448}
1449
1450wifi_error WifiLegacyHal::nanSubscribeCancelRequest(const std::string& iface_name,
1451 transaction_id id,
1452 const NanSubscribeCancelRequest& msg) {
1453 NanSubscribeCancelRequest msg_internal(msg);
1454 return global_func_table_.wifi_nan_subscribe_cancel_request(id, getIfaceHandle(iface_name),
1455 &msg_internal);
1456}
1457
1458wifi_error WifiLegacyHal::nanTransmitFollowupRequest(const std::string& iface_name,
1459 transaction_id id,
1460 const NanTransmitFollowupRequest& msg) {
1461 NanTransmitFollowupRequest msg_internal(msg);
1462 return global_func_table_.wifi_nan_transmit_followup_request(id, getIfaceHandle(iface_name),
1463 &msg_internal);
1464}
1465
1466wifi_error WifiLegacyHal::nanStatsRequest(const std::string& iface_name, transaction_id id,
1467 const NanStatsRequest& msg) {
1468 NanStatsRequest msg_internal(msg);
1469 return global_func_table_.wifi_nan_stats_request(id, getIfaceHandle(iface_name), &msg_internal);
1470}
1471
1472wifi_error WifiLegacyHal::nanConfigRequest(const std::string& iface_name, transaction_id id,
1473 const NanConfigRequest& msg) {
1474 NanConfigRequest msg_internal(msg);
1475 return global_func_table_.wifi_nan_config_request(id, getIfaceHandle(iface_name),
1476 &msg_internal);
1477}
1478
1479wifi_error WifiLegacyHal::nanTcaRequest(const std::string& iface_name, transaction_id id,
1480 const NanTCARequest& msg) {
1481 NanTCARequest msg_internal(msg);
1482 return global_func_table_.wifi_nan_tca_request(id, getIfaceHandle(iface_name), &msg_internal);
1483}
1484
1485wifi_error WifiLegacyHal::nanBeaconSdfPayloadRequest(const std::string& iface_name,
1486 transaction_id id,
1487 const NanBeaconSdfPayloadRequest& msg) {
1488 NanBeaconSdfPayloadRequest msg_internal(msg);
1489 return global_func_table_.wifi_nan_beacon_sdf_payload_request(id, getIfaceHandle(iface_name),
1490 &msg_internal);
1491}
1492
1493std::pair<wifi_error, NanVersion> WifiLegacyHal::nanGetVersion() {
1494 NanVersion version;
1495 wifi_error status = global_func_table_.wifi_nan_get_version(global_handle_, &version);
1496 return {status, version};
1497}
1498
1499wifi_error WifiLegacyHal::nanGetCapabilities(const std::string& iface_name, transaction_id id) {
1500 return global_func_table_.wifi_nan_get_capabilities(id, getIfaceHandle(iface_name));
1501}
1502
1503wifi_error WifiLegacyHal::nanDataInterfaceCreate(const std::string& iface_name, transaction_id id,
1504 const std::string& data_iface_name) {
1505 return global_func_table_.wifi_nan_data_interface_create(id, getIfaceHandle(iface_name),
1506 makeCharVec(data_iface_name).data());
1507}
1508
1509wifi_error WifiLegacyHal::nanDataInterfaceDelete(const std::string& iface_name, transaction_id id,
1510 const std::string& data_iface_name) {
1511 return global_func_table_.wifi_nan_data_interface_delete(id, getIfaceHandle(iface_name),
1512 makeCharVec(data_iface_name).data());
1513}
1514
1515wifi_error WifiLegacyHal::nanDataRequestInitiator(const std::string& iface_name, transaction_id id,
1516 const NanDataPathInitiatorRequest& msg) {
1517 NanDataPathInitiatorRequest msg_internal(msg);
1518 return global_func_table_.wifi_nan_data_request_initiator(id, getIfaceHandle(iface_name),
1519 &msg_internal);
1520}
1521
1522wifi_error WifiLegacyHal::nanDataIndicationResponse(const std::string& iface_name,
1523 transaction_id id,
1524 const NanDataPathIndicationResponse& msg) {
1525 NanDataPathIndicationResponse msg_internal(msg);
1526 return global_func_table_.wifi_nan_data_indication_response(id, getIfaceHandle(iface_name),
1527 &msg_internal);
1528}
1529
Nate Jiang38e8db52022-12-02 17:30:27 -08001530wifi_error WifiLegacyHal::nanPairingRequest(const std::string& iface_name, transaction_id id,
1531 const NanPairingRequest& msg) {
1532 NanPairingRequest msg_internal(msg);
1533 return global_func_table_.wifi_nan_pairing_request(id, getIfaceHandle(iface_name),
1534 &msg_internal);
1535}
1536
1537wifi_error WifiLegacyHal::nanPairingIndicationResponse(const std::string& iface_name,
1538 transaction_id id,
1539 const NanPairingIndicationResponse& msg) {
1540 NanPairingIndicationResponse msg_internal(msg);
1541 return global_func_table_.wifi_nan_pairing_indication_response(id, getIfaceHandle(iface_name),
1542 &msg_internal);
1543}
1544
1545wifi_error WifiLegacyHal::nanBootstrappingRequest(const std::string& iface_name, transaction_id id,
1546 const NanBootstrappingRequest& msg) {
1547 NanBootstrappingRequest msg_internal(msg);
1548 return global_func_table_.wifi_nan_bootstrapping_request(id, getIfaceHandle(iface_name),
1549 &msg_internal);
1550}
1551
1552wifi_error WifiLegacyHal::nanBootstrappingIndicationResponse(
1553 const std::string& iface_name, transaction_id id,
1554 const NanBootstrappingIndicationResponse& msg) {
1555 NanBootstrappingIndicationResponse msg_internal(msg);
1556 return global_func_table_.wifi_nan_bootstrapping_indication_response(
1557 id, getIfaceHandle(iface_name), &msg_internal);
1558}
1559
Gabriel Birenf3262f92022-07-15 23:25:39 +00001560typedef struct {
1561 u8 num_ndp_instances;
1562 NanDataPathId ndp_instance_id;
1563} NanDataPathEndSingleNdpIdRequest;
1564
1565wifi_error WifiLegacyHal::nanDataEnd(const std::string& iface_name, transaction_id id,
1566 uint32_t ndpInstanceId) {
1567 NanDataPathEndSingleNdpIdRequest msg;
1568 msg.num_ndp_instances = 1;
1569 msg.ndp_instance_id = ndpInstanceId;
1570 wifi_error status = global_func_table_.wifi_nan_data_end(id, getIfaceHandle(iface_name),
1571 (NanDataPathEndRequest*)&msg);
1572 return status;
1573}
1574
Nate Jiangbae6fdd2023-02-10 17:16:40 -08001575wifi_error WifiLegacyHal::nanPairingEnd(const std::string& iface_name, transaction_id id,
1576 uint32_t pairingId) {
1577 NanPairingEndRequest msg;
1578 msg.pairing_instance_id = pairingId;
1579 wifi_error status =
1580 global_func_table_.wifi_nan_pairing_end(id, getIfaceHandle(iface_name), &msg);
1581 return status;
1582}
1583
Phill Hayers02a97242022-12-15 16:05:14 +00001584wifi_error WifiLegacyHal::nanSuspendRequest(const std::string& iface_name, transaction_id id,
1585 const NanSuspendRequest& msg) {
1586 NanSuspendRequest msg_internal(msg);
1587 wifi_error status = global_func_table_.wifi_nan_suspend_request(id, getIfaceHandle(iface_name),
1588 &msg_internal);
1589 return status;
1590}
1591
1592wifi_error WifiLegacyHal::nanResumeRequest(const std::string& iface_name, transaction_id id,
1593 const NanResumeRequest& msg) {
1594 NanResumeRequest msg_internal(msg);
1595 wifi_error status = global_func_table_.wifi_nan_resume_request(id, getIfaceHandle(iface_name),
1596 &msg_internal);
1597 return status;
1598}
1599
Gabriel Birenf3262f92022-07-15 23:25:39 +00001600wifi_error WifiLegacyHal::setCountryCode(const std::string& iface_name,
1601 const std::array<uint8_t, 2> code) {
1602 std::string code_str(code.data(), code.data() + code.size());
1603 return global_func_table_.wifi_set_country_code(getIfaceHandle(iface_name), code_str.c_str());
1604}
1605
1606wifi_error WifiLegacyHal::retrieveIfaceHandles() {
1607 wifi_interface_handle* iface_handles = nullptr;
1608 int num_iface_handles = 0;
1609 wifi_error status =
1610 global_func_table_.wifi_get_ifaces(global_handle_, &num_iface_handles, &iface_handles);
1611 if (status != WIFI_SUCCESS) {
1612 LOG(ERROR) << "Failed to enumerate interface handles";
1613 return status;
1614 }
1615 iface_name_to_handle_.clear();
1616 for (int i = 0; i < num_iface_handles; ++i) {
1617 std::array<char, IFNAMSIZ> iface_name_arr = {};
1618 status = global_func_table_.wifi_get_iface_name(iface_handles[i], iface_name_arr.data(),
1619 iface_name_arr.size());
1620 if (status != WIFI_SUCCESS) {
1621 LOG(WARNING) << "Failed to get interface handle name";
1622 continue;
1623 }
1624 // Assuming the interface name is null terminated since the legacy HAL
1625 // API does not return a size.
1626 std::string iface_name(iface_name_arr.data());
1627 LOG(INFO) << "Adding interface handle for " << iface_name;
1628 iface_name_to_handle_[iface_name] = iface_handles[i];
1629 }
1630 return WIFI_SUCCESS;
1631}
1632
1633wifi_interface_handle WifiLegacyHal::getIfaceHandle(const std::string& iface_name) {
1634 const auto iface_handle_iter = iface_name_to_handle_.find(iface_name);
1635 if (iface_handle_iter == iface_name_to_handle_.end()) {
1636 LOG(ERROR) << "Unknown iface name: " << iface_name;
1637 return nullptr;
1638 }
1639 return iface_handle_iter->second;
1640}
1641
1642void WifiLegacyHal::runEventLoop() {
1643 LOG(DEBUG) << "Starting legacy HAL event loop";
1644 global_func_table_.wifi_event_loop(global_handle_);
1645 const auto lock = aidl_sync_util::acquireGlobalLock();
1646 if (!awaiting_event_loop_termination_) {
1647 LOG(FATAL) << "Legacy HAL event loop terminated, but HAL was not stopping";
1648 }
1649 LOG(DEBUG) << "Legacy HAL event loop terminated";
1650 awaiting_event_loop_termination_ = false;
1651 stop_wait_cv_.notify_one();
1652}
1653
1654std::pair<wifi_error, std::vector<wifi_cached_scan_results>> WifiLegacyHal::getGscanCachedResults(
1655 const std::string& iface_name) {
1656 std::vector<wifi_cached_scan_results> cached_scan_results;
1657 cached_scan_results.resize(kMaxCachedGscanResults);
1658 int32_t num_results = 0;
1659 wifi_error status = global_func_table_.wifi_get_cached_gscan_results(
1660 getIfaceHandle(iface_name), true /* always flush */, cached_scan_results.size(),
1661 cached_scan_results.data(), &num_results);
1662 CHECK(num_results >= 0 && static_cast<uint32_t>(num_results) <= kMaxCachedGscanResults);
1663 cached_scan_results.resize(num_results);
1664 // Check for invalid IE lengths in these cached scan results and correct it.
1665 for (auto& cached_scan_result : cached_scan_results) {
1666 int num_scan_results = cached_scan_result.num_results;
1667 for (int i = 0; i < num_scan_results; i++) {
1668 auto& scan_result = cached_scan_result.results[i];
1669 if (scan_result.ie_length > 0) {
1670 LOG(DEBUG) << "Cached scan result has non-zero IE length " << scan_result.ie_length;
1671 scan_result.ie_length = 0;
1672 }
1673 }
1674 }
1675 return {status, std::move(cached_scan_results)};
1676}
1677
1678wifi_error WifiLegacyHal::createVirtualInterface(const std::string& ifname,
1679 wifi_interface_type iftype) {
1680 // Create the interface if it doesn't exist. If interface already exist,
1681 // Vendor Hal should return WIFI_SUCCESS.
1682 wifi_error status = global_func_table_.wifi_virtual_interface_create(global_handle_,
1683 ifname.c_str(), iftype);
1684 return handleVirtualInterfaceCreateOrDeleteStatus(ifname, status);
1685}
1686
1687wifi_error WifiLegacyHal::deleteVirtualInterface(const std::string& ifname) {
1688 // Delete the interface if it was created dynamically.
1689 wifi_error status =
1690 global_func_table_.wifi_virtual_interface_delete(global_handle_, ifname.c_str());
1691 return handleVirtualInterfaceCreateOrDeleteStatus(ifname, status);
1692}
1693
1694wifi_error WifiLegacyHal::handleVirtualInterfaceCreateOrDeleteStatus(const std::string& ifname,
1695 wifi_error status) {
1696 if (status == WIFI_SUCCESS) {
1697 // refresh list of handlers now.
1698 status = retrieveIfaceHandles();
1699 } else if (status == WIFI_ERROR_NOT_SUPPORTED) {
1700 // Vendor hal does not implement this API. Such vendor implementations
1701 // are expected to create / delete interface by other means.
1702
1703 // check if interface exists.
1704 if (if_nametoindex(ifname.c_str())) {
1705 status = retrieveIfaceHandles();
1706 }
1707 }
1708 return status;
1709}
1710
1711wifi_error WifiLegacyHal::getSupportedIfaceName(uint32_t iface_type, std::string& ifname) {
1712 std::array<char, IFNAMSIZ> buffer;
1713
1714 wifi_error res = global_func_table_.wifi_get_supported_iface_name(
1715 global_handle_, (uint32_t)iface_type, buffer.data(), buffer.size());
1716 if (res == WIFI_SUCCESS) ifname = buffer.data();
1717
1718 return res;
1719}
1720
1721wifi_error WifiLegacyHal::multiStaSetPrimaryConnection(const std::string& ifname) {
1722 return global_func_table_.wifi_multi_sta_set_primary_connection(global_handle_,
1723 getIfaceHandle(ifname));
1724}
1725
1726wifi_error WifiLegacyHal::multiStaSetUseCase(wifi_multi_sta_use_case use_case) {
1727 return global_func_table_.wifi_multi_sta_set_use_case(global_handle_, use_case);
1728}
1729
1730wifi_error WifiLegacyHal::setCoexUnsafeChannels(
1731 std::vector<wifi_coex_unsafe_channel> unsafe_channels, uint32_t restrictions) {
1732 return global_func_table_.wifi_set_coex_unsafe_channels(global_handle_, unsafe_channels.size(),
1733 unsafe_channels.data(), restrictions);
1734}
1735
1736wifi_error WifiLegacyHal::setVoipMode(const std::string& iface_name, wifi_voip_mode mode) {
1737 return global_func_table_.wifi_set_voip_mode(getIfaceHandle(iface_name), mode);
1738}
1739
1740wifi_error WifiLegacyHal::twtRegisterHandler(const std::string& iface_name,
1741 const TwtCallbackHandlers& user_callbacks) {
1742 on_twt_event_setup_response_callback = user_callbacks.on_setup_response;
1743 on_twt_event_teardown_completion_callback = user_callbacks.on_teardown_completion;
1744 on_twt_event_info_frame_received_callback = user_callbacks.on_info_frame_received;
1745 on_twt_event_device_notify_callback = user_callbacks.on_device_notify;
1746
1747 return global_func_table_.wifi_twt_register_handler(
1748 getIfaceHandle(iface_name),
1749 {onAsyncTwtEventSetupResponse, onAsyncTwtEventTeardownCompletion,
1750 onAsyncTwtEventInfoFrameReceived, onAsyncTwtEventDeviceNotify});
1751}
1752
1753std::pair<wifi_error, TwtCapabilitySet> WifiLegacyHal::twtGetCapability(
1754 const std::string& iface_name) {
1755 TwtCapabilitySet capSet;
1756 wifi_error status =
1757 global_func_table_.wifi_twt_get_capability(getIfaceHandle(iface_name), &capSet);
1758 return {status, capSet};
1759}
1760
1761wifi_error WifiLegacyHal::twtSetupRequest(const std::string& iface_name,
1762 const TwtSetupRequest& msg) {
1763 TwtSetupRequest msgInternal(msg);
1764 return global_func_table_.wifi_twt_setup_request(getIfaceHandle(iface_name), &msgInternal);
1765}
1766
1767wifi_error WifiLegacyHal::twtTearDownRequest(const std::string& iface_name,
1768 const TwtTeardownRequest& msg) {
1769 TwtTeardownRequest msgInternal(msg);
1770 return global_func_table_.wifi_twt_teardown_request(getIfaceHandle(iface_name), &msgInternal);
1771}
1772
1773wifi_error WifiLegacyHal::twtInfoFrameRequest(const std::string& iface_name,
1774 const TwtInfoFrameRequest& msg) {
1775 TwtInfoFrameRequest msgInternal(msg);
1776 return global_func_table_.wifi_twt_info_frame_request(getIfaceHandle(iface_name), &msgInternal);
1777}
1778
1779std::pair<wifi_error, TwtStats> WifiLegacyHal::twtGetStats(const std::string& iface_name,
1780 uint8_t configId) {
1781 TwtStats stats;
1782 wifi_error status =
1783 global_func_table_.wifi_twt_get_stats(getIfaceHandle(iface_name), configId, &stats);
1784 return {status, stats};
1785}
1786
1787wifi_error WifiLegacyHal::twtClearStats(const std::string& iface_name, uint8_t configId) {
1788 return global_func_table_.wifi_twt_clear_stats(getIfaceHandle(iface_name), configId);
1789}
1790
Ye Jiao50274f72023-01-17 14:53:22 +08001791wifi_error WifiLegacyHal::setScanMode(const std::string& iface_name, bool enable) {
1792 return global_func_table_.wifi_set_scan_mode(iface_name.c_str(), enable);
1793}
1794
Gabriel Birenf3262f92022-07-15 23:25:39 +00001795wifi_error WifiLegacyHal::setDtimConfig(const std::string& iface_name, uint32_t multiplier) {
1796 return global_func_table_.wifi_set_dtim_config(getIfaceHandle(iface_name), multiplier);
1797}
1798
1799std::pair<wifi_error, std::vector<wifi_usable_channel>> WifiLegacyHal::getUsableChannels(
1800 uint32_t band_mask, uint32_t iface_mode_mask, uint32_t filter_mask) {
1801 std::vector<wifi_usable_channel> channels;
1802 channels.resize(kMaxWifiUsableChannels);
1803 uint32_t size = 0;
1804 wifi_error status = global_func_table_.wifi_get_usable_channels(
1805 global_handle_, band_mask, iface_mode_mask, filter_mask, channels.size(), &size,
1806 reinterpret_cast<wifi_usable_channel*>(channels.data()));
1807 CHECK(size >= 0 && size <= kMaxWifiUsableChannels);
1808 channels.resize(size);
1809 return {status, std::move(channels)};
1810}
1811
1812wifi_error WifiLegacyHal::triggerSubsystemRestart() {
1813 return global_func_table_.wifi_trigger_subsystem_restart(global_handle_);
1814}
1815
1816wifi_error WifiLegacyHal::setIndoorState(bool isIndoor) {
1817 return global_func_table_.wifi_set_indoor_state(global_handle_, isIndoor);
1818}
1819
1820std::pair<wifi_error, wifi_radio_combination_matrix*>
1821WifiLegacyHal::getSupportedRadioCombinationsMatrix() {
1822 char* buffer = new char[kMaxSupportedRadioCombinationsMatrixLength];
1823 std::fill(buffer, buffer + kMaxSupportedRadioCombinationsMatrixLength, 0);
1824 uint32_t size = 0;
1825 wifi_radio_combination_matrix* radio_combination_matrix_ptr =
1826 reinterpret_cast<wifi_radio_combination_matrix*>(buffer);
1827 wifi_error status = global_func_table_.wifi_get_supported_radio_combinations_matrix(
1828 global_handle_, kMaxSupportedRadioCombinationsMatrixLength, &size,
1829 radio_combination_matrix_ptr);
1830 CHECK(size >= 0 && size <= kMaxSupportedRadioCombinationsMatrixLength);
1831 return {status, radio_combination_matrix_ptr};
1832}
1833
1834wifi_error WifiLegacyHal::chreNanRttRequest(const std::string& iface_name, bool enable) {
1835 if (enable)
1836 return global_func_table_.wifi_nan_rtt_chre_enable_request(0, getIfaceHandle(iface_name),
1837 NULL);
1838 else
1839 return global_func_table_.wifi_nan_rtt_chre_disable_request(0, getIfaceHandle(iface_name));
1840}
1841
1842wifi_error WifiLegacyHal::chreRegisterHandler(const std::string& iface_name,
1843 const ChreCallbackHandlers& handler) {
1844 if (on_chre_nan_rtt_internal_callback) {
1845 return WIFI_ERROR_NOT_AVAILABLE;
1846 }
1847
1848 on_chre_nan_rtt_internal_callback = handler.on_wifi_chre_nan_rtt_state;
1849
1850 wifi_error status = global_func_table_.wifi_chre_register_handler(getIfaceHandle(iface_name),
1851 {onAsyncChreNanRttState});
1852 if (status != WIFI_SUCCESS) {
1853 on_chre_nan_rtt_internal_callback = nullptr;
1854 }
1855 return status;
1856}
1857
1858wifi_error WifiLegacyHal::enableWifiTxPowerLimits(const std::string& iface_name, bool enable) {
1859 return global_func_table_.wifi_enable_tx_power_limits(getIfaceHandle(iface_name), enable);
1860}
1861
Kai Shi7d0e5e92023-11-20 19:23:36 -08001862wifi_error WifiLegacyHal::getWifiCachedScanResults(const std::string& iface_name,
1863 WifiCachedScanReport& report) {
1864 on_cached_scan_results_internal_callback = [&report](wifi_cached_scan_report* report_ptr) {
1865 report.results.assign(report_ptr->results, report_ptr->results + report_ptr->result_cnt);
1866 report.scanned_freqs.assign(report_ptr->scanned_freq_list,
1867 report_ptr->scanned_freq_list + report_ptr->scanned_freq_num);
1868 report.ts = report_ptr->ts;
1869 };
Gabriel Birenf3262f92022-07-15 23:25:39 +00001870 wifi_error status = global_func_table_.wifi_get_cached_scan_results(getIfaceHandle(iface_name),
1871 {onSyncCachedScanResults});
Gabriel Birenf3262f92022-07-15 23:25:39 +00001872 on_cached_scan_results_internal_callback = nullptr;
1873 return status;
1874}
1875
Mahesh KKVc84d3772022-12-02 16:53:28 -08001876std::pair<wifi_error, wifi_chip_capabilities> WifiLegacyHal::getWifiChipCapabilities() {
1877 wifi_chip_capabilities chip_capabilities;
1878 wifi_error status =
1879 global_func_table_.wifi_get_chip_capabilities(global_handle_, &chip_capabilities);
1880 return {status, chip_capabilities};
1881}
1882
Shuibing Daie5fbcab2022-12-19 15:37:19 -08001883wifi_error WifiLegacyHal::enableStaChannelForPeerNetwork(uint32_t channelCategoryEnableFlag) {
1884 return global_func_table_.wifi_enable_sta_channel_for_peer_network(global_handle_,
1885 channelCategoryEnableFlag);
1886}
1887
maheshkkva8aba172023-02-13 12:33:26 -08001888wifi_error WifiLegacyHal::setMloMode(wifi_mlo_mode mode) {
1889 return global_func_table_.wifi_set_mlo_mode(global_handle_, mode);
1890}
1891
Sunil Ravif68b9a22023-02-15 20:56:56 +00001892std::pair<wifi_error, wifi_iface_concurrency_matrix>
1893WifiLegacyHal::getSupportedIfaceConcurrencyMatrix() {
1894 wifi_iface_concurrency_matrix iface_concurrency_matrix;
1895 wifi_error status = global_func_table_.wifi_get_supported_iface_concurrency_matrix(
1896 global_handle_, &iface_concurrency_matrix);
1897 return {status, iface_concurrency_matrix};
1898}
1899
Gabriel Birenf3262f92022-07-15 23:25:39 +00001900void WifiLegacyHal::invalidate() {
1901 global_handle_ = nullptr;
1902 iface_name_to_handle_.clear();
1903 on_driver_memory_dump_internal_callback = nullptr;
1904 on_firmware_memory_dump_internal_callback = nullptr;
1905 on_gscan_event_internal_callback = nullptr;
1906 on_gscan_full_result_internal_callback = nullptr;
1907 on_link_layer_stats_result_internal_callback = nullptr;
Mahesh KKV5f30d332022-10-26 14:07:44 -07001908 on_link_layer_ml_stats_result_internal_callback = nullptr;
Gabriel Birenf3262f92022-07-15 23:25:39 +00001909 on_rssi_threshold_breached_internal_callback = nullptr;
1910 on_ring_buffer_data_internal_callback = nullptr;
1911 on_error_alert_internal_callback = nullptr;
1912 on_radio_mode_change_internal_callback = nullptr;
1913 on_subsystem_restart_internal_callback = nullptr;
Sunil Ravif8fc2372022-11-10 18:37:41 +00001914 invalidateRttResultsCallbacks();
Gabriel Birenf3262f92022-07-15 23:25:39 +00001915 on_nan_notify_response_user_callback = nullptr;
1916 on_nan_event_publish_terminated_user_callback = nullptr;
1917 on_nan_event_match_user_callback = nullptr;
1918 on_nan_event_match_expired_user_callback = nullptr;
1919 on_nan_event_subscribe_terminated_user_callback = nullptr;
1920 on_nan_event_followup_user_callback = nullptr;
1921 on_nan_event_disc_eng_event_user_callback = nullptr;
1922 on_nan_event_disabled_user_callback = nullptr;
1923 on_nan_event_tca_user_callback = nullptr;
1924 on_nan_event_beacon_sdf_payload_user_callback = nullptr;
1925 on_nan_event_data_path_request_user_callback = nullptr;
Nate Jiang38e8db52022-12-02 17:30:27 -08001926 on_nan_event_pairing_request_user_callback = nullptr;
1927 on_nan_event_pairing_confirm_user_callback = nullptr;
1928 on_nan_event_bootstrapping_request_user_callback = nullptr;
1929 on_nan_event_bootstrapping_confirm_user_callback = nullptr;
Gabriel Birenf3262f92022-07-15 23:25:39 +00001930 on_nan_event_data_path_confirm_user_callback = nullptr;
1931 on_nan_event_data_path_end_user_callback = nullptr;
1932 on_nan_event_transmit_follow_up_user_callback = nullptr;
1933 on_nan_event_range_request_user_callback = nullptr;
1934 on_nan_event_range_report_user_callback = nullptr;
1935 on_nan_event_schedule_update_user_callback = nullptr;
1936 on_twt_event_setup_response_callback = nullptr;
1937 on_twt_event_teardown_completion_callback = nullptr;
1938 on_twt_event_info_frame_received_callback = nullptr;
1939 on_twt_event_device_notify_callback = nullptr;
1940 on_chre_nan_rtt_internal_callback = nullptr;
Kai Shi7d0e5e92023-11-20 19:23:36 -08001941 on_cached_scan_results_internal_callback = nullptr;
Gabriel Birenf3262f92022-07-15 23:25:39 +00001942}
1943
1944} // namespace legacy_hal
1945} // namespace wifi
1946} // namespace hardware
1947} // namespace android
1948} // namespace aidl