| // Copyright 2018 The Chromium OS Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #ifndef SHILL_WIFI_WIFI_H_ |
| #define SHILL_WIFI_WIFI_H_ |
| |
| // A WiFi device represents a wireless network interface implemented as an IEEE |
| // 802.11 station. An Access Point (AP) (or, more correctly, a Basic Service |
| // Set(BSS)) is represented by a WiFiEndpoint. An AP provides a WiFiService, |
| // which is the same concept as Extended Service Set (ESS) in 802.11, |
| // identified by an SSID. A WiFiService includes zero or more WiFiEndpoints |
| // that provide that service. |
| // |
| // A WiFi device interacts with a real device through WPA Supplicant. |
| // Wifi::Start() creates a connection to WPA Supplicant, represented by |
| // |supplicant_interface_proxy_|. [1] |
| // |
| // A WiFi device becomes aware of WiFiEndpoints through BSSAdded signals from |
| // WPA Supplicant, which identifies them by a "path". The WiFi object maintains |
| // an EndpointMap in |endpoint_by_rpcid_|, in which the key is the "path" and |
| // the value is a pointer to a WiFiEndpoint object. When a WiFiEndpoint is |
| // added, it is associated with a WiFiService. |
| // |
| // The WiFi device connects to a WiFiService, not a WiFiEndpoint, through WPA |
| // Supplicant. It is the job of WPA Supplicant to select a BSS (aka |
| // WiFiEndpoint) to connect to. The protocol for establishing a connection is |
| // as follows: |
| // |
| // 1. The WiFi device sends AddNetwork to WPA Supplicant, which returns a |
| // "network path" when done. |
| // |
| // 2. The WiFi device sends SelectNetwork, indicating the network path |
| // received in 1, to WPA Supplicant, which begins the process of associating |
| // with an AP in the ESS. At this point the WiFiService which is being |
| // connected is called the |pending_service_|. |
| // |
| // 3. During association to an EAP-TLS network, WPA Supplicant can send |
| // multiple "Certification" events, which provide information about the |
| // identity of the remote entity. |
| // |
| // 4. When association is complete, WPA Supplicant sends a PropertiesChanged |
| // signal to the WiFi device, indicating a change in the CurrentBSS. The |
| // WiFiService indicated by the new value of CurrentBSS is set as the |
| // |current_service_|, and |pending_service_| is (normally) cleared. |
| // |
| // Some key things to notice are 1) WPA Supplicant does the work of selecting |
| // the AP (aka WiFiEndpoint) and it tells the WiFi device which AP it selected. |
| // 2) The process of connecting is asynchronous. There is a |current_service_| |
| // to which the WiFi device is presently using and a |pending_service_| to which |
| // the WiFi device has initiated a connection. |
| // |
| // A WiFi device is notified that an AP has gone away via the BSSRemoved signal. |
| // When the last WiFiEndpoint of a WiFiService is removed, the WiFiService |
| // itself is deleted. |
| // |
| // TODO(gmorain): Add explanation of hidden SSIDs. |
| // |
| // WPA Supplicant's PropertiesChanged signal communicates changes in the state |
| // of WPA Supplicant's current service. This state is stored in |
| // |supplicant_state_| and reflects WPA Supplicant's view of the state of the |
| // connection to an AP. Changes in this state sometimes cause state changes in |
| // the WiFiService to which a WiFi device is connected. For example, when WPA |
| // Supplicant signals the new state to be "completed", then the WiFiService |
| // state gets changed to "configuring". State change notifications are not |
| // reliable because WPA Supplicant may coalesce state changes in quick |
| // succession so that only the last of the changes is signaled. |
| // |
| // Notes: |
| // |
| // 1. Shill's definition of the interface is described in |
| // shill/dbus_proxies/supplicant-interface.xml, and the WPA Supplicant's |
| // description of the same interface is in |
| // third_party/wpa_supplicant/doc/dbus.doxygen. |
| |
| #include <time.h> |
| |
| #include <map> |
| #include <memory> |
| #include <set> |
| #include <string> |
| #include <vector> |
| |
| #include <base/callback_forward.h> |
| #include <base/cancelable_callback.h> |
| #include <base/memory/weak_ptr.h> |
| #include <gtest/gtest_prod.h> // for FRIEND_TEST |
| |
| #include "shill/device.h" |
| #include "shill/event_dispatcher.h" |
| #include "shill/key_value_store.h" |
| #include "shill/net/ieee80211.h" |
| #include "shill/net/netlink_manager.h" |
| #include "shill/refptr_types.h" |
| #include "shill/service.h" |
| #include "shill/supplicant/supplicant_event_delegate_interface.h" |
| #include "shill/supplicant/supplicant_manager.h" |
| |
| namespace shill { |
| |
| class Error; |
| class Mac80211Monitor; |
| class Metrics; |
| class NetlinkManager; |
| class NetlinkMessage; |
| class Nl80211Message; |
| class SupplicantEAPStateHandler; |
| class SupplicantInterfaceProxyInterface; |
| class SupplicantProcessProxyInterface; |
| class WakeOnWiFiInterface; |
| class WiFiProvider; |
| class WiFiService; |
| |
| // WiFi class. Specialization of Device for WiFi. |
| class WiFi : public Device, public SupplicantEventDelegateInterface { |
| public: |
| using FreqSet = std::set<uint32_t>; |
| |
| WiFi(Manager* manager, |
| const std::string& link, |
| const std::string& address, |
| int interface_index, |
| std::unique_ptr<WakeOnWiFiInterface> wake_on_wifi); |
| ~WiFi() override; |
| |
| void Start(Error* error, |
| const EnabledStateChangedCallback& callback) override; |
| void Stop(Error* error, const EnabledStateChangedCallback& callback) override; |
| void Scan(Error* error, const std::string& reason) override; |
| // Callback for system suspend. |
| void OnBeforeSuspend(const ResultCallback& callback) override; |
| // Callback for dark resume. |
| void OnDarkResume(const ResultCallback& callback) override; |
| // Callback for system resume. If this WiFi device is idle, a scan |
| // is initiated. Additionally, the base class implementation is |
| // invoked unconditionally. |
| void OnAfterResume() override; |
| // Callback for when a service is configured with an IP. |
| void OnConnected() override; |
| // Callback for when a service fails to configure with an IP. |
| void OnIPConfigFailure() override; |
| |
| // Calls corresponding functions of |wake_on_wifi_|. Refer to wake_on_wifi.h |
| // for documentation. |
| void AddWakeOnPacketConnection(const std::string& ip_endpoint, |
| Error* error) override; |
| void AddWakeOnPacketOfTypes(const std::vector<std::string>& packet_types, |
| Error* error) override; |
| void RemoveWakeOnPacketConnection(const std::string& ip_endpoint, |
| Error* error) override; |
| void RemoveWakeOnPacketOfTypes(const std::vector<std::string>& packet_types, |
| Error* error) override; |
| void RemoveAllWakeOnPacketConnections(Error* error) override; |
| |
| // Implementation of SupplicantEventDelegateInterface. These methods |
| // are called by SupplicantInterfaceProxy, in response to events from |
| // wpa_supplicant. |
| void BSSAdded(const RpcIdentifier& BSS, |
| const KeyValueStore& properties) override; |
| void BSSRemoved(const RpcIdentifier& BSS) override; |
| void Certification(const KeyValueStore& properties) override; |
| void EAPEvent(const std::string& status, |
| const std::string& parameter) override; |
| void PropertiesChanged(const KeyValueStore& properties) override; |
| void ScanDone(const bool& success) override; |
| |
| // Called by WiFiService. |
| virtual void ConnectTo(WiFiService* service, Error* error); |
| |
| // After checking |service| state is active, initiate |
| // process of disconnecting. Log and return if not active. |
| virtual void DisconnectFromIfActive(WiFiService* service); |
| |
| // If |service| is connected, initiate the process of disconnecting it. |
| // Otherwise, if it a pending or current service, discontinue the process |
| // of connecting and return |service| to the idle state. |
| virtual void DisconnectFrom(WiFiService* service); |
| virtual bool IsIdle() const; |
| // Clear any cached credentials wpa_supplicant may be holding for |
| // |service|. This has a side-effect of disconnecting the service |
| // if it is connected. |
| virtual void ClearCachedCredentials(const WiFiService* service); |
| |
| // Called by WiFiEndpoint. |
| virtual void NotifyEndpointChanged(const WiFiEndpointConstRefPtr& endpoint); |
| |
| // Utility, used by WiFiService and WiFiEndpoint. |
| // Replace non-ASCII characters with '?'. Return true if one or more |
| // characters were changed. |
| static bool SanitizeSSID(std::string* ssid); |
| |
| // Formats |ssid| for logging purposes, to ease scrubbing. |
| static std::string LogSSID(const std::string& ssid); |
| |
| // Called by Linkmonitor (overridden from Device superclass). |
| void OnLinkMonitorFailure() override; |
| |
| virtual bool IsCurrentService(const WiFiService* service) const { |
| return service == current_service_.get(); |
| } |
| |
| bool IsPendingService(const WiFiService* service) const { |
| return service == pending_service_.get(); |
| } |
| |
| const WiFiEndpointConstRefPtr GetCurrentEndpoint() const; |
| |
| // Overridden from Device superclass |
| std::vector<GeolocationInfo> GetGeolocationObjects() const override; |
| |
| // Overridden from Device superclass |
| bool ShouldUseArpGateway() const override; |
| |
| // Called by a WiFiService when it disassociates itself from this Device. |
| virtual void DisassociateFromService(const WiFiServiceRefPtr& service); |
| |
| // Called by a WiFiService when it unloads to destroy its lease file. |
| virtual void DestroyServiceLease(const WiFiService& service); |
| |
| // Overridden from Device superclass. |
| bool IsTrafficMonitorEnabled() const override; |
| |
| // Remove all networks from WPA supplicant. |
| // Passed as a callback to |wake_on_wifi_| where it is used. |
| void RemoveSupplicantNetworks(); |
| |
| bool RequestRoam(const std::string& addr, Error* error) override; |
| |
| private: |
| enum ScanMethod { kScanMethodNone, kScanMethodFull }; |
| enum ScanState { |
| kScanIdle, |
| kScanScanning, |
| kScanBackgroundScanning, |
| kScanTransitionToConnecting, |
| kScanConnecting, |
| kScanConnected, |
| kScanFoundNothing |
| }; |
| |
| // Result from a BSSAdded or BSSRemoved event. |
| struct ScanResult { |
| ScanResult() : is_removal(false) {} |
| ScanResult(const RpcIdentifier& path_in, |
| const KeyValueStore& properties_in, |
| bool is_removal_in) |
| : path(path_in), properties(properties_in), is_removal(is_removal_in) {} |
| RpcIdentifier path; |
| KeyValueStore properties; |
| bool is_removal; |
| }; |
| |
| struct PendingScanResults { |
| PendingScanResults() : is_complete(false) {} |
| explicit PendingScanResults(const base::Closure& process_results_callback) |
| : is_complete(false), callback(process_results_callback) {} |
| |
| // List of pending scan results to process. |
| std::vector<ScanResult> results; |
| |
| // If true, denotes that the scan is complete (ScanDone() was called). |
| bool is_complete; |
| |
| // Cancelable closure used to process the scan results. |
| base::CancelableClosure callback; |
| }; |
| |
| friend class WiFiObjectTest; // access to supplicant_*_proxy_, link_up_ |
| friend class WiFiTimerTest; // kNumFastScanAttempts, kFastScanIntervalSeconds |
| friend class WiFiMainTest; // ScanState, ScanMethod |
| FRIEND_TEST(WiFiMainTest, AppendBgscan); |
| FRIEND_TEST(WiFiMainTest, BackgroundScan); // ScanMethod, ScanState |
| FRIEND_TEST(WiFiMainTest, ConnectToServiceNotPending); // ScanState |
| FRIEND_TEST(WiFiMainTest, ConnectToServiceWithoutRecentIssues); |
| // is_debugging_connection_ |
| FRIEND_TEST(WiFiMainTest, ConnectToWithError); // ScanState |
| FRIEND_TEST(WiFiMainTest, ConnectWhileNotScanning); // ScanState |
| FRIEND_TEST(WiFiMainTest, CurrentBSSChangedUpdateServiceEndpoint); |
| FRIEND_TEST(WiFiMainTest, DisconnectReasonUpdated); |
| FRIEND_TEST(WiFiMainTest, DisconnectReasonCleared); |
| FRIEND_TEST(WiFiMainTest, CurrentAuthModeChanged); // supplicant_auth_mode_ |
| FRIEND_TEST(WiFiMainTest, GetSuffixFromAuthMode); |
| FRIEND_TEST(WiFiMainTest, FlushBSSOnResume); // kMaxBSSResumeAgeSeconds |
| FRIEND_TEST(WiFiMainTest, FullScanConnectingToConnected); |
| FRIEND_TEST(WiFiMainTest, FullScanFindsNothing); // ScanMethod, ScanState |
| FRIEND_TEST(WiFiMainTest, InitialSupplicantState); // kInterfaceStateUnknown |
| FRIEND_TEST(WiFiMainTest, LinkMonitorFailure); // set_link_monitor() |
| FRIEND_TEST(WiFiMainTest, NoScansWhileConnecting); // ScanState |
| FRIEND_TEST(WiFiMainTest, PendingScanEvents); // EndpointMap |
| FRIEND_TEST(WiFiMainTest, ScanRejected); // ScanState |
| FRIEND_TEST(WiFiMainTest, ScanResults); // EndpointMap |
| FRIEND_TEST(WiFiMainTest, ScanStateHandleDisconnect); // ScanState |
| FRIEND_TEST(WiFiMainTest, ScanStateNotScanningNoUma); // ScanState |
| FRIEND_TEST(WiFiMainTest, ScanStateUma); // ScanState, ScanMethod |
| FRIEND_TEST(WiFiMainTest, Stop); // weak_ptr_factory_while_started_ |
| FRIEND_TEST(WiFiMainTest, TimeoutPendingServiceWithEndpoints); |
| FRIEND_TEST(WiFiPropertyTest, BgscanMethodProperty); // bgscan_method_ |
| FRIEND_TEST(WiFiTimerTest, FastRescan); // kFastScanIntervalSeconds |
| FRIEND_TEST(WiFiTimerTest, RequestStationInfo); // kRequestStationInfoPeriod |
| // kPostWakeConnectivityReportDelayMilliseconds |
| FRIEND_TEST(WiFiTimerTest, ResumeDispatchesConnectivityReportTask); |
| // kFastScanIntervalSeconds |
| FRIEND_TEST(WiFiTimerTest, StartScanTimer_HaveFastScansRemaining); |
| FRIEND_TEST(WiFiMainTest, ParseWiphyIndex_Success); // kDefaultWiphyIndex |
| // ScanMethod, ScanState |
| FRIEND_TEST(WiFiMainTest, ResetScanStateWhenScanFailed); |
| // kPostScanFailedDelayMilliseconds |
| FRIEND_TEST(WiFiTimerTest, ScanDoneDispatchesTasks); |
| // kMaxPassiveScanRetries, kMaxFreqsForPassiveScanRetries |
| FRIEND_TEST(WiFiMainTest, InitiateScanInDarkResume_Idle); |
| |
| using EndpointMap = std::map<const RpcIdentifier, WiFiEndpointRefPtr>; |
| using ReverseServiceMap = std::map<const WiFiService*, RpcIdentifier>; |
| |
| static const char* const kDefaultBgscanMethod; |
| static const int kSingleEndpointBgscanIntervalSeconds; |
| static const uint16_t kBackgroundScanIntervalSeconds; |
| static const uint16_t kDefaultScanIntervalSeconds; |
| static const time_t kMaxBSSResumeAgeSeconds; |
| static const char kInterfaceStateUnknown[]; |
| // Number of times to quickly attempt a scan after startup / disconnect. |
| static const int kNumFastScanAttempts; |
| static const int kFastScanIntervalSeconds; |
| static const int kReconnectTimeoutSeconds; |
| static const int kRequestStationInfoPeriodSeconds; |
| static const size_t kStuckQueueLengthThreshold; |
| // Number of milliseconds to wait after waking from suspend to report the |
| // connection status to metrics. |
| static const int kPostWakeConnectivityReportDelayMilliseconds; |
| // Used to instantiate |wiphy_index_| in WiFi. Assigned a large value so that |
| // any attempts to match the default value of |wiphy_index_| against an actual |
| // wiphy index reported in an NL80211 message will fail. |
| static const uint32_t kDefaultWiphyIndex; |
| // Number of milliseconds to wait after failing to launch a scan before |
| // resetting the scan state to idle. |
| static const int kPostScanFailedDelayMilliseconds; |
| // Used when enabling MAC randomization to request that the OUI remain |
| // constant and the last three octets are randomized. |
| static const std::vector<unsigned char> kRandomMacMask; |
| |
| void GetPhyInfo(); |
| std::string AppendBgscan(WiFiService* service, |
| KeyValueStore* service_params) const; |
| bool ReconfigureBgscan(WiFiService* service); |
| bool ReconfigureBgscanForRelevantServices(); |
| std::string GetBgscanMethod(Error* error); |
| uint16_t GetBgscanShortInterval(Error* /* error */) { |
| return bgscan_short_interval_seconds_; |
| } |
| int32_t GetBgscanSignalThreshold(Error* /* error */) { |
| return bgscan_signal_threshold_dbm_; |
| } |
| // These methods can't be 'const' because they are passed to |
| // HelpRegisterDerivedUint16 which don't take const methods. |
| uint16_t GetScanInterval(Error* /* error */) /*const*/ { |
| return scan_interval_seconds_; |
| } |
| |
| SupplicantProcessProxyInterface* supplicant_process_proxy() const; |
| |
| // RPC accessor for |link_statistics_|. |
| KeyValueStore GetLinkStatistics(Error* error); |
| |
| Uint16s GetAllScanFrequencies(Error* /* error */); |
| |
| bool GetScanPending(Error* /* error */); |
| bool SetBgscanMethod(const std::string& method, Error* error); |
| bool SetBgscanShortInterval(const uint16_t& seconds, Error* error); |
| bool SetBgscanSignalThreshold(const int32_t& dbm, Error* error); |
| bool SetScanInterval(const uint16_t& seconds, Error* error); |
| void ClearBgscanMethod(Error* error); |
| |
| bool GetRandomMacEnabled(Error* error); |
| bool SetRandomMacEnabled(const bool& enabled, Error* error); |
| |
| void AssocStatusChanged(const int32_t new_assoc_status); |
| void AuthStatusChanged(const int32_t new_auth_status); |
| void CurrentBSSChanged(const RpcIdentifier& new_bss); |
| void DisconnectReasonChanged(const int32_t new_disconnect_reason); |
| void CurrentAuthModeChanged(const std::string& auth_mode); |
| // Return the correct Metrics suffix (PSK, FTPSK, EAP, FTEAP) corresponding to |
| // the current service's authentication mode. |
| std::string GetSuffixFromAuthMode(const std::string& auth_mode) const; |
| // Return the RPC identifier associated with the wpa_supplicant network |
| // entry created for |service|. If one does not exist, an empty string |
| // is returned, and |error| is populated. |
| RpcIdentifier FindNetworkRpcidForService(const WiFiService* service, |
| Error* error); |
| void HandleDisconnect(); |
| // Update failure and state for disconnected service. |
| // Set failure for disconnected service if disconnect is not user-initiated |
| // and failure is not already set. Then set the state of the service back |
| // to idle, so it can be used for future connections. |
| void ServiceDisconnected(WiFiServiceRefPtr service); |
| // Log and send to UMA any auth/assoc status code indicating a failure. |
| // Returns inferred type of failure, which is useful in cases where we don't |
| // have a disconnect reason from supplicant. |
| Service::ConnectFailure ExamineStatusCodes() const; |
| void HandleRoam(const RpcIdentifier& new_bssid); |
| void BSSAddedTask(const RpcIdentifier& BSS, const KeyValueStore& properties); |
| void BSSRemovedTask(const RpcIdentifier& BSS); |
| void CertificationTask(const KeyValueStore& properties); |
| void EAPEventTask(const std::string& status, const std::string& parameter); |
| void PropertiesChangedTask(const KeyValueStore& properties); |
| void ScanDoneTask(); |
| void ScanFailedTask(); |
| // UpdateScanStateAfterScanDone is spawned as a task from ScanDoneTask in |
| // order to guarantee that it is run after the start of any connections that |
| // result from a scan. This works because supplicant sends all BSSAdded |
| // signals to shill before it sends a ScanDone signal. The code that |
| // handles those signals launch tasks such that the tasks have the following |
| // dependencies (an arrow from X->Y indicates X is guaranteed to run before |
| // Y): |
| // |
| // [BSSAdded]-->[BssAddedTask]-->[SortServiceTask (calls ConnectTo)] |
| // | | | |
| // V V V |
| // [ScanDone]-->[ScanDoneTask]-->[UpdateScanStateAfterScanDone] |
| void UpdateScanStateAfterScanDone(); |
| void ScanTask(); |
| void StateChanged(const std::string& new_state); |
| // Heuristic check if a connection failure was due to bad credentials. |
| // Returns true and puts type of failure in |failure| if a credential |
| // problem is detected. |
| bool SuspectCredentials(WiFiServiceRefPtr service, |
| Service::ConnectFailure* failure) const; |
| |
| void HelpRegisterDerivedInt32(PropertyStore* store, |
| const std::string& name, |
| int32_t (WiFi::*get)(Error* error), |
| bool (WiFi::*set)(const int32_t& value, |
| Error* error)); |
| void HelpRegisterDerivedUint16(PropertyStore* store, |
| const std::string& name, |
| uint16_t (WiFi::*get)(Error* error), |
| bool (WiFi::*set)(const uint16_t& value, |
| Error* error)); |
| void HelpRegisterDerivedBool(PropertyStore* store, |
| const std::string& name, |
| bool (WiFi::*get)(Error* error), |
| bool (WiFi::*set)(const bool& value, |
| Error* error)); |
| void HelpRegisterConstDerivedBool(PropertyStore* store, |
| const std::string& name, |
| bool (WiFi::*get)(Error* error)); |
| void HelpRegisterConstDerivedUint16s(PropertyStore* store, |
| const std::string& name, |
| Uint16s (WiFi::*get)(Error* error)); |
| |
| // Disable a network entry in wpa_supplicant, and catch any exception |
| // that occurs. Returns false if an exception occurred, true otherwise. |
| bool DisableNetwork(const RpcIdentifier& network); |
| // Disable the wpa_supplicant network entry associated with |service|. |
| // Any cached credentials stored in wpa_supplicant related to this |
| // network entry will be preserved. This will have the side-effect of |
| // disconnecting this service if it is currently connected. Returns |
| // true if successful, otherwise returns false and populates |error| |
| // with the reason for failure. |
| virtual bool DisableNetworkForService(const WiFiService* service, |
| Error* error); |
| // Remove a network entry from wpa_supplicant, and catch any exception |
| // that occurs. Returns false if an exception occurred, true otherwise. |
| bool RemoveNetwork(const RpcIdentifier& network); |
| // Remove the wpa_supplicant network entry associated with |service|. |
| // Any cached credentials stored in wpa_supplicant related to this |
| // network entry will be removed. This will have the side-effect of |
| // disconnecting this service if it is currently connected. Returns |
| // true if successful, otherwise returns false and populates |error| |
| // with the reason for failure. |
| virtual bool RemoveNetworkForService(const WiFiService* service, |
| Error* error); |
| // Perform the next in a series of progressive scans. |
| void ProgressiveScanTask(); |
| // Recovers from failed progressive scan. |
| void OnFailedProgressiveScan(); |
| // Restart fast scanning after disconnection. |
| void RestartFastScanAttempts(); |
| // Schedules a scan attempt at time |scan_interval_seconds_| in the |
| // future. Cancels any currently pending scan timer. |
| void StartScanTimer(); |
| // Cancels any currently pending scan timer. |
| void StopScanTimer(); |
| // Initiates a scan, if idle. Reschedules the scan timer regardless. |
| void ScanTimerHandler(); |
| // Abort any current scan (at the shill-level; let any request that's |
| // already gone out finish). |
| void AbortScan(); |
| // Abort any current scan and start a new scan of type |type| if shill is |
| // currently idle. |
| void InitiateScan(); |
| // Suppresses manager auto-connects and flushes supplicant BSS cache, then |
| // triggers the passive scan. Meant for use in dark resume where we want to |
| // ensure that shill and supplicant do not use stale information to launch |
| // connection attempts. |
| void InitiateScanInDarkResume(const FreqSet& freqs); |
| // If |freqs| contains at least one frequency channel a passive scan is |
| // launched on all the frequencies in |freqs|. Otherwise, a passive scan is |
| // launched on all channels. |
| void TriggerPassiveScan(const FreqSet& freqs); |
| // Starts a timer in order to limit the length of an attempt to |
| // connect to a pending network. |
| void StartPendingTimer(); |
| // Cancels any currently pending network timer. |
| void StopPendingTimer(); |
| // Aborts a pending network that is taking too long to connect. |
| void PendingTimeoutHandler(); |
| // Starts a timer in order to limit the length of an attempt to |
| // reconnect to the current network. |
| void StartReconnectTimer(); |
| // Stops any pending reconnect timer. |
| void StopReconnectTimer(); |
| // Disconnects from the current service that is taking too long |
| // to reconnect on its own. |
| void ReconnectTimeoutHandler(); |
| // Sets the current pending service. If the argument is non-NULL, |
| // the Pending timer is started and the associated service is set |
| // to "Associating", otherwise it is stopped. |
| void SetPendingService(const WiFiServiceRefPtr& service); |
| |
| void OnSupplicantPresence(bool present); |
| // Called by ScopeLogger when WiFi debug scope is enabled/disabled. |
| void OnWiFiDebugScopeChanged(bool enabled); |
| // Enable or disable debugging for the current connection attempt. |
| void SetConnectionDebugging(bool enabled); |
| |
| // Request and retrieve information about the currently connected station. |
| void RequestStationInfo(); |
| void OnReceivedStationInfo(const Nl80211Message& nl80211_message); |
| static bool ParseStationBitrate(const AttributeListConstRefPtr& rate_info, |
| std::string* out, |
| int* rate_out); |
| void StopRequestingStationInfo(); |
| |
| void ConnectToSupplicant(); |
| |
| void Restart(); |
| |
| std::string GetServiceLeaseName(const WiFiService& service); |
| |
| // Netlink message handler for NL80211_CMD_NEW_WIPHY messages; copies |
| // device's supported frequencies from that message into |
| // |all_scan_frequencies_|. |
| void OnNewWiphy(const Nl80211Message& nl80211_message); |
| |
| // Requests regulatory information via NL80211_CMD_GET_REG. |
| void GetRegulatory(); |
| |
| void OnTriggerPassiveScanResponse(const Nl80211Message& netlink_message); |
| |
| void SetScanState(ScanState new_state, |
| ScanMethod new_method, |
| const char* reason); |
| void ReportScanResultToUma(ScanState state, ScanMethod method); |
| static std::string ScanStateString(ScanState state, ScanMethod type); |
| |
| // In addition to calling the implementations of these functions in Device, |
| // calls WakeOnWiFi::PrepareForWakeOnWiFiBeforeSuspend. |
| void OnIPConfigUpdated(const IPConfigRefPtr& ipconfig, |
| bool new_lease_acquired) override; |
| void OnIPv6ConfigUpdated() override; |
| |
| // Returns true iff the WiFi device is connected to the current service. |
| bool IsConnectedToCurrentService(); |
| |
| // Callback invoked to report whether this WiFi device is connected to |
| // a service after waking from suspend. Wraps around a Call the function |
| // with the same name in WakeOnWiFi. |
| void ReportConnectedToServiceAfterWake(); |
| |
| // Add a scan result to the list of pending scan results, and post a task |
| // for handling these results if one is not already running. |
| void AddPendingScanResult(const RpcIdentifier& path, |
| const KeyValueStore& properties, |
| bool is_removal); |
| |
| // Callback invoked to handle pending scan results from AddPendingScanResult. |
| void PendingScanResultsHandler(); |
| |
| // Given a NL80211_CMD_NEW_WIPHY message |nl80211_message|, parses the |
| // wiphy index of the NIC and sets |wiphy_index_| with the parsed index. |
| // Returns true iff the wiphy index was parsed successfully, false otherwise. |
| bool ParseWiphyIndex(const Nl80211Message& nl80211_message); |
| |
| // Given a NL80211_CMD_NEW_WIPHY message |nl80211_message|, parses the |
| // feature flags and sets members of this WiFi class appropriately. |
| void ParseFeatureFlags(const Nl80211Message& nl80211_message); |
| |
| // Callback invoked when broadcasted netlink messages are received. |
| // Forwards (Wiphy)RegChangeMessages and TriggerScanMessages to their |
| // appropriate handler functions. |
| void HandleNetlinkBroadcast(const NetlinkMessage& netlink_message); |
| |
| // Called when the kernel broadcasts a notification that a scan has |
| // started. |
| void OnScanStarted(const Nl80211Message& scan_trigger_msg); |
| |
| // Handles NL80211_CMD_GET_REG. |
| void OnGetReg(const Nl80211Message& nl80211_message); |
| |
| // Handles regulatory domain changes (NL80211_CMD_WIPHY_REG_CHANGE and |
| // NL80211_CMD_REG_CHANGE). |
| void OnRegChange(const Nl80211Message& nl80211_message); |
| |
| // Handles country change metric. |
| void HandleCountryChange(std::string country_code); |
| |
| // Helper function for setting supplicant_interface_proxy_ pointer. |
| void SetSupplicantInterfaceProxy( |
| std::unique_ptr<SupplicantInterfaceProxyInterface> proxy); |
| |
| // Pointer to the provider object that maintains WiFiService objects. |
| WiFiProvider* provider_; |
| |
| // Store cached copies of singletons for speed/ease of testing. |
| Time* time_; |
| |
| // Number of times we have attempted to set up device via wpa_supplicant |
| // {Create,Get}Interface() since the last Start(). Errors may be transient or |
| // they may be permanent, so we only retry a limited number of times. |
| int supplicant_connect_attempts_; |
| |
| bool supplicant_present_; |
| |
| std::unique_ptr<SupplicantInterfaceProxyInterface> |
| supplicant_interface_proxy_; |
| // wpa_supplicant's RPC path for this device/interface. |
| RpcIdentifier supplicant_interface_path_; |
| // The rpcid used as the key is wpa_supplicant's D-Bus path for the |
| // Endpoint (BSS, in supplicant parlance). |
| EndpointMap endpoint_by_rpcid_; |
| // Map from Services to the D-Bus path for the corresponding wpa_supplicant |
| // Network. |
| ReverseServiceMap rpcid_by_service_; |
| // The Service we are presently connected to. May be nullptr is we're not |
| // not connected to any Service. |
| WiFiServiceRefPtr current_service_; |
| // The Service we're attempting to connect to. May be nullptr if we're |
| // not attempting to connect to a new Service. If non-NULL, should |
| // be distinct from |current_service_|. (A service should not |
| // simultaneously be both pending, and current.) |
| WiFiServiceRefPtr pending_service_; |
| std::string supplicant_state_; |
| RpcIdentifier supplicant_bss_; |
| int32_t supplicant_assoc_status_; |
| int32_t supplicant_auth_status_; |
| // Sanitized disconnect reason received from supplicant. If there is currently |
| // no disconnect reason set, this will be of value |
| // IEEE_80211::kDisconnectReasonInvalid. |
| IEEE_80211::WiFiReasonCode supplicant_disconnect_reason_; |
| int16_t disconnect_signal_dbm_; |
| int16_t disconnect_threshold_dbm_; |
| |
| // The auth mode of the last successful connection. |
| std::string supplicant_auth_mode_; |
| std::string phy_name_; |
| // Indicates that we should flush supplicant's BSS cache after the |
| // next scan completes. |
| bool need_bss_flush_; |
| struct timeval resumed_at_; |
| // Executes when the (foreground) scan timer expires. Calls ScanTimerHandler. |
| base::CancelableClosure scan_timer_callback_; |
| // Executes when a pending service connect timer expires. Calls |
| // PendingTimeoutHandler. |
| base::CancelableClosure pending_timeout_callback_; |
| // Executes when a reconnecting service timer expires. Calls |
| // ReconnectTimeoutHandler. |
| base::CancelableClosure reconnect_timeout_callback_; |
| // Executes periodically while a service is connected, to update the |
| // signal strength from the currently connected AP. |
| base::CancelableClosure request_station_info_callback_; |
| // Executes when WPA supplicant reports that a scan has failed via a ScanDone |
| // signal. |
| base::CancelableClosure scan_failed_callback_; |
| // Number of remaining fast scans to be done during startup and disconnect. |
| int fast_scans_remaining_; |
| // Indicates that the current BSS has reached the completed state according |
| // to supplicant. |
| bool has_already_completed_; |
| // Indicates that the current BSS for a connected service has changed, which |
| // implies that a driver-based roam has been initiated. If this roam |
| // succeeds, we should renew our lease. |
| bool is_roaming_in_progress_; |
| // Indicates that we are debugging a problematic connection. |
| bool is_debugging_connection_; |
| // Tracks the process of an EAP negotiation. |
| std::unique_ptr<SupplicantEAPStateHandler> eap_state_handler_; |
| // Tracks mac80211 state, to diagnose problems such as queue stalls. |
| std::unique_ptr<Mac80211Monitor> mac80211_monitor_; |
| |
| // Properties |
| std::string bgscan_method_; |
| uint16_t bgscan_short_interval_seconds_; |
| int32_t bgscan_signal_threshold_dbm_; |
| uint16_t scan_interval_seconds_; |
| |
| NetlinkManager* netlink_manager_; |
| std::set<uint16_t> all_scan_frequencies_; |
| |
| bool random_mac_supported_; |
| bool random_mac_enabled_; |
| bool sched_scan_supported_; |
| |
| // Holds the list of scan results waiting to be processed and a cancelable |
| // closure for processing the pending tasks in PendingScanResultsHandler(). |
| std::unique_ptr<PendingScanResults> pending_scan_results_; |
| |
| ScanState scan_state_; |
| ScanMethod scan_method_; |
| |
| // Used to compute the number of bytes received since the link went up. |
| uint64_t receive_byte_count_at_connect_; |
| |
| // Used to report the current state of our wireless link. |
| KeyValueStore link_statistics_; |
| |
| // Wiphy interface index of this WiFi device. |
| uint32_t wiphy_index_; |
| |
| std::unique_ptr<WakeOnWiFiInterface> wake_on_wifi_; |
| |
| // Netlink broadcast handler, for scan results. |
| NetlinkManager::NetlinkMessageHandler netlink_handler_; |
| |
| // Managed supplicant listener, for watching service (re)start. |
| std::unique_ptr<SupplicantManager::ScopedSupplicantListener> |
| scoped_supplicant_listener_; |
| |
| // For weak pointers that will be invalidated in Stop(). |
| base::WeakPtrFactory<WiFi> weak_ptr_factory_while_started_; |
| |
| // For weak pointers that will only be invalidated at destruction. Useful for |
| // callbacks that need to survive Restart(). |
| base::WeakPtrFactory<WiFi> weak_ptr_factory_; |
| |
| DISALLOW_COPY_AND_ASSIGN(WiFi); |
| }; |
| |
| } // namespace shill |
| |
| #endif // SHILL_WIFI_WIFI_H_ |