Merge "Add PrefController in XML support"
diff --git a/res/values/attrs.xml b/res/values/attrs.xml
index 2ba7919..e3fa070 100644
--- a/res/values/attrs.xml
+++ b/res/values/attrs.xml
@@ -97,6 +97,7 @@
     <!-- For Search -->
     <declare-styleable name="Preference">
         <attr name="keywords" format="string" />
+        <attr name="controller" format="string" />
     </declare-styleable>
 
     <!-- For DotsPageIndicator -->
diff --git a/res/xml/display_settings.xml b/res/xml/display_settings.xml
index f9f5d2b..333fd2a 100644
--- a/res/xml/display_settings.xml
+++ b/res/xml/display_settings.xml
@@ -25,8 +25,9 @@
     <Preference
         android:key="brightness"
         android:title="@string/brightness"
-        settings:keywords="@string/keywords_display_brightness_level">
-        <intent android:action="com.android.intent.action.SHOW_BRIGHTNESS_DIALOG" />
+        settings:keywords="@string/keywords_display_brightness_level"
+        settings:controller="com.android.settings.display.AutoBrightnessPreferenceController">
+    <intent android:action="com.android.intent.action.SHOW_BRIGHTNESS_DIALOG" />
     </Preference>
 
     <com.android.settings.display.NightDisplayPreference
diff --git a/res/xml/system_dashboard_fragment.xml b/res/xml/system_dashboard_fragment.xml
index 8b9d0ca..1dfa6fb 100644
--- a/res/xml/system_dashboard_fragment.xml
+++ b/res/xml/system_dashboard_fragment.xml
@@ -26,7 +26,8 @@
         android:title="@string/gesture_preference_title"
         android:icon="@drawable/ic_settings_gestures"
         android:order="-250"
-        android:fragment="com.android.settings.gestures.GestureSettings" />
+        android:fragment="com.android.settings.gestures.GestureSettings"
+        settings:controller="com.android.settings.gestures.GesturesSettingPreferenceController"/>
 
     <!-- Backup -->
     <Preference
@@ -34,7 +35,8 @@
         android:title="@string/privacy_settings_title"
         android:summary="@string/summary_placeholder"
         android:icon="@drawable/ic_settings_backup"
-        android:order="-60">
+        android:order="-60"
+        settings:controller="com.android.settings.backup.BackupSettingsActivityPreferenceController">
         <intent android:action="android.settings.BACKUP_AND_RESET_SETTINGS" />
     </Preference>
 
@@ -44,14 +46,16 @@
         android:title="@string/system_update_settings_list_item_title"
         android:summary="@string/summary_placeholder"
         android:icon="@drawable/ic_system_update"
-        android:order="-30">
+        android:order="-30"
+        settings:controller="com.android.settings.deviceinfo.SystemUpdatePreferenceController">
         <intent android:action="android.settings.SYSTEM_UPDATE_SETTINGS" />
     </Preference>
 
     <Preference
         android:key="additional_system_update_settings"
         android:title="@string/additional_system_update_settings_list_item_title"
-        android:order="-31">
+        android:order="-31"
+        settings:controller="com.android.settings.deviceinfo.AdditionalSystemUpdatePreferenceController">
         <intent android:action="android.intent.action.MAIN"
                 android:targetPackage="@string/additional_system_update"
                 android:targetClass="@string/additional_system_update_menu" />
diff --git a/src/com/android/settings/backup/BackupSettingsActivityPreferenceController.java b/src/com/android/settings/backup/BackupSettingsActivityPreferenceController.java
index afc13b4..7a7530c 100644
--- a/src/com/android/settings/backup/BackupSettingsActivityPreferenceController.java
+++ b/src/com/android/settings/backup/BackupSettingsActivityPreferenceController.java
@@ -22,31 +22,29 @@
 import android.support.v7.preference.Preference;
 
 import com.android.settings.R;
