Android WiFi 连接

Android WiFi 连接

  • 1、设置中WiFi显示
  • 2、WiFi 连接流程
    • 2.1 获取PrimaryClientModeManager
    • 2.2 ClientModeImpl状态机ConnectableState
    • 2.3 ISupplicantStaNetworkCallback 回调监听
  • 3、 简要时序图
  • 4、原生低层驱动
  • 5、关键日志

1、设置中WiFi显示

Android WiFi基础概览
packages/apps/Settings/src/com/android/settings/network/NetworkProviderSettings.java
packages/apps/Settings/src/com/android/settings/wifi/WifiPickerTrackerHelper.java
frameworks/opt/net/wifi/libs/WifiTrackerLib/src/com/android/wifitrackerlib/WifiPickerTracker.java
frameworks/opt/net/wifi/libs/WifiTrackerLib/src/com/android/wifitrackerlib/BaseWifiTracker.java
frameworks/opt/net/wifi/libs/WifiTrackerLib/src/com/android/wifitrackerlib/WifiEntry.java

  • mWifiPickerTracker.getConnectedWifiEntry() 当前连接的WiFi
  • mWifiPickerTracker.getWifiEntries() 搜索的WiFi
  • mAddWifiNetworkPreference 添加WiFi项
  • WifiManager.java#connectStandardWifiEntry.java#connect->WifiManager.java#connect 连接WiFi
    protected void updateWifiEntryPreferences() {
        // bypass the update if the activity and the view are not ready, or it's restricted UI.
        if (getActivity() == null || getView() == null || mIsRestricted) {
            return;
        }
        // in case state has changed
        if (mWifiPickerTracker == null
                || mWifiPickerTracker.getWifiState() != WifiManager.WIFI_STATE_ENABLED) {
            return;
        }

        boolean hasAvailableWifiEntries = false;
        mWifiEntryPreferenceCategory.setVisible(true);

        final WifiEntry connectedEntry = mWifiPickerTracker.getConnectedWifiEntry();
        PreferenceCategory connectedWifiPreferenceCategory = getConnectedWifiPreferenceCategory();
        connectedWifiPreferenceCategory.setVisible(connectedEntry != null);
        if (connectedEntry != null) {
            final LongPressWifiEntryPreference connectedPref =
                    connectedWifiPreferenceCategory.findPreference(connectedEntry.getKey());
            if (connectedPref == null || connectedPref.getWifiEntry() != connectedEntry) {
                connectedWifiPreferenceCategory.removeAll();
                final ConnectedWifiEntryPreference pref =
                        createConnectedWifiEntryPreference(connectedEntry);
                pref.setKey(connectedEntry.getKey());
                pref.refresh();
                connectedWifiPreferenceCategory.addPreference(pref);
                pref.setOnPreferenceClickListener(preference -> {
                    if (connectedEntry.canSignIn()) {
                        connectedEntry.signIn(null /* callback */);
                    } else {
                        launchNetworkDetailsFragment(pref);
                    }
                    return true;
                });
                pref.setOnGearClickListener(preference -> {
                    launchNetworkDetailsFragment(pref);
                });

                if (mClickedConnect) {
                    mClickedConnect = false;
                    scrollToPreference(connectedWifiPreferenceCategory);
                }
            }
        } else {
            connectedWifiPreferenceCategory.removeAll();
        }

        int index = 0;
        cacheRemoveAllPrefs(mWifiEntryPreferenceCategory);
        List<WifiEntry> wifiEntries = mWifiPickerTracker.getWifiEntries();
        for (WifiEntry wifiEntry : wifiEntries) {
            hasAvailableWifiEntries = true;

            String key = wifiEntry.getKey();
            LongPressWifiEntryPreference pref =
                    (LongPressWifiEntryPreference) getCachedPreference(key);
            if (pref != null) {
                if (pref.getWifiEntry() == wifiEntry) {
                    pref.setOrder(index++);
                    continue;
                } else {
                    // Create a new preference if the underlying WifiEntry object has changed
                    removePreference(key);
                }
            }

            pref = createLongPressWifiEntryPreference(wifiEntry);
            pref.setKey(wifiEntry.getKey());
            pref.setOrder(index++);
            pref.refresh();

            if (wifiEntry.getHelpUriString() != null) {
                pref.setOnButtonClickListener(preference -> {
                    openSubscriptionHelpPage(wifiEntry);
                });
            }
            mWifiEntryPreferenceCategory.addPreference(pref);
        }
        removeCachedPrefs(mWifiEntryPreferenceCategory);

        if (!hasAvailableWifiEntries) {
            setProgressBarVisible(true);
            Preference pref = new Preference(getPrefContext());
            pref.setSelectable(false);
            pref.setSummary(R.string.wifi_empty_list_wifi_on);
            pref.setOrder(index++);
            pref.setKey(PREF_KEY_EMPTY_WIFI_LIST);
            mWifiEntryPreferenceCategory.addPreference(pref);
        } else {
            // Continuing showing progress bar for an additional delay to overlap with animation
            getView().postDelayed(mHideProgressBarRunnable, 1700 /* delay millis */);
        }

        mAddWifiNetworkPreference.setOrder(index++);
        mWifiEntryPreferenceCategory.addPreference(mAddWifiNetworkPreference);
        setAdditionalSettingsSummaries();
    }

