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