+import com.android.settings.core.BasePreferenceController;
 import com.android.settings.core.PreferenceControllerMixin;
 import com.android.settingslib.core.AbstractPreferenceController;
 
-public class BackupSettingsActivityPreferenceController extends
-        AbstractPreferenceController implements PreferenceControllerMixin {
+public class BackupSettingsActivityPreferenceController extends BasePreferenceController {
+    private static final String TAG = "BackupSettingActivityPC";
+
     private static final String KEY_BACKUP_SETTINGS = "backup_settings";
-    private static final String TAG = "BackupSettingActivityPC" ;
 
     private final UserManager mUm;
     private final BackupManager mBackupManager;
 
     public BackupSettingsActivityPreferenceController(Context context) {
-        super(context);
+        super(context, KEY_BACKUP_SETTINGS);
         mUm = (UserManager) context.getSystemService(Context.USER_SERVICE);
         mBackupManager = new BackupManager(context);
     }
 
     @Override
-    public boolean isAvailable() {
-        return mUm.isAdminUser();
-    }
-
-    @Override
-    public String getPreferenceKey() {
-        return KEY_BACKUP_SETTINGS;
+    public int getAvailabilityStatus() {
+        return mUm.isAdminUser()
+                ? AVAILABLE
+                : DISABLED_UNSUPPORTED;
     }
 
     @Override
@@ -57,4 +55,4 @@
                 ? R.string.accessibility_feature_state_on
                 : R.string.accessibility_feature_state_off);
     }
-}
+}
\ No newline at end of file
diff --git a/src/com/android/settings/deviceinfo/AdditionalSystemUpdatePreferenceController.java b/src/com/android/settings/deviceinfo/AdditionalSystemUpdatePreferenceController.java
index 06bdb3f..f91ed4e 100644
--- a/src/com/android/settings/deviceinfo/AdditionalSystemUpdatePreferenceController.java
+++ b/src/com/android/settings/deviceinfo/AdditionalSystemUpdatePreferenceController.java
@@ -17,26 +17,23 @@
 
 import android.content.Context;
 
+import com.android.settings.core.BasePreferenceController;
 import com.android.settings.core.PreferenceControllerMixin;
 import com.android.settingslib.core.AbstractPreferenceController;
 
-public class AdditionalSystemUpdatePreferenceController extends
-        AbstractPreferenceController implements PreferenceControllerMixin {
+public class AdditionalSystemUpdatePreferenceController extends BasePreferenceController {
 
     private static final String KEY_UPDATE_SETTING = "additional_system_update_settings";
 
     public AdditionalSystemUpdatePreferenceController(Context context) {
-        super(context);
+        super(context, KEY_UPDATE_SETTING);
     }
 
     @Override
-    public boolean isAvailable() {
+    public int getAvailabilityStatus() {
         return mContext.getResources().getBoolean(
-                com.android.settings.R.bool.config_additional_system_update_setting_enable);
+                com.android.settings.R.bool.config_additional_system_update_setting_enable)
+                ? AVAILABLE
+                : DISABLED_UNSUPPORTED;
     }
-
-    @Override
-    public String getPreferenceKey() {
-        return KEY_UPDATE_SETTING;
-    }
-}
+}
\ No newline at end of file
diff --git a/src/com/android/settings/deviceinfo/SystemUpdatePreferenceController.java b/src/com/android/settings/deviceinfo/SystemUpdatePreferenceController.java
index d8a64a8..92c33d8 100644
--- a/src/com/android/settings/deviceinfo/SystemUpdatePreferenceController.java
+++ b/src/com/android/settings/deviceinfo/SystemUpdatePreferenceController.java
@@ -30,11 +30,9 @@
 
 import com.android.settings.R;
 import com.android.settings.Utils;
-import com.android.settings.core.PreferenceControllerMixin;
-import com.android.settingslib.core.AbstractPreferenceController;
+import com.android.settings.core.BasePreferenceController;
 