2、WiFi 连接流程

2.1 获取PrimaryClientModeManager

packages/modules/Wifi/framework/java/android/net/wifi/WifiManager.java
packages/modules/Wifi/service/java/com/android/server/wifi/WifiServiceImpl.java
packages/modules/Wifi/service/java/com/android/server/wifi/ConnectHelper.java
packages/modules/Wifi/service/java/com/android/server/wifi/ActiveModeWarden.java
packages/modules/Wifi/service/java/com/android/server/wifi/ConcreteClientModeManager.java
packages/modules/Wifi/service/java/com/android/server/wifi/ClientModeImpl.java
packages/modules/Wifi/service/java/com/android/server/wifi/WifiNative.java
packages/modules/Wifi/service/java/com/android/server/wifi/SupplicantStaIfaceHal.java
packages/modules/Wifi/service/java/com/android/server/wifi/ISupplicantStaIfaceHal.java

WifiManager.java#connect > WifiServiceImpl.java#connect > ConnectHelper.java#connectToNetwork > ActiveModeWarden.java#getPrimaryClientModeManager/getPrimaryClientModeManagerNullable/getClientModeManagerInRole(ROLE_CLIENT_PRIMARY)

在这里插入图片描述

2.2 ClientModeImpl状态机ConnectableState

packages/modules/Wifi/service/java/com/android/server/wifi/ConnectHelper.java
packages/modules/Wifi/service/java/com/android/server/wifi/ConcreteClientModeManager.java
packages/modules/Wifi/service/java/com/android/server/wifi/ClientModeImpl.java
packages/modules/Wifi/service/java/com/android/server/wifi/WifiNative.java
packages/modules/Wifi/service/java/com/android/server/wifi/SupplicantStaIfaceHal.java
packages/modules/Wifi/service/java/com/android/server/wifi/SupplicantStaIfaceHalAidlImpl.java

