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 #ifndef WIFI_LEGACY_HAL_H_ 18 #define WIFI_LEGACY_HAL_H_ 19 20 #include <condition_variable> 21 #include <functional> 22 #include <map> 23 #include <thread> 24 #include <vector> 25 26 #include <wifi_system/interface_tool.h> 27 28 // HACK: The include inside the namespace below also transitively includes a 29 // bunch of libc headers into the namespace, which leads to functions like 30 // socketpair being defined in 31 // android::hardware::wifi::V1_1::implementation::legacy_hal. Include this one 32 // particular header as a hacky workaround until that's fixed. 33 #include <sys/socket.h> 34 35 namespace android { 36 namespace hardware { 37 namespace wifi { 38 namespace V1_4 { 39 namespace implementation { 40 // This is in a separate namespace to prevent typename conflicts between 41 // the legacy HAL types and the HIDL interface types. 42 namespace legacy_hal { 43 // Wrap all the types defined inside the legacy HAL header files inside this 44 // namespace. 45 #include <hardware_legacy/wifi_hal.h> 46 47 // APF capabilities supported by the iface. 48 struct PacketFilterCapabilities { 49 uint32_t version; 50 uint32_t max_len; 51 }; 52 53 // WARNING: We don't care about the variable sized members of either 54 // |wifi_iface_stat|, |wifi_radio_stat| structures. So, using the pragma 55 // to escape the compiler warnings regarding this. 56 #pragma GCC diagnostic push 57 #pragma GCC diagnostic ignored "-Wgnu-variable-sized-type-not-at-end" 58 // The |wifi_radio_stat.tx_time_per_levels| stats is provided as a pointer in 59 // |wifi_radio_stat| structure in the legacy HAL API. Separate that out 60 // into a separate return element to avoid passing pointers around. 61 struct LinkLayerRadioStats { 62 wifi_radio_stat stats; 63 std::vector<uint32_t> tx_time_per_levels; 64 std::vector<wifi_channel_stat> channel_stats; 65 }; 66 67 struct LinkLayerStats { 68 wifi_iface_stat iface; 69 std::vector<LinkLayerRadioStats> radios; 70 }; 71 #pragma GCC diagnostic pop 72 73 // The |WLAN_DRIVER_WAKE_REASON_CNT.cmd_event_wake_cnt| and 74 // |WLAN_DRIVER_WAKE_REASON_CNT.driver_fw_local_wake_cnt| stats is provided 75 // as a pointer in |WLAN_DRIVER_WAKE_REASON_CNT| structure in the legacy HAL 76 // API. Separate that out into a separate return elements to avoid passing 77 // pointers around. 78 struct WakeReasonStats { 79 WLAN_DRIVER_WAKE_REASON_CNT wake_reason_cnt; 80 std::vector<uint32_t> cmd_event_wake_cnt; 81 std::vector<uint32_t> driver_fw_local_wake_cnt; 82 }; 83 84 // NAN response and event callbacks struct. 85 struct NanCallbackHandlers { 86 // NotifyResponse invoked to notify the status of the Request. 87 std::function<void(transaction_id, const NanResponseMsg&)> 88 on_notify_response; 89 // Various event callbacks. 90 std::function<void(const NanPublishTerminatedInd&)> 91 on_event_publish_terminated; 92 std::function<void(const NanMatchInd&)> on_event_match; 93 std::function<void(const NanMatchExpiredInd&)> on_event_match_expired; 94 std::function<void(const NanSubscribeTerminatedInd&)> 95 on_event_subscribe_terminated; 96 std::function<void(const NanFollowupInd&)> on_event_followup; 97 std::function<void(const NanDiscEngEventInd&)> on_event_disc_eng_event; 98 std::function<void(const NanDisabledInd&)> on_event_disabled; 99 std::function<void(const NanTCAInd&)> on_event_tca; 100 std::function<void(const NanBeaconSdfPayloadInd&)> 101 on_event_beacon_sdf_payload; 102 std::function<void(const NanDataPathRequestInd&)> 103 on_event_data_path_request; 104 std::function<void(const NanDataPathConfirmInd&)> 105 on_event_data_path_confirm; 106 std::function<void(const NanDataPathEndInd&)> on_event_data_path_end; 107 std::function<void(const NanTransmitFollowupInd&)> 108 on_event_transmit_follow_up; 109 std::function<void(const NanRangeRequestInd&)> on_event_range_request; 110 std::function<void(const NanRangeReportInd&)> on_event_range_report; 111 std::function<void(const NanDataPathScheduleUpdateInd&)> 112 on_event_schedule_update; 113 }; 114 115 // Full scan results contain IE info and are hence passed by reference, to 116 // preserve the variable length array member |ie_data|. Callee must not retain 117 // the pointer. 118 using on_gscan_full_result_callback = 119 std::function<void(wifi_request_id, const wifi_scan_result*, uint32_t)>; 120 // These scan results don't contain any IE info, so no need to pass by 121 // reference. 122 using on_gscan_results_callback = std::function<void( 123 wifi_request_id, const std::vector<wifi_cached_scan_results>&)>; 124 125 // Invoked when the rssi value breaches the thresholds set. 126 using on_rssi_threshold_breached_callback = 127 std::function<void(wifi_request_id, std::array<uint8_t, 6>, int8_t)>; 128 129 // Callback for RTT range request results. 130 // Rtt results contain IE info and are hence passed by reference, to 131 // preserve the |LCI| and |LCR| pointers. Callee must not retain 132 // the pointer. 133 using on_rtt_results_callback = std::function<void( 134 wifi_request_id, const std::vector<const wifi_rtt_result*>&)>; 135 136 // Callback for ring buffer data. 137 using on_ring_buffer_data_callback = 138 std::function<void(const std::string&, const std::vector<uint8_t>&, 139 const wifi_ring_buffer_status&)>; 140 141 // Callback for alerts. 142 using on_error_alert_callback = 143 std::function<void(int32_t, const std::vector<uint8_t>&)>; 144 145 // Struct for the mac info from the legacy HAL. This is a cleaner version 146 // of the |wifi_mac_info| & |wifi_iface_info|. 147 typedef struct { 148 std::string name; 149 wifi_channel channel; 150 } WifiIfaceInfo; 151 152 typedef struct { 153 uint32_t wlan_mac_id; 154 /* BIT MASK of BIT(WLAN_MAC*) as represented by wlan_mac_band */ 155 uint32_t mac_band; 156 /* Represents the connected Wi-Fi interfaces associated with each MAC */ 157 std::vector<WifiIfaceInfo> iface_infos; 158 } WifiMacInfo; 159 160 // Callback for radio mode change 161 using on_radio_mode_change_callback = 162 std::function<void(const std::vector<WifiMacInfo>&)>; 163 164 /** 165 * Class that encapsulates all legacy HAL interactions. 166 * This class manages the lifetime of the event loop thread used by legacy HAL. 167 * 168 * Note: There will only be a single instance of this class created in the Wifi 169 * object and will be valid for the lifetime of the process. 170 */ 171 class WifiLegacyHal { 172 public: 173 WifiLegacyHal(const std::weak_ptr<wifi_system::InterfaceTool> iface_tool); 174 virtual ~WifiLegacyHal() = default; 175 176 // Initialize the legacy HAL function table. 177 virtual wifi_error initialize(); 178 // Start the legacy HAL and the event looper thread. 179 virtual wifi_error start(); 180 // Deinitialize the legacy HAL and wait for the event loop thread to exit 181 // using a predefined timeout. 182 virtual wifi_error stop(std::unique_lock<std::recursive_mutex>* lock, 183 const std::function<void()>& on_complete_callback); 184 // Checks if legacy HAL has successfully started 185 bool isStarted(); 186 // Wrappers for all the functions in the legacy HAL function table. 187 virtual std::pair<wifi_error, std::string> getDriverVersion( 188 const std::string& iface_name); 189 virtual std::pair<wifi_error, std::string> getFirmwareVersion( 190 const std::string& iface_name); 191 std::pair<wifi_error, std::vector<uint8_t>> requestDriverMemoryDump( 192 const std::string& iface_name); 193 std::pair<wifi_error, std::vector<uint8_t>> requestFirmwareMemoryDump( 194 const std::string& iface_name); 195 std::pair<wifi_error, uint32_t> getSupportedFeatureSet( 196 const std::string& iface_name); 197 // APF functions. 198 std::pair<wifi_error, PacketFilterCapabilities> getPacketFilterCapabilities( 199 const std::string& iface_name); 200 wifi_error setPacketFilter(const std::string& iface_name, 201 const std::vector<uint8_t>& program); 202 std::pair<wifi_error, std::vector<uint8_t>> readApfPacketFilterData( 203 const std::string& iface_name); 204 // Gscan functions. 205 std::pair<wifi_error, wifi_gscan_capabilities> getGscanCapabilities( 206 const std::string& iface_name); 207 // These API's provides a simplified interface over the legacy Gscan API's: 208 // a) All scan events from the legacy HAL API other than the 209 // |WIFI_SCAN_FAILED| are treated as notification of results. 210 // This method then retrieves the cached scan results from the legacy 211 // HAL API and triggers the externally provided 212 // |on_results_user_callback| on success. 213 // b) |WIFI_SCAN_FAILED| scan event or failure to retrieve cached scan 214 // results 215 // triggers the externally provided |on_failure_user_callback|. 216 // c) Full scan result event triggers the externally provided 217 // |on_full_result_user_callback|. 218 wifi_error startGscan( 219 const std::string& iface_name, wifi_request_id id, 220 const wifi_scan_cmd_params& params, 221 const std::function<void(wifi_request_id)>& on_failure_callback, 222 const on_gscan_results_callback& on_results_callback, 223 const on_gscan_full_result_callback& on_full_result_callback); 224 wifi_error stopGscan(const std::string& iface_name, wifi_request_id id); 225 std::pair<wifi_error, std::vector<uint32_t>> getValidFrequenciesForBand( 226 const std::string& iface_name, wifi_band band); 227 virtual wifi_error setDfsFlag(const std::string& iface_name, bool dfs_on); 228 // Link layer stats functions. 229 wifi_error enableLinkLayerStats(const std::string& iface_name, bool debug); 230 wifi_error disableLinkLayerStats(const std::string& iface_name); 231 std::pair<wifi_error, LinkLayerStats> getLinkLayerStats( 232 const std::string& iface_name); 233 // RSSI monitor functions. 234 wifi_error startRssiMonitoring(const std::string& iface_name, 235 wifi_request_id id, int8_t max_rssi, 236 int8_t min_rssi, 237 const on_rssi_threshold_breached_callback& 238 on_threshold_breached_callback); 239 wifi_error stopRssiMonitoring(const std::string& iface_name, 240 wifi_request_id id); 241 std::pair<wifi_error, wifi_roaming_capabilities> getRoamingCapabilities( 242 const std::string& iface_name); 243 wifi_error configureRoaming(const std::string& iface_name, 244 const wifi_roaming_config& config); 245 wifi_error enableFirmwareRoaming(const std::string& iface_name, 246 fw_roaming_state_t state); 247 wifi_error configureNdOffload(const std::string& iface_name, bool enable); 248 wifi_error startSendingOffloadedPacket( 249 const std::string& iface_name, uint32_t cmd_id, uint16_t ether_type, 250 const std::vector<uint8_t>& ip_packet_data, 251 const std::array<uint8_t, 6>& src_address, 252 const std::array<uint8_t, 6>& dst_address, uint32_t period_in_ms); 253 wifi_error stopSendingOffloadedPacket(const std::string& iface_name, 254 uint32_t cmd_id); 255 virtual wifi_error selectTxPowerScenario(const std::string& iface_name, 256 wifi_power_scenario scenario); 257 virtual wifi_error resetTxPowerScenario(const std::string& iface_name); 258 wifi_error setLatencyMode(const std::string& iface_name, 259 wifi_latency_mode mode); 260 wifi_error setThermalMitigationMode(wifi_thermal_mode mode, 261 uint32_t completion_window); 262 wifi_error setDscpToAccessCategoryMapping(uint32_t start, uint32_t end, 263 uint32_t access_category); 264 wifi_error resetDscpToAccessCategoryMapping(); 265 // Logger/debug functions. 266 std::pair<wifi_error, uint32_t> getLoggerSupportedFeatureSet( 267 const std::string& iface_name); 268 wifi_error startPktFateMonitoring(const std::string& iface_name); 269 std::pair<wifi_error, std::vector<wifi_tx_report>> getTxPktFates( 270 const std::string& iface_name); 271 std::pair<wifi_error, std::vector<wifi_rx_report>> getRxPktFates( 272 const std::string& iface_name); 273 std::pair<wifi_error, WakeReasonStats> getWakeReasonStats( 274 const std::string& iface_name); 275 wifi_error registerRingBufferCallbackHandler( 276 const std::string& iface_name, 277 const on_ring_buffer_data_callback& on_data_callback); 278 wifi_error deregisterRingBufferCallbackHandler( 279 const std::string& iface_name); 280 std::pair<wifi_error, std::vector<wifi_ring_buffer_status>> 281 getRingBuffersStatus(const std::string& iface_name); 282 wifi_error startRingBufferLogging(const std::string& iface_name, 283 const std::string& ring_name, 284 uint32_t verbose_level, 285 uint32_t max_interval_sec, 286 uint32_t min_data_size); 287 wifi_error getRingBufferData(const std::string& iface_name, 288 const std::string& ring_name); 289 wifi_error registerErrorAlertCallbackHandler( 290 const std::string& iface_name, 291 const on_error_alert_callback& on_alert_callback); 292 wifi_error deregisterErrorAlertCallbackHandler( 293 const std::string& iface_name); 294 // Radio mode functions. 295 virtual wifi_error registerRadioModeChangeCallbackHandler( 296 const std::string& iface_name, 297 const on_radio_mode_change_callback& on_user_change_callback); 298 // RTT functions. 299 wifi_error startRttRangeRequest( 300 const std::string& iface_name, wifi_request_id id, 301 const std::vector<wifi_rtt_config>& rtt_configs, 302 const on_rtt_results_callback& on_results_callback); 303 wifi_error cancelRttRangeRequest( 304 const std::string& iface_name, wifi_request_id id, 305 const std::vector<std::array<uint8_t, 6>>& mac_addrs); 306 std::pair<wifi_error, wifi_rtt_capabilities> getRttCapabilities( 307 const std::string& iface_name); 308 std::pair<wifi_error, wifi_rtt_responder> getRttResponderInfo( 309 const std::string& iface_name); 310 wifi_error enableRttResponder(const std::string& iface_name, 311 wifi_request_id id, 312 const wifi_channel_info& channel_hint, 313 uint32_t max_duration_secs, 314 const wifi_rtt_responder& info); 315 wifi_error disableRttResponder(const std::string& iface_name, 316 wifi_request_id id); 317 wifi_error setRttLci(const std::string& iface_name, wifi_request_id id, 318 const wifi_lci_information& info); 319 wifi_error setRttLcr(const std::string& iface_name, wifi_request_id id, 320 const wifi_lcr_information& info); 321 // NAN functions. 322 virtual wifi_error nanRegisterCallbackHandlers( 323 const std::string& iface_name, const NanCallbackHandlers& callbacks); 324 wifi_error nanEnableRequest(const std::string& iface_name, 325 transaction_id id, const NanEnableRequest& msg); 326 virtual wifi_error nanDisableRequest(const std::string& iface_name, 327 transaction_id id); 328 wifi_error nanPublishRequest(const std::string& iface_name, 329 transaction_id id, 330 const NanPublishRequest& msg); 331 wifi_error nanPublishCancelRequest(const std::string& iface_name, 332 transaction_id id, 333 const NanPublishCancelRequest& msg); 334 wifi_error nanSubscribeRequest(const std::string& iface_name, 335 transaction_id id, 336 const NanSubscribeRequest& msg); 337 wifi_error nanSubscribeCancelRequest(const std::string& iface_name, 338 transaction_id id, 339 const NanSubscribeCancelRequest& msg); 340 wifi_error nanTransmitFollowupRequest( 341 const std::string& iface_name, transaction_id id, 342 const NanTransmitFollowupRequest& msg); 343 wifi_error nanStatsRequest(const std::string& iface_name, transaction_id id, 344 const NanStatsRequest& msg); 345 wifi_error nanConfigRequest(const std::string& iface_name, 346 transaction_id id, const NanConfigRequest& msg); 347 wifi_error nanTcaRequest(const std::string& iface_name, transaction_id id, 348 const NanTCARequest& msg); 349 wifi_error nanBeaconSdfPayloadRequest( 350 const std::string& iface_name, transaction_id id, 351 const NanBeaconSdfPayloadRequest& msg); 352 std::pair<wifi_error, NanVersion> nanGetVersion(); 353 wifi_error nanGetCapabilities(const std::string& iface_name, 354 transaction_id id); 355 wifi_error nanDataInterfaceCreate(const std::string& iface_name, 356 transaction_id id, 357 const std::string& data_iface_name); 358 virtual wifi_error nanDataInterfaceDelete( 359 const std::string& iface_name, transaction_id id, 360 const std::string& data_iface_name); 361 wifi_error nanDataRequestInitiator(const std::string& iface_name, 362 transaction_id id, 363 const NanDataPathInitiatorRequest& msg); 364 wifi_error nanDataIndicationResponse( 365 const std::string& iface_name, transaction_id id, 366 const NanDataPathIndicationResponse& msg); 367 wifi_error nanDataEnd(const std::string& iface_name, transaction_id id, 368 uint32_t ndpInstanceId); 369 // AP functions. 370 wifi_error setCountryCode(const std::string& iface_name, 371 std::array<int8_t, 2> code); 372 373 // interface functions. 374 virtual wifi_error createVirtualInterface(const std::string& ifname, 375 wifi_interface_type iftype); 376 virtual wifi_error deleteVirtualInterface(const std::string& ifname); 377 378 private: 379 // Retrieve interface handles for all the available interfaces. 380 wifi_error retrieveIfaceHandles(); 381 wifi_interface_handle getIfaceHandle(const std::string& iface_name); 382 // Run the legacy HAL event loop thread. 383 void runEventLoop(); 384 // Retrieve the cached gscan results to pass the results back to the 385 // external callbacks. 386 std::pair<wifi_error, std::vector<wifi_cached_scan_results>> 387 getGscanCachedResults(const std::string& iface_name); 388 void invalidate(); 389 // Handles wifi (error) status of Virtual interface create/delete 390 wifi_error handleVirtualInterfaceCreateOrDeleteStatus( 391 const std::string& ifname, wifi_error status); 392 393 // Global function table of legacy HAL. 394 wifi_hal_fn global_func_table_; 395 // Opaque handle to be used for all global operations. 396 wifi_handle global_handle_; 397 // Map of interface name to handle that is to be used for all interface 398 // specific operations. 399 std::map<std::string, wifi_interface_handle> iface_name_to_handle_; 400 // Flag to indicate if we have initiated the cleanup of legacy HAL. 401 std::atomic<bool> awaiting_event_loop_termination_; 402 std::condition_variable_any stop_wait_cv_; 403 // Flag to indicate if the legacy HAL has been started. 404 bool is_started_; 405 std::weak_ptr<wifi_system::InterfaceTool> iface_tool_; 406 }; 407 408 } // namespace legacy_hal 409 } // namespace implementation 410 } // namespace V1_4 411 } // namespace wifi 412 } // namespace hardware 413 } // namespace android 414 415 #endif // WIFI_LEGACY_HAL_H_ 416