-public class SystemUpdatePreferenceController extends AbstractPreferenceController implements
-        PreferenceControllerMixin {
+public class SystemUpdatePreferenceController extends BasePreferenceController {
 
     private static final String TAG = "SysUpdatePrefContr";
 
@@ -42,19 +40,16 @@
 
     private final UserManager mUm;
 
-    public SystemUpdatePreferenceController(Context context, UserManager um) {
-        super(context);
-        mUm = um;
+    public SystemUpdatePreferenceController(Context context) {
+        super(context, KEY_SYSTEM_UPDATE_SETTINGS);
+        mUm = UserManager.get(context);
     }
 
     @Override
-    public boolean isAvailable() {
-        return mUm.isAdminUser();
-    }
-
-    @Override
-    public String getPreferenceKey() {
-        return KEY_SYSTEM_UPDATE_SETTINGS;
+    public int getAvailabilityStatus() {
+        return mUm.isAdminUser()
+                ? AVAILABLE
+                : DISABLED_UNSUPPORTED;
     }
 
     @Override
@@ -62,14 +57,14 @@
         super.displayPreference(screen);
         if (isAvailable()) {
             Utils.updatePreferenceToSpecificActivityOrRemove(mContext, screen,
-                    KEY_SYSTEM_UPDATE_SETTINGS,
+                    getPreferenceKey(),
                     Utils.UPDATE_PREFERENCE_FLAG_SET_TITLE_TO_MATCHING_ACTIVITY);
         }
     }
 
     @Override
     public boolean handlePreferenceTreeClick(Preference preference) {
-        if (KEY_SYSTEM_UPDATE_SETTINGS.equals(preference.getKey())) {
+        if (TextUtils.equals(getPreferenceKey(), preference.getKey())) {
             CarrierConfigManager configManager =
                     (CarrierConfigManager) mContext.getSystemService(CARRIER_CONFIG_SERVICE);
             PersistableBundle b = configManager.getConfig();
@@ -108,4 +103,4 @@
             mContext.getApplicationContext().sendBroadcast(intent);
         }
     }
-}
+}
\ No newline at end of file
diff --git a/src/com/android/settings/gestures/GesturesSettingPreferenceController.java b/src/com/android/settings/gestures/GesturesSettingPreferenceController.java
index d1b47b2..819b128 100644
--- a/src/com/android/settings/gestures/GesturesSettingPreferenceController.java
+++ b/src/com/android/settings/gestures/GesturesSettingPreferenceController.java
@@ -23,27 +23,26 @@
 
 import com.android.internal.hardware.AmbientDisplayConfiguration;
 import com.android.settings.R;
+import com.android.settings.core.BasePreferenceController;
 import com.android.settings.core.PreferenceControllerMixin;
 import com.android.settings.overlay.FeatureFactory;
 import com.android.settingslib.core.AbstractPreferenceController;
 
 import java.util.List;
 
-public class GesturesSettingPreferenceController extends AbstractPreferenceController
-        implements PreferenceControllerMixin {
-
-    private static final String KEY_GESTURES_SETTINGS = "gesture_settings";
-
+public class GesturesSettingPreferenceController extends BasePreferenceController {
     private final AssistGestureFeatureProvider mFeatureProvider;
     private List<AbstractPreferenceController> mGestureControllers;
 
+    private static final String KEY_GESTURES_SETTINGS = "gesture_settings";
+
     public GesturesSettingPreferenceController(Context context) {
-        super(context);
+        super(context, KEY_GESTURES_SETTINGS);
         mFeatureProvider = FeatureFactory.getFactory(context).getAssistGestureFeatureProvider();
     }
 
     @Override
-    public boolean isAvailable() {
+    public int getAvailabilityStatus() {
         if (mGestureControllers == null) {
             mGestureControllers = GestureSettings.buildPreferenceControllers(mContext,
                     null /* lifecycle */, new AmbientDisplayConfiguration(mContext));
@@ -52,12 +51,9 @@
         for (AbstractPreferenceController controller : mGestureControllers) {
             isAvailable = isAvailable || controller.isAvailable();
         }
-        return isAvailable;
-    }
-
-    @Override
-    public String getPreferenceKey() {
-        return KEY_GESTURES_SETTINGS;
+        return isAvailable
+                ? AVAILABLE
+                : DISABLED_UNSUPPORTED;
     }
 
     @Override
@@ -83,5 +79,4 @@
         }
         preference.setSummary(summary);
     }
-
-}
+}
\ No newline at end of file
diff --git a/src/com/android/settings/search/XmlParserUtils.java b/src/com/android/settings/search/XmlParserUtils.java
index b4ffc53..27c5cd3 100644
--- a/src/com/android/settings/search/XmlParserUtils.java
+++ b/src/com/android/settings/search/XmlParserUtils.java
@@ -71,6 +71,10 @@
         return getData(context, attrs, R.styleable.Preference, R.styleable.Preference_keywords);
     }
 
+    public static String getController(Context context, AttributeSet attrs) {
+        return getData(context, attrs, R.styleable.Preference, R.styleable.Preference_controller);
+    }
+
     public static int getDataIcon(Context context, AttributeSet attrs) {
         final TypedArray ta = context.obtainStyledAttributes(attrs,
                 com.android.internal.R.styleable.Preference);
diff --git a/src/com/android/settings/system/SystemDashboardFragment.java b/src/com/android/settings/system/SystemDashboardFragment.java
index b344d8b..323a2d4 100644
--- a/src/com/android/settings/system/SystemDashboardFragment.java
+++ b/src/com/android/settings/system/SystemDashboardFragment.java
@@ -82,7 +82,7 @@
 
     private static List<AbstractPreferenceController> buildPreferenceControllers(Context context) {
         final List<AbstractPreferenceController> controllers = new ArrayList<>();
-        controllers.add(new SystemUpdatePreferenceController(context, UserManager.get(context)));
+        controllers.add(new SystemUpdatePreferenceController(context));
         controllers.add(new AdditionalSystemUpdatePreferenceController(context));
         controllers.add(new BackupSettingsActivityPreferenceController(context));
         controllers.add(new GesturesSettingPreferenceController(context));
@@ -124,10 +124,10 @@
                 @Override
                 public List<String> getNonIndexableKeys(Context context) {
                     List<String> keys = super.getNonIndexableKeys(context);
-                    keys.add((new BackupSettingsActivityPreferenceController(context)
-                            .getPreferenceKey()));
+                    keys.add((new BackupSettingsActivityPreferenceController(
+                            context).getPreferenceKey()));
                     keys.add(KEY_RESET);
                     return keys;
                 }
             };
-}
+}
\ No newline at end of file
diff --git a/tests/robotests/res/xml-mcc999/about_legal.xml b/tests/robotests/res/xml-mcc999/about_legal.xml
index 53a2b89..3e008cb 100644
--- a/tests/robotests/res/xml-mcc999/about_legal.xml
+++ b/tests/robotests/res/xml-mcc999/about_legal.xml
@@ -30,5 +30,6 @@
 
     <Preference
             android:key="pref_key_1"