ConnectHelper.java#connectToNetwork > ConcreteClientModeManager.java#connectToNetwork > ClientModeImpl.java#connectNetwork > ConnectableState#CMD_CONNECT_NETWORK > ClientModeImpl.java#connectToUserSelectNetwork > ClientModeImpl.java#connectToUserSelectNetwork > ConnectableState#CMD_START_CONNECT > ClientModeImpl.java#connectToNetwork > WifiNative.java#connectToNetwork > SupplicantStaIfaceHal.java#connectToNetwork > SupplicantStaIfaceHalAidlImpl.java#connectToNetwork

    class ConnectableState extends State {
        private boolean mIsScreenStateChangeReceiverRegistered = false;
        BroadcastReceiver mScreenStateChangeReceiver = new BroadcastReceiver() {
            @Override
            public void onReceive(Context context, Intent intent) {
                String action = intent.getAction();
                if (TextUtils.equals(action, Intent.ACTION_SCREEN_ON)) {
                    sendMessage(CMD_SCREEN_STATE_CHANGED, 1);
                } else if (TextUtils.equals(action, Intent.ACTION_SCREEN_OFF)) {
                    sendMessage(CMD_SCREEN_STATE_CHANGED, 0);
                }
            }
        };

        @Override
        public void enter() {
            Log.d(getTag(), "entering ConnectableState: ifaceName = " + mInterfaceName);

            setSuspendOptimizationsNative(SUSPEND_DUE_TO_HIGH_PERF, true);

            mWifiStateTracker.updateState(mInterfaceName, WifiStateTracker.INVALID);
            mIpClientCallbacks = new IpClientCallbacksImpl();
            Log.d(getTag(), "Start makeIpClient ifaceName = " + mInterfaceName);
            mFacade.makeIpClient(mContext, mInterfaceName, mIpClientCallbacks);
            mIpClientCallbacks.awaitCreation();
        }

        private void continueEnterSetup(IpClientManager ipClientManager) {
            mIpClient = ipClientManager;
            setupClientMode();

            IntentFilter filter = new IntentFilter();
            filter.addAction(Intent.ACTION_SCREEN_ON);
            filter.addAction(Intent.ACTION_SCREEN_OFF);
            if (!mIsScreenStateChangeReceiverRegistered) {
                mContext.registerReceiver(mScreenStateChangeReceiver, filter);
                mIsScreenStateChangeReceiverRegistered = true;
            }
            // Learn the initial state of whether the screen is on.
            // We update this field when we receive broadcasts from the system.
            handleScreenStateChanged(mContext.getSystemService(PowerManager.class).isInteractive());

            if (!mWifiNative.removeAllNetworks(mInterfaceName)) {
                loge("Failed to remove networks on entering connect mode");
            }
            mWifiInfo.reset();
            mWifiInfo.setSupplicantState(SupplicantState.DISCONNECTED);

            sendNetworkChangeBroadcast(DetailedState.DISCONNECTED);

            // Inform metrics that Wifi is Enabled (but not yet connected)
            mWifiMetrics.setWifiState(mInterfaceName, WifiMetricsProto.WifiLog.WIFI_DISCONNECTED);
            mWifiMetrics.logStaEvent(mInterfaceName, StaEvent.TYPE_WIFI_ENABLED);
            mWifiScoreCard.noteSupplicantStateChanged(mWifiInfo);
        }

        @Override
        public void exit() {
            // Inform metrics that Wifi is being disabled (Toggled, airplane enabled, etc)
            mWifiMetrics.setWifiState(mInterfaceName, WifiMetricsProto.WifiLog.WIFI_DISABLED);
            mWifiMetrics.logStaEvent(mInterfaceName, StaEvent.TYPE_WIFI_DISABLED);

            if (!mWifiNative.removeAllNetworks(mInterfaceName)) {
                loge("Failed to remove networks on exiting connect mode");
            }
            if (mIsScreenStateChangeReceiverRegistered) {
                mContext.unregisterReceiver(mScreenStateChangeReceiver);
                mIsScreenStateChangeReceiverRegistered = false;
            }

            stopClientMode();
            mWifiScoreCard.doWrites();
        }

        @Override
        public boolean processMessage(Message message) {
            switch (message.what) {
                case CMD_CONNECTABLE_STATE_SETUP:
                    if (mIpClient != null) {
                        loge("Setup connectable state again when IpClient is ready?");
                    } else {
                        IpClientManager ipClientManager = (IpClientManager) message.obj;
                        continueEnterSetup(ipClientManager);
                    }
                    break;
                case CMD_ENABLE_RSSI_POLL: {
                    mEnableRssiPolling = (message.arg1 == 1);
                    break;
                }
                case CMD_SCREEN_STATE_CHANGED: {
                    handleScreenStateChanged(message.arg1 != 0);
                    break;
                }
                case WifiP2pServiceImpl.DISCONNECT_WIFI_REQUEST: {
                    if (mIpClient == null) {
                        logd("IpClient is not ready, "
                                + "WifiP2pServiceImpl.DISCONNECT_WIFI_REQUEST dropped");
                        break;
                    }
                    if (mWifiP2pConnection.shouldTemporarilyDisconnectWifi()) {
                        mWifiMetrics.logStaEvent(mInterfaceName, StaEvent.TYPE_FRAMEWORK_DISCONNECT,
                                StaEvent.DISCONNECT_P2P_DISCONNECT_WIFI_REQUEST);
                        mWifiNative.disconnect(mInterfaceName);
                    } else {
                        mWifiNative.reconnect(mInterfaceName);
                    }
                    break;
                }
                case CMD_RECONNECT: {
                    WorkSource workSource = (WorkSource) message.obj;
                    mWifiConnectivityManager.forceConnectivityScan(workSource);
                    break;
                }
                case CMD_REASSOCIATE: {
                    if (mIpClient != null) {
                        logd("IpClient is not ready, REASSOCIATE dropped");

                        mWifiNative.reassociate(mInterfaceName);
                    }
                    break;
                }
                case CMD_START_CONNECT: {
                    if (mIpClient == null) {
                        logd("IpClient is not ready, START_CONNECT dropped");

                        break;
                    }
                    /* connect command coming from auto-join */
                    int netId = message.arg1;
                    int uid = message.arg2;
                    String bssid = (String) message.obj;
                    mSentHLPs = false;
                    // Stop lingering (if it was lingering before) if we start a new connection.
                    // This means that the ClientModeManager was reused for another purpose, so it
                    // should no longer be in lingering mode.
                    mClientModeManager.setShouldReduceNetworkScore(false);

                    if (!hasConnectionRequests()) {
                        if (mNetworkAgent == null) {
                            loge("CMD_START_CONNECT but no requests and not connected,"
                                    + " bailing");
                            break;
                        } else if (!mWifiPermissionsUtil.checkNetworkSettingsPermission(uid)) {
                            loge("CMD_START_CONNECT but no requests and connected, but app "
                                    + "does not have sufficient permissions, bailing");
                            break;
                        }
                    }
                    WifiConfiguration config =
                            mWifiConfigManager.getConfiguredNetworkWithoutMasking(netId);
                    logd("CMD_START_CONNECT "
                            + " my state " + getCurrentState().getName()
                            + " nid=" + netId
                            + " roam=" + mIsAutoRoaming);
                    if (config == null) {
                        loge("CMD_START_CONNECT and no config, bail out...");
                        break;
                    }
                    mCurrentConnectionDetectedCaptivePortal = false;
                    mTargetNetworkId = netId;
                    // Update scorecard while there is still state from existing connection
                    mLastScanRssi = mWifiConfigManager.findScanRssi(netId,
                            mWifiHealthMonitor.getScanRssiValidTimeMs());
                    mWifiScoreCard.noteConnectionAttempt(mWifiInfo, mLastScanRssi, config.SSID);
                    mWifiBlocklistMonitor.setAllowlistSsids(config.SSID, Collections.emptyList());
                    mWifiBlocklistMonitor.updateFirmwareRoamingConfiguration(Set.of(config.SSID));

                    updateWifiConfigOnStartConnection(config, bssid);
                    reportConnectionAttemptStart(config, mTargetBssid,
                            WifiMetricsProto.ConnectionEvent.ROAM_UNRELATED);

                    String currentMacAddress = mWifiNative.getMacAddress(mInterfaceName);
                    mWifiInfo.setMacAddress(currentMacAddress);
                    Log.i(getTag(), "Connecting with " + currentMacAddress + " as the mac address");

                    mTargetWifiConfiguration = config;
                    mNetworkNotFoundEventCount = 0;
                    /* Check for FILS configuration again after updating the config */
                    if (config.isFilsSha256Enabled() || config.isFilsSha384Enabled()) {
                        boolean isIpClientStarted = startIpClient(config, true);
                        if (isIpClientStarted) {
                            mIpClientWithPreConnection = true;
                            transitionTo(mL2ConnectingState);
                            break;
                        }
                    }
                    mInsecureEapNetworkHandler.prepareConnection(mTargetWifiConfiguration);
                    setSelectedRcoiForPasspoint(config);
                    connectToNetwork(config);
                    break;
                }
                case CMD_START_FILS_CONNECTION: {
                    if (mIpClient == null) {
                        logd("IpClient is not ready, START_FILS_CONNECTION dropped");
                        break;
                    }
                    mWifiMetrics.incrementConnectRequestWithFilsAkmCount();
                    List<Layer2PacketParcelable> packets;
                    packets = (List<Layer2PacketParcelable>) message.obj;
                    if (mVerboseLoggingEnabled) {
                        Log.d(getTag(), "Send HLP IEs to supplicant");
                    }
                    addLayer2PacketsToHlpReq(packets);
                    WifiConfiguration config = mTargetWifiConfiguration;
                    connectToNetwork(config);
                    break;
                }
                case CMD_CONNECT_NETWORK: {
                    ConnectNetworkMessage cnm = (ConnectNetworkMessage) message.obj;
                    if (mIpClient == null) {
                        logd("IpClient is not ready, CONNECT_NETWORK dropped");
                        cnm.listener.sendFailure(WifiManager.ActionListener.FAILURE_INTERNAL_ERROR);
                        break;
                    }
                    NetworkUpdateResult result = cnm.result;
                    int netId = result.getNetworkId();
                    connectToUserSelectNetwork(
                            netId, message.sendingUid, result.hasCredentialChanged(),
                            cnm.packageName);
                    mWifiMetrics.logStaEvent(mInterfaceName, StaEvent.TYPE_CONNECT_NETWORK,
                            mWifiConfigManager.getConfiguredNetwork(netId));
                    cnm.listener.sendSuccess();
                    break;
                }
                case CMD_SAVE_NETWORK: {
                    ConnectNetworkMessage cnm = (ConnectNetworkMessage) message.obj;
                    if (mIpClient == null) {
                        logd("IpClient is not ready, SAVE_NETWORK dropped");
                        cnm.listener.sendFailure(WifiManager.ActionListener.FAILURE_INTERNAL_ERROR);
                        break;
                    }
                    NetworkUpdateResult result = cnm.result;
                    int netId = result.getNetworkId();
                    if (mWifiInfo.getNetworkId() == netId) {
                        if (result.hasCredentialChanged()) {
                            // The network credentials changed and we're connected to this network,
                            // start a new connection with the updated credentials.
                            logi("CMD_SAVE_NETWORK credential changed for nid="
                                    + netId + ". Reconnecting.");
                            startConnectToNetwork(netId, message.sendingUid, SUPPLICANT_BSSID_ANY);
                        } else {
                            if (result.hasProxyChanged()) {
                                if (mIpClient != null) {
                                    log("Reconfiguring proxy on connection");
                                    WifiConfiguration currentConfig =
                                            getConnectedWifiConfigurationInternal();
                                    if (currentConfig != null) {
                                        mIpClient.setHttpProxy(currentConfig.getHttpProxy());
                                    } else {
                                        Log.w(getTag(),
                                                "CMD_SAVE_NETWORK proxy change - but no current "
                                                        + "Wi-Fi config");
                                    }
                                }
                            }
                            if (result.hasIpChanged()) {
                                // The current connection configuration was changed
                                // We switched from DHCP to static or from static to DHCP, or the
                                // static IP address has changed.
                                log("Reconfiguring IP on connection");
                                WifiConfiguration currentConfig =
                                        getConnectedWifiConfigurationInternal();
                                if (currentConfig != null) {
                                    transitionTo(mL3ProvisioningState);
                                } else {
                                    Log.w(getTag(), "CMD_SAVE_NETWORK Ip change - but no current "
                                            + "Wi-Fi config");
                                }
                            }
                        }
                    } else if (mWifiInfo.getNetworkId() == WifiConfiguration.INVALID_NETWORK_ID
                            && result.hasCredentialChanged()) {
                        logi("CMD_SAVE_NETWORK credential changed for nid="
                                + netId + " while disconnected. Connecting.");
                        WifiConfiguration config =
                                mWifiConfigManager.getConfiguredNetwork(netId);
                        if (!mWifiPermissionsUtil.isAdminRestrictedNetwork(config)) {
                            startConnectToNetwork(netId, message.sendingUid, SUPPLICANT_BSSID_ANY);
                        }
                    } else if (result.hasCredentialChanged()) {
                        WifiConfiguration currentConfig =
                                getConnectedWifiConfigurationInternal();
                        WifiConfiguration updatedConfig =
                                mWifiConfigManager.getConfiguredNetwork(netId);
                        if (currentConfig != null && currentConfig.isLinked(updatedConfig)) {
                            logi("current network linked config saved, update linked networks");
                            updateLinkedNetworks(currentConfig);
                        }
                    }
                    cnm.listener.sendSuccess();
                    break;
                }
                case CMD_BLUETOOTH_CONNECTION_STATE_CHANGE: {
                    mWifiNative.setBluetoothCoexistenceScanMode(
                            mInterfaceName, mWifiGlobals.isBluetoothConnected());
                    break;
                }
                case CMD_SET_SUSPEND_OPT_ENABLED: {
                    if (message.arg1 == 1) {
                        setSuspendOptimizationsNative(SUSPEND_DUE_TO_SCREEN, true);
                        if (message.arg2 == 1) {
                            mSuspendWakeLock.release();
                        }
                    } else {
                        setSuspendOptimizationsNative(SUSPEND_DUE_TO_SCREEN, false);
                    }
                    break;
                }
                case WifiMonitor.ANQP_DONE_EVENT: {
                    mPasspointManager.notifyANQPDone((AnqpEvent) message.obj);
                    break;
                }
                case CMD_STOP_IP_PACKET_OFFLOAD: {
                    int slot = message.arg1;
                    int ret = stopWifiIPPacketOffload(slot);
                    if (mNetworkAgent != null) {
                        mNetworkAgent.sendSocketKeepaliveEvent(slot, ret);
                    }
                    break;
                }
                case WifiMonitor.RX_HS20_ANQP_ICON_EVENT: {
                    mPasspointManager.notifyIconDone((IconEvent) message.obj);
                    break;
                }
                case WifiMonitor.HS20_DEAUTH_IMMINENT_EVENT:
                    mPasspointManager.handleDeauthImminentEvent((WnmData) message.obj,
                            getConnectedWifiConfigurationInternal());
                    break;
                case WifiMonitor.HS20_TERMS_AND_CONDITIONS_ACCEPTANCE_REQUIRED_EVENT:
                    mWifiMetrics
                            .incrementTotalNumberOfPasspointConnectionsWithTermsAndConditionsUrl();
                    mTermsAndConditionsUrl = mPasspointManager
                            .handleTermsAndConditionsEvent((WnmData) message.obj,
                            getConnectedWifiConfigurationInternal());
                    if (mTermsAndConditionsUrl == null) {
                        loge("Disconnecting from Passpoint network due to an issue with the "
                                + "Terms and Conditions URL");
                        sendMessage(CMD_DISCONNECT, StaEvent.DISCONNECT_PASSPOINT_TAC);
                    }
                    break;
                case WifiMonitor.HS20_REMEDIATION_EVENT:
                    mPasspointManager.receivedWnmFrame((WnmData) message.obj);
                    break;
                case WifiMonitor.MBO_OCE_BSS_TM_HANDLING_DONE: {
                    handleBssTransitionRequest((BtmFrameData) message.obj);
                    break;
                }
                case CMD_CONFIG_ND_OFFLOAD: {
                    final boolean enabled = (message.arg1 > 0);
                    mWifiNative.configureNeighborDiscoveryOffload(mInterfaceName, enabled);
                    break;
                }
                // Link configuration (IP address, DNS, ...) changes notified via netlink
                case CMD_UPDATE_LINKPROPERTIES: {
                    updateLinkProperties((LinkProperties) message.obj);
                    break;
                }
                case CMD_START_IP_PACKET_OFFLOAD:
                case CMD_ADD_KEEPALIVE_PACKET_FILTER_TO_APF:
                case CMD_REMOVE_KEEPALIVE_PACKET_FILTER_FROM_APF: {
                    if (mNetworkAgent != null) {
                        mNetworkAgent.sendSocketKeepaliveEvent(message.arg1,
                                SocketKeepalive.ERROR_INVALID_NETWORK);
                    }
                    break;
                }
                case CMD_INSTALL_PACKET_FILTER: {
                    mCachedPacketFilter = (byte[]) message.obj;
                    if (mContext.getResources().getBoolean(
                            R.bool.config_wifiEnableApfOnNonPrimarySta)
                            || isPrimary()) {
                        mWifiNative.installPacketFilter(mInterfaceName, mCachedPacketFilter);
                    } else {
                        Log.v(TAG, "Not applying packet filter on non primary CMM");
                    }
                    break;
                }
                case CMD_READ_PACKET_FILTER: {
                    final byte[] packetFilter;
                    if (mContext.getResources().getBoolean(
                            R.bool.config_wifiEnableApfOnNonPrimarySta)
                            || isPrimary()) {
                        packetFilter = mWifiNative.readPacketFilter(mInterfaceName);
                    } else {
                        Log.v(TAG, "Retrieving cached packet filter on non primary CMM");
                        packetFilter = mCachedPacketFilter;
                    }
                    if (mIpClient != null) {
                        mIpClient.readPacketFilterComplete(packetFilter);
                    }
                    break;
                }
                case CMD_SET_FALLBACK_PACKET_FILTERING: {
                    if ((boolean) message.obj) {
                        mWifiNative.startFilteringMulticastV4Packets(mInterfaceName);
                    } else {
                        mWifiNative.stopFilteringMulticastV4Packets(mInterfaceName);
                    }
                    break;
                }
                case CMD_DIAGS_CONNECT_TIMEOUT: {
                    mWifiDiagnostics.reportConnectionEvent(
                            WifiDiagnostics.CONNECTION_EVENT_TIMEOUT, mClientModeManager);
                    break;
                }
                case WifiP2pServiceImpl.P2P_CONNECTION_CHANGED:
                case CMD_RESET_SIM_NETWORKS:
                case WifiMonitor.NETWORK_CONNECTION_EVENT:
                case WifiMonitor.NETWORK_DISCONNECTION_EVENT:
                case WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT:
                case WifiMonitor.AUTHENTICATION_FAILURE_EVENT:
                case WifiMonitor.ASSOCIATION_REJECTION_EVENT:
                case CMD_RSSI_POLL:
                case CMD_ONESHOT_RSSI_POLL:
                case CMD_PRE_DHCP_ACTION:
                case CMD_PRE_DHCP_ACTION_COMPLETE:
                case CMD_POST_DHCP_ACTION:
                case WifiMonitor.SUP_REQUEST_IDENTITY:
                case WifiMonitor.SUP_REQUEST_SIM_AUTH:
                case WifiMonitor.TARGET_BSSID_EVENT:
                case WifiMonitor.ASSOCIATED_BSSID_EVENT:
                case WifiMonitor.TRANSITION_DISABLE_INDICATION:
                case CMD_UNWANTED_NETWORK:
                case CMD_CONNECTING_WATCHDOG_TIMER:
                case WifiMonitor.NETWORK_NOT_FOUND_EVENT:
                case CMD_ROAM_WATCHDOG_TIMER: {
                    // no-op: all messages must be handled in the base state in case it was missed
                    // in one of the child states.
                    break;
                }
                case CMD_ACCEPT_EAP_SERVER_CERTIFICATE:
                case CMD_REJECT_EAP_SERVER_CERTIFICATE:
                case CMD_START_ROAM:
                case CMD_START_RSSI_MONITORING_OFFLOAD:
                case CMD_STOP_RSSI_MONITORING_OFFLOAD:
                case CMD_IP_CONFIGURATION_SUCCESSFUL:
                case CMD_IP_CONFIGURATION_LOST:
                case CMD_IP_REACHABILITY_LOST:
                case CMD_IP_REACHABILITY_FAILURE: {
                    mMessageHandlingStatus = MESSAGE_HANDLING_STATUS_DISCARD;
                    break;
                }
                case 0: {
                    // We want to notice any empty messages (with what == 0) that might crop up.
                    // For example, we may have recycled a message sent to multiple handlers.
                    Log.wtf(getTag(), "Error! empty message encountered");
                    break;
                }
                default: {
                    loge("Error! unhandled message" + message);
                    break;
                }
            }

            logStateAndMessage(message, this);
            return HANDLED;
        }
    }

