Merge "Add a seekbar to change text-to-speech rate and a switch to enable higher speech rates."
diff --git a/AndroidManifest.xml b/AndroidManifest.xml
index 4ff16f9..3764b95 100644
--- a/AndroidManifest.xml
+++ b/AndroidManifest.xml
@@ -1539,6 +1539,22 @@
             android:windowSoftInputMode="stateHidden|adjustResize"
             android:theme="@style/Theme.ConfirmDeviceCredentials"/>
 
+        <activity
+            android:name=".Settings$FingerprintSuggestionActivity"
+            android:label="@string/security_settings_fingerprint_preference_title"
+            android:icon="@drawable/ic_fingerprint">
+            <intent-filter>
+                <action android:name="android.intent.action.MAIN" />
+                <category android:name="com.android.settings.suggested.category.SETTINGS_ONLY" />
+            </intent-filter>
+            <meta-data android:name="com.android.settings.dismiss"
+                android:value="10,30" />
+            <meta-data android:name="com.android.settings.require_feature"
+                android:value="android.hardware.fingerprint" />
+            <meta-data android:name="com.android.settings.title"
+                android:resource="@string/suggestion_additional_fingerprints" />
+        </activity>
+
         <activity android:name=".fingerprint.FingerprintSettings" android:exported="false"/>
         <activity android:name=".fingerprint.FingerprintEnrollFindSensor" android:exported="false"/>
         <activity android:name=".fingerprint.FingerprintEnrollEnrolling" android:exported="false"/>
@@ -1591,6 +1607,34 @@
                 android:value="true" />
         </activity>
 
+        <activity-alias android:name=".suggestion.ChooseLockGeneric"
+            android:icon="@drawable/ic_settings_security"
+            android:targetActivity=".ChooseLockGeneric">
+            <intent-filter android:priority="1">
+                <action android:name="android.intent.action.MAIN" />
+                <category android:name="com.android.settings.suggested.category.LOCK_SCREEN" />
+            </intent-filter>
+            <meta-data android:name="com.android.settings.title"
+                       android:resource="@string/suggested_lock_settings_title" />
+            <meta-data android:name="com.android.settings.summary"
+                       android:resource="@string/suggested_lock_settings_summary" />
+        </activity-alias>
+
+        <activity-alias android:name=".suggestion.FingerprintEnrollIntroduction"
+            android:icon="@drawable/ic_settings_security"
+            android:targetActivity=".fingerprint.FingerprintEnrollIntroduction">
+            <intent-filter android:priority="2">
+                <action android:name="android.intent.action.MAIN" />
+                <category android:name="com.android.settings.suggested.category.LOCK_SCREEN" />
+            </intent-filter>
+            <meta-data android:name="com.android.settings.require_feature"
+                android:value="android.hardware.fingerprint" />
+            <meta-data android:name="com.android.settings.title"
+                android:resource="@string/suggested_lock_settings_title" />
+            <meta-data android:name="com.android.settings.summary"
+                android:resource="@string/suggested_lock_settings_summary" />
+        </activity-alias>
+
         <activity android:name="ChooseLockGeneric$InternalActivity" android:exported="false"
             android:label="@string/lockpassword_choose_lock_generic_header"
             android:excludeFromRecents="true"
@@ -2638,6 +2682,22 @@
                        android:value="true" />
         </activity>
 
+        <activity android:name="Settings$WifiCallingSuggestionActivity"
+                  android:label="@string/wifi_calling_settings_title"
+                  android:icon="@drawable/ic_settings_wireless"
+                  android:taskAffinity="">
+            <intent-filter>
+                <action android:name="android.intent.action.MAIN" />
+                <category android:name="com.android.settings.suggested.category.SETTINGS_ONLY" />
+            </intent-filter>
+            <meta-data android:name="com.android.settings.FRAGMENT_CLASS"
+                       android:value="com.android.settings.WifiCallingSettings" />
+            <meta-data android:name="com.android.settings.dismiss"
+                android:value="10" />
+            <meta-data android:name="com.android.settings.title"
+                android:resource="@string/wifi_calling_suggestion_title" />
+        </activity>
+
         <provider
             android:name=".search.SettingsSearchIndexablesProvider"
             android:authorities="com.android.settings"
@@ -2719,8 +2779,6 @@
             </intent-filter>
             <meta-data android:name="com.android.settings.FRAGMENT_CLASS"
                        android:value="com.android.settings.applications.ManageDefaultApps" />
-            <meta-data android:name="com.android.settings.PRIMARY_PROFILE_CONTROLLED"
-                       android:value="true" />
         </activity>
 
         <!-- Conditional receivers, only enabled during silenced state, default off-->
diff --git a/res/layout/wifi_dialog.xml b/res/layout/wifi_dialog.xml
index bce8fb0..c5e554d 100644
--- a/res/layout/wifi_dialog.xml
+++ b/res/layout/wifi_dialog.xml
@@ -107,7 +107,7 @@
                             android:prompt="@string/wifi_eap_method"
                             android:entries="@array/wifi_eap_method" />
                 </LinearLayout>
-                
+
                 <LinearLayout android:id="@+id/l_phase2"
                         android:layout_width="match_parent"
                         android:layout_height="wrap_content"
@@ -145,6 +145,18 @@
                             android:prompt="@string/wifi_eap_ca_cert" />
                 </LinearLayout>
 
+                <LinearLayout android:id="@+id/no_ca_cert_warning"
+                        android:layout_width="match_parent"
+                        android:layout_height="wrap_content"
+                        android:visibility="gone"
+                        style="@style/wifi_item" >
+                    <TextView
+                            android:layout_width="wrap_content"
+                            android:layout_height="wrap_content"
+                            style="@style/wifi_item_warning"
+                            android:text="@string/wifi_do_not_validate_eap_server_warning" />
+                </LinearLayout>
+
                 <LinearLayout android:id="@+id/l_user_cert"
                         android:layout_width="match_parent"
                         android:layout_height="wrap_content"
@@ -301,7 +313,7 @@
                     android:layout_height="wrap_content"
                     style="@style/wifi_section"
                     android:visibility="gone">
-                <LinearLayout 
+                <LinearLayout
                         android:layout_width="match_parent"
                         android:layout_height="wrap_content"
                         style="@style/wifi_item">
diff --git a/res/values/strings.xml b/res/values/strings.xml
index 5e58847..399db32 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -959,6 +959,13 @@
     <!-- Unlock Picker Settings --><skip />
 
     <!-- Security Picker --><skip />
+
+    <!-- Title for suggested actions for screen lock -->
+    <string name="suggested_lock_settings_title">Screen lock</string>
+
+    <!-- Summary for suggested actions for screen lock -->
+    <string name="suggested_lock_settings_summary">Protect your device</string>
+
     <!--  Title for security picker to choose the unlock method: None/Pattern/PIN/Password [CHAR LIMIT=22] -->
     <string name="lock_settings_picker_title">Choose screen lock</string>
 
@@ -1629,9 +1636,15 @@
     <!-- Hint for unchanged fields -->
     <string name="wifi_unchanged">(unchanged)</string>
     <!-- Hint for unspecified fields -->
-    <string name="wifi_unspecified">(unspecified)</string>
+    <string name="wifi_unspecified">Please select</string>
     <!-- Hint for multiple certificates being added to the configuration -->
     <string name="wifi_multiple_cert_added">(Multiple certificates added)</string>
+    <!-- Menu option for not providing an EAP user certificate -->
+    <string name="wifi_do_not_provide_eap_user_cert">Do not provide</string>
+    <!-- Menu option for not validating the EAP server -->
+    <string name="wifi_do_not_validate_eap_server">Do not validate</string>
+    <!-- Warning message displayed if user choses not to validate the EAP server -->
+    <string name="wifi_do_not_validate_eap_server_warning">No certificate specified. Your connection will not be private.</string>
     <!-- Substring of status line when Wi-Fi Protected Setup (WPS) is available and
          string is listed first [CHAR LIMIT=20]-->
     <string name="wifi_wps_available_first_item">WPS available</string>