-            android:title="bears_bears_bears"/>
+            android:title="bears_bears_bears"
+            settings:controller="mind_flayer"/>
 </PreferenceScreen>
\ No newline at end of file
diff --git a/tests/robotests/src/com/android/settings/core/XmlControllerAttributeTest.java b/tests/robotests/src/com/android/settings/core/XmlControllerAttributeTest.java
new file mode 100644
index 0000000..ed4e815
--- /dev/null
+++ b/tests/robotests/src/com/android/settings/core/XmlControllerAttributeTest.java
@@ -0,0 +1,275 @@
+package com.android.settings.core;
+
+import static com.google.common.truth.Truth.assertWithMessage;
+
+import android.content.Context;
+import android.content.res.XmlResourceParser;
+import android.provider.SearchIndexableResource;
+import android.text.TextUtils;
+import android.util.AttributeSet;
+import android.util.Xml;
+
+import com.android.settings.R;
+import com.android.settings.TestConfig;
+import com.android.settings.search.DatabaseIndexingUtils;
+import com.android.settings.search.Indexable;
+import com.android.settings.search.SearchIndexableResources;
+import com.android.settings.search.XmlParserUtils;
+import com.android.settings.security.SecuritySettings;
+import com.android.settings.testutils.SettingsRobolectricTestRunner;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.robolectric.RuntimeEnvironment;
+import org.robolectric.annotation.Config;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.lang.reflect.Constructor;
+import java.lang.reflect.InvocationTargetException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+
+@RunWith(SettingsRobolectricTestRunner.class)
+@Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION)
+public class XmlControllerAttributeTest {
+
+    // List of classes that are too hard to mock in order to retrieve xml information.
+    private final List<Class> illegalClasses = new ArrayList<>(
+            Arrays.asList(
+                    SecuritySettings.class
+            ));
+
+    // List of XML that could be retrieved from the illegalClasses list.
+    private final List<Integer> whitelistXml = new ArrayList<>(
+            Arrays.asList(
+                    R.xml.security_settings_misc,
+                    R.xml.security_settings_lockscreen_profile,
+                    R.xml.security_settings_lockscreen,
+                    R.xml.security_settings_chooser,
+                    R.xml.security_settings_pattern_profile,
+                    R.xml.security_settings_pin_profile,
+                    R.xml.security_settings_password_profile,
+                    R.xml.security_settings_pattern,
+                    R.xml.security_settings_pin,
+                    R.xml.security_settings_password,
+                    R.xml.security_settings,
+                    R.xml.security_settings_status
+            ));
+
+    private static final String NO_VALID_CONSTRUCTOR_ERROR =
+            "Controllers added in XML need a constructor following either:"
+                    + "\n\tClassName(Context)\n\tClassName(Context, String)"
+                    + "\nThese controllers are missing a valid constructor:\n";
+
+    private static final String NOT_BASE_PREF_CONTROLLER_ERROR =
+            "Controllers added in XML need to extend com.android.settings.core"
+                    + ".BasePreferenceController\nThese controllers do not:\n";
+
+    private static final String BAD_CLASSNAME_ERROR =
+            "The following controllers set in the XML did not have valid class names:\n";
+
+    private static final String BAD_CONSTRUCTOR_ERROR =
+            "The constructor provided by the following classes were insufficient to instantiate "
+                    + "the object. It could be due to being an interface, abstract, or an "
+                    + "IllegalAccessException. Please fix the following classes:\n";
+
+    Context mContext;
+
+    private Set<Class> mProviderClassesCopy;
+
+    @Before
+    public void setUp() {
+        mContext = RuntimeEnvironment.application;
+        mProviderClassesCopy = new HashSet<>(SearchIndexableResources.providerValues());
+    }
+
+    @After
+    public void cleanUp() {
+        SearchIndexableResources.providerValues().clear();
+        SearchIndexableResources.providerValues().addAll(mProviderClassesCopy);
+    }
+
+    @Test
+    public void testAllIndexableXML_onlyValidBasePreferenceControllersAdded() {
+        Set<Integer> xmlSet = getIndexableXml();
+        xmlSet.addAll(whitelistXml);
+
+        List<String> xmlControllers = new ArrayList<>();
+        Set<String> invalidConstructors = new HashSet<>();
+        Set<String> invalidClassHierarchy = new HashSet<>();
+        Set<String> badClassNameControllers = new HashSet<>();
+        Set<String> badConstructorControllers = new HashSet<>();
+
+        for (int resId : xmlSet) {
+            xmlControllers.addAll(getXmlControllers(resId));
+        }
+
+        for (String controllerClassName : xmlControllers) {
+            Class<?> clazz = getClassFromClassName(controllerClassName);
+
+            if (clazz == null) {
+                badClassNameControllers.add(controllerClassName);
+                continue;
+            }
+
+            Constructor<?> constructor = getConstructorFromClass(clazz);
+
+            if (constructor == null) {
+                invalidConstructors.add(controllerClassName);
+                continue;
+            }
+
+            Object controller = getObjectFromConstructor(constructor);
+            if (controller == null) {
+                badConstructorControllers.add(controllerClassName);
+                continue;
+            }
+
+            if (!(controller instanceof BasePreferenceController)) {
+                invalidClassHierarchy.add(controllerClassName);
+            }
+        }
+
+        final String invalidConstructorError = buildErrorMessage(NO_VALID_CONSTRUCTOR_ERROR,
+                invalidConstructors);
+        final String invalidClassHierarchyError = buildErrorMessage(NOT_BASE_PREF_CONTROLLER_ERROR,
+                invalidClassHierarchy);
+        final String badClassNameError = buildErrorMessage(BAD_CLASSNAME_ERROR,
+                badClassNameControllers);
+        final String badConstructorError = buildErrorMessage(BAD_CONSTRUCTOR_ERROR,
+                badConstructorControllers);
+
+        assertWithMessage(invalidConstructorError).that(invalidConstructors).isEmpty();
+        assertWithMessage(invalidClassHierarchyError).that(invalidClassHierarchy).isEmpty();
+        assertWithMessage(badClassNameError).that(badClassNameControllers).isEmpty();
+        assertWithMessage(badConstructorError).that(badConstructorControllers).isEmpty();
+    }
+
+    private Set<Integer> getIndexableXml() {
+        Set<Integer> xmlResSet = new HashSet();
+
+        Collection<Class> indexableClasses = SearchIndexableResources.providerValues();
+        indexableClasses.removeAll(illegalClasses);
+
+        for (Class clazz : indexableClasses) {
+
+            Indexable.SearchIndexProvider provider = DatabaseIndexingUtils.getSearchIndexProvider(
+                    clazz);
+
+            if (provider == null) {
+                continue;
+            }
+
+            List<SearchIndexableResource> resources = provider.getXmlResourcesToIndex(mContext,
+                    true);
+
+            if (resources == null) {
+                continue;
+            }
+
+            for (SearchIndexableResource resource : resources) {
+                // Add '0's anyway. It won't break the test.
+                xmlResSet.add(resource.xmlResId);
+            }
+        }
+        return xmlResSet;
+    }
+
+    private List<String> getXmlControllers(int xmlResId) {
+        List<String> xmlControllers = new ArrayList<>();
+
+        XmlResourceParser parser;
+        try {
+            parser = mContext.getResources().getXml(xmlResId);
+
+            int type;
+            while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
+                    && type != XmlPullParser.START_TAG) {
+                // Parse next until start tag is found
+            }
+
+            final int outerDepth = parser.getDepth();
+            final AttributeSet attrs = Xml.asAttributeSet(parser);
+            String controllerClassName;
+            while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
+                    && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
+                if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
+                    continue;
+                }
+
+                controllerClassName = XmlParserUtils.getController(mContext, attrs);
+                // If controller is not indexed, then it is not compatible with
+                if (!TextUtils.isEmpty(controllerClassName)) {
+                    xmlControllers.add(controllerClassName);
+                }
+            }
+        } catch (Exception e) {
+            // Assume an issue with robolectric resources
+        }
+        return xmlControllers;
+    }
+
+    private String buildErrorMessage(String errorSummary, Set<String> errorClasses) {
+        final StringBuilder error = new StringBuilder(errorSummary);
+        for (String c : errorClasses) {
+            error.append(c).append("\n");
+        }
+        return error.toString();
+    }
+
+    private Class<?> getClassFromClassName(String className) {
+        Class<?> clazz = null;
+        try {
+            clazz = Class.forName(className);
+        } catch (ClassNotFoundException e) {
+        }
+        return clazz;
+    }
+
+    private Constructor<?> getConstructorFromClass(Class<?> clazz) {
+        Constructor<?> constructor = null;
+        try {
+            constructor = clazz.getConstructor(Context.class);
+        } catch (NoSuchMethodException e) {
+        }
+
+        if (constructor != null) {
+            return constructor;
+        }
+
+        try {
+            constructor = clazz.getConstructor(Context.class, String.class);
+        } catch (NoSuchMethodException e) {
+        }
+
+        return constructor;
+    }
+
+    private Object getObjectFromConstructor(Constructor<?> constructor) {
+        Object controller = null;
+
+        try {
+            controller = constructor.newInstance(mContext);
+        } catch (InstantiationException | IllegalAccessException | InvocationTargetException |
+                IllegalArgumentException e) {
+        }
+
+        if (controller != null) {
+            return controller;
+        }
+
+        try {
+            controller = constructor.newInstance(mContext, "key");
+        } catch (InstantiationException | IllegalAccessException | InvocationTargetException |
+                IllegalArgumentException e) {
+        }
+
+        return controller;
+    }
+}
diff --git a/tests/robotests/src/com/android/settings/deviceinfo/SystemUpdatePreferenceControllerTest.java b/tests/robotests/src/com/android/settings/deviceinfo/SystemUpdatePreferenceControllerTest.java
index 05670e2..1fd5430 100644
--- a/tests/robotests/src/com/android/settings/deviceinfo/SystemUpdatePreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/deviceinfo/SystemUpdatePreferenceControllerTest.java
@@ -57,7 +57,9 @@
     @Before
     public void setUp() {
         MockitoAnnotations.initMocks(this);
-        mController = new SystemUpdatePreferenceController(mContext, mUserManager);
+
+        when(mContext.getSystemService(Context.USER_SERVICE)).thenReturn(mUserManager);
+        mController = new SystemUpdatePreferenceController(mContext);
         mPreference = new Preference(RuntimeEnvironment.application);
         mPreference.setKey(mController.getPreferenceKey());
         when(mScreen.findPreference(mController.getPreferenceKey())).thenReturn(mPreference);
@@ -82,7 +84,7 @@
 
         mController.updateNonIndexableKeys(keys);
 
-        assertThat(keys.size()).isEqualTo(1);
+        assertThat(keys).hasSize(1);
     }
 
     @Test