2.3 ISupplicantStaNetworkCallback 回调监听

packages/modules/Wifi/service/java/com/android/server/wifi/SupplicantStaNetworkHalAidlImpl.java
packages/modules/Wifi/service/java/com/android/server/wifi/SupplicantStaNetworkCallbackAidlImpl.java

SupplicantStaIfaceHalAidlImpl.java#connectToNetwork / addNetworkAndSaveConfig > SupplicantStaNetworkHalAidlImpl.java#saveWifiConfiguration / registerNewCallback / registerCallback > mISupplicantStaNetwork.registerCallback(callback)

3、 简要时序图

在这里插入图片描述

4、原生低层驱动

external/wpa_supplicant_8

在这里插入图片描述

5、关键日志

WifiService: connect uid=|WifiConfigManager: Adding/Updating network|WifiConfigManager: Enable disabled network:|WifiConfigManager: Enabling network|WifiConfigManager: Update network last connect|WifiPickerTracker: Received broadcast:|WifiClientModeImpl.*entering.*State|WifiClientModeImpl.*entering|WifiClientModeImpl.*connectToUserSelectNetwork netId|WifiClientModeImpl.*CMD_START_CONNECT|WifiClientModeImpl.*Select candidate security params for|WifiClientModeImpl.*Connecting with|SupplicantStaIfaceHalAidlImpl: connectToNetwork|SupplicantStaNetworkHalAidlImpl: Successfully set SSID|SupplicantStaNetworkHalAidlImpl: The target security params|SupplicantStaIfaceHalAidlImpl: ISupplicantStaIfaceCallback|wpa_supplicant:.* State:|wpa_supplicant: Notifying state change event|wpa_supplicant: wlan