@@ -1892,6 +1905,8 @@
 
     <!-- Wireless networks, item title to go into the WFC settings [CHAR LIMIT=30] -->
     <string name="wifi_calling_settings_title">Wi-Fi calling</string>
+    <!-- Title of suggestion to turn on wifi calling [CHAR LIMIT=30] -->
+    <string name="wifi_calling_suggestion_title">Enable Wi-Fi Calling</string>
     <!-- WFC mode [CHAR LIMIT=30] -->
     <string name="wifi_calling_mode_title">Calling preference</string>
     <!-- WFC mode dialog [CHAR LIMIT=30] -->
@@ -5290,10 +5305,6 @@
     <string name="user_enable_calling_and_sms_confirm_title">Turn on phone calls &amp; SMS?</string>
     <!-- Message for confirmation of turning on calls and SMS [CHAR LIMIT=none] -->
     <string name="user_enable_calling_and_sms_confirm_message">Call and SMS history will be shared with this user.</string>
-    <!-- Title for the emergency info preference [CHAR LIMIT=40] -->
-    <string name="emergency_info_title">Emergency information</string>
-    <!-- Description of the emergency info preference [CHAR LIMIT=80] -->
-    <string name="emergency_info_subtitle">Accessible through lock screen in the emergency dialer</string>
 
     <!-- Application Restrictions screen title [CHAR LIMIT=45] -->
     <string name="application_restrictions">Allow apps and content</string>
@@ -7009,4 +7020,7 @@
     <!-- No default home set summary [CHAR LIMIT=NONE] -->
     <string name="no_default_home">No default Home</string>
 
+    <!-- Title for suggestion adding more fingerprints [CHAR LIMIT=30] -->
+    <string name="suggestion_additional_fingerprints">Additional Fingerprints</string>
+
 </resources>
diff --git a/res/values/styles.xml b/res/values/styles.xml
index 7065265..df5490b 100644
--- a/res/values/styles.xml
+++ b/res/values/styles.xml
@@ -204,6 +204,14 @@
         <item name="android:textColor">?android:attr/textColorSecondary</item>
     </style>
 
+    <style name="wifi_item_warning">
+        <item name="android:paddingStart">8dip</item>
+        <item name="android:textSize">12sp</item>
+        <item name="android:textAlignment">viewStart</item>
+        <item name="android:textAppearance">@android:style/TextAppearance.Material.Body1</item>
+        <item name="android:textColor">@color/warning</item>
+    </style>
+
     <style name="wifi_item_content">
         <item name="android:textAlignment">viewStart</item>
         <item name="android:textAppearance">@android:style/TextAppearance.Material.Subhead</item>
diff --git a/res/xml/user_settings.xml b/res/xml/user_settings.xml
index ac2685f..4fefc10 100644
--- a/res/xml/user_settings.xml
+++ b/res/xml/user_settings.xml
@@ -35,9 +35,5 @@
                 android:key="add_users_when_locked"
                 android:title="@string/user_add_on_lockscreen_menu"
                 android:summary="@string/user_add_on_lockscreen_menu_summary" />
-        <Preference
-                android:key="emergency_info"
-                android:title="@string/emergency_info_title"
-                android:summary="@string/emergency_info_subtitle"/>
     </PreferenceCategory>
 </PreferenceScreen>
diff --git a/src/com/android/settings/ChooseLockGeneric.java b/src/com/android/settings/ChooseLockGeneric.java
index b44ee48..d2eae7e 100644
--- a/src/com/android/settings/ChooseLockGeneric.java
+++ b/src/com/android/settings/ChooseLockGeneric.java
@@ -24,9 +24,11 @@
 import android.app.Fragment;
 import android.app.FragmentManager;
 import android.app.admin.DevicePolicyManager;
+import android.content.ComponentName;
 import android.content.Context;
 import android.content.DialogInterface;
 import android.content.Intent;
+import android.content.pm.PackageManager;
 import android.hardware.fingerprint.Fingerprint;
 import android.hardware.fingerprint.FingerprintManager;
 import android.hardware.fingerprint.FingerprintManager.RemovalCallback;
@@ -267,6 +269,7 @@
                     || requestCode == ENABLE_ENCRYPTION_REQUEST) {
                 if (resultCode != RESULT_CANCELED) {
                     getActivity().setResult(resultCode, data);
+                    disableScreenLockSuggestion();
                     finish();
                 }
             } else {
@@ -545,9 +548,30 @@
                 getActivity().setResult(Activity.RESULT_OK);
             } else {
                 removeAllFingerprintTemplatesAndFinish();
+                disableScreenLockSuggestion();
             }
         }
 
