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

Commit 42eecf88 authored by Tim Yu's avatar Tim Yu Committed by mse1969
Browse files

[RESTRICT AUTOMERGE] Fix Autofill Inflating as User 0

Autofill will inflate views as the current foreground user instead of
the system_server user (0).

Bug: 327137311
Test: atest CtsAutoFillServiceTestCases --user-type secondary_user
Flag: EXEMPT security bug fix
Cherrypick-From: https://googleplex-android-review.googlesource.com/q/commit:1cdf83b61b533b8174b4fae5b1bd15039751ed42
Merged-In: I8a2c96259976e61d297dec914d10d86e585a6d6f
Change-Id: I8a2c96259976e61d297dec914d10d86e585a6d6f
parent 619382be
Loading
Loading
Loading
Loading
+29 −0
Original line number Original line Diff line number Diff line
@@ -16,8 +16,13 @@


package com.android.server.autofill;
package com.android.server.autofill;


import static android.Manifest.permission.INTERACT_ACROSS_USERS;

import static com.android.server.autofill.Helper.sDebug;

import android.annotation.NonNull;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.annotation.Nullable;
import android.annotation.RequiresPermission;
import android.annotation.UserIdInt;
import android.annotation.UserIdInt;
import android.app.ActivityManager;
import android.app.ActivityManager;
import android.app.assist.AssistStructure;
import android.app.assist.AssistStructure;
@@ -26,8 +31,11 @@ import android.app.assist.AssistStructure.WindowNode;
import android.app.slice.Slice;
import android.app.slice.Slice;
import android.app.slice.SliceItem;
import android.app.slice.SliceItem;
import android.content.ComponentName;
import android.content.ComponentName;
import android.content.Context;
import android.graphics.drawable.Icon;
import android.graphics.drawable.Icon;
import android.metrics.LogMaker;
import android.metrics.LogMaker;
import android.os.UserHandle;
import android.os.UserManager;
import android.service.autofill.Dataset;
import android.service.autofill.Dataset;
import android.service.autofill.InternalSanitizer;
import android.service.autofill.InternalSanitizer;
import android.service.autofill.SaveInfo;
import android.service.autofill.SaveInfo;
@@ -41,6 +49,7 @@ import android.view.autofill.AutofillId;
import android.view.autofill.AutofillValue;
import android.view.autofill.AutofillValue;
import android.widget.RemoteViews;
import android.widget.RemoteViews;



import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import com.android.internal.util.ArrayUtils;
import com.android.internal.util.ArrayUtils;


@@ -95,6 +104,26 @@ public final class Helper {
        return permissionsOk.get();
        return permissionsOk.get();
    }
    }


    /**
     * Creates the context as the foreground user
     *
     * <p>Returns the current context as the current foreground user
     */
    @RequiresPermission(INTERACT_ACROSS_USERS)
    public static Context getUserContext(Context context) {
        int userId = ActivityManager.getCurrentUser();
        Context c = context.createContextAsUser(UserHandle.of(userId), /* flags= */ 0);
        if (sDebug) {
            Slog.d(
                    TAG,
                    "Current User: "
                            + userId
                            + ", context created as: "
                            + c.getContentResolver().getUserId());
        }
        return c;
    }

    /**
    /**
     * Checks the URI permissions of the remote view,
     * Checks the URI permissions of the remote view,
     * to see if the current userId is able to access it.
     * to see if the current userId is able to access it.
+7 −3
Original line number Original line Diff line number Diff line
@@ -93,6 +93,7 @@ final class DialogFillUi {
    private final ComponentName mComponentName;
    private final ComponentName mComponentName;
    private final int mThemeId;
    private final int mThemeId;
    private final @NonNull Context mContext;
    private final @NonNull Context mContext;
    private final @NonNull Context mUserContext;
    private final @NonNull UiCallback mCallback;
    private final @NonNull UiCallback mCallback;
    private final @NonNull ListView mListView;
    private final @NonNull ListView mListView;
    private final @Nullable ItemsAdapter mAdapter;
    private final @Nullable ItemsAdapter mAdapter;
@@ -102,6 +103,8 @@ final class DialogFillUi {
    private @Nullable AnnounceFilterResult mAnnounceFilterResult;
    private @Nullable AnnounceFilterResult mAnnounceFilterResult;
    private boolean mDestroyed;
    private boolean mDestroyed;


    // System has all permissions, see b/228957088
    @SuppressWarnings("AndroidFrameworkRequiresPermission")
    DialogFillUi(@NonNull Context context, @NonNull FillResponse response,
    DialogFillUi(@NonNull Context context, @NonNull FillResponse response,
            @NonNull AutofillId focusedViewId, @Nullable String filterText,
            @NonNull AutofillId focusedViewId, @Nullable String filterText,
            @Nullable Drawable serviceIcon, @Nullable String servicePackageName,
            @Nullable Drawable serviceIcon, @Nullable String servicePackageName,
@@ -115,6 +118,7 @@ final class DialogFillUi {
        mComponentName = componentName;
        mComponentName = componentName;


        mContext = new ContextThemeWrapper(context, mThemeId);
        mContext = new ContextThemeWrapper(context, mThemeId);
        mUserContext = Helper.getUserContext(mContext);
        final LayoutInflater inflater = LayoutInflater.from(mContext);
        final LayoutInflater inflater = LayoutInflater.from(mContext);
        final View decor = inflater.inflate(R.layout.autofill_fill_dialog, null);
        final View decor = inflater.inflate(R.layout.autofill_fill_dialog, null);


@@ -213,7 +217,7 @@ final class DialogFillUi {
        };
        };


        final View content = presentation.applyWithTheme(
        final View content = presentation.applyWithTheme(
                mContext, (ViewGroup) decor, interceptionHandler, mThemeId);
                mUserContext, (ViewGroup) decor, interceptionHandler, mThemeId);
        container.addView(content);
        container.addView(content);
        container.setVisibility(View.VISIBLE);
        container.setVisibility(View.VISIBLE);
    }
    }
@@ -252,7 +256,7 @@ final class DialogFillUi {
            return true;
            return true;
        };
        };
        final View content = presentation.applyWithTheme(
        final View content = presentation.applyWithTheme(
                mContext, (ViewGroup) decor, interceptionHandler, mThemeId);
                mUserContext, (ViewGroup) decor, interceptionHandler, mThemeId);
        container.addView(content);
        container.addView(content);
        container.setVisibility(View.VISIBLE);
        container.setVisibility(View.VISIBLE);
        container.setFocusable(true);
        container.setFocusable(true);
@@ -294,7 +298,7 @@ final class DialogFillUi {
                try {
                try {
                    if (sVerbose) Slog.v(TAG, "setting remote view for " + focusedViewId);
                    if (sVerbose) Slog.v(TAG, "setting remote view for " + focusedViewId);
                    view = presentation.applyWithTheme(
                    view = presentation.applyWithTheme(
                            mContext, null, interceptionHandler, mThemeId);
                            mUserContext, null, interceptionHandler, mThemeId);
                } catch (RuntimeException e) {
                } catch (RuntimeException e) {
                    Slog.e(TAG, "Error inflating remote views", e);
                    Slog.e(TAG, "Error inflating remote views", e);
                    continue;
                    continue;
+10 −4
Original line number Original line Diff line number Diff line
@@ -100,6 +100,7 @@ final class FillUi {
            new AutofillWindowPresenter();
            new AutofillWindowPresenter();


    private final @NonNull Context mContext;
    private final @NonNull Context mContext;
    private final @NonNull Context mUserContext;


    private final @NonNull AnchoredWindow mWindow;
    private final @NonNull AnchoredWindow mWindow;


@@ -132,6 +133,8 @@ final class FillUi {
        return context.getPackageManager().hasSystemFeature(PackageManager.FEATURE_LEANBACK);
        return context.getPackageManager().hasSystemFeature(PackageManager.FEATURE_LEANBACK);
    }
    }


    // System has all permissions, see b/228957088
    @SuppressWarnings("AndroidFrameworkRequiresPermission")
    FillUi(@NonNull Context context, @NonNull FillResponse response,
    FillUi(@NonNull Context context, @NonNull FillResponse response,
            @NonNull AutofillId focusedViewId, @Nullable String filterText,
            @NonNull AutofillId focusedViewId, @Nullable String filterText,
            @NonNull OverlayControl overlayControl, @NonNull CharSequence serviceLabel,
            @NonNull OverlayControl overlayControl, @NonNull CharSequence serviceLabel,
@@ -141,6 +144,7 @@ final class FillUi {
        mCallback = callback;
        mCallback = callback;
        mFullScreen = isFullScreen(context);
        mFullScreen = isFullScreen(context);
        mContext = new ContextThemeWrapper(context, mThemeId);
        mContext = new ContextThemeWrapper(context, mThemeId);
        mUserContext = Helper.getUserContext(mContext);


        final LayoutInflater inflater = LayoutInflater.from(mContext);
        final LayoutInflater inflater = LayoutInflater.from(mContext);


@@ -228,7 +232,7 @@ final class FillUi {
                    throw new RuntimeException("Permission error accessing RemoteView");
                    throw new RuntimeException("Permission error accessing RemoteView");
                }
                }
                content = response.getPresentation().applyWithTheme(
                content = response.getPresentation().applyWithTheme(
                        mContext, decor, interceptionHandler, mThemeId);
                        mUserContext, decor, interceptionHandler, mThemeId);
                container.addView(content);
                container.addView(content);
            } catch (RuntimeException e) {
            } catch (RuntimeException e) {
                callback.onCanceled();
                callback.onCanceled();
@@ -269,7 +273,7 @@ final class FillUi {
            if (headerPresentation != null) {
            if (headerPresentation != null) {
                interactionBlocker = newInteractionBlocker();
                interactionBlocker = newInteractionBlocker();
                mHeader = headerPresentation.applyWithTheme(
                mHeader = headerPresentation.applyWithTheme(
                        mContext, null, interactionBlocker, mThemeId);
                        mUserContext, null, interactionBlocker, mThemeId);
                final LinearLayout headerContainer =
                final LinearLayout headerContainer =
                        decor.findViewById(R.id.autofill_dataset_header);
                        decor.findViewById(R.id.autofill_dataset_header);
                applyCancelAction(mHeader, response.getCancelIds());
                applyCancelAction(mHeader, response.getCancelIds());
@@ -288,7 +292,7 @@ final class FillUi {
                        interactionBlocker = newInteractionBlocker();
                        interactionBlocker = newInteractionBlocker();
                    }
                    }
                    mFooter = footerPresentation.applyWithTheme(
                    mFooter = footerPresentation.applyWithTheme(
                            mContext, null, interactionBlocker, mThemeId);
                            mUserContext, null, interactionBlocker, mThemeId);
                    applyCancelAction(mFooter, response.getCancelIds());
                    applyCancelAction(mFooter, response.getCancelIds());
                    // Footer not supported on some platform e.g. TV
                    // Footer not supported on some platform e.g. TV
                    if (sVerbose) Slog.v(TAG, "adding footer");
                    if (sVerbose) Slog.v(TAG, "adding footer");
@@ -317,7 +321,7 @@ final class FillUi {
                    try {
                    try {
                        if (sVerbose) Slog.v(TAG, "setting remote view for " + focusedViewId);
                        if (sVerbose) Slog.v(TAG, "setting remote view for " + focusedViewId);
                        view = presentation.applyWithTheme(
                        view = presentation.applyWithTheme(
                                mContext, null, interceptionHandler, mThemeId);
                                mUserContext, null, interceptionHandler, mThemeId);
                    } catch (RuntimeException e) {
                    } catch (RuntimeException e) {
                        Slog.e(TAG, "Error inflating remote views", e);
                        Slog.e(TAG, "Error inflating remote views", e);
                        continue;
                        continue;
@@ -777,6 +781,8 @@ final class FillUi {
        pw.print(prefix); pw.print("mContentWidth: "); pw.println(mContentWidth);
        pw.print(prefix); pw.print("mContentWidth: "); pw.println(mContentWidth);
        pw.print(prefix); pw.print("mContentHeight: "); pw.println(mContentHeight);
        pw.print(prefix); pw.print("mContentHeight: "); pw.println(mContentHeight);
        pw.print(prefix); pw.print("mDestroyed: "); pw.println(mDestroyed);
        pw.print(prefix); pw.print("mDestroyed: "); pw.println(mDestroyed);
        pw.print(prefix); pw.print("mContext: "); pw.println(mContext);
        pw.print(prefix); pw.print("mUserContext: "); pw.println(mUserContext);
        pw.print(prefix); pw.print("theme id: "); pw.print(mThemeId);
        pw.print(prefix); pw.print("theme id: "); pw.print(mThemeId);
        switch (mThemeId) {
        switch (mThemeId) {
            case THEME_ID_DARK:
            case THEME_ID_DARK:
+4 −1
Original line number Original line Diff line number Diff line
@@ -172,6 +172,8 @@ final class SaveUi {


    private boolean mDestroyed;
    private boolean mDestroyed;


    // System has all permissions, see b/228957088
    @SuppressWarnings("AndroidFrameworkRequiresPermission")
    SaveUi(@NonNull Context context, @NonNull PendingUi pendingUi,
    SaveUi(@NonNull Context context, @NonNull PendingUi pendingUi,
           @NonNull CharSequence serviceLabel, @NonNull Drawable serviceIcon,
           @NonNull CharSequence serviceLabel, @NonNull Drawable serviceIcon,
           @Nullable String servicePackageName, @NonNull ComponentName componentName,
           @Nullable String servicePackageName, @NonNull ComponentName componentName,
@@ -187,7 +189,7 @@ final class SaveUi {
        mComponentName = componentName;
        mComponentName = componentName;
        mCompatMode = compatMode;
        mCompatMode = compatMode;


        context = new ContextThemeWrapper(context, mThemeId) {
        context = new ContextThemeWrapper(Helper.getUserContext(context), mThemeId) {
            @Override
            @Override
            public void startActivity(Intent intent) {
            public void startActivity(Intent intent) {
                if (resolveActivity(intent) == null) {
                if (resolveActivity(intent) == null) {
@@ -224,6 +226,7 @@ final class SaveUi {
                return null;
                return null;
            }
            }
        };
        };

        final LayoutInflater inflater = LayoutInflater.from(context);
        final LayoutInflater inflater = LayoutInflater.from(context);
        final View view = inflater.inflate(R.layout.autofill_save, null);
        final View view = inflater.inflate(R.layout.autofill_save, null);