wpa_supplicant: wlan|wpa_supplicant:

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/300610.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

阿里云服务器可用区是什么?

阿里云服务器地域和可用区怎么选择&#xff1f;地域是指云服务器所在物理数据中心的位置&#xff0c;地域选择就近选择&#xff0c;访客距离地域所在城市越近网络延迟越低&#xff0c;速度就越快&#xff1b;可用区是指同一个地域下&#xff0c;网络和电力相互独立的区域&#…

天津最新web前端培训班 如何提升web技能?

随着互联网的迅猛发展&#xff0c;web前端成为了一个热门的职业方向。越来越多的人希望能够通过学习web前端技术来提升自己的就业竞争力。为了满足市场的需求&#xff0c;许多培训机构纷纷推出了web前端培训课程。 什么是WEB前端 web前端就是web给用户展示的东西&#xff0c;…

DataFunSummit:2023年知识图谱在线峰会-核心PPT资料下载

一、峰会简介 AIGC&#xff0c;ChatGPT以及发布的GPT-4相信已经给大家带来足够的冲击&#xff0c;那么对于知识图谱的应用产生哪些变化和变革&#xff1f;知识图谱在其中如何发挥作用呢&#xff1f;通过LLM是否有可能辅助创建通用大规模知识图谱&#xff1f;AIGC时代下行业知识…