+        private void disableScreenLockSuggestion() {
+            final ComponentName suggestionChooseLock = new ComponentName("com.android.settings",
+                    "com.android.settings.suggestion.ChooseLockGeneric");
+            disableComponent(suggestionChooseLock);
+            PackageManager pm = getContext().getPackageManager();
+            if (pm.hasSystemFeature(PackageManager.FEATURE_FINGERPRINT)) {
+                final ComponentName suggestionFingerprint = new ComponentName(
+                        "com.android.settings",
+                        "com.android.settings.suggestion.FingerprintEnrollIntroduction");
+                disableComponent(suggestionFingerprint);
+            }
+        }
+
+        private void disableComponent(ComponentName componentName) {
+            getContext().getPackageManager().setComponentEnabledSetting(
+                    componentName,
+                    PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
+                    PackageManager.DONT_KILL_APP);
+        }
+
         private Intent getIntentForUnlockMethod(int quality, boolean disabled) {
             Intent intent = null;
             final Context context = getActivity();
diff --git a/src/com/android/settings/PreviewSeekBarPreferenceFragment.java b/src/com/android/settings/PreviewSeekBarPreferenceFragment.java
index 0b4c1a9..ea8b55a 100644
--- a/src/com/android/settings/PreviewSeekBarPreferenceFragment.java
+++ b/src/com/android/settings/PreviewSeekBarPreferenceFragment.java
@@ -57,6 +57,29 @@
     private View mLarger;
     private View mSmaller;
 
+    private class onPreviewSeekBarChangeListener implements OnSeekBarChangeListener {
+        private boolean mSeekByTouch;
+
+        @Override
+        public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
+            setPreviewLayer(progress, true);
+            if (!mSeekByTouch) {
+                commit();
+            }
+        }
+
+        @Override
+        public void onStartTrackingTouch(SeekBar seekBar) {
+            mSeekByTouch = true;
+        }
+
+        @Override
+        public void onStopTrackingTouch(SeekBar seekBar) {
+            commit();
+            mSeekByTouch = false;
+        }
+    }
+
     @Override
     public View onCreateView(LayoutInflater inflater, ViewGroup container,
                              Bundle savedInstanceState) {
@@ -77,20 +100,7 @@
         final SeekBar seekBar = (SeekBar) content.findViewById(R.id.seek_bar);
         seekBar.setMax(max);
         seekBar.setProgress(mInitialIndex);
-        seekBar.setOnSeekBarChangeListener(new OnSeekBarChangeListener() {
-            @Override
-            public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
-                setPreviewLayer(progress, true);
-            }
-
-            @Override
-            public void onStartTrackingTouch(SeekBar seekBar) {
-            }
-
-            @Override
-            public void onStopTrackingTouch(SeekBar seekBar) {
-            }
-        });
+        seekBar.setOnSeekBarChangeListener(new onPreviewSeekBarChangeListener());
 
         mSmaller = content.findViewById(R.id.smaller);
         mSmaller.setOnClickListener(new OnClickListener() {
diff --git a/src/com/android/settings/Settings.java b/src/com/android/settings/Settings.java
index 4141274..5d2468e 100644
--- a/src/com/android/settings/Settings.java
+++ b/src/com/android/settings/Settings.java
@@ -17,6 +17,7 @@
 package com.android.settings;
 
 import com.android.settings.applications.AppOpsSummary;
+import com.android.settings.fingerprint.FingerprintSettings;
 
 /**
  * Top-level Settings activity
@@ -103,7 +104,6 @@
     public static class ZenModeSettingsActivity extends SettingsActivity { /* empty */ }
     public static class ZenModePrioritySettingsActivity extends SettingsActivity { /* empty */ }
     public static class ZenModeAutomationSettingsActivity extends SettingsActivity { /* empty */ }
-    public static class ZenModeAutomationSuggestionActivity extends SettingsActivity { /* empty */ }
     public static class ZenModeScheduleRuleSettingsActivity extends SettingsActivity { /* empty */ }
     public static class ZenModeEventRuleSettingsActivity extends SettingsActivity { /* empty */ }
     public static class ZenModeExternalRuleSettingsActivity extends SettingsActivity { /* empty */ }
@@ -125,7 +125,10 @@
     public static class AppWriteSettingsActivity extends SettingsActivity { /* empty */ }
     public static class ManageDefaultAppsActivity extends SettingsActivity { /* empty */ }
 
+    public static class WifiCallingSuggestionActivity extends SettingsActivity { /* empty */ }
+    public static class ZenModeAutomationSuggestionActivity extends SettingsActivity { /* empty */ }
     public static class WallpaperSuggestionActivity extends SettingsActivity { /* empty */ }
+    public static class FingerprintSuggestionActivity extends FingerprintSettings { /* empty */ }
 
     // Categories.
     public static class WirelessSettings extends SettingsActivity { /* empty */ }
diff --git a/src/com/android/settings/applications/DefaultEmergencyPreference.java b/src/com/android/settings/applications/DefaultEmergencyPreference.java
index 0062625..7c9b124 100644
--- a/src/com/android/settings/applications/DefaultEmergencyPreference.java
+++ b/src/com/android/settings/applications/DefaultEmergencyPreference.java
@@ -24,6 +24,7 @@
 import android.content.pm.PackageManager;
 import android.content.pm.ResolveInfo;
 import android.os.AsyncTask;
+import android.os.UserManager;
 import android.provider.Settings;
 import android.telephony.TelephonyManager;
 import android.text.TextUtils;
@@ -31,6 +32,7 @@
 import android.util.AttributeSet;
 
 import com.android.settings.AppListPreference;
+import com.android.settings.Utils;
 
 import java.util.List;
 import java.util.Objects;
@@ -135,7 +137,8 @@
 
     public static boolean isAvailable(Context context) {
         return isCapable(context)
-                && context.getPackageManager().resolveActivity(QUERY_INTENT, 0) != null;
+                && context.getPackageManager().resolveActivity(QUERY_INTENT, 0) != null
+                && !Utils.isManagedProfile(UserManager.get(context)) ;
     }
 
     public static boolean isCapable(Context context) {
diff --git a/src/com/android/settings/applications/DefaultNotificationAssistantPreference.java b/src/com/android/settings/applications/DefaultNotificationAssistantPreference.java
index 20c1a9e..186c442 100644
--- a/src/com/android/settings/applications/DefaultNotificationAssistantPreference.java
+++ b/src/com/android/settings/applications/DefaultNotificationAssistantPreference.java
@@ -25,6 +25,7 @@
 import android.content.pm.PackageManager;
 import android.content.pm.ResolveInfo;
 import android.content.pm.ServiceInfo;
+import android.os.UserManager;
 import android.provider.Settings;
 import android.service.notification.NotificationAssistantService;
 import android.util.AttributeSet;
@@ -34,6 +35,7 @@
 import java.util.List;
 
 import com.android.settings.R;
+import com.android.settings.Utils;
 import com.android.settings.notification.ManagedServiceSettings;
 
 public class DefaultNotificationAssistantPreference extends AppListPreference {
@@ -108,4 +110,8 @@
         c.emptyText = R.string.no_notification_listeners;
         return c;
     }
+
+    public static boolean isAvailable(Context context) {
+        return !Utils.isManagedProfile(UserManager.get(context));
+    }
 }
diff --git a/src/com/android/settings/applications/DefaultSmsPreference.java b/src/com/android/settings/applications/DefaultSmsPreference.java
index bf616c3..7281394 100644
--- a/src/com/android/settings/applications/DefaultSmsPreference.java
+++ b/src/com/android/settings/applications/DefaultSmsPreference.java
@@ -17,6 +17,7 @@
 
 import android.content.ComponentName;
 import android.content.Context;
+import android.os.UserManager;
 import android.telephony.TelephonyManager;
 import android.text.TextUtils;
 import android.util.AttributeSet;
@@ -24,6 +25,7 @@
 import com.android.internal.telephony.SmsApplication;
 import com.android.internal.telephony.SmsApplication.SmsApplicationData;
 import com.android.settings.AppListPreference;
+import com.android.settings.Utils;
 
 import java.util.Collection;
 import java.util.Objects;
@@ -69,7 +71,7 @@
     public static boolean isAvailable(Context context) {
         TelephonyManager tm =
                 (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
-        return tm.isSmsCapable();
+        return tm.isSmsCapable() && !Utils.isManagedProfile(UserManager.get(context));
     }
 
 }
diff --git a/src/com/android/settings/applications/ManageAssist.java b/src/com/android/settings/applications/ManageAssist.java
index 24c558c..fca124f 100644
--- a/src/com/android/settings/applications/ManageAssist.java
+++ b/src/com/android/settings/applications/ManageAssist.java
@@ -18,9 +18,11 @@
 
 import android.app.AlertDialog;
 import android.content.ComponentName;
+import android.content.Context;
 import android.content.DialogInterface;
 import android.os.Bundle;
 import android.os.Handler;
+import android.os.UserManager;
 import android.provider.Settings;
 import android.support.v14.preference.SwitchPreference;
 import android.support.v7.preference.Preference;
@@ -28,6 +30,7 @@
 import com.android.internal.logging.MetricsProto.MetricsEvent;
 import com.android.settings.R;
 import com.android.settings.SettingsPreferenceFragment;
+import com.android.settings.Utils;
 import com.android.settings.voice.VoiceInputListPreference;
 
 /**
@@ -175,4 +178,8 @@
         mDefaultAssitPref.setValue(assistPackage);
         updateUi();
     }
+
+    public static boolean isAvailable(Context context) {
+        return !Utils.isManagedProfile(UserManager.get(context));
+    }
 }
diff --git a/src/com/android/settings/applications/ManageDefaultApps.java b/src/com/android/settings/applications/ManageDefaultApps.java
index 77d268d..b421c9d 100644
--- a/src/com/android/settings/applications/ManageDefaultApps.java
+++ b/src/com/android/settings/applications/ManageDefaultApps.java
@@ -26,6 +26,7 @@
 import android.os.UserHandle;
 import android.os.UserManager;
 import android.provider.SearchIndexableResource;
+import android.provider.Settings;
 import android.support.v7.preference.Preference;
 import android.text.TextUtils;
 import android.util.Log;
@@ -33,29 +34,32 @@
 import com.android.internal.content.PackageMonitor;
 import com.android.internal.logging.MetricsProto.MetricsEvent;
 import com.android.settings.R;
-import com.android.settings.SettingsPreferenceFragment;
 import com.android.settings.search.BaseSearchIndexProvider;
 import com.android.settings.search.Index;
 import com.android.settings.search.Indexable;
+import com.android.settings.utils.ProfileSettingsPreferenceFragment;
 
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.List;
 
-public class ManageDefaultApps extends SettingsPreferenceFragment
+public class ManageDefaultApps extends ProfileSettingsPreferenceFragment
         implements Preference.OnPreferenceClickListener, Indexable {
 
     private static final String TAG = ManageDefaultApps.class.getSimpleName();
 
+    private static final String KEY_ASSIST_AND_VOICE_INPUT = "assist_and_voice_input";
     private static final String KEY_DEFAULT_BROWSER = "default_browser";
     private static final String KEY_DEFAULT_PHONE_APP = "default_phone_app";
     private static final String KEY_DEFAULT_EMERGENCY_APP = "default_emergency_app";
     private static final String KEY_SMS_APPLICATION = "default_sms_app";
+    private static final String KEY_DEFAULT_NOTIFICATION_ASST = "default_notification_asst_app";
 
     private DefaultBrowserPreference mDefaultBrowserPreference;
     private PackageManager mPm;
     private int myUserId;
 
+
     private static final long DELAY_UPDATE_BROWSER_MILLIS = 500;
 
     private final Handler mHandler = new Handler();
@@ -130,6 +134,7 @@
         mPm = getPackageManager();
         myUserId = UserHandle.myUserId();
 
+
         mDefaultBrowserPreference = (DefaultBrowserPreference) findPreference(KEY_DEFAULT_BROWSER);
         mDefaultBrowserPreference.setOnPreferenceChangeListener(
                 new Preference.OnPreferenceChangeListener() {
@@ -151,7 +156,7 @@
                         }
                         return result;
                     }
-        });
+                });
         final boolean isRestrictedUser = UserManager.get(getActivity())
                 .getUserInfo(myUserId).isRestricted();
 
@@ -169,6 +174,14 @@
             removePreference(KEY_DEFAULT_EMERGENCY_APP);
         }
 
+        if (!ManageAssist.isAvailable(getActivity())) {
+            removePreference(KEY_ASSIST_AND_VOICE_INPUT);
+        }
+
+        if (!DefaultNotificationAssistantPreference.isAvailable(getActivity())) {
+            removePreference(KEY_DEFAULT_NOTIFICATION_ASST);
+        }
+
         if (DefaultEmergencyPreference.isCapable(getActivity())) {
             Index.getInstance(getActivity()).updateFromClassNameResource(
                     ManageDefaultApps.class.getName(), true, true);
@@ -200,31 +213,36 @@
     }
 
     public static final Indexable.SearchIndexProvider SEARCH_INDEX_DATA_PROVIDER =
-        new BaseSearchIndexProvider() {
-            @Override
-            public List<SearchIndexableResource> getXmlResourcesToIndex(
-                    Context context, boolean enabled) {
-                SearchIndexableResource sir = new SearchIndexableResource(context);
-                sir.xmlResId = R.xml.default_apps;
-                return Arrays.asList(sir);
-            }
-
-            @Override
-            public List<String> getNonIndexableKeys(Context context) {
-                final ArrayList<String> result = new ArrayList<String>();
-
-                // Remove SMS Application if the device does not support SMS
-                final boolean isRestrictedUser = UserManager.get(context)
-                        .getUserInfo(UserHandle.myUserId()).isRestricted();
-                if (!DefaultSmsPreference.isAvailable(context) || isRestrictedUser) {
-                    result.add(KEY_SMS_APPLICATION);
+            new BaseSearchIndexProvider() {
+                @Override
+                public List<SearchIndexableResource> getXmlResourcesToIndex(
+                        Context context, boolean enabled) {
+                    SearchIndexableResource sir = new SearchIndexableResource(context);
+                    sir.xmlResId = R.xml.default_apps;
+                    return Arrays.asList(sir);
                 }
 
-                if (!DefaultEmergencyPreference.isAvailable(context)) {
-                    result.add(KEY_DEFAULT_EMERGENCY_APP);
-                }
+                @Override
+                public List<String> getNonIndexableKeys(Context context) {
+                    final ArrayList<String> result = new ArrayList<String>();
 
-                return result;
-            }
-    };
+                    // Remove SMS Application if the device does not support SMS
+                    final boolean isRestrictedUser = UserManager.get(context)
+                            .getUserInfo(UserHandle.myUserId()).isRestricted();
+                    if (!DefaultSmsPreference.isAvailable(context) || isRestrictedUser) {
+                        result.add(KEY_SMS_APPLICATION);
+                    }
+
+                    if (!DefaultEmergencyPreference.isAvailable(context)) {
+                        result.add(KEY_DEFAULT_EMERGENCY_APP);
+                    }
+
+                    return result;
+                }
+            };
+
+    protected String getIntentActionString() {
+        return Settings.ACTION_MANAGE_DEFAULT_APPS_SETTINGS;
+    }
+
 }
diff --git a/src/com/android/settings/dashboard/DashboardSummary.java b/src/com/android/settings/dashboard/DashboardSummary.java
index ba9136a..69fd8e7 100644
--- a/src/com/android/settings/dashboard/DashboardSummary.java
+++ b/src/com/android/settings/dashboard/DashboardSummary.java
@@ -161,6 +161,9 @@
         List<DashboardCategory> categories =
                 ((SettingsActivity) getActivity()).getDashboardCategories();
         mAdapter.setCategories(categories);
+
+        // recheck to see if any suggestions have been changed.
+        mAdapter.setSuggestions(mSuggestionParser);
         mDashboard.setAdapter(mAdapter);
 
         long delta = System.currentTimeMillis() - start;
diff --git a/src/com/android/settings/dashboard/SuggestionsChecks.java b/src/com/android/settings/dashboard/SuggestionsChecks.java
index b483ac7..fde7bc1 100644
--- a/src/com/android/settings/dashboard/SuggestionsChecks.java
+++ b/src/com/android/settings/dashboard/SuggestionsChecks.java
@@ -20,11 +20,15 @@
 import android.app.IWallpaperManagerCallback;
 import android.app.NotificationManager;
 import android.content.Context;
+import android.hardware.fingerprint.FingerprintManager;
 import android.os.Bundle;
 import android.os.IBinder;
 import android.os.RemoteException;
 import android.os.ServiceManager;
+import com.android.ims.ImsManager;
+import com.android.settings.Settings.FingerprintSuggestionActivity;
 import com.android.settings.Settings.WallpaperSuggestionActivity;
+import com.android.settings.Settings.WifiCallingSuggestionActivity;
 import com.android.settings.Settings.ZenModeAutomationSuggestionActivity;
 import com.android.settingslib.drawer.Tile;
 
@@ -47,10 +51,27 @@
             return hasEnabledZenAutoRules();
         } else if (className.equals(WallpaperSuggestionActivity.class.getName())) {
             return hasWallpaperSet();
+        } else if (className.equals(WifiCallingSuggestionActivity.class.getName())) {
+            return isWifiCallingUnavailableOrEnabled();
+        } else if (className.equals(FingerprintSuggestionActivity.class.getName())) {
+            return isNotSingleFingerprintEnrolled();
         }
         return false;
     }
 
+    private boolean isNotSingleFingerprintEnrolled() {
+        FingerprintManager manager = mContext.getSystemService(FingerprintManager.class);
+        return manager == null || manager.getEnrolledFingerprints().size() != 1;
+    }
+
+    public boolean isWifiCallingUnavailableOrEnabled() {
+        if (!ImsManager.isWfcEnabledByPlatform(mContext)) {
+            return true;
+        }
+        return ImsManager.isWfcEnabledByUser(mContext)
+                && ImsManager.isNonTtyOrTtyOnVolteEnabled(mContext);
+    }
+
     private boolean hasEnabledZenAutoRules() {
         List<AutomaticZenRule> zenRules = NotificationManager.from(mContext).getAutomaticZenRules();
         final int N = zenRules.size();
diff --git a/src/com/android/settings/fuelgauge/FakeUid.java b/src/com/android/settings/fuelgauge/FakeUid.java
index 9d3e2ad..d616010 100644
--- a/src/com/android/settings/fuelgauge/FakeUid.java
+++ b/src/com/android/settings/fuelgauge/FakeUid.java
@@ -16,6 +16,7 @@
 
 package com.android.settings.fuelgauge;
 
+import android.os.BatteryStats;
 import android.os.BatteryStats.Timer;
 import android.os.BatteryStats.Uid;
 import android.util.ArrayMap;
@@ -73,16 +74,6 @@
     }
 
     @Override
-    public long getWifiControllerActivity(int type, int which) {
-        return 0;
-    }
-
-    @Override
-    public long getBluetoothControllerActivity(int type, int which) {
-        return 0;
-    }
-
-    @Override
     public void noteWifiRunningLocked(long elapsedRealtime) {
     }
 
@@ -258,4 +249,19 @@
     public long getCpuPowerMaUs(int which) {
         return 0;
     }
+
+    @Override
+    public BatteryStats.ControllerActivityCounter getWifiControllerActivity() {
+        return null;
+    }
+
+    @Override
+    public BatteryStats.ControllerActivityCounter getBluetoothControllerActivity() {
+        return null;
+    }
+
+    @Override
+    public BatteryStats.ControllerActivityCounter getModemControllerActivity() {
+        return null;
+    }
 }
diff --git a/src/com/android/settings/print/PrintSettingsFragment.java b/src/com/android/settings/print/PrintSettingsFragment.java
index 537f5de..b59c297 100644
--- a/src/com/android/settings/print/PrintSettingsFragment.java
+++ b/src/com/android/settings/print/PrintSettingsFragment.java
@@ -33,8 +33,6 @@
 import android.os.Bundle;
 import android.os.Handler;
 import android.os.Message;
-import android.os.UserHandle;
-import android.os.UserManager;
 import android.print.PrintJob;
 import android.print.PrintJobId;
 import android.print.PrintJobInfo;
@@ -52,22 +50,18 @@
 import android.view.View;
 import android.view.View.OnClickListener;
 import android.view.ViewGroup;
-import android.widget.AdapterView;
-import android.widget.AdapterView.OnItemSelectedListener;
 import android.widget.Button;
-import android.widget.Spinner;
 import android.widget.TextView;
 
 import com.android.internal.content.PackageMonitor;
 import com.android.internal.logging.MetricsProto.MetricsEvent;
 import com.android.settings.DialogCreatable;
 import com.android.settings.R;
-import com.android.settings.SettingsPreferenceFragment;
+import com.android.settings.utils.ProfileSettingsPreferenceFragment;
 import com.android.settings.dashboard.SummaryLoader;
 import com.android.settings.search.BaseSearchIndexProvider;
 import com.android.settings.search.Indexable;
 import com.android.settings.search.SearchIndexableRaw;
-import com.android.settingslib.drawer.UserAdapter;
 
 import java.text.DateFormat;
 import java.util.ArrayList;
@@ -76,8 +70,8 @@
 /**
  * Fragment with the top level print settings.
  */
-public class PrintSettingsFragment extends SettingsPreferenceFragment
-        implements DialogCreatable, Indexable, OnItemSelectedListener, OnClickListener {
+public class PrintSettingsFragment extends ProfileSettingsPreferenceFragment
+        implements DialogCreatable, Indexable, OnClickListener {
     public static final String TAG = "PrintSettingsFragment";
     private static final int LOADER_ID_PRINT_JOBS_LOADER = 1;
 
@@ -122,8 +116,6 @@
     private PreferenceCategory mPrintServicesCategory;
 
     private PrintJobsController mPrintJobsController;
-    private UserAdapter mProfileSpinnerAdapter;
-    private Spinner mSpinner;
     private Button mAddNewServiceButton;
 
     @Override
@@ -188,14 +180,11 @@
 
         contentRoot.addView(emptyView);
         setEmptyView(emptyView);
+    }
 
-        final UserManager um = (UserManager) getSystemService(Context.USER_SERVICE);
-        mProfileSpinnerAdapter = UserAdapter.createUserSpinnerAdapter(um, getActivity());
-        if (mProfileSpinnerAdapter != null) {
-            mSpinner = (Spinner) setPinnedHeaderView(R.layout.spinner_view);
-            mSpinner.setAdapter(mProfileSpinnerAdapter);
-            mSpinner.setOnItemSelectedListener(this);
-        }
+    @Override
+    protected String getIntentActionString() {
+        return Settings.ACTION_PRINT_SETTINGS;
     }
 
     private void updateServicesPreferences() {
@@ -327,24 +316,6 @@
     }
 
     @Override
-    public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
-        UserHandle selectedUser = mProfileSpinnerAdapter.getUserHandle(position);
-        if (selectedUser.getIdentifier() != UserHandle.myUserId()) {
-            Intent intent = new Intent(Settings.ACTION_PRINT_SETTINGS);
-            intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
-            intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK);
-            getActivity().startActivityAsUser(intent, selectedUser);
-            // Go back to default selection, which is the first one
-            mSpinner.setSelection(0);
-        }
-    }
-
-    @Override
-    public void onNothingSelected(AdapterView<?> parent) {
-        // Nothing to do
-    }
-
-    @Override
     public void onClick(View v) {
         if (mAddNewServiceButton == v) {
             final Intent addNewServiceIntent = createAddNewServiceIntentOrNull();
diff --git a/src/com/android/settings/users/UserSettings.java b/src/com/android/settings/users/UserSettings.java
index bf03ff9..1837a2c 100644
--- a/src/com/android/settings/users/UserSettings.java
+++ b/src/com/android/settings/users/UserSettings.java
@@ -101,7 +101,6 @@
     private static final String KEY_USER_LIST = "user_list";
     private static final String KEY_USER_ME = "user_me";
     private static final String KEY_ADD_USER = "user_add";
-    private static final String KEY_EMERGENCY_INFO = "emergency_info";
 
     private static final int MENU_REMOVE_USER = Menu.FIRST;
 
@@ -135,7 +134,6 @@
     private DimmableIconPreference mAddUser;
     private PreferenceGroup mLockScreenSettings;
     private RestrictedSwitchPreference mAddUserWhenLocked;
-    private Preference mEmergencyInfoPreference;
     private int mRemovingUserId = -1;
     private int mAddedUserId = 0;
     private boolean mAddingUser;
@@ -231,8 +229,6 @@
         }
         mLockScreenSettings = (PreferenceGroup) findPreference("lock_screen_settings");
         mAddUserWhenLocked = (RestrictedSwitchPreference) findPreference("add_users_when_locked");
-        mEmergencyInfoPreference = findPreference(KEY_EMERGENCY_INFO);
-        mEmergencyInfoPreference.setOnPreferenceClickListener(this);
         loadProfile();
         setHasOptionsMenu(true);
         IntentFilter filter = new IntentFilter(Intent.ACTION_USER_REMOVED);
@@ -921,9 +917,6 @@
             } else {
                 onAddUserClicked(USER_TYPE_USER);
             }
