Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit d4292256 authored by Pavel Grafov's avatar Pavel Grafov
Browse files

Block editing of locked down wifi network from details page.

Test: make ROBOTEST_FILTER=WifiDetailPreferenceControllerTest RunSettingsRoboTests
Bug: 68990370
Change-Id: Idceb064486afd93bc8b2f52d605a788520de8e56
parent 268de492
Loading
Loading
Loading
Loading
+1 −2
Original line number Diff line number Diff line
@@ -119,8 +119,7 @@ public class WifiDialog extends AlertDialog implements WifiConfigUiBase, DialogI
                    mListener.onSubmit(this);
                    break;
                case BUTTON_FORGET:
                    if (WifiSettings.isEditabilityLockedDown(
                            getContext(), mAccessPoint.getConfig())) {
                    if (WifiUtils.isNetworkLockedDown(getContext(), mAccessPoint.getConfig())) {
                        RestrictedLockUtils.sendShowAdminSupportDetailsIntent(getContext(),
                                RestrictedLockUtils.getDeviceOwner(getContext()));
                        return;
+2 −62
Original line number Diff line number Diff line
@@ -21,13 +21,9 @@ import static android.os.UserManager.DISALLOW_CONFIG_WIFI;
import android.annotation.NonNull;
import android.app.Activity;
import android.app.Dialog;
import android.app.admin.DevicePolicyManager;
import android.content.ComponentName;
import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.content.pm.PackageManager.NameNotFoundException;
import android.content.res.Resources;
import android.net.ConnectivityManager;
import android.net.NetworkInfo;
@@ -491,7 +487,7 @@ public class WifiSettings extends RestrictedSettingsFragment

                WifiConfiguration config = mSelectedAccessPoint.getConfig();
                // Some configs are ineditable
                if (isEditabilityLockedDown(getActivity(), config)) {
                if (WifiUtils.isNetworkLockedDown(getActivity(), config)) {
                    return;
                }

@@ -594,7 +590,7 @@ public class WifiSettings extends RestrictedSettingsFragment
    private void showDialog(AccessPoint accessPoint, int dialogMode) {
        if (accessPoint != null) {
            WifiConfiguration config = accessPoint.getConfig();
            if (isEditabilityLockedDown(getActivity(), config) && accessPoint.isActive()) {
            if (WifiUtils.isNetworkLockedDown(getActivity(), config) && accessPoint.isActive()) {
                RestrictedLockUtils.sendShowAdminSupportDetailsIntent(getActivity(),
                        RestrictedLockUtils.getDeviceOwner(getActivity()));
                return;
@@ -1120,62 +1116,6 @@ public class WifiSettings extends RestrictedSettingsFragment
            }
        };

    /**
     * Returns true if the config is not editable through Settings.
     * @param context Context of caller
     * @param config The WiFi config.
     * @return true if the config is not editable through Settings.
     */
    public static boolean isEditabilityLockedDown(Context context, WifiConfiguration config) {
        return !canModifyNetwork(context, config);
    }

    /**
     * This method is a stripped version of WifiConfigStore.canModifyNetwork.
     * TODO: refactor to have only one method.
     * @param context Context of caller
     * @param config The WiFi config.
     * @return true if Settings can modify the config.
     */
    static boolean canModifyNetwork(Context context, WifiConfiguration config) {
        if (config == null) {
            return true;
        }

        final DevicePolicyManager dpm = (DevicePolicyManager) context.getSystemService(
                Context.DEVICE_POLICY_SERVICE);

        // Check if device has DPM capability. If it has and dpm is still null, then we
        // treat this case with suspicion and bail out.
        final PackageManager pm = context.getPackageManager();
        if (pm.hasSystemFeature(PackageManager.FEATURE_DEVICE_ADMIN) && dpm == null) {
            return false;
        }

        boolean isConfigEligibleForLockdown = false;
        if (dpm != null) {
            final ComponentName deviceOwner = dpm.getDeviceOwnerComponentOnAnyUser();
            if (deviceOwner != null) {
                final int deviceOwnerUserId = dpm.getDeviceOwnerUserId();
                try {
                    final int deviceOwnerUid = pm.getPackageUidAsUser(deviceOwner.getPackageName(),
                            deviceOwnerUserId);
                    isConfigEligibleForLockdown = deviceOwnerUid == config.creatorUid;
                } catch (NameNotFoundException e) {
                    // don't care
                }
            }
        }
        if (!isConfigEligibleForLockdown) {
            return true;
        }

        final ContentResolver resolver = context.getContentResolver();
        final boolean isLockdownFeatureEnabled = Settings.Global.getInt(resolver,
                Settings.Global.WIFI_DEVICE_OWNER_CONFIGS_LOCKDOWN, 0) != 0;
        return !isLockdownFeatureEnabled;
    }

    private static class SummaryProvider
            implements SummaryLoader.SummaryProvider, OnSummaryChangeListener {

+54 −0
Original line number Diff line number Diff line
@@ -16,8 +16,18 @@

package com.android.settings.wifi;

import android.app.admin.DevicePolicyManager;
import android.content.ComponentName;
import android.content.ContentResolver;
import android.content.Context;
import android.content.pm.PackageManager;
import android.net.wifi.WifiConfiguration;
import android.provider.Settings;
import android.text.TextUtils;

import com.android.settings.wrapper.DevicePolicyManagerWrapper;
import com.android.settingslib.wrapper.PackageManagerWrapper;

public class WifiUtils {

    private static final int SSID_ASCII_MIN_LENGTH = 1;
@@ -47,4 +57,48 @@ public class WifiUtils {
        final int length = password.length();
        return length >= PASSWORD_MIN_LENGTH && length <= PASSWORD_MAX_LENGTH;
    }

    /**
     * This method is a stripped and negated version of WifiConfigStore.canModifyNetwork.
     * @param context Context of caller
     * @param config The WiFi config.
     * @return true if Settings cannot modify the config due to lockDown.
     */
    public static boolean isNetworkLockedDown(Context context, WifiConfiguration config) {
        if (config == null) {
            return false;
        }

        final DevicePolicyManagerWrapper dpm = DevicePolicyManagerWrapper.from(context);
        final PackageManagerWrapper pm = new PackageManagerWrapper(context.getPackageManager());

        // Check if device has DPM capability. If it has and dpm is still null, then we
        // treat this case with suspicion and bail out.
        if (pm.hasSystemFeature(PackageManager.FEATURE_DEVICE_ADMIN) && dpm == null) {
            return true;
        }

        boolean isConfigEligibleForLockdown = false;
        if (dpm != null) {
            final ComponentName deviceOwner = dpm.getDeviceOwnerComponentOnAnyUser();
            if (deviceOwner != null) {
                final int deviceOwnerUserId = dpm.getDeviceOwnerUserId();
                try {
                    final int deviceOwnerUid = pm.getPackageUidAsUser(deviceOwner.getPackageName(),
                            deviceOwnerUserId);
                    isConfigEligibleForLockdown = deviceOwnerUid == config.creatorUid;
                } catch (PackageManager.NameNotFoundException e) {
                    // don't care
                }
            }
        }
        if (!isConfigEligibleForLockdown) {
            return false;
        }

        final ContentResolver resolver = context.getContentResolver();
        final boolean isLockdownFeatureEnabled = Settings.Global.getInt(resolver,
                Settings.Global.WIFI_DEVICE_OWNER_CONFIGS_LOCKDOWN, 0) != 0;
        return isLockdownFeatureEnabled;
    }
}
+10 −6
Original line number Diff line number Diff line
@@ -19,8 +19,6 @@ import static android.net.NetworkCapabilities.NET_CAPABILITY_CAPTIVE_PORTAL;
import static android.net.NetworkCapabilities.NET_CAPABILITY_VALIDATED;
import static android.net.NetworkCapabilities.TRANSPORT_WIFI;

import static com.android.settings.wifi.WifiSettings.isEditabilityLockedDown;

import android.app.Activity;
import android.app.Fragment;
import android.content.BroadcastReceiver;
@@ -62,6 +60,7 @@ import com.android.settings.widget.EntityHeaderController;
import com.android.settings.wifi.WifiDetailPreference;
import com.android.settings.wifi.WifiDialog;
import com.android.settings.wifi.WifiDialog.WifiDialogListener;
import com.android.settings.wifi.WifiUtils;
import com.android.settings.wrapper.ConnectivityManagerWrapper;
import com.android.settingslib.core.AbstractPreferenceController;
import com.android.settingslib.core.lifecycle.Lifecycle;
@@ -280,8 +279,8 @@ public class WifiDetailPreferenceController extends AbstractPreferenceController
        mButtonsPref = ((ActionButtonPreference) screen.findPreference(KEY_BUTTONS_PREF))
                .setButton1Text(R.string.forget)
                .setButton1Positive(false)
                .setButton2Text(R.string.support_sign_in_button_text)
                .setButton1OnClickListener(view -> forgetNetwork())
                .setButton2Text(R.string.support_sign_in_button_text)
                .setButton2Positive(true)
                .setButton2OnClickListener(view -> signIntoNetwork());

@@ -498,9 +497,14 @@ public class WifiDetailPreferenceController extends AbstractPreferenceController
     * Returns whether the network represented by this preference can be forgotten.
     */
    private boolean canForgetNetwork() {
        // TODO(65396674): create test for the locked down scenario
        return (mWifiInfo != null && mWifiInfo.isEphemeral())
                || (mWifiConfig != null && !isEditabilityLockedDown(mContext, mWifiConfig));
        return (mWifiInfo != null && mWifiInfo.isEphemeral()) || canModifyNetwork();
    }

    /**
     * Returns whether the network represented by this preference can be modified.
     */
    public boolean canModifyNetwork() {
        return mWifiConfig != null && !WifiUtils.isNetworkLockedDown(mContext, mWifiConfig);
    }

    /**
+9 −1
Original line number Diff line number Diff line
@@ -27,6 +27,7 @@ import android.os.Looper;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;

import com.android.internal.logging.nano.MetricsProto;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import com.android.settings.R;
@@ -34,8 +35,10 @@ import com.android.settings.dashboard.DashboardFragment;
import com.android.settings.wifi.WifiConfigUiBase;
import com.android.settings.wifi.WifiDialog;
import com.android.settings.wrapper.ConnectivityManagerWrapper;
import com.android.settingslib.RestrictedLockUtils;
import com.android.settingslib.core.AbstractPreferenceController;
import com.android.settingslib.wifi.AccessPoint;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
@@ -105,7 +108,12 @@ public class WifiNetworkDetailsFragment extends DashboardFragment {
    public boolean onOptionsItemSelected(MenuItem menuItem) {
        switch (menuItem.getItemId()) {
            case Menu.FIRST:
                if (!mWifiDetailPreferenceController.canModifyNetwork()) {
                    RestrictedLockUtils.sendShowAdminSupportDetailsIntent(getContext(),
                            RestrictedLockUtils.getDeviceOwner(getContext()));
                } else {
                    showDialog(WIFI_DIALOG_ID);
                }
                return true;
            default:
                return super.onOptionsItemSelected(menuItem);
Loading