http缓存

http缓存 header里缓存相关的属性 Expires 响应头,代表该资源的过期时间&#xff0c;在http1.0引入Cache-control 请求/响应头&#xff0c;可以配置缓存策略&#xff0c;在http1.1引入&#xff0c;与Expires同时存在时&#xff0c;优先使用Cache-controlIf-Modified-Since …

实现在一个文件夹中找到特定名称特点格式的文件

当你要在一个文件夹中查找特定名称和格式的文件时&#xff0c;你可以使用 Python 的 os 和 fnmatch 模块。以下是一个简单的脚本示例&#xff0c;它可以在指定目录中查找文件&#xff1a; import os import fnmatchdef find_files(directory, pattern):"""在指…

关于图像分割任务中按照比例将数据集随机划分成训练集和测试集

1. 前言 之前写了分类和检测任务划分数据集的脚本&#xff0c;三大任务实现了俩&#xff0c;基于强迫症&#xff0c;也实现一下图像分割的划分脚本 分类划分数据&#xff1a;关于图像分类任务中划分数据集&#xff0c;并且生成分类类别的josn字典文件 检测划分数据&#xff…

【IDEA】 解决在idea中连接 Mysql8.0,驱动无法下载问题

本篇继【idea】解决sprintboot项目创建遇到的问题2-CSDN博客 目录 一、Failed to download https://download.jetbrains.com/idea/jdbc-drivers/MySQL/8/LICENSE.txt:Remote host terminated the handshake 二、no dirver files provided com.mysql.cj.jdbc.Driver 三、Serv…