-        } else if (pref == mEmergencyInfoPreference) {
-            Intent intent = new Intent("com.android.emergency.EDIT_EMERGENGY_INFO");
-            startActivity(intent);
         }
         return false;
     }
diff --git a/src/com/android/settings/utils/ProfileSettingsPreferenceFragment.java b/src/com/android/settings/utils/ProfileSettingsPreferenceFragment.java
new file mode 100644
index 0000000..e1c4d28
--- /dev/null
+++ b/src/com/android/settings/utils/ProfileSettingsPreferenceFragment.java
@@ -0,0 +1,74 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.settings.utils;
+
+import android.content.Context;
+import android.content.Intent;
+import android.os.Bundle;
+import android.os.UserHandle;
+import android.os.UserManager;
+import android.view.View;
+import android.widget.AdapterView;
+import android.widget.Spinner;
+
+import com.android.settings.R;
+import com.android.settings.SettingsPreferenceFragment;
+import com.android.settingslib.drawer.UserAdapter;
+
+/**
+ * Base fragment class for per profile settings.
+ */
+public abstract class ProfileSettingsPreferenceFragment extends SettingsPreferenceFragment {
+
+    @Override
+    public void onViewCreated(View view, Bundle savedInstanceState) {
+        super.onViewCreated(view, savedInstanceState);
+        final UserManager um = (UserManager) getSystemService(Context.USER_SERVICE);
+        final UserAdapter profileSpinnerAdapter =
+                UserAdapter.createUserSpinnerAdapter(um, getActivity());
+        if (profileSpinnerAdapter != null) {
+            final Spinner spinner = (Spinner) setPinnedHeaderView(R.layout.spinner_view);
+            spinner.setAdapter(profileSpinnerAdapter);
+            spinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
+                @Override
+                public void onItemSelected(AdapterView<?> parent, View view, int position,
+                                           long id) {
+                    UserHandle selectedUser = profileSpinnerAdapter.getUserHandle(position);
+                    if (selectedUser.getIdentifier() != UserHandle.myUserId()) {
+                        Intent intent = new Intent(getIntentActionString());
+                        intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+                        intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK);
+                        getActivity().startActivityAsUser(intent, selectedUser);
+                        // Go back to default selection, which is the first one
+                        spinner.setSelection(0);
+                    }
+                }
+
+                @Override
+                public void onNothingSelected(AdapterView<?> parent) {
+                    // Nothing to do
+                }
+            });
+        }
+    }
+
+    /**
+     * @return intent action string that will bring user to this fragment.
+     */
+    protected abstract String getIntentActionString();
+
+}
diff --git a/src/com/android/settings/wifi/WifiConfigController.java b/src/com/android/settings/wifi/WifiConfigController.java
index 335c40b..3bb1473 100644
--- a/src/com/android/settings/wifi/WifiConfigController.java
+++ b/src/com/android/settings/wifi/WifiConfigController.java
@@ -100,14 +100,14 @@
     public static final int WIFI_EAP_METHOD_AKA_PRIME  = 6;
 
     /* These values come from "wifi_peap_phase2_entries" resource array */
