Commit c36db6d4 authored by akirilov's avatar akirilov Committed by Atanas Kirilov

RESTRICT AUTOMERGE: Prevent reporting fake package name - framework (backport to oc-mr1-dev)

Test: added AccessibilityEndToEndTest#testPackageNameCannotBeFaked
      cts-tradefed run cts -m CtsAccessibilityServiceTestCases
      cts-tradefed run cts -m CtsAccessibilityTestCases

Bug: 69981755
Change-Id: If3752e106aa7fdee4645dc9852289af471ceff18
Merged-In: I13304efbee10d1affa087e9c8bc4ec237643283e
parent d7431f23
......@@ -35,23 +35,23 @@ interface IAccessibilityServiceConnection {
void setServiceInfo(in AccessibilityServiceInfo info);
boolean findAccessibilityNodeInfoByAccessibilityId(int accessibilityWindowId,
String[] findAccessibilityNodeInfoByAccessibilityId(int accessibilityWindowId,
long accessibilityNodeId, int interactionId,
IAccessibilityInteractionConnectionCallback callback, int flags, long threadId,
in Bundle arguments);
boolean findAccessibilityNodeInfosByText(int accessibilityWindowId, long accessibilityNodeId,
String[] findAccessibilityNodeInfosByText(int accessibilityWindowId, long accessibilityNodeId,
String text, int interactionId, IAccessibilityInteractionConnectionCallback callback,
long threadId);
boolean findAccessibilityNodeInfosByViewId(int accessibilityWindowId,
String[] findAccessibilityNodeInfosByViewId(int accessibilityWindowId,
long accessibilityNodeId, String viewId, int interactionId,
IAccessibilityInteractionConnectionCallback callback, long threadId);
boolean findFocus(int accessibilityWindowId, long accessibilityNodeId, int focusType,
String[] findFocus(int accessibilityWindowId, long accessibilityNodeId, int focusType,
int interactionId, IAccessibilityInteractionConnectionCallback callback, long threadId);
boolean focusSearch(int accessibilityWindowId, long accessibilityNodeId, int direction,
String[] focusSearch(int accessibilityWindowId, long accessibilityNodeId, int direction,
int interactionId, IAccessibilityInteractionConnectionCallback callback, long threadId);
boolean performAccessibilityAction(int accessibilityWindowId, long accessibilityNodeId,
......
/*
* Copyright (C) 2018 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 android.appwidget;
import android.annotation.Nullable;
import android.util.ArraySet;
/**
* App widget manager local system service interface.
*
* @hide Only for use within the system server.
*/
public abstract class AppWidgetManagerInternal {
/**
* Gets the packages from which the uid hosts widgets.
*
* @param uid The potential host UID.
* @return Whether the UID hosts widgets from the package.
*/
public abstract @Nullable ArraySet<String> getHostedWidgetPackages(int uid);
}
......@@ -7733,6 +7733,7 @@ public final class ViewRootImpl implements ViewParent,
if (!registered) {
mAttachInfo.mAccessibilityWindowId =
mAccessibilityManager.addAccessibilityInteractionConnection(mWindow,
mContext.getPackageName(),
new AccessibilityInteractionConnection(ViewRootImpl.this));
}
}
......
......@@ -28,6 +28,8 @@ import android.util.Log;
import android.util.LongSparseArray;
import android.util.SparseArray;
import com.android.internal.util.ArrayUtils;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
......@@ -283,14 +285,19 @@ public final class AccessibilityInteractionClient
}
final int interactionId = mInteractionIdCounter.getAndIncrement();
final long identityToken = Binder.clearCallingIdentity();
final boolean success = connection.findAccessibilityNodeInfoByAccessibilityId(
final String[] packageNames;
try {
packageNames = connection.findAccessibilityNodeInfoByAccessibilityId(
accessibilityWindowId, accessibilityNodeId, interactionId, this,
prefetchFlags, Thread.currentThread().getId(), arguments);
} finally {
Binder.restoreCallingIdentity(identityToken);
if (success) {
}
if (packageNames != null) {
List<AccessibilityNodeInfo> infos = getFindAccessibilityNodeInfosResultAndClear(
interactionId);
finalizeAndCacheAccessibilityNodeInfos(infos, connectionId);
finalizeAndCacheAccessibilityNodeInfos(infos, connectionId,
bypassCache, packageNames);
if (infos != null && !infos.isEmpty()) {
for (int i = 1; i < infos.size(); i++) {
infos.get(i).recycle();
......@@ -333,15 +340,21 @@ public final class AccessibilityInteractionClient
if (connection != null) {
final int interactionId = mInteractionIdCounter.getAndIncrement();
final long identityToken = Binder.clearCallingIdentity();
final boolean success = connection.findAccessibilityNodeInfosByViewId(
final String[] packageNames;
try {
packageNames = connection.findAccessibilityNodeInfosByViewId(
accessibilityWindowId, accessibilityNodeId, viewId, interactionId, this,
Thread.currentThread().getId());
} finally {
Binder.restoreCallingIdentity(identityToken);
if (success) {
}
if (packageNames != null) {
List<AccessibilityNodeInfo> infos = getFindAccessibilityNodeInfosResultAndClear(
interactionId);
if (infos != null) {
finalizeAndCacheAccessibilityNodeInfos(infos, connectionId);
finalizeAndCacheAccessibilityNodeInfos(infos, connectionId,
false, packageNames);
return infos;
}
}
......@@ -381,15 +394,21 @@ public final class AccessibilityInteractionClient
if (connection != null) {
final int interactionId = mInteractionIdCounter.getAndIncrement();
final long identityToken = Binder.clearCallingIdentity();
final boolean success = connection.findAccessibilityNodeInfosByText(
final String[] packageNames;
try {
packageNames = connection.findAccessibilityNodeInfosByText(
accessibilityWindowId, accessibilityNodeId, text, interactionId, this,
Thread.currentThread().getId());
} finally {
Binder.restoreCallingIdentity(identityToken);
if (success) {
}
if (packageNames != null) {
List<AccessibilityNodeInfo> infos = getFindAccessibilityNodeInfosResultAndClear(
interactionId);
if (infos != null) {
finalizeAndCacheAccessibilityNodeInfos(infos, connectionId);
finalizeAndCacheAccessibilityNodeInfos(infos, connectionId,
false, packageNames);
return infos;
}
}
......@@ -428,14 +447,19 @@ public final class AccessibilityInteractionClient
if (connection != null) {
final int interactionId = mInteractionIdCounter.getAndIncrement();
final long identityToken = Binder.clearCallingIdentity();
final boolean success = connection.findFocus(accessibilityWindowId,
final String[] packageNames;
try {
packageNames = connection.findFocus(accessibilityWindowId,
accessibilityNodeId, focusType, interactionId, this,
Thread.currentThread().getId());
} finally {
Binder.restoreCallingIdentity(identityToken);
if (success) {
}
if (packageNames != null) {
AccessibilityNodeInfo info = getFindAccessibilityNodeInfoResultAndClear(
interactionId);
finalizeAndCacheAccessibilityNodeInfo(info, connectionId);
finalizeAndCacheAccessibilityNodeInfo(info, connectionId, false, packageNames);
return info;
}
} else {
......@@ -472,14 +496,19 @@ public final class AccessibilityInteractionClient
if (connection != null) {
final int interactionId = mInteractionIdCounter.getAndIncrement();
final long identityToken = Binder.clearCallingIdentity();
final boolean success = connection.focusSearch(accessibilityWindowId,
final String[] packageNames;
try {
packageNames = connection.focusSearch(accessibilityWindowId,
accessibilityNodeId, direction, interactionId, this,
Thread.currentThread().getId());
} finally {
Binder.restoreCallingIdentity(identityToken);
if (success) {
}
if (packageNames != null) {
AccessibilityNodeInfo info = getFindAccessibilityNodeInfoResultAndClear(
interactionId);
finalizeAndCacheAccessibilityNodeInfo(info, connectionId);
finalizeAndCacheAccessibilityNodeInfo(info, connectionId, false, packageNames);
return info;
}
} else {
......@@ -580,7 +609,7 @@ public final class AccessibilityInteractionClient
int interactionId) {
synchronized (mInstanceLock) {
final boolean success = waitForResultTimedLocked(interactionId);
List<AccessibilityNodeInfo> result = null;
final List<AccessibilityNodeInfo> result;
if (success) {
result = mFindAccessibilityNodeInfosResult;
} else {
......@@ -696,29 +725,45 @@ public final class AccessibilityInteractionClient
*
* @param info The info.
* @param connectionId The id of the connection to the system.
* @param bypassCache Whether or not to bypass the cache. The node is added to the cache if
* this value is {@code false}
* @param packageNames The valid package names a node can come from.
*/
private void finalizeAndCacheAccessibilityNodeInfo(AccessibilityNodeInfo info,
int connectionId) {
int connectionId, boolean bypassCache, String[] packageNames) {
if (info != null) {
info.setConnectionId(connectionId);
// Empty array means any package name is Okay
if (!ArrayUtils.isEmpty(packageNames)
&& !ArrayUtils.contains(packageNames, info.getPackageName().toString())) {
// If the node package not one of the valid ones, pick the top one - this
// is one of the packages running in the introspected UID.
info.setPackageName(packageNames[0]);
}
info.setSealed(true);
if (!bypassCache) {
sAccessibilityCache.add(info);
}
}
}
/**
* Finalize {@link AccessibilityNodeInfo}s before passing them to the client.
*
* @param infos The {@link AccessibilityNodeInfo}s.
* @param connectionId The id of the connection to the system.
* @param bypassCache Whether or not to bypass the cache. The nodes are added to the cache if
* this value is {@code false}
* @param packageNames The valid package names a node can come from.
*/
private void finalizeAndCacheAccessibilityNodeInfos(List<AccessibilityNodeInfo> infos,
int connectionId) {
int connectionId, boolean bypassCache, String[] packageNames) {
if (infos != null) {
final int infosCount = infos.size();
for (int i = 0; i < infosCount; i++) {
AccessibilityNodeInfo info = infos.get(i);
finalizeAndCacheAccessibilityNodeInfo(info, connectionId);
finalizeAndCacheAccessibilityNodeInfo(info, connectionId,
bypassCache, packageNames);
}
}
}
......
......@@ -885,7 +885,7 @@ public final class AccessibilityManager {
* @hide
*/
public int addAccessibilityInteractionConnection(IWindow windowToken,
IAccessibilityInteractionConnection connection) {
String packageName, IAccessibilityInteractionConnection connection) {
final IAccessibilityManager service;
final int userId;
synchronized (mLock) {
......@@ -896,7 +896,8 @@ public final class AccessibilityManager {
userId = mUserId;
}
try {
return service.addAccessibilityInteractionConnection(windowToken, connection, userId);
return service.addAccessibilityInteractionConnection(windowToken, connection,
packageName, userId);
} catch (RemoteException re) {
Log.e(LOG_TAG, "Error while adding an accessibility interaction connection. ", re);
}
......
......@@ -45,7 +45,7 @@ interface IAccessibilityManager {
List<AccessibilityServiceInfo> getEnabledAccessibilityServiceList(int feedbackType, int userId);
int addAccessibilityInteractionConnection(IWindow windowToken,
in IAccessibilityInteractionConnection connection, int userId);
in IAccessibilityInteractionConnection connection, String packageName, int userId);
void removeAccessibilityInteractionConnection(IWindow windowToken);
......
......@@ -29,6 +29,7 @@ import android.app.PendingIntent;
import android.app.admin.DevicePolicyManagerInternal;
import android.app.admin.DevicePolicyManagerInternal.OnCrossProfileWidgetProvidersChangeListener;
import android.appwidget.AppWidgetManager;
import android.appwidget.AppWidgetManagerInternal;
import android.appwidget.AppWidgetProviderInfo;
import android.appwidget.PendingHostUpdate;
import android.content.BroadcastReceiver;
......@@ -99,6 +100,7 @@ import com.android.internal.appwidget.IAppWidgetService;
import com.android.internal.os.BackgroundThread;
import com.android.internal.os.SomeArgs;
import com.android.internal.util.DumpUtils;
import com.android.internal.util.ArrayUtils;
import com.android.internal.util.FastXmlSerializer;
import com.android.internal.widget.IRemoteViewsAdapterConnection;
import com.android.internal.widget.IRemoteViewsFactory;
......@@ -107,6 +109,7 @@ import com.android.server.WidgetBackupProvider;
import com.android.server.policy.IconUtilities;
import libcore.io.IoUtils;
import libcore.util.EmptyArray;
import org.xmlpull.v1.XmlPullParser;
import org.xmlpull.v1.XmlPullParserException;
......@@ -256,6 +259,8 @@ class AppWidgetServiceImpl extends IAppWidgetService.Stub implements WidgetBacku
computeMaximumWidgetBitmapMemory();
registerBroadcastReceiver();
registerOnCrossProfileProvidersChangedListener();
LocalServices.addService(AppWidgetManagerInternal.class, new AppWidgetManagerLocal());
}
private void computeMaximumWidgetBitmapMemory() {
......@@ -4709,4 +4714,24 @@ class AppWidgetServiceImpl extends IAppWidgetService.Stub implements WidgetBacku
}
}
}
private class AppWidgetManagerLocal extends AppWidgetManagerInternal {
@Override
public ArraySet<String> getHostedWidgetPackages(int uid) {
synchronized (mLock) {
ArraySet<String> widgetPackages = null;
final int widgetCount = mWidgets.size();
for (int i = 0; i < widgetCount; i++) {
final Widget widget = mWidgets.get(i);
if (widget.host.id.uid == uid) {
if (widgetPackages == null) {
widgetPackages = new ArraySet<>();
}
widgetPackages.add(widget.provider.id.componentName.getPackageName());
}
}
return widgetPackages;
}
}
}
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment