ContextImpl.java revision 6c418d585e0a91054b168fde3130188afd006c98
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; 20 21import android.content.BroadcastReceiver; 22import android.content.ComponentName; 23import android.content.ContentResolver; 24import android.content.Context; 25import android.content.ContextWrapper; 26import android.content.IContentProvider; 27import android.content.Intent; 28import android.content.IntentFilter; 29import android.content.IIntentReceiver; 30import android.content.IntentSender; 31import android.content.ReceiverCallNotAllowedException; 32import android.content.ServiceConnection; 33import android.content.SharedPreferences; 34import android.content.pm.ApplicationInfo; 35import android.content.pm.IPackageManager; 36import android.content.pm.PackageManager; 37import android.content.res.AssetManager; 38import android.content.res.CompatibilityInfo; 39import android.content.res.Resources; 40import android.database.DatabaseErrorHandler; 41import android.database.sqlite.SQLiteDatabase; 42import android.database.sqlite.SQLiteDatabase.CursorFactory; 43import android.graphics.Bitmap; 44import android.graphics.drawable.Drawable; 45import android.hardware.SensorManager; 46import android.hardware.usb.IUsbManager; 47import android.hardware.usb.UsbManager; 48import android.location.CountryDetector; 49import android.location.ICountryDetector; 50import android.location.ILocationManager; 51import android.location.LocationManager; 52import android.media.AudioManager; 53import android.net.ConnectivityManager; 54import android.net.IConnectivityManager; 55import android.net.INetworkPolicyManager; 56import android.net.NetworkPolicyManager; 57import android.net.ThrottleManager; 58import android.net.IThrottleManager; 59import android.net.Uri; 60import android.net.wifi.IWifiManager; 61import android.net.wifi.WifiManager; 62import android.nfc.NfcManager; 63import android.os.Binder; 64import android.os.Bundle; 65import android.os.DropBoxManager; 66import android.os.Environment; 67import android.os.FileUtils; 68import android.os.Handler; 69import android.os.IBinder; 70import android.os.IPowerManager; 71import android.os.Looper; 72import android.os.PowerManager; 73import android.os.Process; 74import android.os.RemoteException; 75import android.os.ServiceManager; 76import android.os.Vibrator; 77import android.os.storage.StorageManager; 78import android.telephony.TelephonyManager; 79import android.content.ClipboardManager; 80import android.util.AndroidRuntimeException; 81import android.util.Log; 82import android.view.ContextThemeWrapper; 83import android.view.WindowManagerImpl; 84import android.view.accessibility.AccessibilityManager; 85import android.view.inputmethod.InputMethodManager; 86import android.accounts.AccountManager; 87import android.accounts.IAccountManager; 88import android.app.admin.DevicePolicyManager; 89import com.android.internal.os.IDropBoxManagerService; 90 91import java.io.File; 92import java.io.FileInputStream; 93import java.io.FileNotFoundException; 94import java.io.FileOutputStream; 95import java.io.IOException; 96import java.io.InputStream; 97import java.util.ArrayList; 98import java.util.HashMap; 99 100class ReceiverRestrictedContext extends ContextWrapper { 101 ReceiverRestrictedContext(Context base) { 102 super(base); 103 } 104 105 @Override 106 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter) { 107 return registerReceiver(receiver, filter, null, null); 108 } 109 110 @Override 111 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter, 112 String broadcastPermission, Handler scheduler) { 113 throw new ReceiverCallNotAllowedException( 114 "IntentReceiver components are not allowed to register to receive intents"); 115 //ex.fillInStackTrace(); 116 //Log.e("IntentReceiver", ex.getMessage(), ex); 117 //return mContext.registerReceiver(receiver, filter, broadcastPermission, 118 // scheduler); 119 } 120 121 @Override 122 public boolean bindService(Intent service, ServiceConnection conn, int flags) { 123 throw new ReceiverCallNotAllowedException( 124 "IntentReceiver components are not allowed to bind to services"); 125 //ex.fillInStackTrace(); 126 //Log.e("IntentReceiver", ex.getMessage(), ex); 127 //return mContext.bindService(service, interfaceName, conn, flags); 128 } 129} 130 131/** 132 * Common implementation of Context API, which provides the base 133 * context object for Activity and other application components. 134 */ 135class ContextImpl extends Context { 136 private final static String TAG = "ApplicationContext"; 137 private final static boolean DEBUG = false; 138 139 private static final HashMap<String, SharedPreferencesImpl> sSharedPrefs = 140 new HashMap<String, SharedPreferencesImpl>(); 141 142 /*package*/ LoadedApk mPackageInfo; 143 private String mBasePackageName; 144 private Resources mResources; 145 /*package*/ ActivityThread mMainThread; 146 private Context mOuterContext; 147 private IBinder mActivityToken = null; 148 private ApplicationContentResolver mContentResolver; 149 private int mThemeResource = 0; 150 private Resources.Theme mTheme = null; 151 private PackageManager mPackageManager; 152 private Context mReceiverRestrictedContext = null; 153 private boolean mRestricted; 154 155 private final Object mSync = new Object(); 156 157 private File mDatabasesDir; 158 private File mPreferencesDir; 159 private File mFilesDir; 160 private File mCacheDir; 161 private File mObbDir; 162 private File mExternalFilesDir; 163 private File mExternalCacheDir; 164 165 private static final String[] EMPTY_FILE_LIST = {}; 166 167 /** 168 * Override this class when the system service constructor needs a 169 * ContextImpl. Else, use StaticServiceFetcher below. 170 */ 171 /*package*/ static class ServiceFetcher { 172 int mContextCacheIndex = -1; 173 174 /** 175 * Main entrypoint; only override if you don't need caching. 176 */ 177 public Object getService(ContextImpl ctx) { 178 ArrayList<Object> cache = ctx.mServiceCache; 179 Object service; 180 synchronized (cache) { 181 if (cache.size() == 0) { 182 // Initialize the cache vector on first access. 183 // At this point sNextPerContextServiceCacheIndex 184 // is the number of potential services that are 185 // cached per-Context. 186 for (int i = 0; i < sNextPerContextServiceCacheIndex; i++) { 187 cache.add(null); 188 } 189 } else { 190 service = cache.get(mContextCacheIndex); 191 if (service != null) { 192 return service; 193 } 194 } 195 service = createService(ctx); 196 cache.set(mContextCacheIndex, service); 197 return service; 198 } 199 } 200 201 /** 202 * Override this to create a new per-Context instance of the 203 * service. getService() will handle locking and caching. 204 */ 205 public Object createService(ContextImpl ctx) { 206 throw new RuntimeException("Not implemented"); 207 } 208 } 209 210 /** 211 * Override this class for services to be cached process-wide. 212 */ 213 abstract static class StaticServiceFetcher extends ServiceFetcher { 214 private Object mCachedInstance; 215 216 @Override 217 public final Object getService(ContextImpl unused) { 218 synchronized (StaticServiceFetcher.this) { 219 Object service = mCachedInstance; 220 if (service != null) { 221 return service; 222 } 223 return mCachedInstance = createStaticService(); 224 } 225 } 226 227 public abstract Object createStaticService(); 228 } 229 230 private static final HashMap<String, ServiceFetcher> SYSTEM_SERVICE_MAP = 231 new HashMap<String, ServiceFetcher>(); 232 233 private static int sNextPerContextServiceCacheIndex = 0; 234 private static void registerService(String serviceName, ServiceFetcher fetcher) { 235 if (!(fetcher instanceof StaticServiceFetcher)) { 236 fetcher.mContextCacheIndex = sNextPerContextServiceCacheIndex++; 237 } 238 SYSTEM_SERVICE_MAP.put(serviceName, fetcher); 239 } 240 241 // This one's defined separately and given a variable name so it 242 // can be re-used by getWallpaperManager(), avoiding a HashMap 243 // lookup. 244 private static ServiceFetcher WALLPAPER_FETCHER = new ServiceFetcher() { 245 public Object createService(ContextImpl ctx) { 246 return new WallpaperManager(ctx.getOuterContext(), 247 ctx.mMainThread.getHandler()); 248 }}; 249 250 static { 251 registerService(ACCESSIBILITY_SERVICE, new ServiceFetcher() { 252 public Object getService(ContextImpl ctx) { 253 return AccessibilityManager.getInstance(ctx); 254 }}); 255 256 registerService(ACCOUNT_SERVICE, new ServiceFetcher() { 257 public Object createService(ContextImpl ctx) { 258 IBinder b = ServiceManager.getService(ACCOUNT_SERVICE); 259 IAccountManager service = IAccountManager.Stub.asInterface(b); 260 return new AccountManager(ctx, service); 261 }}); 262 263 registerService(ACTIVITY_SERVICE, new ServiceFetcher() { 264 public Object createService(ContextImpl ctx) { 265 return new ActivityManager(ctx.getOuterContext(), ctx.mMainThread.getHandler()); 266 }}); 267 268 registerService(ALARM_SERVICE, new StaticServiceFetcher() { 269 public Object createStaticService() { 270 IBinder b = ServiceManager.getService(ALARM_SERVICE); 271 IAlarmManager service = IAlarmManager.Stub.asInterface(b); 272 return new AlarmManager(service); 273 }}); 274 275 registerService(AUDIO_SERVICE, new ServiceFetcher() { 276 public Object createService(ContextImpl ctx) { 277 return new AudioManager(ctx); 278 }}); 279 280 registerService(CLIPBOARD_SERVICE, new ServiceFetcher() { 281 public Object createService(ContextImpl ctx) { 282 return new ClipboardManager(ctx.getOuterContext(), 283 ctx.mMainThread.getHandler()); 284 }}); 285 286 registerService(CONNECTIVITY_SERVICE, new StaticServiceFetcher() { 287 public Object createStaticService() { 288 IBinder b = ServiceManager.getService(CONNECTIVITY_SERVICE); 289 return new ConnectivityManager(IConnectivityManager.Stub.asInterface(b)); 290 }}); 291 292 registerService(COUNTRY_DETECTOR, new StaticServiceFetcher() { 293 public Object createStaticService() { 294 IBinder b = ServiceManager.getService(COUNTRY_DETECTOR); 295 return new CountryDetector(ICountryDetector.Stub.asInterface(b)); 296 }}); 297 298 registerService(DEVICE_POLICY_SERVICE, new ServiceFetcher() { 299 public Object createService(ContextImpl ctx) { 300 return DevicePolicyManager.create(ctx, ctx.mMainThread.getHandler()); 301 }}); 302 303 registerService(DOWNLOAD_SERVICE, new ServiceFetcher() { 304 public Object createService(ContextImpl ctx) { 305 return new DownloadManager(ctx.getContentResolver(), ctx.getPackageName()); 306 }}); 307 308 registerService(NFC_SERVICE, new ServiceFetcher() { 309 public Object createService(ContextImpl ctx) { 310 return new NfcManager(ctx); 311 }}); 312 313 registerService(DROPBOX_SERVICE, new StaticServiceFetcher() { 314 public Object createStaticService() { 315 return createDropBoxManager(); 316 }}); 317 318 registerService(INPUT_METHOD_SERVICE, new ServiceFetcher() { 319 public Object createService(ContextImpl ctx) { 320 return InputMethodManager.getInstance(ctx); 321 }}); 322 323 registerService(KEYGUARD_SERVICE, new ServiceFetcher() { 324 public Object getService(ContextImpl ctx) { 325 // TODO: why isn't this caching it? It wasn't 326 // before, so I'm preserving the old behavior and 327 // using getService(), instead of createService() 328 // which would do the caching. 329 return new KeyguardManager(); 330 }}); 331 332 registerService(LAYOUT_INFLATER_SERVICE, new ServiceFetcher() { 333 public Object createService(ContextImpl ctx) { 334 return PolicyManager.makeNewLayoutInflater(ctx.getOuterContext()); 335 }}); 336 337 registerService(LOCATION_SERVICE, new StaticServiceFetcher() { 338 public Object createStaticService() { 339 IBinder b = ServiceManager.getService(LOCATION_SERVICE); 340 return new LocationManager(ILocationManager.Stub.asInterface(b)); 341 }}); 342 343 registerService(NETWORK_POLICY_SERVICE, new ServiceFetcher() { 344 @Override 345 public Object createService(ContextImpl ctx) { 346 return new NetworkPolicyManager(INetworkPolicyManager.Stub.asInterface( 347 ServiceManager.getService(NETWORK_POLICY_SERVICE))); 348 } 349 }); 350 351 registerService(NOTIFICATION_SERVICE, new ServiceFetcher() { 352 public Object createService(ContextImpl ctx) { 353 final Context outerContext = ctx.getOuterContext(); 354 return new NotificationManager( 355 new ContextThemeWrapper(outerContext, 356 Resources.selectSystemTheme(0, 357 outerContext.getApplicationInfo().targetSdkVersion, 358 com.android.internal.R.style.Theme_Dialog, 359 com.android.internal.R.style.Theme_Holo_Dialog)), 360 ctx.mMainThread.getHandler()); 361 }}); 362 363 // Note: this was previously cached in a static variable, but 364 // constructed using mMainThread.getHandler(), so converting 365 // it to be a regular Context-cached service... 366 registerService(POWER_SERVICE, new ServiceFetcher() { 367 public Object createService(ContextImpl ctx) { 368 IBinder b = ServiceManager.getService(POWER_SERVICE); 369 IPowerManager service = IPowerManager.Stub.asInterface(b); 370 return new PowerManager(service, ctx.mMainThread.getHandler()); 371 }}); 372 373 registerService(SEARCH_SERVICE, new ServiceFetcher() { 374 public Object createService(ContextImpl ctx) { 375 return new SearchManager(ctx.getOuterContext(), 376 ctx.mMainThread.getHandler()); 377 }}); 378 379 registerService(SENSOR_SERVICE, new ServiceFetcher() { 380 public Object createService(ContextImpl ctx) { 381 return new SensorManager(ctx.mMainThread.getHandler().getLooper()); 382 }}); 383 384 registerService(STATUS_BAR_SERVICE, new ServiceFetcher() { 385 public Object createService(ContextImpl ctx) { 386 return new StatusBarManager(ctx.getOuterContext()); 387 }}); 388 389 registerService(STORAGE_SERVICE, new ServiceFetcher() { 390 public Object createService(ContextImpl ctx) { 391 try { 392 return new StorageManager(ctx.mMainThread.getHandler().getLooper()); 393 } catch (RemoteException rex) { 394 Log.e(TAG, "Failed to create StorageManager", rex); 395 return null; 396 } 397 }}); 398 399 registerService(TELEPHONY_SERVICE, new ServiceFetcher() { 400 public Object createService(ContextImpl ctx) { 401 return new TelephonyManager(ctx.getOuterContext()); 402 }}); 403 404 registerService(THROTTLE_SERVICE, new StaticServiceFetcher() { 405 public Object createStaticService() { 406 IBinder b = ServiceManager.getService(THROTTLE_SERVICE); 407 return new ThrottleManager(IThrottleManager.Stub.asInterface(b)); 408 }}); 409 410 registerService(UI_MODE_SERVICE, new ServiceFetcher() { 411 public Object createService(ContextImpl ctx) { 412 return new UiModeManager(); 413 }}); 414 415 registerService(USB_SERVICE, new ServiceFetcher() { 416 public Object createService(ContextImpl ctx) { 417 IBinder b = ServiceManager.getService(USB_SERVICE); 418 return new UsbManager(ctx, IUsbManager.Stub.asInterface(b)); 419 }}); 420 421 registerService(VIBRATOR_SERVICE, new ServiceFetcher() { 422 public Object createService(ContextImpl ctx) { 423 return new Vibrator(); 424 }}); 425 426 registerService(WALLPAPER_SERVICE, WALLPAPER_FETCHER); 427 428 registerService(WIFI_SERVICE, new ServiceFetcher() { 429 public Object createService(ContextImpl ctx) { 430 IBinder b = ServiceManager.getService(WIFI_SERVICE); 431 IWifiManager service = IWifiManager.Stub.asInterface(b); 432 return new WifiManager(service, ctx.mMainThread.getHandler()); 433 }}); 434 435 registerService(WINDOW_SERVICE, new ServiceFetcher() { 436 public Object getService(ContextImpl ctx) { 437 return WindowManagerImpl.getDefault(ctx.mPackageInfo.mCompatibilityInfo); 438 }}); 439 } 440 441 static ContextImpl getImpl(Context context) { 442 Context nextContext; 443 while ((context instanceof ContextWrapper) && 444 (nextContext=((ContextWrapper)context).getBaseContext()) != null) { 445 context = nextContext; 446 } 447 return (ContextImpl)context; 448 } 449 450 // The system service cache for the system services that are 451 // cached per-ContextImpl. Package-scoped to avoid accessor 452 // methods. 453 final ArrayList<Object> mServiceCache = new ArrayList<Object>(); 454 455 @Override 456 public AssetManager getAssets() { 457 return mResources.getAssets(); 458 } 459 460 @Override 461 public Resources getResources() { 462 return mResources; 463 } 464 465 @Override 466 public PackageManager getPackageManager() { 467 if (mPackageManager != null) { 468 return mPackageManager; 469 } 470 471 IPackageManager pm = ActivityThread.getPackageManager(); 472 if (pm != null) { 473 // Doesn't matter if we make more than one instance. 474 return (mPackageManager = new ApplicationPackageManager(this, pm)); 475 } 476 477 return null; 478 } 479 480 @Override 481 public ContentResolver getContentResolver() { 482 return mContentResolver; 483 } 484 485 @Override 486 public Looper getMainLooper() { 487 return mMainThread.getLooper(); 488 } 489 490 @Override 491 public Context getApplicationContext() { 492 return (mPackageInfo != null) ? 493 mPackageInfo.getApplication() : mMainThread.getApplication(); 494 } 495 496 @Override 497 public void setTheme(int resid) { 498 mThemeResource = resid; 499 } 500 501 @Override 502 public int getThemeResId() { 503 return mThemeResource; 504 } 505 506 @Override 507 public Resources.Theme getTheme() { 508 if (mTheme == null) { 509 mThemeResource = Resources.selectDefaultTheme(mThemeResource, 510 getOuterContext().getApplicationInfo().targetSdkVersion); 511 mTheme = mResources.newTheme(); 512 mTheme.applyStyle(mThemeResource, true); 513 } 514 return mTheme; 515 } 516 517 @Override 518 public ClassLoader getClassLoader() { 519 return mPackageInfo != null ? 520 mPackageInfo.getClassLoader() : ClassLoader.getSystemClassLoader(); 521 } 522 523 @Override 524 public String getPackageName() { 525 if (mPackageInfo != null) { 526 return mPackageInfo.getPackageName(); 527 } 528 throw new RuntimeException("Not supported in system context"); 529 } 530 531 @Override 532 public ApplicationInfo getApplicationInfo() { 533 if (mPackageInfo != null) { 534 return mPackageInfo.getApplicationInfo(); 535 } 536 throw new RuntimeException("Not supported in system context"); 537 } 538 539 @Override 540 public String getPackageResourcePath() { 541 if (mPackageInfo != null) { 542 return mPackageInfo.getResDir(); 543 } 544 throw new RuntimeException("Not supported in system context"); 545 } 546 547 @Override 548 public String getPackageCodePath() { 549 if (mPackageInfo != null) { 550 return mPackageInfo.getAppDir(); 551 } 552 throw new RuntimeException("Not supported in system context"); 553 } 554 555 public File getSharedPrefsFile(String name) { 556 return makeFilename(getPreferencesDir(), name + ".xml"); 557 } 558 559 @Override 560 public SharedPreferences getSharedPreferences(String name, int mode) { 561 SharedPreferencesImpl sp; 562 synchronized (sSharedPrefs) { 563 sp = sSharedPrefs.get(name); 564 if (sp == null) { 565 File prefsFile = getSharedPrefsFile(name); 566 sp = new SharedPreferencesImpl(prefsFile, mode); 567 sSharedPrefs.put(name, sp); 568 return sp; 569 } 570 } 571 if ((mode & Context.MODE_MULTI_PROCESS) != 0 || 572 getApplicationInfo().targetSdkVersion < android.os.Build.VERSION_CODES.HONEYCOMB) { 573 // If somebody else (some other process) changed the prefs 574 // file behind our back, we reload it. This has been the 575 // historical (if undocumented) behavior. 576 sp.startReloadIfChangedUnexpectedly(); 577 } 578 return sp; 579 } 580 581 private File getPreferencesDir() { 582 synchronized (mSync) { 583 if (mPreferencesDir == null) { 584 mPreferencesDir = new File(getDataDirFile(), "shared_prefs"); 585 } 586 return mPreferencesDir; 587 } 588 } 589 590 @Override 591 public FileInputStream openFileInput(String name) 592 throws FileNotFoundException { 593 File f = makeFilename(getFilesDir(), name); 594 return new FileInputStream(f); 595 } 596 597 @Override 598 public FileOutputStream openFileOutput(String name, int mode) 599 throws FileNotFoundException { 600 final boolean append = (mode&MODE_APPEND) != 0; 601 File f = makeFilename(getFilesDir(), name); 602 try { 603 FileOutputStream fos = new FileOutputStream(f, append); 604 setFilePermissionsFromMode(f.getPath(), mode, 0); 605 return fos; 606 } catch (FileNotFoundException e) { 607 } 608 609 File parent = f.getParentFile(); 610 parent.mkdir(); 611 FileUtils.setPermissions( 612 parent.getPath(), 613 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH, 614 -1, -1); 615 FileOutputStream fos = new FileOutputStream(f, append); 616 setFilePermissionsFromMode(f.getPath(), mode, 0); 617 return fos; 618 } 619 620 @Override 621 public boolean deleteFile(String name) { 622 File f = makeFilename(getFilesDir(), name); 623 return f.delete(); 624 } 625 626 @Override 627 public File getFilesDir() { 628 synchronized (mSync) { 629 if (mFilesDir == null) { 630 mFilesDir = new File(getDataDirFile(), "files"); 631 } 632 if (!mFilesDir.exists()) { 633 if(!mFilesDir.mkdirs()) { 634 Log.w(TAG, "Unable to create files directory " + mFilesDir.getPath()); 635 return null; 636 } 637 FileUtils.setPermissions( 638 mFilesDir.getPath(), 639 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH, 640 -1, -1); 641 } 642 return mFilesDir; 643 } 644 } 645 646 @Override 647 public File getExternalFilesDir(String type) { 648 synchronized (mSync) { 649 if (mExternalFilesDir == null) { 650 mExternalFilesDir = Environment.getExternalStorageAppFilesDirectory( 651 getPackageName()); 652 } 653 if (!mExternalFilesDir.exists()) { 654 try { 655 (new File(Environment.getExternalStorageAndroidDataDir(), 656 ".nomedia")).createNewFile(); 657 } catch (IOException e) { 658 } 659 if (!mExternalFilesDir.mkdirs()) { 660 Log.w(TAG, "Unable to create external files directory"); 661 return null; 662 } 663 } 664 if (type == null) { 665 return mExternalFilesDir; 666 } 667 File dir = new File(mExternalFilesDir, type); 668 if (!dir.exists()) { 669 if (!dir.mkdirs()) { 670 Log.w(TAG, "Unable to create external media directory " + dir); 671 return null; 672 } 673 } 674 return dir; 675 } 676 } 677 678 @Override 679 public File getObbDir() { 680 synchronized (mSync) { 681 if (mObbDir == null) { 682 mObbDir = Environment.getExternalStorageAppObbDirectory( 683 getPackageName()); 684 } 685 return mObbDir; 686 } 687 } 688 689 @Override 690 public File getCacheDir() { 691 synchronized (mSync) { 692 if (mCacheDir == null) { 693 mCacheDir = new File(getDataDirFile(), "cache"); 694 } 695 if (!mCacheDir.exists()) { 696 if(!mCacheDir.mkdirs()) { 697 Log.w(TAG, "Unable to create cache directory"); 698 return null; 699 } 700 FileUtils.setPermissions( 701 mCacheDir.getPath(), 702 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH, 703 -1, -1); 704 } 705 } 706 return mCacheDir; 707 } 708 709 @Override 710 public File getExternalCacheDir() { 711 synchronized (mSync) { 712 if (mExternalCacheDir == null) { 713 mExternalCacheDir = Environment.getExternalStorageAppCacheDirectory( 714 getPackageName()); 715 } 716 if (!mExternalCacheDir.exists()) { 717 try { 718 (new File(Environment.getExternalStorageAndroidDataDir(), 719 ".nomedia")).createNewFile(); 720 } catch (IOException e) { 721 } 722 if (!mExternalCacheDir.mkdirs()) { 723 Log.w(TAG, "Unable to create external cache directory"); 724 return null; 725 } 726 } 727 return mExternalCacheDir; 728 } 729 } 730 731 @Override 732 public File getFileStreamPath(String name) { 733 return makeFilename(getFilesDir(), name); 734 } 735 736 @Override 737 public String[] fileList() { 738 final String[] list = getFilesDir().list(); 739 return (list != null) ? list : EMPTY_FILE_LIST; 740 } 741 742 @Override 743 public SQLiteDatabase openOrCreateDatabase(String name, int mode, CursorFactory factory) { 744 File f = validateFilePath(name, true); 745 SQLiteDatabase db = SQLiteDatabase.openOrCreateDatabase(f, factory); 746 setFilePermissionsFromMode(f.getPath(), mode, 0); 747 return db; 748 } 749 750 @Override 751 public SQLiteDatabase openOrCreateDatabase(String name, int mode, CursorFactory factory, 752 DatabaseErrorHandler errorHandler) { 753 File f = validateFilePath(name, true); 754 SQLiteDatabase db = SQLiteDatabase.openOrCreateDatabase(f.getPath(), factory, errorHandler); 755 setFilePermissionsFromMode(f.getPath(), mode, 0); 756 return db; 757 } 758 759 @Override 760 public boolean deleteDatabase(String name) { 761 try { 762 File f = validateFilePath(name, false); 763 return f.delete(); 764 } catch (Exception e) { 765 } 766 return false; 767 } 768 769 @Override 770 public File getDatabasePath(String name) { 771 return validateFilePath(name, false); 772 } 773 774 @Override 775 public String[] databaseList() { 776 final String[] list = getDatabasesDir().list(); 777 return (list != null) ? list : EMPTY_FILE_LIST; 778 } 779 780 781 private File getDatabasesDir() { 782 synchronized (mSync) { 783 if (mDatabasesDir == null) { 784 mDatabasesDir = new File(getDataDirFile(), "databases"); 785 } 786 if (mDatabasesDir.getPath().equals("databases")) { 787 mDatabasesDir = new File("/data/system"); 788 } 789 return mDatabasesDir; 790 } 791 } 792 793 @Override 794 public Drawable getWallpaper() { 795 return getWallpaperManager().getDrawable(); 796 } 797 798 @Override 799 public Drawable peekWallpaper() { 800 return getWallpaperManager().peekDrawable(); 801 } 802 803 @Override 804 public int getWallpaperDesiredMinimumWidth() { 805 return getWallpaperManager().getDesiredMinimumWidth(); 806 } 807 808 @Override 809 public int getWallpaperDesiredMinimumHeight() { 810 return getWallpaperManager().getDesiredMinimumHeight(); 811 } 812 813 @Override 814 public void setWallpaper(Bitmap bitmap) throws IOException { 815 getWallpaperManager().setBitmap(bitmap); 816 } 817 818 @Override 819 public void setWallpaper(InputStream data) throws IOException { 820 getWallpaperManager().setStream(data); 821 } 822 823 @Override 824 public void clearWallpaper() throws IOException { 825 getWallpaperManager().clear(); 826 } 827 828 @Override 829 public void startActivity(Intent intent) { 830 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_TASK) == 0) { 831 throw new AndroidRuntimeException( 832 "Calling startActivity() from outside of an Activity " 833 + " context requires the FLAG_ACTIVITY_NEW_TASK flag." 834 + " Is this really what you want?"); 835 } 836 mMainThread.getInstrumentation().execStartActivity( 837 getOuterContext(), mMainThread.getApplicationThread(), null, 838 (Activity)null, intent, -1); 839 } 840 841 @Override 842 public void startActivities(Intent[] intents) { 843 if ((intents[0].getFlags()&Intent.FLAG_ACTIVITY_NEW_TASK) == 0) { 844 throw new AndroidRuntimeException( 845 "Calling startActivities() from outside of an Activity " 846 + " context requires the FLAG_ACTIVITY_NEW_TASK flag on first Intent." 847 + " Is this really what you want?"); 848 } 849 mMainThread.getInstrumentation().execStartActivities( 850 getOuterContext(), mMainThread.getApplicationThread(), null, 851 (Activity)null, intents); 852 } 853 854 @Override 855 public void startIntentSender(IntentSender intent, 856 Intent fillInIntent, int flagsMask, int flagsValues, int extraFlags) 857 throws IntentSender.SendIntentException { 858 try { 859 String resolvedType = null; 860 if (fillInIntent != null) { 861 resolvedType = fillInIntent.resolveTypeIfNeeded(getContentResolver()); 862 } 863 int result = ActivityManagerNative.getDefault() 864 .startActivityIntentSender(mMainThread.getApplicationThread(), intent, 865 fillInIntent, resolvedType, null, null, 866 0, flagsMask, flagsValues); 867 if (result == IActivityManager.START_CANCELED) { 868 throw new IntentSender.SendIntentException(); 869 } 870 Instrumentation.checkStartActivityResult(result, null); 871 } catch (RemoteException e) { 872 } 873 } 874 875 @Override 876 public void sendBroadcast(Intent intent) { 877 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 878 try { 879 ActivityManagerNative.getDefault().broadcastIntent( 880 mMainThread.getApplicationThread(), intent, resolvedType, null, 881 Activity.RESULT_OK, null, null, null, false, false); 882 } catch (RemoteException e) { 883 } 884 } 885 886 @Override 887 public void sendBroadcast(Intent intent, String receiverPermission) { 888 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 889 try { 890 ActivityManagerNative.getDefault().broadcastIntent( 891 mMainThread.getApplicationThread(), intent, resolvedType, null, 892 Activity.RESULT_OK, null, null, receiverPermission, false, false); 893 } catch (RemoteException e) { 894 } 895 } 896 897 @Override 898 public void sendOrderedBroadcast(Intent intent, 899 String receiverPermission) { 900 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 901 try { 902 ActivityManagerNative.getDefault().broadcastIntent( 903 mMainThread.getApplicationThread(), intent, resolvedType, null, 904 Activity.RESULT_OK, null, null, receiverPermission, true, false); 905 } catch (RemoteException e) { 906 } 907 } 908 909 @Override 910 public void sendOrderedBroadcast(Intent intent, 911 String receiverPermission, BroadcastReceiver resultReceiver, 912 Handler scheduler, int initialCode, String initialData, 913 Bundle initialExtras) { 914 IIntentReceiver rd = null; 915 if (resultReceiver != null) { 916 if (mPackageInfo != null) { 917 if (scheduler == null) { 918 scheduler = mMainThread.getHandler(); 919 } 920 rd = mPackageInfo.getReceiverDispatcher( 921 resultReceiver, getOuterContext(), scheduler, 922 mMainThread.getInstrumentation(), false); 923 } else { 924 if (scheduler == null) { 925 scheduler = mMainThread.getHandler(); 926 } 927 rd = new LoadedApk.ReceiverDispatcher( 928 resultReceiver, getOuterContext(), scheduler, null, false).getIIntentReceiver(); 929 } 930 } 931 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 932 try { 933 ActivityManagerNative.getDefault().broadcastIntent( 934 mMainThread.getApplicationThread(), intent, resolvedType, rd, 935 initialCode, initialData, initialExtras, receiverPermission, 936 true, false); 937 } catch (RemoteException e) { 938 } 939 } 940 941 @Override 942 public void sendStickyBroadcast(Intent intent) { 943 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 944 try { 945 ActivityManagerNative.getDefault().broadcastIntent( 946 mMainThread.getApplicationThread(), intent, resolvedType, null, 947 Activity.RESULT_OK, null, null, null, false, true); 948 } catch (RemoteException e) { 949 } 950 } 951 952 @Override 953 public void sendStickyOrderedBroadcast(Intent intent, 954 BroadcastReceiver resultReceiver, 955 Handler scheduler, int initialCode, String initialData, 956 Bundle initialExtras) { 957 IIntentReceiver rd = null; 958 if (resultReceiver != null) { 959 if (mPackageInfo != null) { 960 if (scheduler == null) { 961 scheduler = mMainThread.getHandler(); 962 } 963 rd = mPackageInfo.getReceiverDispatcher( 964 resultReceiver, getOuterContext(), scheduler, 965 mMainThread.getInstrumentation(), false); 966 } else { 967 if (scheduler == null) { 968 scheduler = mMainThread.getHandler(); 969 } 970 rd = new LoadedApk.ReceiverDispatcher( 971 resultReceiver, getOuterContext(), scheduler, null, false).getIIntentReceiver(); 972 } 973 } 974 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 975 try { 976 ActivityManagerNative.getDefault().broadcastIntent( 977 mMainThread.getApplicationThread(), intent, resolvedType, rd, 978 initialCode, initialData, initialExtras, null, 979 true, true); 980 } catch (RemoteException e) { 981 } 982 } 983 984 @Override 985 public void removeStickyBroadcast(Intent intent) { 986 String resolvedType = intent.resolveTypeIfNeeded(getContentResolver()); 987 if (resolvedType != null) { 988 intent = new Intent(intent); 989 intent.setDataAndType(intent.getData(), resolvedType); 990 } 991 try { 992 ActivityManagerNative.getDefault().unbroadcastIntent( 993 mMainThread.getApplicationThread(), intent); 994 } catch (RemoteException e) { 995 } 996 } 997 998 @Override 999 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter) { 1000 return registerReceiver(receiver, filter, null, null); 1001 } 1002 1003 @Override 1004 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter, 1005 String broadcastPermission, Handler scheduler) { 1006 return registerReceiverInternal(receiver, filter, broadcastPermission, 1007 scheduler, getOuterContext()); 1008 } 1009 1010 private Intent registerReceiverInternal(BroadcastReceiver receiver, 1011 IntentFilter filter, String broadcastPermission, 1012 Handler scheduler, Context context) { 1013 IIntentReceiver rd = null; 1014 if (receiver != null) { 1015 if (mPackageInfo != null && context != null) { 1016 if (scheduler == null) { 1017 scheduler = mMainThread.getHandler(); 1018 } 1019 rd = mPackageInfo.getReceiverDispatcher( 1020 receiver, context, scheduler, 1021 mMainThread.getInstrumentation(), true); 1022 } else { 1023 if (scheduler == null) { 1024 scheduler = mMainThread.getHandler(); 1025 } 1026 rd = new LoadedApk.ReceiverDispatcher( 1027 receiver, context, scheduler, null, true).getIIntentReceiver(); 1028 } 1029 } 1030 try { 1031 return ActivityManagerNative.getDefault().registerReceiver( 1032 mMainThread.getApplicationThread(), mBasePackageName, 1033 rd, filter, broadcastPermission); 1034 } catch (RemoteException e) { 1035 return null; 1036 } 1037 } 1038 1039 @Override 1040 public void unregisterReceiver(BroadcastReceiver receiver) { 1041 if (mPackageInfo != null) { 1042 IIntentReceiver rd = mPackageInfo.forgetReceiverDispatcher( 1043 getOuterContext(), receiver); 1044 try { 1045 ActivityManagerNative.getDefault().unregisterReceiver(rd); 1046 } catch (RemoteException e) { 1047 } 1048 } else { 1049 throw new RuntimeException("Not supported in system context"); 1050 } 1051 } 1052 1053 @Override 1054 public ComponentName startService(Intent service) { 1055 try { 1056 ComponentName cn = ActivityManagerNative.getDefault().startService( 1057 mMainThread.getApplicationThread(), service, 1058 service.resolveTypeIfNeeded(getContentResolver())); 1059 if (cn != null && cn.getPackageName().equals("!")) { 1060 throw new SecurityException( 1061 "Not allowed to start service " + service 1062 + " without permission " + cn.getClassName()); 1063 } 1064 return cn; 1065 } catch (RemoteException e) { 1066 return null; 1067 } 1068 } 1069 1070 @Override 1071 public boolean stopService(Intent service) { 1072 try { 1073 int res = ActivityManagerNative.getDefault().stopService( 1074 mMainThread.getApplicationThread(), service, 1075 service.resolveTypeIfNeeded(getContentResolver())); 1076 if (res < 0) { 1077 throw new SecurityException( 1078 "Not allowed to stop service " + service); 1079 } 1080 return res != 0; 1081 } catch (RemoteException e) { 1082 return false; 1083 } 1084 } 1085 1086 @Override 1087 public boolean bindService(Intent service, ServiceConnection conn, 1088 int flags) { 1089 IServiceConnection sd; 1090 if (mPackageInfo != null) { 1091 sd = mPackageInfo.getServiceDispatcher(conn, getOuterContext(), 1092 mMainThread.getHandler(), flags); 1093 } else { 1094 throw new RuntimeException("Not supported in system context"); 1095 } 1096 try { 1097 int res = ActivityManagerNative.getDefault().bindService( 1098 mMainThread.getApplicationThread(), getActivityToken(), 1099 service, service.resolveTypeIfNeeded(getContentResolver()), 1100 sd, flags); 1101 if (res < 0) { 1102 throw new SecurityException( 1103 "Not allowed to bind to service " + service); 1104 } 1105 return res != 0; 1106 } catch (RemoteException e) { 1107 return false; 1108 } 1109 } 1110 1111 @Override 1112 public void unbindService(ServiceConnection conn) { 1113 if (mPackageInfo != null) { 1114 IServiceConnection sd = mPackageInfo.forgetServiceDispatcher( 1115 getOuterContext(), conn); 1116 try { 1117 ActivityManagerNative.getDefault().unbindService(sd); 1118 } catch (RemoteException e) { 1119 } 1120 } else { 1121 throw new RuntimeException("Not supported in system context"); 1122 } 1123 } 1124 1125 @Override 1126 public boolean startInstrumentation(ComponentName className, 1127 String profileFile, Bundle arguments) { 1128 try { 1129 return ActivityManagerNative.getDefault().startInstrumentation( 1130 className, profileFile, 0, arguments, null); 1131 } catch (RemoteException e) { 1132 // System has crashed, nothing we can do. 1133 } 1134 return false; 1135 } 1136 1137 @Override 1138 public Object getSystemService(String name) { 1139 ServiceFetcher fetcher = SYSTEM_SERVICE_MAP.get(name); 1140 return fetcher == null ? null : fetcher.getService(this); 1141 } 1142 1143 private WallpaperManager getWallpaperManager() { 1144 return (WallpaperManager) WALLPAPER_FETCHER.getService(this); 1145 } 1146 1147 /* package */ static DropBoxManager createDropBoxManager() { 1148 IBinder b = ServiceManager.getService(DROPBOX_SERVICE); 1149 IDropBoxManagerService service = IDropBoxManagerService.Stub.asInterface(b); 1150 if (service == null) { 1151 // Don't return a DropBoxManager that will NPE upon use. 1152 // This also avoids caching a broken DropBoxManager in 1153 // getDropBoxManager during early boot, before the 1154 // DROPBOX_SERVICE is registered. 1155 return null; 1156 } 1157 return new DropBoxManager(service); 1158 } 1159 1160 @Override 1161 public int checkPermission(String permission, int pid, int uid) { 1162 if (permission == null) { 1163 throw new IllegalArgumentException("permission is null"); 1164 } 1165 1166 if (!Process.supportsProcesses()) { 1167 return PackageManager.PERMISSION_GRANTED; 1168 } 1169 try { 1170 return ActivityManagerNative.getDefault().checkPermission( 1171 permission, pid, uid); 1172 } catch (RemoteException e) { 1173 return PackageManager.PERMISSION_DENIED; 1174 } 1175 } 1176 1177 @Override 1178 public int checkCallingPermission(String permission) { 1179 if (permission == null) { 1180 throw new IllegalArgumentException("permission is null"); 1181 } 1182 1183 if (!Process.supportsProcesses()) { 1184 return PackageManager.PERMISSION_GRANTED; 1185 } 1186 int pid = Binder.getCallingPid(); 1187 if (pid != Process.myPid()) { 1188 return checkPermission(permission, pid, 1189 Binder.getCallingUid()); 1190 } 1191 return PackageManager.PERMISSION_DENIED; 1192 } 1193 1194 @Override 1195 public int checkCallingOrSelfPermission(String permission) { 1196 if (permission == null) { 1197 throw new IllegalArgumentException("permission is null"); 1198 } 1199 1200 return checkPermission(permission, Binder.getCallingPid(), 1201 Binder.getCallingUid()); 1202 } 1203 1204 private void enforce( 1205 String permission, int resultOfCheck, 1206 boolean selfToo, int uid, String message) { 1207 if (resultOfCheck != PackageManager.PERMISSION_GRANTED) { 1208 throw new SecurityException( 1209 (message != null ? (message + ": ") : "") + 1210 (selfToo 1211 ? "Neither user " + uid + " nor current process has " 1212 : "User " + uid + " does not have ") + 1213 permission + 1214 "."); 1215 } 1216 } 1217 1218 public void enforcePermission( 1219 String permission, int pid, int uid, String message) { 1220 enforce(permission, 1221 checkPermission(permission, pid, uid), 1222 false, 1223 uid, 1224 message); 1225 } 1226 1227 public void enforceCallingPermission(String permission, String message) { 1228 enforce(permission, 1229 checkCallingPermission(permission), 1230 false, 1231 Binder.getCallingUid(), 1232 message); 1233 } 1234 1235 public void enforceCallingOrSelfPermission( 1236 String permission, String message) { 1237 enforce(permission, 1238 checkCallingOrSelfPermission(permission), 1239 true, 1240 Binder.getCallingUid(), 1241 message); 1242 } 1243 1244 @Override 1245 public void grantUriPermission(String toPackage, Uri uri, int modeFlags) { 1246 try { 1247 ActivityManagerNative.getDefault().grantUriPermission( 1248 mMainThread.getApplicationThread(), toPackage, uri, 1249 modeFlags); 1250 } catch (RemoteException e) { 1251 } 1252 } 1253 1254 @Override 1255 public void revokeUriPermission(Uri uri, int modeFlags) { 1256 try { 1257 ActivityManagerNative.getDefault().revokeUriPermission( 1258 mMainThread.getApplicationThread(), uri, 1259 modeFlags); 1260 } catch (RemoteException e) { 1261 } 1262 } 1263 1264 @Override 1265 public int checkUriPermission(Uri uri, int pid, int uid, int modeFlags) { 1266 if (!Process.supportsProcesses()) { 1267 return PackageManager.PERMISSION_GRANTED; 1268 } 1269 try { 1270 return ActivityManagerNative.getDefault().checkUriPermission( 1271 uri, pid, uid, modeFlags); 1272 } catch (RemoteException e) { 1273 return PackageManager.PERMISSION_DENIED; 1274 } 1275 } 1276 1277 @Override 1278 public int checkCallingUriPermission(Uri uri, int modeFlags) { 1279 if (!Process.supportsProcesses()) { 1280 return PackageManager.PERMISSION_GRANTED; 1281 } 1282 int pid = Binder.getCallingPid(); 1283 if (pid != Process.myPid()) { 1284 return checkUriPermission(uri, pid, 1285 Binder.getCallingUid(), modeFlags); 1286 } 1287 return PackageManager.PERMISSION_DENIED; 1288 } 1289 1290 @Override 1291 public int checkCallingOrSelfUriPermission(Uri uri, int modeFlags) { 1292 return checkUriPermission(uri, Binder.getCallingPid(), 1293 Binder.getCallingUid(), modeFlags); 1294 } 1295 1296 @Override 1297 public int checkUriPermission(Uri uri, String readPermission, 1298 String writePermission, int pid, int uid, int modeFlags) { 1299 if (DEBUG) { 1300 Log.i("foo", "checkUriPermission: uri=" + uri + "readPermission=" 1301 + readPermission + " writePermission=" + writePermission 1302 + " pid=" + pid + " uid=" + uid + " mode" + modeFlags); 1303 } 1304 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 1305 if (readPermission == null 1306 || checkPermission(readPermission, pid, uid) 1307 == PackageManager.PERMISSION_GRANTED) { 1308 return PackageManager.PERMISSION_GRANTED; 1309 } 1310 } 1311 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 1312 if (writePermission == null 1313 || checkPermission(writePermission, pid, uid) 1314 == PackageManager.PERMISSION_GRANTED) { 1315 return PackageManager.PERMISSION_GRANTED; 1316 } 1317 } 1318 return uri != null ? checkUriPermission(uri, pid, uid, modeFlags) 1319 : PackageManager.PERMISSION_DENIED; 1320 } 1321 1322 private String uriModeFlagToString(int uriModeFlags) { 1323 switch (uriModeFlags) { 1324 case Intent.FLAG_GRANT_READ_URI_PERMISSION | 1325 Intent.FLAG_GRANT_WRITE_URI_PERMISSION: 1326 return "read and write"; 1327 case Intent.FLAG_GRANT_READ_URI_PERMISSION: 1328 return "read"; 1329 case Intent.FLAG_GRANT_WRITE_URI_PERMISSION: 1330 return "write"; 1331 } 1332 throw new IllegalArgumentException( 1333 "Unknown permission mode flags: " + uriModeFlags); 1334 } 1335 1336 private void enforceForUri( 1337 int modeFlags, int resultOfCheck, boolean selfToo, 1338 int uid, Uri uri, String message) { 1339 if (resultOfCheck != PackageManager.PERMISSION_GRANTED) { 1340 throw new SecurityException( 1341 (message != null ? (message + ": ") : "") + 1342 (selfToo 1343 ? "Neither user " + uid + " nor current process has " 1344 : "User " + uid + " does not have ") + 1345 uriModeFlagToString(modeFlags) + 1346 " permission on " + 1347 uri + 1348 "."); 1349 } 1350 } 1351 1352 public void enforceUriPermission( 1353 Uri uri, int pid, int uid, int modeFlags, String message) { 1354 enforceForUri( 1355 modeFlags, checkUriPermission(uri, pid, uid, modeFlags), 1356 false, uid, uri, message); 1357 } 1358 1359 public void enforceCallingUriPermission( 1360 Uri uri, int modeFlags, String message) { 1361 enforceForUri( 1362 modeFlags, checkCallingUriPermission(uri, modeFlags), 1363 false, Binder.getCallingUid(), uri, message); 1364 } 1365 1366 public void enforceCallingOrSelfUriPermission( 1367 Uri uri, int modeFlags, String message) { 1368 enforceForUri( 1369 modeFlags, 1370 checkCallingOrSelfUriPermission(uri, modeFlags), true, 1371 Binder.getCallingUid(), uri, message); 1372 } 1373 1374 public void enforceUriPermission( 1375 Uri uri, String readPermission, String writePermission, 1376 int pid, int uid, int modeFlags, String message) { 1377 enforceForUri(modeFlags, 1378 checkUriPermission( 1379 uri, readPermission, writePermission, pid, uid, 1380 modeFlags), 1381 false, 1382 uid, 1383 uri, 1384 message); 1385 } 1386 1387 @Override 1388 public Context createPackageContext(String packageName, int flags) 1389 throws PackageManager.NameNotFoundException { 1390 if (packageName.equals("system") || packageName.equals("android")) { 1391 return new ContextImpl(mMainThread.getSystemContext()); 1392 } 1393 1394 LoadedApk pi = 1395 mMainThread.getPackageInfo(packageName, mResources.getCompatibilityInfo(), flags); 1396 if (pi != null) { 1397 ContextImpl c = new ContextImpl(); 1398 c.mRestricted = (flags & CONTEXT_RESTRICTED) == CONTEXT_RESTRICTED; 1399 c.init(pi, null, mMainThread, mResources, mBasePackageName); 1400 if (c.mResources != null) { 1401 return c; 1402 } 1403 } 1404 1405 // Should be a better exception. 1406 throw new PackageManager.NameNotFoundException( 1407 "Application package " + packageName + " not found"); 1408 } 1409 1410 @Override 1411 public boolean isRestricted() { 1412 return mRestricted; 1413 } 1414 1415 private File getDataDirFile() { 1416 if (mPackageInfo != null) { 1417 return mPackageInfo.getDataDirFile(); 1418 } 1419 throw new RuntimeException("Not supported in system context"); 1420 } 1421 1422 @Override 1423 public File getDir(String name, int mode) { 1424 name = "app_" + name; 1425 File file = makeFilename(getDataDirFile(), name); 1426 if (!file.exists()) { 1427 file.mkdir(); 1428 setFilePermissionsFromMode(file.getPath(), mode, 1429 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH); 1430 } 1431 return file; 1432 } 1433 1434 static ContextImpl createSystemContext(ActivityThread mainThread) { 1435 ContextImpl context = new ContextImpl(); 1436 context.init(Resources.getSystem(), mainThread); 1437 return context; 1438 } 1439 1440 ContextImpl() { 1441 mOuterContext = this; 1442 } 1443 1444 /** 1445 * Create a new ApplicationContext from an existing one. The new one 1446 * works and operates the same as the one it is copying. 1447 * 1448 * @param context Existing application context. 1449 */ 1450 public ContextImpl(ContextImpl context) { 1451 mPackageInfo = context.mPackageInfo; 1452 mBasePackageName = context.mBasePackageName; 1453 mResources = context.mResources; 1454 mMainThread = context.mMainThread; 1455 mContentResolver = context.mContentResolver; 1456 mOuterContext = this; 1457 } 1458 1459 final void init(LoadedApk packageInfo, 1460 IBinder activityToken, ActivityThread mainThread) { 1461 init(packageInfo, activityToken, mainThread, null, null); 1462 } 1463 1464 final void init(LoadedApk packageInfo, 1465 IBinder activityToken, ActivityThread mainThread, 1466 Resources container, String basePackageName) { 1467 mPackageInfo = packageInfo; 1468 mBasePackageName = basePackageName != null ? basePackageName : packageInfo.mPackageName; 1469 mResources = mPackageInfo.getResources(mainThread); 1470 1471 if (mResources != null && container != null 1472 && container.getCompatibilityInfo().applicationScale != 1473 mResources.getCompatibilityInfo().applicationScale) { 1474 if (DEBUG) { 1475 Log.d(TAG, "loaded context has different scaling. Using container's" + 1476 " compatiblity info:" + container.getDisplayMetrics()); 1477 } 1478 mResources = mainThread.getTopLevelResources( 1479 mPackageInfo.getResDir(), container.getCompatibilityInfo()); 1480 } 1481 mMainThread = mainThread; 1482 mContentResolver = new ApplicationContentResolver(this, mainThread); 1483 1484 setActivityToken(activityToken); 1485 } 1486 1487 final void init(Resources resources, ActivityThread mainThread) { 1488 mPackageInfo = null; 1489 mBasePackageName = null; 1490 mResources = resources; 1491 mMainThread = mainThread; 1492 mContentResolver = new ApplicationContentResolver(this, mainThread); 1493 } 1494 1495 final void scheduleFinalCleanup(String who, String what) { 1496 mMainThread.scheduleContextCleanup(this, who, what); 1497 } 1498 1499 final void performFinalCleanup(String who, String what) { 1500 //Log.i(TAG, "Cleanup up context: " + this); 1501 mPackageInfo.removeContextRegistrations(getOuterContext(), who, what); 1502 } 1503 1504 final Context getReceiverRestrictedContext() { 1505 if (mReceiverRestrictedContext != null) { 1506 return mReceiverRestrictedContext; 1507 } 1508 return mReceiverRestrictedContext = new ReceiverRestrictedContext(getOuterContext()); 1509 } 1510 1511 final void setActivityToken(IBinder token) { 1512 mActivityToken = token; 1513 } 1514 1515 final void setOuterContext(Context context) { 1516 mOuterContext = context; 1517 } 1518 1519 final Context getOuterContext() { 1520 return mOuterContext; 1521 } 1522 1523 final IBinder getActivityToken() { 1524 return mActivityToken; 1525 } 1526 1527 static void setFilePermissionsFromMode(String name, int mode, 1528 int extraPermissions) { 1529 int perms = FileUtils.S_IRUSR|FileUtils.S_IWUSR 1530 |FileUtils.S_IRGRP|FileUtils.S_IWGRP 1531 |extraPermissions; 1532 if ((mode&MODE_WORLD_READABLE) != 0) { 1533 perms |= FileUtils.S_IROTH; 1534 } 1535 if ((mode&MODE_WORLD_WRITEABLE) != 0) { 1536 perms |= FileUtils.S_IWOTH; 1537 } 1538 if (DEBUG) { 1539 Log.i(TAG, "File " + name + ": mode=0x" + Integer.toHexString(mode) 1540 + ", perms=0x" + Integer.toHexString(perms)); 1541 } 1542 FileUtils.setPermissions(name, perms, -1, -1); 1543 } 1544 1545 private File validateFilePath(String name, boolean createDirectory) { 1546 File dir; 1547 File f; 1548 1549 if (name.charAt(0) == File.separatorChar) { 1550 String dirPath = name.substring(0, name.lastIndexOf(File.separatorChar)); 1551 dir = new File(dirPath); 1552 name = name.substring(name.lastIndexOf(File.separatorChar)); 1553 f = new File(dir, name); 1554 } else { 1555 dir = getDatabasesDir(); 1556 f = makeFilename(dir, name); 1557 } 1558 1559 if (createDirectory && !dir.isDirectory() && dir.mkdir()) { 1560 FileUtils.setPermissions(dir.getPath(), 1561 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH, 1562 -1, -1); 1563 } 1564 1565 return f; 1566 } 1567 1568 private File makeFilename(File base, String name) { 1569 if (name.indexOf(File.separatorChar) < 0) { 1570 return new File(base, name); 1571 } 1572 throw new IllegalArgumentException( 1573 "File " + name + " contains a path separator"); 1574 } 1575 1576 // ---------------------------------------------------------------------- 1577 // ---------------------------------------------------------------------- 1578 // ---------------------------------------------------------------------- 1579 1580 private static final class ApplicationContentResolver extends ContentResolver { 1581 public ApplicationContentResolver(Context context, ActivityThread mainThread) { 1582 super(context); 1583 mMainThread = mainThread; 1584 } 1585 1586 @Override 1587 protected IContentProvider acquireProvider(Context context, String name) { 1588 return mMainThread.acquireProvider(context, name); 1589 } 1590 1591 @Override 1592 protected IContentProvider acquireExistingProvider(Context context, String name) { 1593 return mMainThread.acquireExistingProvider(context, name); 1594 } 1595 1596 @Override 1597 public boolean releaseProvider(IContentProvider provider) { 1598 return mMainThread.releaseProvider(provider); 1599 } 1600 1601 private final ActivityThread mMainThread; 1602 } 1603} 1604