-    public static final int WIFI_PEAP_PHASE2_NONE 	    = 0;
-    public static final int WIFI_PEAP_PHASE2_MSCHAPV2 	= 1;
+    public static final int WIFI_PEAP_PHASE2_NONE       = 0;
+    public static final int WIFI_PEAP_PHASE2_MSCHAPV2   = 1;
     public static final int WIFI_PEAP_PHASE2_GTC        = 2;
 
     /* Phase2 methods supported by PEAP are limited */
-    private final ArrayAdapter<String> PHASE2_PEAP_ADAPTER;
+    private final ArrayAdapter<String> mPhase2PeapAdapter;
     /* Full list of phase2 methods */
-    private final ArrayAdapter<String> PHASE2_FULL_ADAPTER;
+    private final ArrayAdapter<String> mPhase2FullAdapter;
 
     private final Handler mTextViewChangedHandler;
 
@@ -115,16 +115,20 @@
     private int mAccessPointSecurity;
     private TextView mPasswordView;
 
-    private String unspecifiedCert = "unspecified";
-    private static final int unspecifiedCertIndex = 0;
-    private String multipleCertSet = "multipleCert";
-    private static final int multipleCertSetIndex = 1;
+    private String mUnspecifiedCertString;
+    private String mMultipleCertSetString;
+    private static final int UNSPECIFIED_CERT_INDEX = 0;
+    private static final int NO_CERT_INDEX = 1;
+    private static final int MULTIPLE_CERT_SET_INDEX = 2;
+
+    private String mDoNotProvideEapUserCertString;
+    private String mDoNotValidateEapServerString;
 
     private Spinner mSecuritySpinner;
     private Spinner mEapMethodSpinner;
     private Spinner mEapCaCertSpinner;
     private Spinner mPhase2Spinner;
