[Wi-Fi] Fix crash after editing invalid hotspot password

From Android 11, Wi-Fi framework only supports ASCII encoding
for hotspot password, APP should check if password character is
valid.

This change checks if SoftApConfiguration accepts the password
and disable the OK button if the password is invalid.

Bug: 163353576
Test: make RunSettingsRoboTests ROBOTEST_FILTER=WifiUtilsTest
Change-Id: Icf3b5c85856906e4cbe2f0ad79583c1b7182b8c7
Merged-In: Ief3c6c1f08f8fcdf128768cde3ab8eef91f19fbe
diff --git a/src/com/android/settings/wifi/WifiUtils.java b/src/com/android/settings/wifi/WifiUtils.java
index 1333ab4..2214605 100644
--- a/src/com/android/settings/wifi/WifiUtils.java
+++ b/src/com/android/settings/wifi/WifiUtils.java
@@ -23,6 +23,7 @@
 import android.content.pm.PackageManager;
 import android.net.NetworkCapabilities;
 import android.net.wifi.ScanResult;
+import android.net.wifi.SoftApConfiguration;
 import android.net.wifi.WifiConfiguration;
 import android.os.UserHandle;
 import android.os.UserManager;
@@ -38,8 +39,6 @@
 
     private static final int SSID_ASCII_MIN_LENGTH = 1;
     private static final int SSID_ASCII_MAX_LENGTH = 32;
-    private static final int PASSWORD_MIN_LENGTH = 8;
-    private static final int PASSWORD_MAX_LENGTH = 63;
 
 
     public static boolean isSSIDTooLong(String ssid) {
@@ -56,13 +55,17 @@
         return ssid.length() < SSID_ASCII_MIN_LENGTH;
     }
 
-    public static boolean isHotspotPasswordValid(String password) {
-        if (TextUtils.isEmpty(password)) {
+    /**
+     * Check if the WPA2-PSK hotspot password is valid.
+     */
+    public static boolean isHotspotWpa2PasswordValid(String password) {
+        final SoftApConfiguration.Builder configBuilder = new SoftApConfiguration.Builder();
+        try {
+            configBuilder.setPassphrase(password, SoftApConfiguration.SECURITY_TYPE_WPA2_PSK);
+        } catch (IllegalArgumentException e) {
             return false;
         }
-
-        final int length = password.length();
-        return length >= PASSWORD_MIN_LENGTH && length <= PASSWORD_MAX_LENGTH;
+        return true;
     }
 
     /**
diff --git a/src/com/android/settings/wifi/tether/WifiTetherPasswordPreferenceController.java b/src/com/android/settings/wifi/tether/WifiTetherPasswordPreferenceController.java
index a4a51dc..be67d22 100644
--- a/src/com/android/settings/wifi/tether/WifiTetherPasswordPreferenceController.java
+++ b/src/com/android/settings/wifi/tether/WifiTetherPasswordPreferenceController.java
@@ -118,7 +118,7 @@
 
     @Override
     public boolean isTextValid(String value) {
-        return WifiUtils.isHotspotPasswordValid(value);
+        return WifiUtils.isHotspotWpa2PasswordValid(value);
     }
 
     private static String generateRandomPassword() {
diff --git a/tests/robotests/src/com/android/settings/wifi/WifiUtilsTest.java b/tests/robotests/src/com/android/settings/wifi/WifiUtilsTest.java
index 9de095d..dffd87d 100644
--- a/tests/robotests/src/com/android/settings/wifi/WifiUtilsTest.java
+++ b/tests/robotests/src/com/android/settings/wifi/WifiUtilsTest.java
@@ -18,10 +18,6 @@
 
 import static com.google.common.truth.Truth.assertThat;
 
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-
 import static org.mockito.Mockito.spy;
 
 import android.content.Context;
@@ -30,6 +26,9 @@
 
 import com.android.settingslib.wifi.AccessPoint;
 
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.robolectric.RobolectricTestRunner;
 import org.robolectric.RuntimeEnvironment;
 
 @RunWith(RobolectricTestRunner.class)
@@ -48,11 +47,12 @@
     public void testPassword() {
         final String longPassword = "123456789012345678901234567890"
                 + "1234567890123456789012345678901234567890";
-        assertThat(WifiUtils.isHotspotPasswordValid("123")).isFalse();
-        assertThat(WifiUtils.isHotspotPasswordValid("12345678")).isTrue();
-        assertThat(WifiUtils.isHotspotPasswordValid("1234567890")).isTrue();
-        assertThat(WifiUtils.isHotspotPasswordValid(longPassword)).isFalse();
-        assertThat(WifiUtils.isHotspotPasswordValid("")).isFalse();
+        assertThat(WifiUtils.isHotspotWpa2PasswordValid("123")).isFalse();
+        assertThat(WifiUtils.isHotspotWpa2PasswordValid("12345678")).isTrue();
+        assertThat(WifiUtils.isHotspotWpa2PasswordValid("1234567890")).isTrue();
+        assertThat(WifiUtils.isHotspotWpa2PasswordValid(longPassword)).isFalse();
+        assertThat(WifiUtils.isHotspotWpa2PasswordValid("")).isFalse();
+        assertThat(WifiUtils.isHotspotWpa2PasswordValid("€¥£")).isFalse();
     }
 
     @Test
@@ -73,4 +73,4 @@
     public void getWifiConfigWithNullInput_ThrowIllegalArgumentException() {
         WifiConfiguration config = WifiUtils.getWifiConfig(null, null, null);
     }
-}
\ No newline at end of file
+}