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