-    // Associated with mPhase2Spinner, one of PHASE2_FULL_ADAPTER or PHASE2_PEAP_ADAPTER
+    // Associated with mPhase2Spinner, one of mPhase2FullAdapter or mPhase2PeapAdapter
     private ArrayAdapter<String> mPhase2Adapter;
     private Spinner mEapUserCertSpinner;
     private TextView mEapIdentityView;
@@ -171,18 +175,23 @@
         final Resources res = mContext.getResources();
 
         mLevels = res.getStringArray(R.array.wifi_signal);
-        PHASE2_PEAP_ADAPTER = new ArrayAdapter<String>(
+        mPhase2PeapAdapter = new ArrayAdapter<String>(
             mContext, android.R.layout.simple_spinner_item,
             res.getStringArray(R.array.wifi_peap_phase2_entries));
-        PHASE2_PEAP_ADAPTER.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
+        mPhase2PeapAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
 
-        PHASE2_FULL_ADAPTER = new ArrayAdapter<String>(
+        mPhase2FullAdapter = new ArrayAdapter<String>(
                 mContext, android.R.layout.simple_spinner_item,
                 res.getStringArray(R.array.wifi_phase2_entries));
-        PHASE2_FULL_ADAPTER.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
+        mPhase2FullAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
 
-        unspecifiedCert = mContext.getString(R.string.wifi_unspecified);
-        multipleCertSet = mContext.getString(R.string.wifi_multiple_cert_added);
+        mUnspecifiedCertString = mContext.getString(R.string.wifi_unspecified);
+        mMultipleCertSetString = mContext.getString(R.string.wifi_multiple_cert_added);
+        mDoNotProvideEapUserCertString =
+            mContext.getString(R.string.wifi_do_not_provide_eap_user_cert);
+        mDoNotValidateEapServerString =
+            mContext.getString(R.string.wifi_do_not_validate_eap_server);
+
         mIpSettingsSpinner = (Spinner) mView.findViewById(R.id.ip_settings);
         mIpSettingsSpinner.setOnItemSelectedListener(this);
         mProxySettingsSpinner = (Spinner) mView.findViewById(R.id.proxy_settings);
@@ -201,10 +210,9 @@
             showIpConfigFields();
             showProxyFields();
             mView.findViewById(R.id.wifi_advanced_toggle).setVisibility(View.VISIBLE);
-            ((CheckBox)mView.findViewById(R.id.wifi_advanced_togglebox))
+            ((CheckBox) mView.findViewById(R.id.wifi_advanced_togglebox))
                     .setOnCheckedChangeListener(this);
 
-
             mConfigUi.setSubmitButton(res.getString(R.string.wifi_save));
         } else {
             mConfigUi.setTitle(mAccessPoint.getSsid());
@@ -221,7 +229,7 @@
                     StaticIpConfiguration staticConfig = config.getStaticIpConfiguration();
                     if (staticConfig != null && staticConfig.ipAddress != null) {
                         addRow(group, R.string.wifi_ip_address,
-                           staticConfig.ipAddress.getAddress().getHostAddress());
+                                staticConfig.ipAddress.getAddress().getHostAddress());
                     }
                 } else {
                     mIpSettingsSpinner.setSelection(DHCP);
@@ -242,8 +250,9 @@
                     mProxySettingsSpinner.setSelection(PROXY_NONE);
                 }
                 if (config != null && config.isPasspoint()) {
-                    addRow(group, R.string.passpoint_label, String.format(
-                        mContext.getString(R.string.passpoint_content), config.providerFriendlyName));
+                    addRow(group, R.string.passpoint_label,
+                            String.format(mContext.getString(R.string.passpoint_content),
+                            config.providerFriendlyName));
                 }
             }
 
@@ -253,10 +262,10 @@
                 showIpConfigFields();
                 showProxyFields();
                 mView.findViewById(R.id.wifi_advanced_toggle).setVisibility(View.VISIBLE);
