ContextImpl.java revision 07330791116513710d879c45b2f095cd314cbfd0
1/* 2 * Copyright (C) 2006 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package android.app; 18 19import com.android.internal.policy.PolicyManager; 20import com.android.internal.util.XmlUtils; 21import com.google.android.collect.Maps; 22 23import org.xmlpull.v1.XmlPullParserException; 24 25import android.content.BroadcastReceiver; 26import android.content.ComponentName; 27import android.content.ContentResolver; 28import android.content.Context; 29import android.content.ContextWrapper; 30import android.content.IContentProvider; 31import android.content.Intent; 32import android.content.IntentFilter; 33import android.content.IIntentReceiver; 34import android.content.IntentSender; 35import android.content.ReceiverCallNotAllowedException; 36import android.content.ServiceConnection; 37import android.content.SharedPreferences; 38import android.content.pm.ActivityInfo; 39import android.content.pm.ApplicationInfo; 40import android.content.pm.ComponentInfo; 41import android.content.pm.FeatureInfo; 42import android.content.pm.IPackageDataObserver; 43import android.content.pm.IPackageDeleteObserver; 44import android.content.pm.IPackageInstallObserver; 45import android.content.pm.IPackageMoveObserver; 46import android.content.pm.IPackageManager; 47import android.content.pm.IPackageStatsObserver; 48import android.content.pm.InstrumentationInfo; 49import android.content.pm.PackageInfo; 50import android.content.pm.PackageManager; 51import android.content.pm.PermissionGroupInfo; 52import android.content.pm.PermissionInfo; 53import android.content.pm.ProviderInfo; 54import android.content.pm.ResolveInfo; 55import android.content.pm.ServiceInfo; 56import android.content.pm.PackageParser.Package; 57import android.content.res.AssetManager; 58import android.content.res.Resources; 59import android.content.res.XmlResourceParser; 60import android.database.sqlite.SQLiteDatabase; 61import android.database.sqlite.SQLiteDatabase.CursorFactory; 62import android.graphics.Bitmap; 63import android.graphics.drawable.Drawable; 64import android.hardware.SensorManager; 65import android.location.ILocationManager; 66import android.location.LocationManager; 67import android.media.AudioManager; 68import android.net.ConnectivityManager; 69import android.net.IConnectivityManager; 70import android.net.Uri; 71import android.net.wifi.IWifiManager; 72import android.net.wifi.WifiManager; 73import android.os.Binder; 74import android.os.Bundle; 75import android.os.DropBoxManager; 76import android.os.Environment; 77import android.os.FileUtils; 78import android.os.Handler; 79import android.os.IBinder; 80import android.os.IPowerManager; 81import android.os.Looper; 82import android.os.PowerManager; 83import android.os.Process; 84import android.os.RemoteException; 85import android.os.ServiceManager; 86import android.os.StatFs; 87import android.os.Vibrator; 88import android.os.FileUtils.FileStatus; 89import android.os.storage.StorageManager; 90import android.provider.Settings; 91import android.telephony.TelephonyManager; 92import android.text.ClipboardManager; 93import android.util.AndroidRuntimeException; 94import android.util.Log; 95import android.view.ContextThemeWrapper; 96import android.view.LayoutInflater; 97import android.view.WindowManagerImpl; 98import android.view.accessibility.AccessibilityManager; 99import android.view.inputmethod.InputMethodManager; 100import android.accounts.AccountManager; 101import android.accounts.IAccountManager; 102import android.app.admin.DevicePolicyManager; 103 104import com.android.internal.os.IDropBoxManagerService; 105 106import java.io.File; 107import java.io.FileInputStream; 108import java.io.FileNotFoundException; 109import java.io.FileOutputStream; 110import java.io.IOException; 111import java.io.InputStream; 112import java.lang.ref.WeakReference; 113import java.util.ArrayList; 114import java.util.HashMap; 115import java.util.HashSet; 116import java.util.Iterator; 117import java.util.List; 118import java.util.Map; 119import java.util.Set; 120import java.util.WeakHashMap; 121import java.util.Map.Entry; 122 123class ReceiverRestrictedContext extends ContextWrapper { 124 ReceiverRestrictedContext(Context base) { 125 super(base); 126 } 127 128 @Override 129 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter) { 130 return registerReceiver(receiver, filter, null, null); 131 } 132 133 @Override 134 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter, 135 String broadcastPermission, Handler scheduler) { 136 throw new ReceiverCallNotAllowedException( 137 "IntentReceiver components are not allowed to register to receive intents"); 138 //ex.fillInStackTrace(); 139 //Log.e("IntentReceiver", ex.getMessage(), ex); 140 //return mContext.registerReceiver(receiver, filter, broadcastPermission, 141 // scheduler); 142 } 143 144 @Override 145 public boolean bindService(Intent service, ServiceConnection conn, int flags) { 146 throw new ReceiverCallNotAllowedException( 147 "IntentReceiver components are not allowed to bind to services"); 148 //ex.fillInStackTrace(); 149 //Log.e("IntentReceiver", ex.getMessage(), ex); 150 //return mContext.bindService(service, interfaceName, conn, flags); 151 } 152} 153 154/** 155 * Common implementation of Context API, which provides the base 156 * context object for Activity and other application components. 157 */ 158class ContextImpl extends Context { 159 private final static String TAG = "ApplicationContext"; 160 private final static boolean DEBUG = false; 161 private final static boolean DEBUG_ICONS = false; 162 163 private static final Object sSync = new Object(); 164 private static AlarmManager sAlarmManager; 165 private static PowerManager sPowerManager; 166 private static ConnectivityManager sConnectivityManager; 167 private static WifiManager sWifiManager; 168 private static LocationManager sLocationManager; 169 private static final HashMap<File, SharedPreferencesImpl> sSharedPrefs = 170 new HashMap<File, SharedPreferencesImpl>(); 171 172 private AudioManager mAudioManager; 173 /*package*/ ActivityThread.PackageInfo mPackageInfo; 174 private Resources mResources; 175 /*package*/ ActivityThread mMainThread; 176 private Context mOuterContext; 177 private IBinder mActivityToken = null; 178 private ApplicationContentResolver mContentResolver; 179 private int mThemeResource = 0; 180 private Resources.Theme mTheme = null; 181 private PackageManager mPackageManager; 182 private NotificationManager mNotificationManager = null; 183 private ActivityManager mActivityManager = null; 184 private WallpaperManager mWallpaperManager = null; 185 private Context mReceiverRestrictedContext = null; 186 private SearchManager mSearchManager = null; 187 private SensorManager mSensorManager = null; 188 private StorageManager mStorageManager = null; 189 private Vibrator mVibrator = null; 190 private LayoutInflater mLayoutInflater = null; 191 private StatusBarManager mStatusBarManager = null; 192 private TelephonyManager mTelephonyManager = null; 193 private ClipboardManager mClipboardManager = null; 194 private boolean mRestricted; 195 private AccountManager mAccountManager; // protected by mSync 196 private DropBoxManager mDropBoxManager = null; 197 private DevicePolicyManager mDevicePolicyManager = null; 198 private UiModeManager mUiModeManager = null; 199 200 private final Object mSync = new Object(); 201 202 private File mDatabasesDir; 203 private File mPreferencesDir; 204 private File mFilesDir; 205 private File mCacheDir; 206 private File mExternalFilesDir; 207 private File mExternalCacheDir; 208 209 private static long sInstanceCount = 0; 210 211 private static final String[] EMPTY_FILE_LIST = {}; 212 213 // For debug only 214 /* 215 @Override 216 protected void finalize() throws Throwable { 217 super.finalize(); 218 --sInstanceCount; 219 } 220 */ 221 222 public static long getInstanceCount() { 223 return sInstanceCount; 224 } 225 226 @Override 227 public AssetManager getAssets() { 228 return mResources.getAssets(); 229 } 230 231 @Override 232 public Resources getResources() { 233 return mResources; 234 } 235 236 @Override 237 public PackageManager getPackageManager() { 238 if (mPackageManager != null) { 239 return mPackageManager; 240 } 241 242 IPackageManager pm = ActivityThread.getPackageManager(); 243 if (pm != null) { 244 // Doesn't matter if we make more than one instance. 245 return (mPackageManager = new ApplicationPackageManager(this, pm)); 246 } 247 248 return null; 249 } 250 251 @Override 252 public ContentResolver getContentResolver() { 253 return mContentResolver; 254 } 255 256 @Override 257 public Looper getMainLooper() { 258 return mMainThread.getLooper(); 259 } 260 261 @Override 262 public Context getApplicationContext() { 263 return (mPackageInfo != null) ? 264 mPackageInfo.getApplication() : mMainThread.getApplication(); 265 } 266 267 @Override 268 public void setTheme(int resid) { 269 mThemeResource = resid; 270 } 271 272 @Override 273 public Resources.Theme getTheme() { 274 if (mTheme == null) { 275 if (mThemeResource == 0) { 276 mThemeResource = com.android.internal.R.style.Theme; 277 } 278 mTheme = mResources.newTheme(); 279 mTheme.applyStyle(mThemeResource, true); 280 } 281 return mTheme; 282 } 283 284 @Override 285 public ClassLoader getClassLoader() { 286 return mPackageInfo != null ? 287 mPackageInfo.getClassLoader() : ClassLoader.getSystemClassLoader(); 288 } 289 290 @Override 291 public String getPackageName() { 292 if (mPackageInfo != null) { 293 return mPackageInfo.getPackageName(); 294 } 295 throw new RuntimeException("Not supported in system context"); 296 } 297 298 @Override 299 public ApplicationInfo getApplicationInfo() { 300 if (mPackageInfo != null) { 301 return mPackageInfo.getApplicationInfo(); 302 } 303 throw new RuntimeException("Not supported in system context"); 304 } 305 306 @Override 307 public String getPackageResourcePath() { 308 if (mPackageInfo != null) { 309 return mPackageInfo.getResDir(); 310 } 311 throw new RuntimeException("Not supported in system context"); 312 } 313 314 @Override 315 public String getPackageCodePath() { 316 if (mPackageInfo != null) { 317 return mPackageInfo.getAppDir(); 318 } 319 throw new RuntimeException("Not supported in system context"); 320 } 321 322 private static File makeBackupFile(File prefsFile) { 323 return new File(prefsFile.getPath() + ".bak"); 324 } 325 326 public File getSharedPrefsFile(String name) { 327 return makeFilename(getPreferencesDir(), name + ".xml"); 328 } 329 330 @Override 331 public SharedPreferences getSharedPreferences(String name, int mode) { 332 SharedPreferencesImpl sp; 333 File f = getSharedPrefsFile(name); 334 synchronized (sSharedPrefs) { 335 sp = sSharedPrefs.get(f); 336 if (sp != null && !sp.hasFileChanged()) { 337 //Log.i(TAG, "Returning existing prefs " + name + ": " + sp); 338 return sp; 339 } 340 } 341 342 FileInputStream str = null; 343 File backup = makeBackupFile(f); 344 if (backup.exists()) { 345 f.delete(); 346 backup.renameTo(f); 347 } 348 349 // Debugging 350 if (f.exists() && !f.canRead()) { 351 Log.w(TAG, "Attempt to read preferences file " + f + " without permission"); 352 } 353 354 Map map = null; 355 if (f.exists() && f.canRead()) { 356 try { 357 str = new FileInputStream(f); 358 map = XmlUtils.readMapXml(str); 359 str.close(); 360 } catch (org.xmlpull.v1.XmlPullParserException e) { 361 Log.w(TAG, "getSharedPreferences", e); 362 } catch (FileNotFoundException e) { 363 Log.w(TAG, "getSharedPreferences", e); 364 } catch (IOException e) { 365 Log.w(TAG, "getSharedPreferences", e); 366 } 367 } 368 369 synchronized (sSharedPrefs) { 370 if (sp != null) { 371 //Log.i(TAG, "Updating existing prefs " + name + " " + sp + ": " + map); 372 sp.replace(map); 373 } else { 374 sp = sSharedPrefs.get(f); 375 if (sp == null) { 376 sp = new SharedPreferencesImpl(f, mode, map); 377 sSharedPrefs.put(f, sp); 378 } 379 } 380 return sp; 381 } 382 } 383 384 private File getPreferencesDir() { 385 synchronized (mSync) { 386 if (mPreferencesDir == null) { 387 mPreferencesDir = new File(getDataDirFile(), "shared_prefs"); 388 } 389 return mPreferencesDir; 390 } 391 } 392 393 @Override 394 public FileInputStream openFileInput(String name) 395 throws FileNotFoundException { 396 File f = makeFilename(getFilesDir(), name); 397 return new FileInputStream(f); 398 } 399 400 @Override 401 public FileOutputStream openFileOutput(String name, int mode) 402 throws FileNotFoundException { 403 final boolean append = (mode&MODE_APPEND) != 0; 404 File f = makeFilename(getFilesDir(), name); 405 try { 406 FileOutputStream fos = new FileOutputStream(f, append); 407 setFilePermissionsFromMode(f.getPath(), mode, 0); 408 return fos; 409 } catch (FileNotFoundException e) { 410 } 411 412 File parent = f.getParentFile(); 413 parent.mkdir(); 414 FileUtils.setPermissions( 415 parent.getPath(), 416 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH, 417 -1, -1); 418 FileOutputStream fos = new FileOutputStream(f, append); 419 setFilePermissionsFromMode(f.getPath(), mode, 0); 420 return fos; 421 } 422 423 @Override 424 public boolean deleteFile(String name) { 425 File f = makeFilename(getFilesDir(), name); 426 return f.delete(); 427 } 428 429 @Override 430 public File getFilesDir() { 431 synchronized (mSync) { 432 if (mFilesDir == null) { 433 mFilesDir = new File(getDataDirFile(), "files"); 434 } 435 if (!mFilesDir.exists()) { 436 if(!mFilesDir.mkdirs()) { 437 Log.w(TAG, "Unable to create files directory"); 438 return null; 439 } 440 FileUtils.setPermissions( 441 mFilesDir.getPath(), 442 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH, 443 -1, -1); 444 } 445 return mFilesDir; 446 } 447 } 448 449 @Override 450 public File getExternalFilesDir(String type) { 451 synchronized (mSync) { 452 if (mExternalFilesDir == null) { 453 mExternalFilesDir = Environment.getExternalStorageAppFilesDirectory( 454 getPackageName()); 455 } 456 if (!mExternalFilesDir.exists()) { 457 try { 458 (new File(Environment.getExternalStorageAndroidDataDir(), 459 ".nomedia")).createNewFile(); 460 } catch (IOException e) { 461 } 462 if (!mExternalFilesDir.mkdirs()) { 463 Log.w(TAG, "Unable to create external files directory"); 464 return null; 465 } 466 } 467 if (type == null) { 468 return mExternalFilesDir; 469 } 470 File dir = new File(mExternalFilesDir, type); 471 if (!dir.exists()) { 472 if (!dir.mkdirs()) { 473 Log.w(TAG, "Unable to create external media directory " + dir); 474 return null; 475 } 476 } 477 return dir; 478 } 479 } 480 481 @Override 482 public File getCacheDir() { 483 synchronized (mSync) { 484 if (mCacheDir == null) { 485 mCacheDir = new File(getDataDirFile(), "cache"); 486 } 487 if (!mCacheDir.exists()) { 488 if(!mCacheDir.mkdirs()) { 489 Log.w(TAG, "Unable to create cache directory"); 490 return null; 491 } 492 FileUtils.setPermissions( 493 mCacheDir.getPath(), 494 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH, 495 -1, -1); 496 } 497 } 498 return mCacheDir; 499 } 500 501 @Override 502 public File getExternalCacheDir() { 503 synchronized (mSync) { 504 if (mExternalCacheDir == null) { 505 mExternalCacheDir = Environment.getExternalStorageAppCacheDirectory( 506 getPackageName()); 507 } 508 if (!mExternalCacheDir.exists()) { 509 try { 510 (new File(Environment.getExternalStorageAndroidDataDir(), 511 ".nomedia")).createNewFile(); 512 } catch (IOException e) { 513 } 514 if (!mExternalCacheDir.mkdirs()) { 515 Log.w(TAG, "Unable to create external cache directory"); 516 return null; 517 } 518 } 519 return mExternalCacheDir; 520 } 521 } 522 523 @Override 524 public File getFileStreamPath(String name) { 525 return makeFilename(getFilesDir(), name); 526 } 527 528 @Override 529 public String[] fileList() { 530 final String[] list = getFilesDir().list(); 531 return (list != null) ? list : EMPTY_FILE_LIST; 532 } 533 534 @Override 535 public SQLiteDatabase openOrCreateDatabase(String name, int mode, CursorFactory factory) { 536 File f = validateFilePath(name, true); 537 SQLiteDatabase db = SQLiteDatabase.openOrCreateDatabase(f, factory); 538 setFilePermissionsFromMode(f.getPath(), mode, 0); 539 return db; 540 } 541 542 @Override 543 public boolean deleteDatabase(String name) { 544 try { 545 File f = validateFilePath(name, false); 546 return f.delete(); 547 } catch (Exception e) { 548 } 549 return false; 550 } 551 552 @Override 553 public File getDatabasePath(String name) { 554 return validateFilePath(name, false); 555 } 556 557 @Override 558 public String[] databaseList() { 559 final String[] list = getDatabasesDir().list(); 560 return (list != null) ? list : EMPTY_FILE_LIST; 561 } 562 563 564 private File getDatabasesDir() { 565 synchronized (mSync) { 566 if (mDatabasesDir == null) { 567 mDatabasesDir = new File(getDataDirFile(), "databases"); 568 } 569 if (mDatabasesDir.getPath().equals("databases")) { 570 mDatabasesDir = new File("/data/system"); 571 } 572 return mDatabasesDir; 573 } 574 } 575 576 @Override 577 public Drawable getWallpaper() { 578 return getWallpaperManager().getDrawable(); 579 } 580 581 @Override 582 public Drawable peekWallpaper() { 583 return getWallpaperManager().peekDrawable(); 584 } 585 586 @Override 587 public int getWallpaperDesiredMinimumWidth() { 588 return getWallpaperManager().getDesiredMinimumWidth(); 589 } 590 591 @Override 592 public int getWallpaperDesiredMinimumHeight() { 593 return getWallpaperManager().getDesiredMinimumHeight(); 594 } 595 596 @Override 597 public void setWallpaper(Bitmap bitmap) throws IOException { 598 getWallpaperManager().setBitmap(bitmap); 599 } 600 601 @Override 602 public void setWallpaper(InputStream data) throws IOException { 603 getWallpaperManager().setStream(data); 604 } 605 606 @Override 607 public void clearWallpaper() throws IOException { 608 getWallpaperManager().clear(); 609 } 610 611 @Override 612 public void startActivity(Intent intent) { 613 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_TASK) == 0) { 614 throw new AndroidRuntimeException( 615 "Calling startActivity() from outside of an Activity " 616 + " context requires the FLAG_ACTIVITY_NEW_TASK flag." 617 + " Is this really what you want?"); 618 } 619 mMainThread.getInstrumentation().execStartActivity( 620 getOuterContext(), mMainThread.getApplicationThread(), null, null, intent, -1); 621 } 622 623 @Override 624 public void startIntentSender(IntentSender intent, 625 Intent fillInIntent, int flagsMask, int flagsValues, int extraFlags) 626 throws IntentSender.SendIntentException { 627 try { 628 String resolvedType = null; 629 if (fillInIntent != null) { 630 resolvedType = fillInIntent.resolveTypeIfNeeded(getContentResolver()); 631 } 632 int result = ActivityManagerNative.getDefault() 633 .startActivityIntentSender(mMainThread.getApplicationThread(), intent, 634 fillInIntent, resolvedType, null, null, 635 0, flagsMask, flagsValues); 636 if (result == IActivityManager.START_CANCELED) { 637 throw new IntentSender.SendIntentException(); 638 } 639 Instrumentation.checkStartActivityResult(result, null); 640 } catch (RemoteException e) { 641 } 642 } 643 644 @Override 645 public void sendBroadcast(Intent intent) { 646 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 647 try { 648 ActivityManagerNative.getDefault().broadcastIntent( 649 mMainThread.getApplicationThread(), intent, resolvedType, null, 650 Activity.RESULT_OK, null, null, null, false, false); 651 } catch (RemoteException e) { 652 } 653 } 654 655 @Override 656 public void sendBroadcast(Intent intent, String receiverPermission) { 657 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 658 try { 659 ActivityManagerNative.getDefault().broadcastIntent( 660 mMainThread.getApplicationThread(), intent, resolvedType, null, 661 Activity.RESULT_OK, null, null, receiverPermission, false, false); 662 } catch (RemoteException e) { 663 } 664 } 665 666 @Override 667 public void sendOrderedBroadcast(Intent intent, 668 String receiverPermission) { 669 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 670 try { 671 ActivityManagerNative.getDefault().broadcastIntent( 672 mMainThread.getApplicationThread(), intent, resolvedType, null, 673 Activity.RESULT_OK, null, null, receiverPermission, true, false); 674 } catch (RemoteException e) { 675 } 676 } 677 678 @Override 679 public void sendOrderedBroadcast(Intent intent, 680 String receiverPermission, BroadcastReceiver resultReceiver, 681 Handler scheduler, int initialCode, String initialData, 682 Bundle initialExtras) { 683 IIntentReceiver rd = null; 684 if (resultReceiver != null) { 685 if (mPackageInfo != null) { 686 if (scheduler == null) { 687 scheduler = mMainThread.getHandler(); 688 } 689 rd = mPackageInfo.getReceiverDispatcher( 690 resultReceiver, getOuterContext(), scheduler, 691 mMainThread.getInstrumentation(), false); 692 } else { 693 if (scheduler == null) { 694 scheduler = mMainThread.getHandler(); 695 } 696 rd = new ActivityThread.PackageInfo.ReceiverDispatcher( 697 resultReceiver, getOuterContext(), scheduler, null, false).getIIntentReceiver(); 698 } 699 } 700 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 701 try { 702 ActivityManagerNative.getDefault().broadcastIntent( 703 mMainThread.getApplicationThread(), intent, resolvedType, rd, 704 initialCode, initialData, initialExtras, receiverPermission, 705 true, false); 706 } catch (RemoteException e) { 707 } 708 } 709 710 @Override 711 public void sendStickyBroadcast(Intent intent) { 712 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 713 try { 714 ActivityManagerNative.getDefault().broadcastIntent( 715 mMainThread.getApplicationThread(), intent, resolvedType, null, 716 Activity.RESULT_OK, null, null, null, false, true); 717 } catch (RemoteException e) { 718 } 719 } 720 721 @Override 722 public void sendStickyOrderedBroadcast(Intent intent, 723 BroadcastReceiver resultReceiver, 724 Handler scheduler, int initialCode, String initialData, 725 Bundle initialExtras) { 726 IIntentReceiver rd = null; 727 if (resultReceiver != null) { 728 if (mPackageInfo != null) { 729 if (scheduler == null) { 730 scheduler = mMainThread.getHandler(); 731 } 732 rd = mPackageInfo.getReceiverDispatcher( 733 resultReceiver, getOuterContext(), scheduler, 734 mMainThread.getInstrumentation(), false); 735 } else { 736 if (scheduler == null) { 737 scheduler = mMainThread.getHandler(); 738 } 739 rd = new ActivityThread.PackageInfo.ReceiverDispatcher( 740 resultReceiver, getOuterContext(), scheduler, null, false).getIIntentReceiver(); 741 } 742 } 743 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 744 try { 745 ActivityManagerNative.getDefault().broadcastIntent( 746 mMainThread.getApplicationThread(), intent, resolvedType, rd, 747 initialCode, initialData, initialExtras, null, 748 true, true); 749 } catch (RemoteException e) { 750 } 751 } 752 753 @Override 754 public void removeStickyBroadcast(Intent intent) { 755 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 756 if (resolvedType != null) { 757 intent = new Intent(intent); 758 intent.setDataAndType(intent.getData(), resolvedType); 759 } 760 try { 761 ActivityManagerNative.getDefault().unbroadcastIntent( 762 mMainThread.getApplicationThread(), intent); 763 } catch (RemoteException e) { 764 } 765 } 766 767 @Override 768 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter) { 769 return registerReceiver(receiver, filter, null, null); 770 } 771 772 @Override 773 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter, 774 String broadcastPermission, Handler scheduler) { 775 return registerReceiverInternal(receiver, filter, broadcastPermission, 776 scheduler, getOuterContext()); 777 } 778 779 private Intent registerReceiverInternal(BroadcastReceiver receiver, 780 IntentFilter filter, String broadcastPermission, 781 Handler scheduler, Context context) { 782 IIntentReceiver rd = null; 783 if (receiver != null) { 784 if (mPackageInfo != null && context != null) { 785 if (scheduler == null) { 786 scheduler = mMainThread.getHandler(); 787 } 788 rd = mPackageInfo.getReceiverDispatcher( 789 receiver, context, scheduler, 790 mMainThread.getInstrumentation(), true); 791 } else { 792 if (scheduler == null) { 793 scheduler = mMainThread.getHandler(); 794 } 795 rd = new ActivityThread.PackageInfo.ReceiverDispatcher( 796 receiver, context, scheduler, null, false).getIIntentReceiver(); 797 } 798 } 799 try { 800 return ActivityManagerNative.getDefault().registerReceiver( 801 mMainThread.getApplicationThread(), 802 rd, filter, broadcastPermission); 803 } catch (RemoteException e) { 804 return null; 805 } 806 } 807 808 @Override 809 public void unregisterReceiver(BroadcastReceiver receiver) { 810 if (mPackageInfo != null) { 811 IIntentReceiver rd = mPackageInfo.forgetReceiverDispatcher( 812 getOuterContext(), receiver); 813 try { 814 ActivityManagerNative.getDefault().unregisterReceiver(rd); 815 } catch (RemoteException e) { 816 } 817 } else { 818 throw new RuntimeException("Not supported in system context"); 819 } 820 } 821 822 @Override 823 public ComponentName startService(Intent service) { 824 try { 825 ComponentName cn = ActivityManagerNative.getDefault().startService( 826 mMainThread.getApplicationThread(), service, 827 service.resolveTypeIfNeeded(getContentResolver())); 828 if (cn != null && cn.getPackageName().equals("!")) { 829 throw new SecurityException( 830 "Not allowed to start service " + service 831 + " without permission " + cn.getClassName()); 832 } 833 return cn; 834 } catch (RemoteException e) { 835 return null; 836 } 837 } 838 839 @Override 840 public boolean stopService(Intent service) { 841 try { 842 int res = ActivityManagerNative.getDefault().stopService( 843 mMainThread.getApplicationThread(), service, 844 service.resolveTypeIfNeeded(getContentResolver())); 845 if (res < 0) { 846 throw new SecurityException( 847 "Not allowed to stop service " + service); 848 } 849 return res != 0; 850 } catch (RemoteException e) { 851 return false; 852 } 853 } 854 855 @Override 856 public boolean bindService(Intent service, ServiceConnection conn, 857 int flags) { 858 IServiceConnection sd; 859 if (mPackageInfo != null) { 860 sd = mPackageInfo.getServiceDispatcher(conn, getOuterContext(), 861 mMainThread.getHandler(), flags); 862 } else { 863 throw new RuntimeException("Not supported in system context"); 864 } 865 try { 866 int res = ActivityManagerNative.getDefault().bindService( 867 mMainThread.getApplicationThread(), getActivityToken(), 868 service, service.resolveTypeIfNeeded(getContentResolver()), 869 sd, flags); 870 if (res < 0) { 871 throw new SecurityException( 872 "Not allowed to bind to service " + service); 873 } 874 return res != 0; 875 } catch (RemoteException e) { 876 return false; 877 } 878 } 879 880 @Override 881 public void unbindService(ServiceConnection conn) { 882 if (mPackageInfo != null) { 883 IServiceConnection sd = mPackageInfo.forgetServiceDispatcher( 884 getOuterContext(), conn); 885 try { 886 ActivityManagerNative.getDefault().unbindService(sd); 887 } catch (RemoteException e) { 888 } 889 } else { 890 throw new RuntimeException("Not supported in system context"); 891 } 892 } 893 894 @Override 895 public boolean startInstrumentation(ComponentName className, 896 String profileFile, Bundle arguments) { 897 try { 898 return ActivityManagerNative.getDefault().startInstrumentation( 899 className, profileFile, 0, arguments, null); 900 } catch (RemoteException e) { 901 // System has crashed, nothing we can do. 902 } 903 return false; 904 } 905 906 @Override 907 public Object getSystemService(String name) { 908 if (WINDOW_SERVICE.equals(name)) { 909 return WindowManagerImpl.getDefault(); 910 } else if (LAYOUT_INFLATER_SERVICE.equals(name)) { 911 synchronized (mSync) { 912 LayoutInflater inflater = mLayoutInflater; 913 if (inflater != null) { 914 return inflater; 915 } 916 mLayoutInflater = inflater = 917 PolicyManager.makeNewLayoutInflater(getOuterContext()); 918 return inflater; 919 } 920 } else if (ACTIVITY_SERVICE.equals(name)) { 921 return getActivityManager(); 922 } else if (INPUT_METHOD_SERVICE.equals(name)) { 923 return InputMethodManager.getInstance(this); 924 } else if (ALARM_SERVICE.equals(name)) { 925 return getAlarmManager(); 926 } else if (ACCOUNT_SERVICE.equals(name)) { 927 return getAccountManager(); 928 } else if (POWER_SERVICE.equals(name)) { 929 return getPowerManager(); 930 } else if (CONNECTIVITY_SERVICE.equals(name)) { 931 return getConnectivityManager(); 932 } else if (WIFI_SERVICE.equals(name)) { 933 return getWifiManager(); 934 } else if (NOTIFICATION_SERVICE.equals(name)) { 935 return getNotificationManager(); 936 } else if (KEYGUARD_SERVICE.equals(name)) { 937 return new KeyguardManager(); 938 } else if (ACCESSIBILITY_SERVICE.equals(name)) { 939 return AccessibilityManager.getInstance(this); 940 } else if (LOCATION_SERVICE.equals(name)) { 941 return getLocationManager(); 942 } else if (SEARCH_SERVICE.equals(name)) { 943 return getSearchManager(); 944 } else if (SENSOR_SERVICE.equals(name)) { 945 return getSensorManager(); 946 } else if (STORAGE_SERVICE.equals(name)) { 947 return getStorageManager(); 948 } else if (VIBRATOR_SERVICE.equals(name)) { 949 return getVibrator(); 950 } else if (STATUS_BAR_SERVICE.equals(name)) { 951 synchronized (mSync) { 952 if (mStatusBarManager == null) { 953 mStatusBarManager = new StatusBarManager(getOuterContext()); 954 } 955 return mStatusBarManager; 956 } 957 } else if (AUDIO_SERVICE.equals(name)) { 958 return getAudioManager(); 959 } else if (TELEPHONY_SERVICE.equals(name)) { 960 return getTelephonyManager(); 961 } else if (CLIPBOARD_SERVICE.equals(name)) { 962 return getClipboardManager(); 963 } else if (WALLPAPER_SERVICE.equals(name)) { 964 return getWallpaperManager(); 965 } else if (DROPBOX_SERVICE.equals(name)) { 966 return getDropBoxManager(); 967 } else if (DEVICE_POLICY_SERVICE.equals(name)) { 968 return getDevicePolicyManager(); 969 } else if (UI_MODE_SERVICE.equals(name)) { 970 return getUiModeManager(); 971 } 972 973 return null; 974 } 975 976 private AccountManager getAccountManager() { 977 synchronized (mSync) { 978 if (mAccountManager == null) { 979 IBinder b = ServiceManager.getService(ACCOUNT_SERVICE); 980 IAccountManager service = IAccountManager.Stub.asInterface(b); 981 mAccountManager = new AccountManager(this, service); 982 } 983 return mAccountManager; 984 } 985 } 986 987 private ActivityManager getActivityManager() { 988 synchronized (mSync) { 989 if (mActivityManager == null) { 990 mActivityManager = new ActivityManager(getOuterContext(), 991 mMainThread.getHandler()); 992 } 993 } 994 return mActivityManager; 995 } 996 997 private AlarmManager getAlarmManager() { 998 synchronized (sSync) { 999 if (sAlarmManager == null) { 1000 IBinder b = ServiceManager.getService(ALARM_SERVICE); 1001 IAlarmManager service = IAlarmManager.Stub.asInterface(b); 1002 sAlarmManager = new AlarmManager(service); 1003 } 1004 } 1005 return sAlarmManager; 1006 } 1007 1008 private PowerManager getPowerManager() { 1009 synchronized (sSync) { 1010 if (sPowerManager == null) { 1011 IBinder b = ServiceManager.getService(POWER_SERVICE); 1012 IPowerManager service = IPowerManager.Stub.asInterface(b); 1013 sPowerManager = new PowerManager(service, mMainThread.getHandler()); 1014 } 1015 } 1016 return sPowerManager; 1017 } 1018 1019 private ConnectivityManager getConnectivityManager() 1020 { 1021 synchronized (sSync) { 1022 if (sConnectivityManager == null) { 1023 IBinder b = ServiceManager.getService(CONNECTIVITY_SERVICE); 1024 IConnectivityManager service = IConnectivityManager.Stub.asInterface(b); 1025 sConnectivityManager = new ConnectivityManager(service); 1026 } 1027 } 1028 return sConnectivityManager; 1029 } 1030 1031 private WifiManager getWifiManager() 1032 { 1033 synchronized (sSync) { 1034 if (sWifiManager == null) { 1035 IBinder b = ServiceManager.getService(WIFI_SERVICE); 1036 IWifiManager service = IWifiManager.Stub.asInterface(b); 1037 sWifiManager = new WifiManager(service, mMainThread.getHandler()); 1038 } 1039 } 1040 return sWifiManager; 1041 } 1042 1043 private NotificationManager getNotificationManager() { 1044 synchronized (mSync) { 1045 if (mNotificationManager == null) { 1046 mNotificationManager = new NotificationManager( 1047 new ContextThemeWrapper(getOuterContext(), com.android.internal.R.style.Theme_Dialog), 1048 mMainThread.getHandler()); 1049 } 1050 } 1051 return mNotificationManager; 1052 } 1053 1054 private WallpaperManager getWallpaperManager() { 1055 synchronized (mSync) { 1056 if (mWallpaperManager == null) { 1057 mWallpaperManager = new WallpaperManager(getOuterContext(), 1058 mMainThread.getHandler()); 1059 } 1060 } 1061 return mWallpaperManager; 1062 } 1063 1064 private TelephonyManager getTelephonyManager() { 1065 synchronized (mSync) { 1066 if (mTelephonyManager == null) { 1067 mTelephonyManager = new TelephonyManager(getOuterContext()); 1068 } 1069 } 1070 return mTelephonyManager; 1071 } 1072 1073 private ClipboardManager getClipboardManager() { 1074 synchronized (mSync) { 1075 if (mClipboardManager == null) { 1076 mClipboardManager = new ClipboardManager(getOuterContext(), 1077 mMainThread.getHandler()); 1078 } 1079 } 1080 return mClipboardManager; 1081 } 1082 1083 private LocationManager getLocationManager() { 1084 synchronized (sSync) { 1085 if (sLocationManager == null) { 1086 IBinder b = ServiceManager.getService(LOCATION_SERVICE); 1087 ILocationManager service = ILocationManager.Stub.asInterface(b); 1088 sLocationManager = new LocationManager(service); 1089 } 1090 } 1091 return sLocationManager; 1092 } 1093 1094 private SearchManager getSearchManager() { 1095 synchronized (mSync) { 1096 if (mSearchManager == null) { 1097 mSearchManager = new SearchManager(getOuterContext(), mMainThread.getHandler()); 1098 } 1099 } 1100 return mSearchManager; 1101 } 1102 1103 private SensorManager getSensorManager() { 1104 synchronized (mSync) { 1105 if (mSensorManager == null) { 1106 mSensorManager = new SensorManager(mMainThread.getHandler().getLooper()); 1107 } 1108 } 1109 return mSensorManager; 1110 } 1111 1112 private StorageManager getStorageManager() { 1113 synchronized (mSync) { 1114 if (mStorageManager == null) { 1115 try { 1116 mStorageManager = new StorageManager(mMainThread.getHandler().getLooper()); 1117 } catch (RemoteException rex) { 1118 Log.e(TAG, "Failed to create StorageManager", rex); 1119 mStorageManager = null; 1120 } 1121 } 1122 } 1123 return mStorageManager; 1124 } 1125 1126 private Vibrator getVibrator() { 1127 synchronized (mSync) { 1128 if (mVibrator == null) { 1129 mVibrator = new Vibrator(); 1130 } 1131 } 1132 return mVibrator; 1133 } 1134 1135 private AudioManager getAudioManager() 1136 { 1137 if (mAudioManager == null) { 1138 mAudioManager = new AudioManager(this); 1139 } 1140 return mAudioManager; 1141 } 1142 1143 private DropBoxManager getDropBoxManager() { 1144 synchronized (mSync) { 1145 if (mDropBoxManager == null) { 1146 IBinder b = ServiceManager.getService(DROPBOX_SERVICE); 1147 IDropBoxManagerService service = IDropBoxManagerService.Stub.asInterface(b); 1148 mDropBoxManager = new DropBoxManager(service); 1149 } 1150 } 1151 return mDropBoxManager; 1152 } 1153 1154 private DevicePolicyManager getDevicePolicyManager() { 1155 synchronized (mSync) { 1156 if (mDevicePolicyManager == null) { 1157 mDevicePolicyManager = DevicePolicyManager.create(this, 1158 mMainThread.getHandler()); 1159 } 1160 } 1161 return mDevicePolicyManager; 1162 } 1163 1164 private UiModeManager getUiModeManager() { 1165 synchronized (mSync) { 1166 if (mUiModeManager == null) { 1167 mUiModeManager = new UiModeManager(); 1168 } 1169 } 1170 return mUiModeManager; 1171 } 1172 1173 @Override 1174 public int checkPermission(String permission, int pid, int uid) { 1175 if (permission == null) { 1176 throw new IllegalArgumentException("permission is null"); 1177 } 1178 1179 if (!Process.supportsProcesses()) { 1180 return PackageManager.PERMISSION_GRANTED; 1181 } 1182 try { 1183 return ActivityManagerNative.getDefault().checkPermission( 1184 permission, pid, uid); 1185 } catch (RemoteException e) { 1186 return PackageManager.PERMISSION_DENIED; 1187 } 1188 } 1189 1190 @Override 1191 public int checkCallingPermission(String permission) { 1192 if (permission == null) { 1193 throw new IllegalArgumentException("permission is null"); 1194 } 1195 1196 if (!Process.supportsProcesses()) { 1197 return PackageManager.PERMISSION_GRANTED; 1198 } 1199 int pid = Binder.getCallingPid(); 1200 if (pid != Process.myPid()) { 1201 return checkPermission(permission, pid, 1202 Binder.getCallingUid()); 1203 } 1204 return PackageManager.PERMISSION_DENIED; 1205 } 1206 1207 @Override 1208 public int checkCallingOrSelfPermission(String permission) { 1209 if (permission == null) { 1210 throw new IllegalArgumentException("permission is null"); 1211 } 1212 1213 return checkPermission(permission, Binder.getCallingPid(), 1214 Binder.getCallingUid()); 1215 } 1216 1217 private void enforce( 1218 String permission, int resultOfCheck, 1219 boolean selfToo, int uid, String message) { 1220 if (resultOfCheck != PackageManager.PERMISSION_GRANTED) { 1221 throw new SecurityException( 1222 (message != null ? (message + ": ") : "") + 1223 (selfToo 1224 ? "Neither user " + uid + " nor current process has " 1225 : "User " + uid + " does not have ") + 1226 permission + 1227 "."); 1228 } 1229 } 1230 1231 public void enforcePermission( 1232 String permission, int pid, int uid, String message) { 1233 enforce(permission, 1234 checkPermission(permission, pid, uid), 1235 false, 1236 uid, 1237 message); 1238 } 1239 1240 public void enforceCallingPermission(String permission, String message) { 1241 enforce(permission, 1242 checkCallingPermission(permission), 1243 false, 1244 Binder.getCallingUid(), 1245 message); 1246 } 1247 1248 public void enforceCallingOrSelfPermission( 1249 String permission, String message) { 1250 enforce(permission, 1251 checkCallingOrSelfPermission(permission), 1252 true, 1253 Binder.getCallingUid(), 1254 message); 1255 } 1256 1257 @Override 1258 public void grantUriPermission(String toPackage, Uri uri, int modeFlags) { 1259 try { 1260 ActivityManagerNative.getDefault().grantUriPermission( 1261 mMainThread.getApplicationThread(), toPackage, uri, 1262 modeFlags); 1263 } catch (RemoteException e) { 1264 } 1265 } 1266 1267 @Override 1268 public void revokeUriPermission(Uri uri, int modeFlags) { 1269 try { 1270 ActivityManagerNative.getDefault().revokeUriPermission( 1271 mMainThread.getApplicationThread(), uri, 1272 modeFlags); 1273 } catch (RemoteException e) { 1274 } 1275 } 1276 1277 @Override 1278 public int checkUriPermission(Uri uri, int pid, int uid, int modeFlags) { 1279 if (!Process.supportsProcesses()) { 1280 return PackageManager.PERMISSION_GRANTED; 1281 } 1282 try { 1283 return ActivityManagerNative.getDefault().checkUriPermission( 1284 uri, pid, uid, modeFlags); 1285 } catch (RemoteException e) { 1286 return PackageManager.PERMISSION_DENIED; 1287 } 1288 } 1289 1290 @Override 1291 public int checkCallingUriPermission(Uri uri, int modeFlags) { 1292 if (!Process.supportsProcesses()) { 1293 return PackageManager.PERMISSION_GRANTED; 1294 } 1295 int pid = Binder.getCallingPid(); 1296 if (pid != Process.myPid()) { 1297 return checkUriPermission(uri, pid, 1298 Binder.getCallingUid(), modeFlags); 1299 } 1300 return PackageManager.PERMISSION_DENIED; 1301 } 1302 1303 @Override 1304 public int checkCallingOrSelfUriPermission(Uri uri, int modeFlags) { 1305 return checkUriPermission(uri, Binder.getCallingPid(), 1306 Binder.getCallingUid(), modeFlags); 1307 } 1308 1309 @Override 1310 public int checkUriPermission(Uri uri, String readPermission, 1311 String writePermission, int pid, int uid, int modeFlags) { 1312 if (DEBUG) { 1313 Log.i("foo", "checkUriPermission: uri=" + uri + "readPermission=" 1314 + readPermission + " writePermission=" + writePermission 1315 + " pid=" + pid + " uid=" + uid + " mode" + modeFlags); 1316 } 1317 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 1318 if (readPermission == null 1319 || checkPermission(readPermission, pid, uid) 1320 == PackageManager.PERMISSION_GRANTED) { 1321 return PackageManager.PERMISSION_GRANTED; 1322 } 1323 } 1324 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 1325 if (writePermission == null 1326 || checkPermission(writePermission, pid, uid) 1327 == PackageManager.PERMISSION_GRANTED) { 1328 return PackageManager.PERMISSION_GRANTED; 1329 } 1330 } 1331 return uri != null ? checkUriPermission(uri, pid, uid, modeFlags) 1332 : PackageManager.PERMISSION_DENIED; 1333 } 1334 1335 private String uriModeFlagToString(int uriModeFlags) { 1336 switch (uriModeFlags) { 1337 case Intent.FLAG_GRANT_READ_URI_PERMISSION | 1338 Intent.FLAG_GRANT_WRITE_URI_PERMISSION: 1339 return "read and write"; 1340 case Intent.FLAG_GRANT_READ_URI_PERMISSION: 1341 return "read"; 1342 case Intent.FLAG_GRANT_WRITE_URI_PERMISSION: 1343 return "write"; 1344 } 1345 throw new IllegalArgumentException( 1346 "Unknown permission mode flags: " + uriModeFlags); 1347 } 1348 1349 private void enforceForUri( 1350 int modeFlags, int resultOfCheck, boolean selfToo, 1351 int uid, Uri uri, String message) { 1352 if (resultOfCheck != PackageManager.PERMISSION_GRANTED) { 1353 throw new SecurityException( 1354 (message != null ? (message + ": ") : "") + 1355 (selfToo 1356 ? "Neither user " + uid + " nor current process has " 1357 : "User " + uid + " does not have ") + 1358 uriModeFlagToString(modeFlags) + 1359 " permission on " + 1360 uri + 1361 "."); 1362 } 1363 } 1364 1365 public void enforceUriPermission( 1366 Uri uri, int pid, int uid, int modeFlags, String message) { 1367 enforceForUri( 1368 modeFlags, checkUriPermission(uri, pid, uid, modeFlags), 1369 false, uid, uri, message); 1370 } 1371 1372 public void enforceCallingUriPermission( 1373 Uri uri, int modeFlags, String message) { 1374 enforceForUri( 1375 modeFlags, checkCallingUriPermission(uri, modeFlags), 1376 false, Binder.getCallingUid(), uri, message); 1377 } 1378 1379 public void enforceCallingOrSelfUriPermission( 1380 Uri uri, int modeFlags, String message) { 1381 enforceForUri( 1382 modeFlags, 1383 checkCallingOrSelfUriPermission(uri, modeFlags), true, 1384 Binder.getCallingUid(), uri, message); 1385 } 1386 1387 public void enforceUriPermission( 1388 Uri uri, String readPermission, String writePermission, 1389 int pid, int uid, int modeFlags, String message) { 1390 enforceForUri(modeFlags, 1391 checkUriPermission( 1392 uri, readPermission, writePermission, pid, uid, 1393 modeFlags), 1394 false, 1395 uid, 1396 uri, 1397 message); 1398 } 1399 1400 @Override 1401 public Context createPackageContext(String packageName, int flags) 1402 throws PackageManager.NameNotFoundException { 1403 if (packageName.equals("system") || packageName.equals("android")) { 1404 return new ContextImpl(mMainThread.getSystemContext()); 1405 } 1406 1407 ActivityThread.PackageInfo pi = 1408 mMainThread.getPackageInfo(packageName, flags); 1409 if (pi != null) { 1410 ContextImpl c = new ContextImpl(); 1411 c.mRestricted = (flags & CONTEXT_RESTRICTED) == CONTEXT_RESTRICTED; 1412 c.init(pi, null, mMainThread, mResources); 1413 if (c.mResources != null) { 1414 return c; 1415 } 1416 } 1417 1418 // Should be a better exception. 1419 throw new PackageManager.NameNotFoundException( 1420 "Application package " + packageName + " not found"); 1421 } 1422 1423 @Override 1424 public boolean isRestricted() { 1425 return mRestricted; 1426 } 1427 1428 private File getDataDirFile() { 1429 if (mPackageInfo != null) { 1430 return mPackageInfo.getDataDirFile(); 1431 } 1432 throw new RuntimeException("Not supported in system context"); 1433 } 1434 1435 @Override 1436 public File getDir(String name, int mode) { 1437 name = "app_" + name; 1438 File file = makeFilename(getDataDirFile(), name); 1439 if (!file.exists()) { 1440 file.mkdir(); 1441 setFilePermissionsFromMode(file.getPath(), mode, 1442 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH); 1443 } 1444 return file; 1445 } 1446 1447 static ContextImpl createSystemContext(ActivityThread mainThread) { 1448 ContextImpl context = new ContextImpl(); 1449 context.init(Resources.getSystem(), mainThread); 1450 return context; 1451 } 1452 1453 ContextImpl() { 1454 // For debug only 1455 //++sInstanceCount; 1456 mOuterContext = this; 1457 } 1458 1459 /** 1460 * Create a new ApplicationContext from an existing one. The new one 1461 * works and operates the same as the one it is copying. 1462 * 1463 * @param context Existing application context. 1464 */ 1465 public ContextImpl(ContextImpl context) { 1466 ++sInstanceCount; 1467 mPackageInfo = context.mPackageInfo; 1468 mResources = context.mResources; 1469 mMainThread = context.mMainThread; 1470 mContentResolver = context.mContentResolver; 1471 mOuterContext = this; 1472 } 1473 1474 final void init(ActivityThread.PackageInfo packageInfo, 1475 IBinder activityToken, ActivityThread mainThread) { 1476 init(packageInfo, activityToken, mainThread, null); 1477 } 1478 1479 final void init(ActivityThread.PackageInfo packageInfo, 1480 IBinder activityToken, ActivityThread mainThread, 1481 Resources container) { 1482 mPackageInfo = packageInfo; 1483 mResources = mPackageInfo.getResources(mainThread); 1484 1485 if (container != null && container.getCompatibilityInfo().applicationScale != 1486 mResources.getCompatibilityInfo().applicationScale) { 1487 if (DEBUG) { 1488 Log.d(TAG, "loaded context has different scaling. Using container's" + 1489 " compatiblity info:" + container.getDisplayMetrics()); 1490 } 1491 mResources = mainThread.getTopLevelResources( 1492 mPackageInfo.getResDir(), container.getCompatibilityInfo().copy()); 1493 } 1494 mMainThread = mainThread; 1495 mContentResolver = new ApplicationContentResolver(this, mainThread); 1496 1497 setActivityToken(activityToken); 1498 } 1499 1500 final void init(Resources resources, ActivityThread mainThread) { 1501 mPackageInfo = null; 1502 mResources = resources; 1503 mMainThread = mainThread; 1504 mContentResolver = new ApplicationContentResolver(this, mainThread); 1505 } 1506 1507 final void scheduleFinalCleanup(String who, String what) { 1508 mMainThread.scheduleContextCleanup(this, who, what); 1509 } 1510 1511 final void performFinalCleanup(String who, String what) { 1512 //Log.i(TAG, "Cleanup up context: " + this); 1513 mPackageInfo.removeContextRegistrations(getOuterContext(), who, what); 1514 } 1515 1516 final Context getReceiverRestrictedContext() { 1517 if (mReceiverRestrictedContext != null) { 1518 return mReceiverRestrictedContext; 1519 } 1520 return mReceiverRestrictedContext = new ReceiverRestrictedContext(getOuterContext()); 1521 } 1522 1523 final void setActivityToken(IBinder token) { 1524 mActivityToken = token; 1525 } 1526 1527 final void setOuterContext(Context context) { 1528 mOuterContext = context; 1529 } 1530 1531 final Context getOuterContext() { 1532 return mOuterContext; 1533 } 1534 1535 final IBinder getActivityToken() { 1536 return mActivityToken; 1537 } 1538 1539 private static void setFilePermissionsFromMode(String name, int mode, 1540 int extraPermissions) { 1541 int perms = FileUtils.S_IRUSR|FileUtils.S_IWUSR 1542 |FileUtils.S_IRGRP|FileUtils.S_IWGRP 1543 |extraPermissions; 1544 if ((mode&MODE_WORLD_READABLE) != 0) { 1545 perms |= FileUtils.S_IROTH; 1546 } 1547 if ((mode&MODE_WORLD_WRITEABLE) != 0) { 1548 perms |= FileUtils.S_IWOTH; 1549 } 1550 if (DEBUG) { 1551 Log.i(TAG, "File " + name + ": mode=0x" + Integer.toHexString(mode) 1552 + ", perms=0x" + Integer.toHexString(perms)); 1553 } 1554 FileUtils.setPermissions(name, perms, -1, -1); 1555 } 1556 1557 private File validateFilePath(String name, boolean createDirectory) { 1558 File dir; 1559 File f; 1560 1561 if (name.charAt(0) == File.separatorChar) { 1562 String dirPath = name.substring(0, name.lastIndexOf(File.separatorChar)); 1563 dir = new File(dirPath); 1564 name = name.substring(name.lastIndexOf(File.separatorChar)); 1565 f = new File(dir, name); 1566 } else { 1567 dir = getDatabasesDir(); 1568 f = makeFilename(dir, name); 1569 } 1570 1571 if (createDirectory && !dir.isDirectory() && dir.mkdir()) { 1572 FileUtils.setPermissions(dir.getPath(), 1573 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH, 1574 -1, -1); 1575 } 1576 1577 return f; 1578 } 1579 1580 private File makeFilename(File base, String name) { 1581 if (name.indexOf(File.separatorChar) < 0) { 1582 return new File(base, name); 1583 } 1584 throw new IllegalArgumentException( 1585 "File " + name + " contains a path separator"); 1586 } 1587 1588 // ---------------------------------------------------------------------- 1589 // ---------------------------------------------------------------------- 1590 // ---------------------------------------------------------------------- 1591 1592 private static final class ApplicationContentResolver extends ContentResolver { 1593 public ApplicationContentResolver(Context context, 1594 ActivityThread mainThread) 1595 { 1596 super(context); 1597 mMainThread = mainThread; 1598 } 1599 1600 @Override 1601 protected IContentProvider acquireProvider(Context context, String name) 1602 { 1603 return mMainThread.acquireProvider(context, name); 1604 } 1605 1606 @Override 1607 public boolean releaseProvider(IContentProvider provider) 1608 { 1609 return mMainThread.releaseProvider(provider); 1610 } 1611 1612 private final ActivityThread mMainThread; 1613 } 1614 1615 // ---------------------------------------------------------------------- 1616 // ---------------------------------------------------------------------- 1617 // ---------------------------------------------------------------------- 1618 1619 /*package*/ 1620 static final class ApplicationPackageManager extends PackageManager { 1621 @Override 1622 public PackageInfo getPackageInfo(String packageName, int flags) 1623 throws NameNotFoundException { 1624 try { 1625 PackageInfo pi = mPM.getPackageInfo(packageName, flags); 1626 if (pi != null) { 1627 return pi; 1628 } 1629 } catch (RemoteException e) { 1630 throw new RuntimeException("Package manager has died", e); 1631 } 1632 1633 throw new NameNotFoundException(packageName); 1634 } 1635 1636 @Override 1637 public String[] currentToCanonicalPackageNames(String[] names) { 1638 try { 1639 return mPM.currentToCanonicalPackageNames(names); 1640 } catch (RemoteException e) { 1641 throw new RuntimeException("Package manager has died", e); 1642 } 1643 } 1644 1645 @Override 1646 public String[] canonicalToCurrentPackageNames(String[] names) { 1647 try { 1648 return mPM.canonicalToCurrentPackageNames(names); 1649 } catch (RemoteException e) { 1650 throw new RuntimeException("Package manager has died", e); 1651 } 1652 } 1653 1654 @Override 1655 public Intent getLaunchIntentForPackage(String packageName) { 1656 // First see if the package has an INFO activity; the existence of 1657 // such an activity is implied to be the desired front-door for the 1658 // overall package (such as if it has multiple launcher entries). 1659 Intent intentToResolve = new Intent(Intent.ACTION_MAIN); 1660 intentToResolve.addCategory(Intent.CATEGORY_INFO); 1661 intentToResolve.setPackage(packageName); 1662 ResolveInfo resolveInfo = resolveActivity(intentToResolve, 0); 1663 1664 // Otherwise, try to find a main launcher activity. 1665 if (resolveInfo == null) { 1666 // reuse the intent instance 1667 intentToResolve.removeCategory(Intent.CATEGORY_INFO); 1668 intentToResolve.addCategory(Intent.CATEGORY_LAUNCHER); 1669 intentToResolve.setPackage(packageName); 1670 resolveInfo = resolveActivity(intentToResolve, 0); 1671 } 1672 if (resolveInfo == null) { 1673 return null; 1674 } 1675 Intent intent = new Intent(Intent.ACTION_MAIN); 1676 intent.setClassName(packageName, resolveInfo.activityInfo.name); 1677 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 1678 return intent; 1679 } 1680 1681 @Override 1682 public int[] getPackageGids(String packageName) 1683 throws NameNotFoundException { 1684 try { 1685 int[] gids = mPM.getPackageGids(packageName); 1686 if (gids == null || gids.length > 0) { 1687 return gids; 1688 } 1689 } catch (RemoteException e) { 1690 throw new RuntimeException("Package manager has died", e); 1691 } 1692 1693 throw new NameNotFoundException(packageName); 1694 } 1695 1696 @Override 1697 public PermissionInfo getPermissionInfo(String name, int flags) 1698 throws NameNotFoundException { 1699 try { 1700 PermissionInfo pi = mPM.getPermissionInfo(name, flags); 1701 if (pi != null) { 1702 return pi; 1703 } 1704 } catch (RemoteException e) { 1705 throw new RuntimeException("Package manager has died", e); 1706 } 1707 1708 throw new NameNotFoundException(name); 1709 } 1710 1711 @Override 1712 public List<PermissionInfo> queryPermissionsByGroup(String group, int flags) 1713 throws NameNotFoundException { 1714 try { 1715 List<PermissionInfo> pi = mPM.queryPermissionsByGroup(group, flags); 1716 if (pi != null) { 1717 return pi; 1718 } 1719 } catch (RemoteException e) { 1720 throw new RuntimeException("Package manager has died", e); 1721 } 1722 1723 throw new NameNotFoundException(group); 1724 } 1725 1726 @Override 1727 public PermissionGroupInfo getPermissionGroupInfo(String name, 1728 int flags) throws NameNotFoundException { 1729 try { 1730 PermissionGroupInfo pgi = mPM.getPermissionGroupInfo(name, flags); 1731 if (pgi != null) { 1732 return pgi; 1733 } 1734 } catch (RemoteException e) { 1735 throw new RuntimeException("Package manager has died", e); 1736 } 1737 1738 throw new NameNotFoundException(name); 1739 } 1740 1741 @Override 1742 public List<PermissionGroupInfo> getAllPermissionGroups(int flags) { 1743 try { 1744 return mPM.getAllPermissionGroups(flags); 1745 } catch (RemoteException e) { 1746 throw new RuntimeException("Package manager has died", e); 1747 } 1748 } 1749 1750 @Override 1751 public ApplicationInfo getApplicationInfo(String packageName, int flags) 1752 throws NameNotFoundException { 1753 try { 1754 ApplicationInfo ai = mPM.getApplicationInfo(packageName, flags); 1755 if (ai != null) { 1756 return ai; 1757 } 1758 } catch (RemoteException e) { 1759 throw new RuntimeException("Package manager has died", e); 1760 } 1761 1762 throw new NameNotFoundException(packageName); 1763 } 1764 1765 @Override 1766 public ActivityInfo getActivityInfo(ComponentName className, int flags) 1767 throws NameNotFoundException { 1768 try { 1769 ActivityInfo ai = mPM.getActivityInfo(className, flags); 1770 if (ai != null) { 1771 return ai; 1772 } 1773 } catch (RemoteException e) { 1774 throw new RuntimeException("Package manager has died", e); 1775 } 1776 1777 throw new NameNotFoundException(className.toString()); 1778 } 1779 1780 @Override 1781 public ActivityInfo getReceiverInfo(ComponentName className, int flags) 1782 throws NameNotFoundException { 1783 try { 1784 ActivityInfo ai = mPM.getReceiverInfo(className, flags); 1785 if (ai != null) { 1786 return ai; 1787 } 1788 } catch (RemoteException e) { 1789 throw new RuntimeException("Package manager has died", e); 1790 } 1791 1792 throw new NameNotFoundException(className.toString()); 1793 } 1794 1795 @Override 1796 public ServiceInfo getServiceInfo(ComponentName className, int flags) 1797 throws NameNotFoundException { 1798 try { 1799 ServiceInfo si = mPM.getServiceInfo(className, flags); 1800 if (si != null) { 1801 return si; 1802 } 1803 } catch (RemoteException e) { 1804 throw new RuntimeException("Package manager has died", e); 1805 } 1806 1807 throw new NameNotFoundException(className.toString()); 1808 } 1809 1810 @Override 1811 public String[] getSystemSharedLibraryNames() { 1812 try { 1813 return mPM.getSystemSharedLibraryNames(); 1814 } catch (RemoteException e) { 1815 throw new RuntimeException("Package manager has died", e); 1816 } 1817 } 1818 1819 @Override 1820 public FeatureInfo[] getSystemAvailableFeatures() { 1821 try { 1822 return mPM.getSystemAvailableFeatures(); 1823 } catch (RemoteException e) { 1824 throw new RuntimeException("Package manager has died", e); 1825 } 1826 } 1827 1828 @Override 1829 public boolean hasSystemFeature(String name) { 1830 try { 1831 return mPM.hasSystemFeature(name); 1832 } catch (RemoteException e) { 1833 throw new RuntimeException("Package manager has died", e); 1834 } 1835 } 1836 1837 @Override 1838 public int checkPermission(String permName, String pkgName) { 1839 try { 1840 return mPM.checkPermission(permName, pkgName); 1841 } catch (RemoteException e) { 1842 throw new RuntimeException("Package manager has died", e); 1843 } 1844 } 1845 1846 @Override 1847 public boolean addPermission(PermissionInfo info) { 1848 try { 1849 return mPM.addPermission(info); 1850 } catch (RemoteException e) { 1851 throw new RuntimeException("Package manager has died", e); 1852 } 1853 } 1854 1855 @Override 1856 public boolean addPermissionAsync(PermissionInfo info) { 1857 try { 1858 return mPM.addPermissionAsync(info); 1859 } catch (RemoteException e) { 1860 throw new RuntimeException("Package manager has died", e); 1861 } 1862 } 1863 1864 @Override 1865 public void removePermission(String name) { 1866 try { 1867 mPM.removePermission(name); 1868 } catch (RemoteException e) { 1869 throw new RuntimeException("Package manager has died", e); 1870 } 1871 } 1872 1873 @Override 1874 public int checkSignatures(String pkg1, String pkg2) { 1875 try { 1876 return mPM.checkSignatures(pkg1, pkg2); 1877 } catch (RemoteException e) { 1878 throw new RuntimeException("Package manager has died", e); 1879 } 1880 } 1881 1882 @Override 1883 public int checkSignatures(int uid1, int uid2) { 1884 try { 1885 return mPM.checkUidSignatures(uid1, uid2); 1886 } catch (RemoteException e) { 1887 throw new RuntimeException("Package manager has died", e); 1888 } 1889 } 1890 1891 @Override 1892 public String[] getPackagesForUid(int uid) { 1893 try { 1894 return mPM.getPackagesForUid(uid); 1895 } catch (RemoteException e) { 1896 throw new RuntimeException("Package manager has died", e); 1897 } 1898 } 1899 1900 @Override 1901 public String getNameForUid(int uid) { 1902 try { 1903 return mPM.getNameForUid(uid); 1904 } catch (RemoteException e) { 1905 throw new RuntimeException("Package manager has died", e); 1906 } 1907 } 1908 1909 @Override 1910 public int getUidForSharedUser(String sharedUserName) 1911 throws NameNotFoundException { 1912 try { 1913 int uid = mPM.getUidForSharedUser(sharedUserName); 1914 if(uid != -1) { 1915 return uid; 1916 } 1917 } catch (RemoteException e) { 1918 throw new RuntimeException("Package manager has died", e); 1919 } 1920 throw new NameNotFoundException("No shared userid for user:"+sharedUserName); 1921 } 1922 1923 @Override 1924 public List<PackageInfo> getInstalledPackages(int flags) { 1925 try { 1926 return mPM.getInstalledPackages(flags); 1927 } catch (RemoteException e) { 1928 throw new RuntimeException("Package manager has died", e); 1929 } 1930 } 1931 1932 @Override 1933 public List<ApplicationInfo> getInstalledApplications(int flags) { 1934 try { 1935 return mPM.getInstalledApplications(flags); 1936 } catch (RemoteException e) { 1937 throw new RuntimeException("Package manager has died", e); 1938 } 1939 } 1940 1941 @Override 1942 public ResolveInfo resolveActivity(Intent intent, int flags) { 1943 try { 1944 return mPM.resolveIntent( 1945 intent, 1946 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 1947 flags); 1948 } catch (RemoteException e) { 1949 throw new RuntimeException("Package manager has died", e); 1950 } 1951 } 1952 1953 @Override 1954 public List<ResolveInfo> queryIntentActivities(Intent intent, 1955 int flags) { 1956 try { 1957 return mPM.queryIntentActivities( 1958 intent, 1959 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 1960 flags); 1961 } catch (RemoteException e) { 1962 throw new RuntimeException("Package manager has died", e); 1963 } 1964 } 1965 1966 @Override 1967 public List<ResolveInfo> queryIntentActivityOptions( 1968 ComponentName caller, Intent[] specifics, Intent intent, 1969 int flags) { 1970 final ContentResolver resolver = mContext.getContentResolver(); 1971 1972 String[] specificTypes = null; 1973 if (specifics != null) { 1974 final int N = specifics.length; 1975 for (int i=0; i<N; i++) { 1976 Intent sp = specifics[i]; 1977 if (sp != null) { 1978 String t = sp.resolveTypeIfNeeded(resolver); 1979 if (t != null) { 1980 if (specificTypes == null) { 1981 specificTypes = new String[N]; 1982 } 1983 specificTypes[i] = t; 1984 } 1985 } 1986 } 1987 } 1988 1989 try { 1990 return mPM.queryIntentActivityOptions(caller, specifics, 1991 specificTypes, intent, intent.resolveTypeIfNeeded(resolver), 1992 flags); 1993 } catch (RemoteException e) { 1994 throw new RuntimeException("Package manager has died", e); 1995 } 1996 } 1997 1998 @Override 1999 public List<ResolveInfo> queryBroadcastReceivers(Intent intent, int flags) { 2000 try { 2001 return mPM.queryIntentReceivers( 2002 intent, 2003 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 2004 flags); 2005 } catch (RemoteException e) { 2006 throw new RuntimeException("Package manager has died", e); 2007 } 2008 } 2009 2010 @Override 2011 public ResolveInfo resolveService(Intent intent, int flags) { 2012 try { 2013 return mPM.resolveService( 2014 intent, 2015 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 2016 flags); 2017 } catch (RemoteException e) { 2018 throw new RuntimeException("Package manager has died", e); 2019 } 2020 } 2021 2022 @Override 2023 public List<ResolveInfo> queryIntentServices(Intent intent, int flags) { 2024 try { 2025 return mPM.queryIntentServices( 2026 intent, 2027 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 2028 flags); 2029 } catch (RemoteException e) { 2030 throw new RuntimeException("Package manager has died", e); 2031 } 2032 } 2033 2034 @Override 2035 public ProviderInfo resolveContentProvider(String name, 2036 int flags) { 2037 try { 2038 return mPM.resolveContentProvider(name, flags); 2039 } catch (RemoteException e) { 2040 throw new RuntimeException("Package manager has died", e); 2041 } 2042 } 2043 2044 @Override 2045 public List<ProviderInfo> queryContentProviders(String processName, 2046 int uid, int flags) { 2047 try { 2048 return mPM.queryContentProviders(processName, uid, flags); 2049 } catch (RemoteException e) { 2050 throw new RuntimeException("Package manager has died", e); 2051 } 2052 } 2053 2054 @Override 2055 public InstrumentationInfo getInstrumentationInfo( 2056 ComponentName className, int flags) 2057 throws NameNotFoundException { 2058 try { 2059 InstrumentationInfo ii = mPM.getInstrumentationInfo( 2060 className, flags); 2061 if (ii != null) { 2062 return ii; 2063 } 2064 } catch (RemoteException e) { 2065 throw new RuntimeException("Package manager has died", e); 2066 } 2067 2068 throw new NameNotFoundException(className.toString()); 2069 } 2070 2071 @Override 2072 public List<InstrumentationInfo> queryInstrumentation( 2073 String targetPackage, int flags) { 2074 try { 2075 return mPM.queryInstrumentation(targetPackage, flags); 2076 } catch (RemoteException e) { 2077 throw new RuntimeException("Package manager has died", e); 2078 } 2079 } 2080 2081 @Override public Drawable getDrawable(String packageName, int resid, 2082 ApplicationInfo appInfo) { 2083 ResourceName name = new ResourceName(packageName, resid); 2084 Drawable dr = getCachedIcon(name); 2085 if (dr != null) { 2086 return dr; 2087 } 2088 if (appInfo == null) { 2089 try { 2090 appInfo = getApplicationInfo(packageName, 0); 2091 } catch (NameNotFoundException e) { 2092 return null; 2093 } 2094 } 2095 try { 2096 Resources r = getResourcesForApplication(appInfo); 2097 dr = r.getDrawable(resid); 2098 if (false) { 2099 RuntimeException e = new RuntimeException("here"); 2100 e.fillInStackTrace(); 2101 Log.w(TAG, "Getting drawable 0x" + Integer.toHexString(resid) 2102 + " from package " + packageName 2103 + ": app scale=" + r.getCompatibilityInfo().applicationScale 2104 + ", caller scale=" + mContext.getResources().getCompatibilityInfo().applicationScale, 2105 e); 2106 } 2107 if (DEBUG_ICONS) Log.v(TAG, "Getting drawable 0x" 2108 + Integer.toHexString(resid) + " from " + r 2109 + ": " + dr); 2110 putCachedIcon(name, dr); 2111 return dr; 2112 } catch (NameNotFoundException e) { 2113 Log.w("PackageManager", "Failure retrieving resources for" 2114 + appInfo.packageName); 2115 } catch (RuntimeException e) { 2116 // If an exception was thrown, fall through to return 2117 // default icon. 2118 Log.w("PackageManager", "Failure retrieving icon 0x" 2119 + Integer.toHexString(resid) + " in package " 2120 + packageName, e); 2121 } 2122 return null; 2123 } 2124 2125 @Override public Drawable getActivityIcon(ComponentName activityName) 2126 throws NameNotFoundException { 2127 return getActivityInfo(activityName, 0).loadIcon(this); 2128 } 2129 2130 @Override public Drawable getActivityIcon(Intent intent) 2131 throws NameNotFoundException { 2132 if (intent.getComponent() != null) { 2133 return getActivityIcon(intent.getComponent()); 2134 } 2135 2136 ResolveInfo info = resolveActivity( 2137 intent, PackageManager.MATCH_DEFAULT_ONLY); 2138 if (info != null) { 2139 return info.activityInfo.loadIcon(this); 2140 } 2141 2142 throw new NameNotFoundException(intent.toURI()); 2143 } 2144 2145 @Override public Drawable getDefaultActivityIcon() { 2146 return Resources.getSystem().getDrawable( 2147 com.android.internal.R.drawable.sym_def_app_icon); 2148 } 2149 2150 @Override public Drawable getApplicationIcon(ApplicationInfo info) { 2151 return info.loadIcon(this); 2152 } 2153 2154 @Override public Drawable getApplicationIcon(String packageName) 2155 throws NameNotFoundException { 2156 return getApplicationIcon(getApplicationInfo(packageName, 0)); 2157 } 2158 2159 @Override public Resources getResourcesForActivity( 2160 ComponentName activityName) throws NameNotFoundException { 2161 return getResourcesForApplication( 2162 getActivityInfo(activityName, 0).applicationInfo); 2163 } 2164 2165 @Override public Resources getResourcesForApplication( 2166 ApplicationInfo app) throws NameNotFoundException { 2167 if (app.packageName.equals("system")) { 2168 return mContext.mMainThread.getSystemContext().getResources(); 2169 } 2170 Resources r = mContext.mMainThread.getTopLevelResources( 2171 app.uid == Process.myUid() ? app.sourceDir 2172 : app.publicSourceDir, mContext.mPackageInfo); 2173 if (r != null) { 2174 return r; 2175 } 2176 throw new NameNotFoundException("Unable to open " + app.publicSourceDir); 2177 } 2178 2179 @Override public Resources getResourcesForApplication( 2180 String appPackageName) throws NameNotFoundException { 2181 return getResourcesForApplication( 2182 getApplicationInfo(appPackageName, 0)); 2183 } 2184 2185 int mCachedSafeMode = -1; 2186 @Override public boolean isSafeMode() { 2187 try { 2188 if (mCachedSafeMode < 0) { 2189 mCachedSafeMode = mPM.isSafeMode() ? 1 : 0; 2190 } 2191 return mCachedSafeMode != 0; 2192 } catch (RemoteException e) { 2193 throw new RuntimeException("Package manager has died", e); 2194 } 2195 } 2196 2197 static void configurationChanged() { 2198 synchronized (sSync) { 2199 sIconCache.clear(); 2200 sStringCache.clear(); 2201 } 2202 } 2203 2204 ApplicationPackageManager(ContextImpl context, 2205 IPackageManager pm) { 2206 mContext = context; 2207 mPM = pm; 2208 } 2209 2210 private Drawable getCachedIcon(ResourceName name) { 2211 synchronized (sSync) { 2212 WeakReference<Drawable> wr = sIconCache.get(name); 2213 if (DEBUG_ICONS) Log.v(TAG, "Get cached weak drawable ref for " 2214 + name + ": " + wr); 2215 if (wr != null) { // we have the activity 2216 Drawable dr = wr.get(); 2217 if (dr != null) { 2218 if (DEBUG_ICONS) Log.v(TAG, "Get cached drawable for " 2219 + name + ": " + dr); 2220 return dr; 2221 } 2222 // our entry has been purged 2223 sIconCache.remove(name); 2224 } 2225 } 2226 return null; 2227 } 2228 2229 private void establishPackageRemovedReceiver() { 2230 // mContext.registerReceiverInternal() winds up acquiring the 2231 // main ActivityManagerService.this lock. If we hold our usual 2232 // sSync global lock at the same time, we impose a required ordering 2233 // on those two locks, which is not good for deadlock prevention. 2234 // Use a dedicated lock around initialization of 2235 // sPackageRemovedReceiver to avoid this. 2236 synchronized (sPackageRemovedSync) { 2237 if (sPackageRemovedReceiver == null) { 2238 sPackageRemovedReceiver = new PackageRemovedReceiver(); 2239 IntentFilter filter = new IntentFilter( 2240 Intent.ACTION_PACKAGE_REMOVED); 2241 filter.addDataScheme("package"); 2242 mContext.registerReceiverInternal(sPackageRemovedReceiver, 2243 filter, null, null, null); 2244 // Register for events related to sdcard installation. 2245 IntentFilter sdFilter = new IntentFilter(); 2246 sdFilter.addAction(Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE); 2247 mContext.registerReceiverInternal(sPackageRemovedReceiver, 2248 sdFilter, null, null, null); 2249 } 2250 } 2251 } 2252 2253 private void putCachedIcon(ResourceName name, Drawable dr) { 2254 establishPackageRemovedReceiver(); 2255 2256 synchronized (sSync) { 2257 sIconCache.put(name, new WeakReference<Drawable>(dr)); 2258 if (DEBUG_ICONS) Log.v(TAG, "Added cached drawable for " 2259 + name + ": " + dr); 2260 } 2261 } 2262 2263 private static final class PackageRemovedReceiver extends BroadcastReceiver { 2264 @Override 2265 public void onReceive(Context context, Intent intent) { 2266 String pkgList[] = null; 2267 String action = intent.getAction(); 2268 boolean immediateGc = false; 2269 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(action)) { 2270 pkgList = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 2271 immediateGc = true; 2272 } else { 2273 Uri data = intent.getData(); 2274 if (data != null) { 2275 String ssp = data.getSchemeSpecificPart(); 2276 if (ssp != null) { 2277 pkgList = new String[] { ssp }; 2278 } 2279 } 2280 } 2281 if (pkgList != null && (pkgList.length > 0)) { 2282 boolean needCleanup = false; 2283 boolean hasPkgInfo = false; 2284 for (String ssp : pkgList) { 2285 synchronized (sSync) { 2286 Iterator<ResourceName> it = sIconCache.keySet().iterator(); 2287 while (it.hasNext()) { 2288 ResourceName nm = it.next(); 2289 if (nm.packageName.equals(ssp)) { 2290 //Log.i(TAG, "Removing cached drawable for " + nm); 2291 it.remove(); 2292 needCleanup = true; 2293 } 2294 } 2295 it = sStringCache.keySet().iterator(); 2296 while (it.hasNext()) { 2297 ResourceName nm = it.next(); 2298 if (nm.packageName.equals(ssp)) { 2299 //Log.i(TAG, "Removing cached string for " + nm); 2300 it.remove(); 2301 needCleanup = true; 2302 } 2303 } 2304 } 2305 if (!hasPkgInfo) { 2306 hasPkgInfo = ActivityThread.currentActivityThread().hasPackageInfo(ssp); 2307 } 2308 } 2309 if (needCleanup || hasPkgInfo) { 2310 if (immediateGc) { 2311 // Schedule an immediate gc. 2312 Runtime.getRuntime().gc(); 2313 } else { 2314 ActivityThread.currentActivityThread().scheduleGcIdler(); 2315 } 2316 } 2317 } 2318 } 2319 } 2320 2321 private static final class ResourceName { 2322 final String packageName; 2323 final int iconId; 2324 2325 ResourceName(String _packageName, int _iconId) { 2326 packageName = _packageName; 2327 iconId = _iconId; 2328 } 2329 2330 ResourceName(ApplicationInfo aInfo, int _iconId) { 2331 this(aInfo.packageName, _iconId); 2332 } 2333 2334 ResourceName(ComponentInfo cInfo, int _iconId) { 2335 this(cInfo.applicationInfo.packageName, _iconId); 2336 } 2337 2338 ResourceName(ResolveInfo rInfo, int _iconId) { 2339 this(rInfo.activityInfo.applicationInfo.packageName, _iconId); 2340 } 2341 2342 @Override 2343 public boolean equals(Object o) { 2344 if (this == o) return true; 2345 if (o == null || getClass() != o.getClass()) return false; 2346 2347 ResourceName that = (ResourceName) o; 2348 2349 if (iconId != that.iconId) return false; 2350 return !(packageName != null ? 2351 !packageName.equals(that.packageName) : that.packageName != null); 2352 2353 } 2354 2355 @Override 2356 public int hashCode() { 2357 int result; 2358 result = packageName.hashCode(); 2359 result = 31 * result + iconId; 2360 return result; 2361 } 2362 2363 @Override 2364 public String toString() { 2365 return "{ResourceName " + packageName + " / " + iconId + "}"; 2366 } 2367 } 2368 2369 private CharSequence getCachedString(ResourceName name) { 2370 synchronized (sSync) { 2371 WeakReference<CharSequence> wr = sStringCache.get(name); 2372 if (wr != null) { // we have the activity 2373 CharSequence cs = wr.get(); 2374 if (cs != null) { 2375 return cs; 2376 } 2377 // our entry has been purged 2378 sStringCache.remove(name); 2379 } 2380 } 2381 return null; 2382 } 2383 2384 private void putCachedString(ResourceName name, CharSequence cs) { 2385 establishPackageRemovedReceiver(); 2386 2387 synchronized (sSync) { 2388 sStringCache.put(name, new WeakReference<CharSequence>(cs)); 2389 } 2390 } 2391 2392 @Override 2393 public CharSequence getText(String packageName, int resid, 2394 ApplicationInfo appInfo) { 2395 ResourceName name = new ResourceName(packageName, resid); 2396 CharSequence text = getCachedString(name); 2397 if (text != null) { 2398 return text; 2399 } 2400 if (appInfo == null) { 2401 try { 2402 appInfo = getApplicationInfo(packageName, 0); 2403 } catch (NameNotFoundException e) { 2404 return null; 2405 } 2406 } 2407 try { 2408 Resources r = getResourcesForApplication(appInfo); 2409 text = r.getText(resid); 2410 putCachedString(name, text); 2411 return text; 2412 } catch (NameNotFoundException e) { 2413 Log.w("PackageManager", "Failure retrieving resources for" 2414 + appInfo.packageName); 2415 } catch (RuntimeException e) { 2416 // If an exception was thrown, fall through to return 2417 // default icon. 2418 Log.w("PackageManager", "Failure retrieving text 0x" 2419 + Integer.toHexString(resid) + " in package " 2420 + packageName, e); 2421 } 2422 return null; 2423 } 2424 2425 @Override 2426 public XmlResourceParser getXml(String packageName, int resid, 2427 ApplicationInfo appInfo) { 2428 if (appInfo == null) { 2429 try { 2430 appInfo = getApplicationInfo(packageName, 0); 2431 } catch (NameNotFoundException e) { 2432 return null; 2433 } 2434 } 2435 try { 2436 Resources r = getResourcesForApplication(appInfo); 2437 return r.getXml(resid); 2438 } catch (RuntimeException e) { 2439 // If an exception was thrown, fall through to return 2440 // default icon. 2441 Log.w("PackageManager", "Failure retrieving xml 0x" 2442 + Integer.toHexString(resid) + " in package " 2443 + packageName, e); 2444 } catch (NameNotFoundException e) { 2445 Log.w("PackageManager", "Failure retrieving resources for" 2446 + appInfo.packageName); 2447 } 2448 return null; 2449 } 2450 2451 @Override 2452 public CharSequence getApplicationLabel(ApplicationInfo info) { 2453 return info.loadLabel(this); 2454 } 2455 2456 @Override 2457 public void installPackage(Uri packageURI, IPackageInstallObserver observer, int flags, 2458 String installerPackageName) { 2459 try { 2460 mPM.installPackage(packageURI, observer, flags, installerPackageName); 2461 } catch (RemoteException e) { 2462 // Should never happen! 2463 } 2464 } 2465 2466 @Override 2467 public void movePackage(String packageName, IPackageMoveObserver observer, int flags) { 2468 try { 2469 mPM.movePackage(packageName, observer, flags); 2470 } catch (RemoteException e) { 2471 // Should never happen! 2472 } 2473 } 2474 2475 @Override 2476 public String getInstallerPackageName(String packageName) { 2477 try { 2478 return mPM.getInstallerPackageName(packageName); 2479 } catch (RemoteException e) { 2480 // Should never happen! 2481 } 2482 return null; 2483 } 2484 2485 @Override 2486 public void deletePackage(String packageName, IPackageDeleteObserver observer, int flags) { 2487 try { 2488 mPM.deletePackage(packageName, observer, flags); 2489 } catch (RemoteException e) { 2490 // Should never happen! 2491 } 2492 } 2493 @Override 2494 public void clearApplicationUserData(String packageName, 2495 IPackageDataObserver observer) { 2496 try { 2497 mPM.clearApplicationUserData(packageName, observer); 2498 } catch (RemoteException e) { 2499 // Should never happen! 2500 } 2501 } 2502 @Override 2503 public void deleteApplicationCacheFiles(String packageName, 2504 IPackageDataObserver observer) { 2505 try { 2506 mPM.deleteApplicationCacheFiles(packageName, observer); 2507 } catch (RemoteException e) { 2508 // Should never happen! 2509 } 2510 } 2511 @Override 2512 public void freeStorageAndNotify(long idealStorageSize, IPackageDataObserver observer) { 2513 try { 2514 mPM.freeStorageAndNotify(idealStorageSize, observer); 2515 } catch (RemoteException e) { 2516 // Should never happen! 2517 } 2518 } 2519 2520 @Override 2521 public void freeStorage(long freeStorageSize, IntentSender pi) { 2522 try { 2523 mPM.freeStorage(freeStorageSize, pi); 2524 } catch (RemoteException e) { 2525 // Should never happen! 2526 } 2527 } 2528 2529 @Override 2530 public void getPackageSizeInfo(String packageName, 2531 IPackageStatsObserver observer) { 2532 try { 2533 mPM.getPackageSizeInfo(packageName, observer); 2534 } catch (RemoteException e) { 2535 // Should never happen! 2536 } 2537 } 2538 @Override 2539 public void addPackageToPreferred(String packageName) { 2540 try { 2541 mPM.addPackageToPreferred(packageName); 2542 } catch (RemoteException e) { 2543 // Should never happen! 2544 } 2545 } 2546 2547 @Override 2548 public void removePackageFromPreferred(String packageName) { 2549 try { 2550 mPM.removePackageFromPreferred(packageName); 2551 } catch (RemoteException e) { 2552 // Should never happen! 2553 } 2554 } 2555 2556 @Override 2557 public List<PackageInfo> getPreferredPackages(int flags) { 2558 try { 2559 return mPM.getPreferredPackages(flags); 2560 } catch (RemoteException e) { 2561 // Should never happen! 2562 } 2563 return new ArrayList<PackageInfo>(); 2564 } 2565 2566 @Override 2567 public void addPreferredActivity(IntentFilter filter, 2568 int match, ComponentName[] set, ComponentName activity) { 2569 try { 2570 mPM.addPreferredActivity(filter, match, set, activity); 2571 } catch (RemoteException e) { 2572 // Should never happen! 2573 } 2574 } 2575 2576 @Override 2577 public void replacePreferredActivity(IntentFilter filter, 2578 int match, ComponentName[] set, ComponentName activity) { 2579 try { 2580 mPM.replacePreferredActivity(filter, match, set, activity); 2581 } catch (RemoteException e) { 2582 // Should never happen! 2583 } 2584 } 2585 2586 @Override 2587 public void clearPackagePreferredActivities(String packageName) { 2588 try { 2589 mPM.clearPackagePreferredActivities(packageName); 2590 } catch (RemoteException e) { 2591 // Should never happen! 2592 } 2593 } 2594 2595 @Override 2596 public int getPreferredActivities(List<IntentFilter> outFilters, 2597 List<ComponentName> outActivities, String packageName) { 2598 try { 2599 return mPM.getPreferredActivities(outFilters, outActivities, packageName); 2600 } catch (RemoteException e) { 2601 // Should never happen! 2602 } 2603 return 0; 2604 } 2605 2606 @Override 2607 public void setComponentEnabledSetting(ComponentName componentName, 2608 int newState, int flags) { 2609 try { 2610 mPM.setComponentEnabledSetting(componentName, newState, flags); 2611 } catch (RemoteException e) { 2612 // Should never happen! 2613 } 2614 } 2615 2616 @Override 2617 public int getComponentEnabledSetting(ComponentName componentName) { 2618 try { 2619 return mPM.getComponentEnabledSetting(componentName); 2620 } catch (RemoteException e) { 2621 // Should never happen! 2622 } 2623 return PackageManager.COMPONENT_ENABLED_STATE_DEFAULT; 2624 } 2625 2626 @Override 2627 public void setApplicationEnabledSetting(String packageName, 2628 int newState, int flags) { 2629 try { 2630 mPM.setApplicationEnabledSetting(packageName, newState, flags); 2631 } catch (RemoteException e) { 2632 // Should never happen! 2633 } 2634 } 2635 2636 @Override 2637 public int getApplicationEnabledSetting(String packageName) { 2638 try { 2639 return mPM.getApplicationEnabledSetting(packageName); 2640 } catch (RemoteException e) { 2641 // Should never happen! 2642 } 2643 return PackageManager.COMPONENT_ENABLED_STATE_DEFAULT; 2644 } 2645 2646 private final ContextImpl mContext; 2647 private final IPackageManager mPM; 2648 2649 private static final Object sSync = new Object(); 2650 private static final Object sPackageRemovedSync = new Object(); 2651 private static BroadcastReceiver sPackageRemovedReceiver; 2652 private static HashMap<ResourceName, WeakReference<Drawable> > sIconCache 2653 = new HashMap<ResourceName, WeakReference<Drawable> >(); 2654 private static HashMap<ResourceName, WeakReference<CharSequence> > sStringCache 2655 = new HashMap<ResourceName, WeakReference<CharSequence> >(); 2656 } 2657 2658 // ---------------------------------------------------------------------- 2659 // ---------------------------------------------------------------------- 2660 // ---------------------------------------------------------------------- 2661 2662 private static final class SharedPreferencesImpl implements SharedPreferences { 2663 2664 private final File mFile; 2665 private final File mBackupFile; 2666 private final int mMode; 2667 private Map mMap; 2668 private final FileStatus mFileStatus = new FileStatus(); 2669 private long mTimestamp; 2670 2671 private static final Object mContent = new Object(); 2672 private WeakHashMap<OnSharedPreferenceChangeListener, Object> mListeners; 2673 2674 SharedPreferencesImpl( 2675 File file, int mode, Map initialContents) { 2676 mFile = file; 2677 mBackupFile = makeBackupFile(file); 2678 mMode = mode; 2679 mMap = initialContents != null ? initialContents : new HashMap(); 2680 if (FileUtils.getFileStatus(file.getPath(), mFileStatus)) { 2681 mTimestamp = mFileStatus.mtime; 2682 } 2683 mListeners = new WeakHashMap<OnSharedPreferenceChangeListener, Object>(); 2684 } 2685 2686 public boolean hasFileChanged() { 2687 synchronized (this) { 2688 if (!FileUtils.getFileStatus(mFile.getPath(), mFileStatus)) { 2689 return true; 2690 } 2691 return mTimestamp != mFileStatus.mtime; 2692 } 2693 } 2694 2695 public void replace(Map newContents) { 2696 if (newContents != null) { 2697 synchronized (this) { 2698 mMap = newContents; 2699 } 2700 } 2701 } 2702 2703 public void registerOnSharedPreferenceChangeListener(OnSharedPreferenceChangeListener listener) { 2704 synchronized(this) { 2705 mListeners.put(listener, mContent); 2706 } 2707 } 2708 2709 public void unregisterOnSharedPreferenceChangeListener(OnSharedPreferenceChangeListener listener) { 2710 synchronized(this) { 2711 mListeners.remove(listener); 2712 } 2713 } 2714 2715 public Map<String, ?> getAll() { 2716 synchronized(this) { 2717 //noinspection unchecked 2718 return new HashMap(mMap); 2719 } 2720 } 2721 2722 public String getString(String key, String defValue) { 2723 synchronized (this) { 2724 String v = (String)mMap.get(key); 2725 return v != null ? v : defValue; 2726 } 2727 } 2728 2729 public int getInt(String key, int defValue) { 2730 synchronized (this) { 2731 Integer v = (Integer)mMap.get(key); 2732 return v != null ? v : defValue; 2733 } 2734 } 2735 public long getLong(String key, long defValue) { 2736 synchronized (this) { 2737 Long v = (Long) mMap.get(key); 2738 return v != null ? v : defValue; 2739 } 2740 } 2741 public float getFloat(String key, float defValue) { 2742 synchronized (this) { 2743 Float v = (Float)mMap.get(key); 2744 return v != null ? v : defValue; 2745 } 2746 } 2747 public boolean getBoolean(String key, boolean defValue) { 2748 synchronized (this) { 2749 Boolean v = (Boolean)mMap.get(key); 2750 return v != null ? v : defValue; 2751 } 2752 } 2753 2754 public boolean contains(String key) { 2755 synchronized (this) { 2756 return mMap.containsKey(key); 2757 } 2758 } 2759 2760 public final class EditorImpl implements Editor { 2761 private final Map<String, Object> mModified = Maps.newHashMap(); 2762 private boolean mClear = false; 2763 2764 public Editor putString(String key, String value) { 2765 synchronized (this) { 2766 mModified.put(key, value); 2767 return this; 2768 } 2769 } 2770 public Editor putInt(String key, int value) { 2771 synchronized (this) { 2772 mModified.put(key, value); 2773 return this; 2774 } 2775 } 2776 public Editor putLong(String key, long value) { 2777 synchronized (this) { 2778 mModified.put(key, value); 2779 return this; 2780 } 2781 } 2782 public Editor putFloat(String key, float value) { 2783 synchronized (this) { 2784 mModified.put(key, value); 2785 return this; 2786 } 2787 } 2788 public Editor putBoolean(String key, boolean value) { 2789 synchronized (this) { 2790 mModified.put(key, value); 2791 return this; 2792 } 2793 } 2794 2795 public Editor remove(String key) { 2796 synchronized (this) { 2797 mModified.put(key, this); 2798 return this; 2799 } 2800 } 2801 2802 public Editor clear() { 2803 synchronized (this) { 2804 mClear = true; 2805 return this; 2806 } 2807 } 2808 2809 public boolean commit() { 2810 boolean returnValue; 2811 2812 boolean hasListeners; 2813 List<String> keysModified = null; 2814 Set<OnSharedPreferenceChangeListener> listeners = null; 2815 2816 synchronized (SharedPreferencesImpl.this) { 2817 hasListeners = mListeners.size() > 0; 2818 if (hasListeners) { 2819 keysModified = new ArrayList<String>(); 2820 listeners = 2821 new HashSet<OnSharedPreferenceChangeListener>(mListeners.keySet()); 2822 } 2823 2824 synchronized (this) { 2825 if (mClear) { 2826 mMap.clear(); 2827 mClear = false; 2828 } 2829 2830 for (Entry<String, Object> e : mModified.entrySet()) { 2831 String k = e.getKey(); 2832 Object v = e.getValue(); 2833 if (v == this) { 2834 mMap.remove(k); 2835 } else { 2836 mMap.put(k, v); 2837 } 2838 2839 if (hasListeners) { 2840 keysModified.add(k); 2841 } 2842 } 2843 2844 mModified.clear(); 2845 } 2846 2847 returnValue = writeFileLocked(); 2848 } 2849 2850 if (hasListeners) { 2851 for (int i = keysModified.size() - 1; i >= 0; i--) { 2852 final String key = keysModified.get(i); 2853 for (OnSharedPreferenceChangeListener listener : listeners) { 2854 if (listener != null) { 2855 listener.onSharedPreferenceChanged(SharedPreferencesImpl.this, key); 2856 } 2857 } 2858 } 2859 } 2860 2861 return returnValue; 2862 } 2863 } 2864 2865 public Editor edit() { 2866 return new EditorImpl(); 2867 } 2868 2869 private FileOutputStream createFileOutputStream(File file) { 2870 FileOutputStream str = null; 2871 try { 2872 str = new FileOutputStream(file); 2873 } catch (FileNotFoundException e) { 2874 File parent = file.getParentFile(); 2875 if (!parent.mkdir()) { 2876 Log.e(TAG, "Couldn't create directory for SharedPreferences file " + file); 2877 return null; 2878 } 2879 FileUtils.setPermissions( 2880 parent.getPath(), 2881 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH, 2882 -1, -1); 2883 try { 2884 str = new FileOutputStream(file); 2885 } catch (FileNotFoundException e2) { 2886 Log.e(TAG, "Couldn't create SharedPreferences file " + file, e2); 2887 } 2888 } 2889 return str; 2890 } 2891 2892 private boolean writeFileLocked() { 2893 // Rename the current file so it may be used as a backup during the next read 2894 if (mFile.exists()) { 2895 if (!mBackupFile.exists()) { 2896 if (!mFile.renameTo(mBackupFile)) { 2897 Log.e(TAG, "Couldn't rename file " + mFile 2898 + " to backup file " + mBackupFile); 2899 return false; 2900 } 2901 } else { 2902 mFile.delete(); 2903 } 2904 } 2905 2906 // Attempt to write the file, delete the backup and return true as atomically as 2907 // possible. If any exception occurs, delete the new file; next time we will restore 2908 // from the backup. 2909 try { 2910 FileOutputStream str = createFileOutputStream(mFile); 2911 if (str == null) { 2912 return false; 2913 } 2914 XmlUtils.writeMapXml(mMap, str); 2915 str.close(); 2916 setFilePermissionsFromMode(mFile.getPath(), mMode, 0); 2917 if (FileUtils.getFileStatus(mFile.getPath(), mFileStatus)) { 2918 mTimestamp = mFileStatus.mtime; 2919 } 2920 2921 // Writing was successful, delete the backup file if there is one. 2922 mBackupFile.delete(); 2923 return true; 2924 } catch (XmlPullParserException e) { 2925 Log.w(TAG, "writeFileLocked: Got exception:", e); 2926 } catch (IOException e) { 2927 Log.w(TAG, "writeFileLocked: Got exception:", e); 2928 } 2929 // Clean up an unsuccessfully written file 2930 if (mFile.exists()) { 2931 if (!mFile.delete()) { 2932 Log.e(TAG, "Couldn't clean up partially-written file " + mFile); 2933 } 2934 } 2935 return false; 2936 } 2937 } 2938} 2939