|
24 | 24 | import android.content.ComponentName; |
25 | 25 | import android.content.Context; |
26 | 26 | import android.content.Intent; |
27 | | -import android.content.ServiceConnection; |
28 | 27 | import android.content.Intent.FilterComparison; |
| 28 | +import android.content.ServiceConnection; |
29 | 29 | import android.content.pm.ActivityInfo; |
30 | 30 | import android.content.pm.ApplicationInfo; |
31 | 31 | import android.content.pm.IPackageManager; |
|
56 | 56 | import com.android.internal.util.FastXmlSerializer; |
57 | 57 | import com.android.internal.widget.IRemoteViewsAdapterConnection; |
58 | 58 | import com.android.internal.widget.IRemoteViewsFactory; |
59 | | -import com.android.server.am.ActivityManagerService; |
60 | 59 |
|
61 | 60 | import org.xmlpull.v1.XmlPullParser; |
62 | 61 | import org.xmlpull.v1.XmlPullParserException; |
@@ -167,6 +166,8 @@ public void disconnect() { |
167 | 166 | int mNextAppWidgetId = AppWidgetManager.INVALID_APPWIDGET_ID + 1; |
168 | 167 | final ArrayList<AppWidgetId> mAppWidgetIds = new ArrayList<AppWidgetId>(); |
169 | 168 | ArrayList<Host> mHosts = new ArrayList<Host>(); |
| 169 | + // set of package names |
| 170 | + HashSet<String> mPackagesWithBindWidgetPermission = new HashSet<String>(); |
170 | 171 | boolean mSafeMode; |
171 | 172 | int mUserId; |
172 | 173 | boolean mStateLoaded; |
@@ -493,10 +494,7 @@ void cancelBroadcasts(Provider p) { |
493 | 494 | } |
494 | 495 | } |
495 | 496 |
|
496 | | - public void bindAppWidgetId(int appWidgetId, ComponentName provider) { |
497 | | - mContext.enforceCallingPermission(android.Manifest.permission.BIND_APPWIDGET, |
498 | | - "bindGagetId appWidgetId=" + appWidgetId + " provider=" + provider); |
499 | | - |
| 497 | + private void bindAppWidgetIdImpl(int appWidgetId, ComponentName provider) { |
500 | 498 | final long ident = Binder.clearCallingIdentity(); |
501 | 499 | try { |
502 | 500 | synchronized (mAppWidgetIds) { |
@@ -541,6 +539,67 @@ public void bindAppWidgetId(int appWidgetId, ComponentName provider) { |
541 | 539 | } |
542 | 540 | } |
543 | 541 |
|
| 542 | + public void bindAppWidgetId(int appWidgetId, ComponentName provider) { |
| 543 | + mContext.enforceCallingPermission(android.Manifest.permission.BIND_APPWIDGET, |
| 544 | + "bindAppWidgetId appWidgetId=" + appWidgetId + " provider=" + provider); |
| 545 | + bindAppWidgetIdImpl(appWidgetId, provider); |
| 546 | + } |
| 547 | + |
| 548 | + public boolean bindAppWidgetIdIfAllowed( |
| 549 | + String packageName, int appWidgetId, ComponentName provider) { |
| 550 | + try { |
| 551 | + mContext.enforceCallingPermission(android.Manifest.permission.BIND_APPWIDGET, null); |
| 552 | + } catch (SecurityException se) { |
| 553 | + if (!callerHasBindAppWidgetPermission(packageName)) { |
| 554 | + return false; |
| 555 | + } |
| 556 | + } |
| 557 | + bindAppWidgetIdImpl(appWidgetId, provider); |
| 558 | + return true; |
| 559 | + } |
| 560 | + |
| 561 | + private boolean callerHasBindAppWidgetPermission(String packageName) { |
| 562 | + int callingUid = Binder.getCallingUid(); |
| 563 | + try { |
| 564 | + if (!UserId.isSameApp(callingUid, getUidForPackage(packageName))) { |
| 565 | + return false; |
| 566 | + } |
| 567 | + } catch (Exception e) { |
| 568 | + return false; |
| 569 | + } |
| 570 | + synchronized (mAppWidgetIds) { |
| 571 | + ensureStateLoadedLocked(); |
| 572 | + return mPackagesWithBindWidgetPermission.contains(packageName); |
| 573 | + } |
| 574 | + } |
| 575 | + |
| 576 | + public boolean hasBindAppWidgetPermission(String packageName) { |
| 577 | + mContext.enforceCallingPermission( |
| 578 | + android.Manifest.permission.MODIFY_APPWIDGET_BIND_PERMISSIONS, |
| 579 | + "hasBindAppWidgetPermission packageName=" + packageName); |
| 580 | + |
| 581 | + synchronized (mAppWidgetIds) { |
| 582 | + ensureStateLoadedLocked(); |
| 583 | + return mPackagesWithBindWidgetPermission.contains(packageName); |
| 584 | + } |
| 585 | + } |
| 586 | + |
| 587 | + public void setBindAppWidgetPermission(String packageName, boolean permission) { |
| 588 | + mContext.enforceCallingPermission( |
| 589 | + android.Manifest.permission.MODIFY_APPWIDGET_BIND_PERMISSIONS, |
| 590 | + "setBindAppWidgetPermission packageName=" + packageName); |
| 591 | + |
| 592 | + synchronized (mAppWidgetIds) { |
| 593 | + ensureStateLoadedLocked(); |
| 594 | + if (permission) { |
| 595 | + mPackagesWithBindWidgetPermission.add(packageName); |
| 596 | + } else { |
| 597 | + mPackagesWithBindWidgetPermission.remove(packageName); |
| 598 | + } |
| 599 | + } |
| 600 | + saveStateLocked(); |
| 601 | + } |
| 602 | + |
544 | 603 | // Binds to a specific RemoteViewsService |
545 | 604 | public void bindRemoteViewsService(int appWidgetId, Intent intent, IBinder connection) { |
546 | 605 | synchronized (mAppWidgetIds) { |
@@ -1375,6 +1434,13 @@ boolean writeStateToFileLocked(FileOutputStream stream) { |
1375 | 1434 | out.endTag(null, "g"); |
1376 | 1435 | } |
1377 | 1436 |
|
| 1437 | + Iterator<String> it = mPackagesWithBindWidgetPermission.iterator(); |
| 1438 | + while (it.hasNext()) { |
| 1439 | + out.startTag(null, "b"); |
| 1440 | + out.attribute(null, "packageName", it.next()); |
| 1441 | + out.endTag(null, "b"); |
| 1442 | + } |
| 1443 | + |
1378 | 1444 | out.endTag(null, "gs"); |
1379 | 1445 |
|
1380 | 1446 | out.endDocument(); |
@@ -1445,6 +1511,11 @@ void readStateFromFileLocked(FileInputStream stream) { |
1445 | 1511 | .parseInt(parser.getAttributeValue(null, "id"), 16); |
1446 | 1512 | mHosts.add(host); |
1447 | 1513 | } |
| 1514 | + } else if ("b".equals(tag)) { |
| 1515 | + String packageName = parser.getAttributeValue(null, "packageName"); |
| 1516 | + if (packageName != null) { |
| 1517 | + mPackagesWithBindWidgetPermission.add(packageName); |
| 1518 | + } |
1448 | 1519 | } else if ("g".equals(tag)) { |
1449 | 1520 | AppWidgetId id = new AppWidgetId(); |
1450 | 1521 | id.appWidgetId = Integer.parseInt(parser.getAttributeValue(null, "id"), 16); |
|
0 commit comments