-                ((CheckBox)mView.findViewById(R.id.wifi_advanced_togglebox))
-                    .setOnCheckedChangeListener(this);
+                ((CheckBox) mView.findViewById(R.id.wifi_advanced_togglebox))
+                        .setOnCheckedChangeListener(this);
                 if (showAdvancedFields) {
-                    ((CheckBox)mView.findViewById(R.id.wifi_advanced_togglebox)).setChecked(true);
+                    ((CheckBox) mView.findViewById(R.id.wifi_advanced_togglebox)).setChecked(true);
                     mView.findViewById(R.id.wifi_advanced_fields).setVisibility(View.VISIBLE);
                 }
             }
@@ -340,7 +349,7 @@
         group.addView(row);
     }
 
-    private String getSignalString(){
+    private String getSignalString() {
         final int level = mAccessPoint.getLevel();
 
         return (level > -1 && level < mLevels.length) ? mLevels[level] : null;
@@ -372,27 +381,46 @@
         boolean enabled = false;
         boolean passwordInvalid = false;
 
-        if (mPasswordView != null &&
-                ((mAccessPointSecurity == AccessPoint.SECURITY_WEP && mPasswordView.length() == 0) ||
-                        (mAccessPointSecurity == AccessPoint.SECURITY_PSK && mPasswordView.length() < 8))) {
+        if (mPasswordView != null
+                && ((mAccessPointSecurity == AccessPoint.SECURITY_WEP
+                        && mPasswordView.length() == 0)
+                    || (mAccessPointSecurity == AccessPoint.SECURITY_PSK
+                           && mPasswordView.length() < 8))) {
             passwordInvalid = true;
         }
 
-        if ((mSsidView != null && mSsidView.length() == 0) ||
-                ((mAccessPoint == null || !mAccessPoint.isSaved()) &&
-                        passwordInvalid)) {
+        if ((mSsidView != null && mSsidView.length() == 0)
+                || ((mAccessPoint == null || !mAccessPoint.isSaved()) && passwordInvalid)) {
             enabled = false;
         } else {
             enabled = ipAndProxyFieldsAreValid();
         }
-        if (mEapCaCertSpinner != null &&
-                mView.findViewById(R.id.l_ca_cert).getVisibility() != View.GONE &&
-                ((String)mEapCaCertSpinner.getSelectedItem()).equals(unspecifiedCert)) {
+        if (mEapCaCertSpinner != null
+                && mView.findViewById(R.id.l_ca_cert).getVisibility() != View.GONE
+                && ((String) mEapCaCertSpinner.getSelectedItem()).equals(mUnspecifiedCertString)) {
+            enabled = false;
+        }
+        if (mEapUserCertSpinner != null
+                && mView.findViewById(R.id.l_user_cert).getVisibility() != View.GONE
+                && ((String) mEapUserCertSpinner.getSelectedItem())
+                       .equals(mUnspecifiedCertString)) {
             enabled = false;
         }
         return enabled;
     }
 
+    void showWarningMessageIfAppropriate() {
+        mView.findViewById(R.id.no_ca_cert_warning).setVisibility(View.GONE);
+        if (mEapCaCertSpinner != null
+                && mView.findViewById(R.id.l_ca_cert).getVisibility() != View.GONE
+                && ((String) mEapCaCertSpinner.getSelectedItem())
+                       .equals(mDoNotValidateEapServerString)) {
+            // Display warning if user chooses not to validate the EAP server with a user-supplied
+            // CA certificate in an EAP network configuration.
+            mView.findViewById(R.id.no_ca_cert_warning).setVisibility(View.VISIBLE);
+        }
+    }
+
     /* package */ WifiConfiguration getConfig() {
         if (mMode == WifiConfigUiBase.MODE_VIEW) {
             return null;
@@ -427,8 +455,8 @@
                     int length = mPasswordView.length();
                     String password = mPasswordView.getText().toString();
                     // WEP-40, WEP-104, and 256-bit WEP (WEP-232?)
-                    if ((length == 10 || length == 26 || length == 58) &&
-                            password.matches("[0-9A-Fa-f]*")) {
+                    if ((length == 10 || length == 26 || length == 58)
+                            && password.matches("[0-9A-Fa-f]*")) {
                         config.wepKeys[0] = password;
                     } else {
                         config.wepKeys[0] = '"' + password + '"';
@@ -458,7 +486,7 @@
                 switch (eapMethod) {
                     case Eap.PEAP:
                         // PEAP supports limited phase2 values
-                        // Map the index from the PHASE2_PEAP_ADAPTER to the one used
+                        // Map the index from the mPhase2PeapAdapter to the one used
                         // by the API which has the full list of PEAP methods.
                         switch(phase2Method) {
                             case WIFI_PEAP_PHASE2_NONE:
@@ -476,27 +504,36 @@
                         }
                         break;
                     default:
-                        // The default index from PHASE2_FULL_ADAPTER maps to the API
+                        // The default index from mPhase2FullAdapter maps to the API
                         config.enterpriseConfig.setPhase2Method(phase2Method);
                         break;
                 }
                 String caCert = (String) mEapCaCertSpinner.getSelectedItem();
-                if (caCert.equals(unspecifiedCert)) {
+                if (caCert.equals(mUnspecifiedCertString)
+                        || caCert.equals(mDoNotValidateEapServerString)) {
+                    // Note: |caCert| should not be able to take the value |unspecifiedCert|,
+                    // since we prevent such configurations from being saved.
                     config.enterpriseConfig.setCaCertificateAliases(null);
-                } else if (caCert.equals(multipleCertSet)) {
+                } else if (caCert.equals(mMultipleCertSetString)) {
                     if (mAccessPoint != null) {
                         if (!mAccessPoint.isSaved()) {
                             Log.e(TAG, "Multiple certs can only be set when editing saved network");
                         }
                         config.enterpriseConfig.setCaCertificateAliases(
-                                mAccessPoint.getConfig().enterpriseConfig.getCaCertificateAliases());
+                                mAccessPoint.getConfig().enterpriseConfig
+                                        .getCaCertificateAliases());
                     }
                 } else {
                     config.enterpriseConfig.setCaCertificateAliases(new String[] {caCert});
                 }
 
                 String clientCert = (String) mEapUserCertSpinner.getSelectedItem();
-                if (clientCert.equals(unspecifiedCert)) clientCert = "";
+                if (clientCert.equals(mUnspecifiedCertString)
+                        || clientCert.equals(mDoNotProvideEapUserCertString)) {
+                    // Note: |clientCert| should not be able to take the value |unspecifiedCert|,
+                    // since we prevent such configurations from being saved.
+                    clientCert = "";
+                }
                 config.enterpriseConfig.setClientCertificateAlias(clientCert);
                 if (eapMethod == Eap.SIM || eapMethod == Eap.AKA || eapMethod == Eap.AKA_PRIME) {
                     config.enterpriseConfig.setIdentity("");
@@ -533,9 +570,11 @@
     }
 
     private boolean ipAndProxyFieldsAreValid() {
-        mIpAssignment = (mIpSettingsSpinner != null &&
-                mIpSettingsSpinner.getSelectedItemPosition() == STATIC_IP) ?
-                IpAssignment.STATIC : IpAssignment.DHCP;
+        mIpAssignment =
+                (mIpSettingsSpinner != null
+                    && mIpSettingsSpinner.getSelectedItemPosition() == STATIC_IP)
+                ? IpAssignment.STATIC
+                : IpAssignment.DHCP;
 
         if (mIpAssignment == IpAssignment.STATIC) {
             mStaticIpConfiguration = new StaticIpConfiguration();
@@ -584,7 +623,7 @@
     private Inet4Address getIPv4Address(String text) {
         try {
             return (Inet4Address) NetworkUtils.numericToInetAddress(text);
-        } catch (IllegalArgumentException|ClassCastException e) {
+        } catch (IllegalArgumentException | ClassCastException e) {
             return null;
         }
     }
@@ -619,7 +658,7 @@
                 //Extract a default gateway from IP address
                 InetAddress netPart = NetworkUtils.getNetworkPart(inetAddr, networkPrefixLength);
                 byte[] addr = netPart.getAddress();
-                addr[addr.length-1] = 1;
+                addr[addr.length - 1] = 1;
                 mGatewayView.setText(InetAddress.getByAddress(addr).getHostAddress());
             } catch (RuntimeException ee) {
             } catch (java.net.UnknownHostException u) {
@@ -700,11 +739,14 @@
             mEapCaCertSpinner = (Spinner) mView.findViewById(R.id.ca_cert);
             mEapCaCertSpinner.setOnItemSelectedListener(this);
             mEapUserCertSpinner = (Spinner) mView.findViewById(R.id.user_cert);
+            mEapUserCertSpinner.setOnItemSelectedListener(this);
             mEapIdentityView = (TextView) mView.findViewById(R.id.identity);
             mEapAnonymousView = (TextView) mView.findViewById(R.id.anonymous);
 
-            loadCertificates(mEapCaCertSpinner, Credentials.CA_CERTIFICATE, false);
-            loadCertificates(mEapUserCertSpinner, Credentials.USER_PRIVATE_KEY, false);
+            loadCertificates(mEapCaCertSpinner, Credentials.CA_CERTIFICATE, false,
+                    mDoNotValidateEapServerString);
+            loadCertificates(mEapUserCertSpinner, Credentials.USER_PRIVATE_KEY, false,
+                    mDoNotProvideEapUserCertString);
 
             // Modifying an existing network
             if (mAccessPoint != null && mAccessPoint.isSaved()) {
@@ -736,14 +778,14 @@
                 }
                 String[] caCerts = enterpriseConfig.getCaCertificateAliases();
                 if (caCerts == null) {
-                    setSelection(mEapCaCertSpinner, unspecifiedCert);
+                    setSelection(mEapCaCertSpinner, mUnspecifiedCertString);
                 } else if (caCerts.length == 1) {
                     setSelection(mEapCaCertSpinner, caCerts[0]);
                 } else {
                     // Reload the cert spinner with an extra "multiple certificates added" item
                     loadCertificates(mEapCaCertSpinner,
-                            Credentials.CA_CERTIFICATE, true);
-                    mEapCaCertSpinner.setSelection(multipleCertSetIndex);
+                            Credentials.CA_CERTIFICATE, true, mDoNotValidateEapServerString);
+                    mEapCaCertSpinner.setSelection(MULTIPLE_CERT_SET_INDEX);
                 }
                 setSelection(mEapUserCertSpinner, enterpriseConfig.getClientCertificateAlias());
                 mEapIdentityView.setText(enterpriseConfig.getIdentity());
@@ -804,8 +846,8 @@
                 break;
             case WIFI_EAP_METHOD_PEAP:
                 // Reset adapter if needed
-                if (mPhase2Adapter != PHASE2_PEAP_ADAPTER) {
-                    mPhase2Adapter = PHASE2_PEAP_ADAPTER;
+                if (mPhase2Adapter != mPhase2PeapAdapter) {
+                    mPhase2Adapter = mPhase2PeapAdapter;
                     mPhase2Spinner.setAdapter(mPhase2Adapter);
                 }
                 mView.findViewById(R.id.l_phase2).setVisibility(View.VISIBLE);
@@ -814,8 +856,8 @@
                 break;
             case WIFI_EAP_METHOD_TTLS:
                 // Reset adapter if needed
-                if (mPhase2Adapter != PHASE2_FULL_ADAPTER) {
-                    mPhase2Adapter = PHASE2_FULL_ADAPTER;
+                if (mPhase2Adapter != mPhase2FullAdapter) {
+                    mPhase2Adapter = mPhase2FullAdapter;
                     mPhase2Spinner.setAdapter(mPhase2Adapter);
                 }
                 mView.findViewById(R.id.l_phase2).setVisibility(View.VISIBLE);
@@ -847,12 +889,12 @@
 
     private void setCaCertInvisible() {
         mView.findViewById(R.id.l_ca_cert).setVisibility(View.GONE);
-        mEapCaCertSpinner.setSelection(unspecifiedCertIndex);
+        mEapCaCertSpinner.setSelection(UNSPECIFIED_CERT_INDEX);
     }
 
     private void setUserCertInvisible() {
         mView.findViewById(R.id.l_user_cert).setVisibility(View.GONE);
-        mEapUserCertSpinner.setSelection(unspecifiedCertIndex);
+        mEapUserCertSpinner.setSelection(UNSPECIFIED_CERT_INDEX);
     }
 
     private void setAnonymousIdentInvisible() {
@@ -976,13 +1018,15 @@
         }
     }
 
-    private void loadCertificates(Spinner spinner, String prefix, boolean showMultipleCerts) {
+    private void loadCertificates(
+            Spinner spinner, String prefix, boolean showMultipleCerts, String noCertificateString) {
         final Context context = mConfigUi.getContext();
 
         ArrayList<String> certs = new ArrayList<String>();
-        certs.add(unspecifiedCert);
+        certs.add(UNSPECIFIED_CERT_INDEX, mUnspecifiedCertString);
+        certs.add(NO_CERT_INDEX, noCertificateString);
         if (showMultipleCerts) {
-            certs.add(multipleCertSet);
+            certs.add(MULTIPLE_CERT_SET_INDEX, mMultipleCertSetString);
         }
         certs.addAll(
                 Arrays.asList(KeyStore.getInstance().list(prefix, android.os.Process.WIFI_UID)));
@@ -1056,12 +1100,11 @@
     public void onCheckedChanged(CompoundButton view, boolean isChecked) {
         if (view.getId() == R.id.show_password) {
             int pos = mPasswordView.getSelectionEnd();
-            mPasswordView.setInputType(
-                    InputType.TYPE_CLASS_TEXT | (isChecked ?
-                            InputType.TYPE_TEXT_VARIATION_VISIBLE_PASSWORD :
-                                InputType.TYPE_TEXT_VARIATION_PASSWORD));
+            mPasswordView.setInputType(InputType.TYPE_CLASS_TEXT
+                    | (isChecked ? InputType.TYPE_TEXT_VARIATION_VISIBLE_PASSWORD
+                                 : InputType.TYPE_TEXT_VARIATION_PASSWORD));
             if (pos >= 0) {
-                ((EditText)mPasswordView).setSelection(pos);
+                ((EditText) mPasswordView).setSelection(pos);
             }
         } else if (view.getId() == R.id.wifi_advanced_togglebox) {
             if (isChecked) {
@@ -1084,6 +1127,7 @@
         } else {
             showIpConfigFields();
         }
+        showWarningMessageIfAppropriate();
         enableSubmitIfAppropriate();
     }
 
@@ -1097,11 +1141,10 @@
      */
     public void updatePassword() {
         TextView passwdView = (TextView) mView.findViewById(R.id.password);
-        passwdView.setInputType(
-                InputType.TYPE_CLASS_TEXT |
-                (((CheckBox) mView.findViewById(R.id.show_password)).isChecked() ?
-                InputType.TYPE_TEXT_VARIATION_VISIBLE_PASSWORD :
-                InputType.TYPE_TEXT_VARIATION_PASSWORD));
+        passwdView.setInputType(InputType.TYPE_CLASS_TEXT
+                | (((CheckBox) mView.findViewById(R.id.show_password)).isChecked()
+                   ? InputType.TYPE_TEXT_VARIATION_VISIBLE_PASSWORD
+                   : InputType.TYPE_TEXT_VARIATION_PASSWORD));
     }
 
     public AccessPoint getAccessPoint() {