leetcode“位运算”——只出现一次的数字

只出现一次的数字i&#xff1a; https://leetcode.cn/problems/single-number/ 给你一个非空整数数组 nums&#xff0c;除了某个元素只出现一次以外&#xff0c;其余每个元素均出现两次。找出那个只出现一次的元素。 class Solution { public:int singleNumber(vector<i…

flink table view datastream互转

case class outer(f1:String,f2:Inner) case class outerV1(f1:String,f2:Inner,f3:Int) case class Inner(f3:String,f4:Int) 测试代码 package com.yy.table.convertimport org.apache.flink.streaming.api.scala.StreamExecutionEnvironment import org.apache.flink.tabl…

强化学习的数学原理学习笔记 - 基于模型(Model-based)

文章目录 概览&#xff1a;RL方法分类基于模型&#xff08;Model-Based&#xff09;值迭代&#xff08;Value Iteration&#xff09;&#x1f7e6;策略迭代&#xff08;Policy Iteration&#xff09;&#x1f7e1;截断策略迭代&#xff08;Truncated Policy Iteration&#xff…

从新手到大师:四大编程范式解锁你的编码力!

编程&#xff0c;就是用代码跟计算机交流&#xff0c;告诉它我们想要它做什么。不同的编程范式就是不同的交流方式&#xff0c;每种方式都有自己独特的语法和规则。 今天&#xff0c;我们就来聊聊这四种主要的编程范式&#xff0c;它们分别是命令式、函数式、面向对象和声明式…

cube生成电机库,启用了RTOS,编译报错[0xc43ed8:5050106] in osSignalWait

cube生成电机库&#xff0c;启用了RTOS&#xff0c;编译报错[0xc43ed8:5050106&#xff0c;解决办法] in osSignalWait 1.现象 编译报错[0xc43ed8:5050106] in osSignalWait 导致链接失败 2.解决办法 将keil5的版本升级到5.18.00&#xff0c;我的版本也是5.14.00。

2024阿里云优惠活动有哪些?

2024年阿里云优惠活动大全&#xff0c;包括阿里云服务器优惠活动清单、配置价格表、域名优惠活动、阿里云建站活动、阿里云优惠代金券免费领取、对象存储OSS活动、企业邮箱优惠、无影云电脑优惠、CDN特惠等等&#xff0c;阿里云百科aliyunbaike.com分享2024阿里云优惠活动大全_…

Vue实现加减法验证码

引入Vue.js 在HTML文件的<head>标签中引入Vue.js的CDN链接&#xff1a; <script src"https://cdn.jsdelivr.net/npm/vue2.6.11/dist/vue.min.js"></script>创建Vue实例 接下来&#xff0c;我们要创建一个Vue实例&#xff0c;并将其挂载到HTML文…

用可视化案例讲Rust编程1. 怎么能学会Rust

用可视化案例讲Rust编程 1. 怎么能学会Rust 如果要列举Rust的优势&#xff0c;恐怕写个十条八条是写不完的&#xff0c;而且不管写哪条优势&#xff0c;都有很多同学跳起来反驳&#xff0c;比如我们说Rust比C/C内存安全&#xff0c;肯定有同学说C 20也支持内存安全&#xff0…

使用metricbeat 监控多ES集群

背景 ES 本身自带 监控&#xff0c;属于xpack 中的内容&#xff0c;为商业版&#xff0c;需要收费&#xff1b; 并且 monitor 功能必须要在security开启后才能使用&#xff0c;还有就是集群监控自己&#xff0c;将采集到的性能数据保存到本集群&#xff0c;这是一个比较差的设…

全网最全postman接口测试教程和项目实战~从入门到精通!!!

Postman实现接口测试内容大纲一览&#xff1a; 一、什么是接口&#xff1f;为什么需要接口&#xff1f; 接口指的是实体或者软件提供给外界的一种服务。 因为接口能使我们的实体或者软件的内部数据能够被外部进行修改。从而使得内部和外部实现数据交互。所以需要接口。 比如&…

05 Ciso模拟器连接腾讯云物联网开发平台

Ciso声明&#xff1a;本篇文章基于使用腾讯云物联网平台连接自定义esp8266物联网设备(腾讯连连控制开关实现) - CSDN App改编 一、总体概览 功能描述&#xff1a; 使用腾讯连连小程序进行控制&#xff0c; Alarm&#xff08;警铃&#xff09;&#xff1a;开的时候&#xff…

python编程从入门到实践(3+4)操作列表+if语句

文章目录 第四章 列表操作4.1遍历整个列表&#xff1a;可能会发生变化的数值&#xff0c;列表可修改4.1.2遍历中的缩进 4.3创建数值列表4.3.1 使用range&#xff08;&#xff09;函数range&#xff08;i&#xff0c;m&#xff09;输出从i到m-1range(m) 打印从0到m-1 4.3.1 使用…

UVa12419 Heap Manager

题目链接 UVa12419 - Heap Manager 题意 内存以内存单元为基本单位&#xff0c;每个内存单元用一个固定的整数作为标识&#xff0c;称为地址。地址从0开始连续排列&#xff0c;地址相邻的内存单元被认为是逻辑上连续的。我们把从地址i开始的s个连续的内存单元称为首地址为i长度…