@@ -94,8 +96,8 @@
 
     @Test
     public void updateState_shouldSetToAndroidVersion() {
-        mController = new SystemUpdatePreferenceController(
-                RuntimeEnvironment.application, mUserManager);
+        mController = new SystemUpdatePreferenceController(RuntimeEnvironment.application);
+
         mController.updateState(mPreference);
 
         assertThat(mPreference.getSummary())
diff --git a/tests/robotests/src/com/android/settings/search/XmlParserUtilTest.java b/tests/robotests/src/com/android/settings/search/XmlParserUtilTest.java
index 6050b32..2bec503 100644
--- a/tests/robotests/src/com/android/settings/search/XmlParserUtilTest.java
+++ b/tests/robotests/src/com/android/settings/search/XmlParserUtilTest.java
@@ -129,6 +129,16 @@
     }
 
     @Test
+    @Config(qualifiers = "mcc999")
+    public void testControllerAttribute_returnsValidData() {
+        XmlResourceParser parser = getChildByType(R.xml.about_legal, "Preference");
+        final AttributeSet attrs = Xml.asAttributeSet(parser);
+
+        String controller = XmlParserUtils.getController(mContext, attrs);
+        assertThat(controller).isEqualTo("mind_flayer");
+    }
+
+    @Test
     public void testDataSummaryInvalid_ReturnsNull() {
         XmlResourceParser parser = getParentPrimedParser(R.xml.display_settings);
         final AttributeSet attrs = Xml.asAttributeSet(parser);