Home | History | Annotate | Download | only in pm
      1 /*
      2  * Copyright (C) 2007 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 
     17 package android.content.pm;
     18 
     19 import android.content.pm.PackageManager.NameNotFoundException;
     20 import android.content.res.Resources;
     21 import android.graphics.drawable.Drawable;
     22 import android.os.Parcel;
     23 import android.os.Parcelable;
     24 import android.util.Printer;
     25 
     26 import java.text.Collator;
     27 import java.util.Comparator;
     28 
     29 /**
     30  * Information you can retrieve about a particular application.  This
     31  * corresponds to information collected from the AndroidManifest.xml's
     32  * <application> tag.
     33  */
     34 public class ApplicationInfo extends PackageItemInfo implements Parcelable {
     35 
     36     /**
     37      * Default task affinity of all activities in this application. See
     38      * {@link ActivityInfo#taskAffinity} for more information.  This comes
     39      * from the "taskAffinity" attribute.
     40      */
     41     public String taskAffinity;
     42 
     43     /**
     44      * Optional name of a permission required to be able to access this
     45      * application's components.  From the "permission" attribute.
     46      */
     47     public String permission;
     48 
     49     /**
     50      * The name of the process this application should run in.  From the
     51      * "process" attribute or, if not set, the same as
     52      * <var>packageName</var>.
     53      */
     54     public String processName;
     55 
     56     /**
     57      * Class implementing the Application object.  From the "class"
     58      * attribute.
     59      */
     60     public String className;
     61 
     62     /**
     63      * A style resource identifier (in the package's resources) of the
     64      * description of an application.  From the "description" attribute
     65      * or, if not set, 0.
     66      */
     67     public int descriptionRes;
     68 
     69     /**
     70      * A style resource identifier (in the package's resources) of the
     71      * default visual theme of the application.  From the "theme" attribute
     72      * or, if not set, 0.
     73      */
     74     public int theme;
     75 
     76     /**
     77      * Class implementing the Application's manage space
     78      * functionality.  From the "manageSpaceActivity"
     79      * attribute. This is an optional attribute and will be null if
     80      * applications don't specify it in their manifest
     81      */
     82     public String manageSpaceActivityName;
     83 
     84     /**
     85      * Class implementing the Application's backup functionality.  From
     86      * the "backupAgent" attribute.  This is an optional attribute and
     87      * will be null if the application does not specify it in its manifest.
     88      *
     89      * <p>If android:allowBackup is set to false, this attribute is ignored.
     90      */
     91     public String backupAgentName;
     92 
     93     /**
     94      * Value for {@link #flags}: if set, this application is installed in the
     95      * device's system image.
     96      */
     97     public static final int FLAG_SYSTEM = 1<<0;
     98 
     99     /**
    100      * Value for {@link #flags}: set to true if this application would like to
    101      * allow debugging of its
    102      * code, even when installed on a non-development system.  Comes
    103      * from {@link android.R.styleable#AndroidManifestApplication_debuggable
    104      * android:debuggable} of the &lt;application&gt; tag.
    105      */
    106     public static final int FLAG_DEBUGGABLE = 1<<1;
    107 
    108     /**
    109      * Value for {@link #flags}: set to true if this application has code
    110      * associated with it.  Comes
    111      * from {@link android.R.styleable#AndroidManifestApplication_hasCode
    112      * android:hasCode} of the &lt;application&gt; tag.
    113      */
    114     public static final int FLAG_HAS_CODE = 1<<2;
    115 
    116     /**
    117      * Value for {@link #flags}: set to true if this application is persistent.
    118      * Comes from {@link android.R.styleable#AndroidManifestApplication_persistent
    119      * android:persistent} of the &lt;application&gt; tag.
    120      */
    121     public static final int FLAG_PERSISTENT = 1<<3;
    122 
    123     /**
    124      * Value for {@link #flags}: set to true if this application holds the
    125      * {@link android.Manifest.permission#FACTORY_TEST} permission and the
    126      * device is running in factory test mode.
    127      */
    128     public static final int FLAG_FACTORY_TEST = 1<<4;
    129 
    130     /**
    131      * Value for {@link #flags}: default value for the corresponding ActivityInfo flag.
    132      * Comes from {@link android.R.styleable#AndroidManifestApplication_allowTaskReparenting
    133      * android:allowTaskReparenting} of the &lt;application&gt; tag.
    134      */
    135     public static final int FLAG_ALLOW_TASK_REPARENTING = 1<<5;
    136 
    137     /**
    138      * Value for {@link #flags}: default value for the corresponding ActivityInfo flag.
    139      * Comes from {@link android.R.styleable#AndroidManifestApplication_allowClearUserData
    140      * android:allowClearUserData} of the &lt;application&gt; tag.
    141      */
    142     public static final int FLAG_ALLOW_CLEAR_USER_DATA = 1<<6;
    143 
    144     /**
    145      * Value for {@link #flags}: this is set if this application has been
    146      * install as an update to a built-in system application.
    147      */
    148     public static final int FLAG_UPDATED_SYSTEM_APP = 1<<7;
    149 
    150     /**
    151      * Value for {@link #flags}: this is set of the application has specified
    152      * {@link android.R.styleable#AndroidManifestApplication_testOnly
    153      * android:testOnly} to be true.
    154      */
    155     public static final int FLAG_TEST_ONLY = 1<<8;
    156 
    157     /**
    158      * Value for {@link #flags}: true when the application's window can be
    159      * reduced in size for smaller screens.  Corresponds to
    160      * {@link android.R.styleable#AndroidManifestSupportsScreens_smallScreens
    161      * android:smallScreens}.
    162      */
    163     public static final int FLAG_SUPPORTS_SMALL_SCREENS = 1<<9;
    164 
    165     /**
    166      * Value for {@link #flags}: true when the application's window can be
    167      * displayed on normal screens.  Corresponds to
    168      * {@link android.R.styleable#AndroidManifestSupportsScreens_normalScreens
    169      * android:normalScreens}.
    170      */
    171     public static final int FLAG_SUPPORTS_NORMAL_SCREENS = 1<<10;
    172 
    173     /**
    174      * Value for {@link #flags}: true when the application's window can be
    175      * increased in size for larger screens.  Corresponds to
    176      * {@link android.R.styleable#AndroidManifestSupportsScreens_largeScreens
    177      * android:smallScreens}.
    178      */
    179     public static final int FLAG_SUPPORTS_LARGE_SCREENS = 1<<11;
    180 
    181     /**
    182      * Value for {@link #flags}: true when the application knows how to adjust
    183      * its UI for different screen sizes.  Corresponds to
    184      * {@link android.R.styleable#AndroidManifestSupportsScreens_resizeable
    185      * android:resizeable}.
    186      */
    187     public static final int FLAG_RESIZEABLE_FOR_SCREENS = 1<<12;
    188 
    189     /**
    190      * Value for {@link #flags}: true when the application knows how to
    191      * accomodate different screen densities.  Corresponds to
    192      * {@link android.R.styleable#AndroidManifestSupportsScreens_anyDensity
    193      * android:anyDensity}.
    194      */
    195     public static final int FLAG_SUPPORTS_SCREEN_DENSITIES = 1<<13;
    196 
    197     /**
    198      * Value for {@link #flags}: set to true if this application would like to
    199      * request the VM to operate under the safe mode. Comes from
    200      * {@link android.R.styleable#AndroidManifestApplication_vmSafeMode
    201      * android:vmSafeMode} of the &lt;application&gt; tag.
    202      */
    203     public static final int FLAG_VM_SAFE_MODE = 1<<14;
    204 
    205     /**
    206      * Value for {@link #flags}: set to <code>false</code> if the application does not wish
    207      * to permit any OS-driven backups of its data; <code>true</code> otherwise.
    208      *
    209      * <p>Comes from the
    210      * {@link android.R.styleable#AndroidManifestApplication_allowBackup android:allowBackup}
    211      * attribute of the &lt;application&gt; tag.
    212      */
    213     public static final int FLAG_ALLOW_BACKUP = 1<<15;
    214 
    215     /**
    216      * Value for {@link #flags}: set to <code>false</code> if the application must be kept
    217      * in memory following a full-system restore operation; <code>true</code> otherwise.
    218      * Ordinarily, during a full system restore operation each application is shut down
    219      * following execution of its agent's onRestore() method.  Setting this attribute to
    220      * <code>false</code> prevents this.  Most applications will not need to set this attribute.
    221      *
    222      * <p>If
    223      * {@link android.R.styleable#AndroidManifestApplication_allowBackup android:allowBackup}
    224      * is set to <code>false</code> or no
    225      * {@link android.R.styleable#AndroidManifestApplication_backupAgent android:backupAgent}
    226      * is specified, this flag will be ignored.
    227      *
    228      * <p>Comes from the
    229      * {@link android.R.styleable#AndroidManifestApplication_killAfterRestore android:killAfterRestore}
    230      * attribute of the &lt;application&gt; tag.
    231      */
    232     public static final int FLAG_KILL_AFTER_RESTORE = 1<<16;
    233 
    234     /**
    235      * Value for {@link #flags}: Set to <code>true</code> if the application's backup
    236      * agent claims to be able to handle restore data even "from the future,"
    237      * i.e. from versions of the application with a versionCode greater than
    238      * the one currently installed on the device.  <i>Use with caution!</i>  By default
    239      * this attribute is <code>false</code> and the Backup Manager will ensure that data
    240      * from "future" versions of the application are never supplied during a restore operation.
    241      *
    242      * <p>If
    243      * {@link android.R.styleable#AndroidManifestApplication_allowBackup android:allowBackup}
    244      * is set to <code>false</code> or no
    245      * {@link android.R.styleable#AndroidManifestApplication_backupAgent android:backupAgent}
    246      * is specified, this flag will be ignored.
    247      *
    248      * <p>Comes from the
    249      * {@link android.R.styleable#AndroidManifestApplication_restoreAnyVersion android:restoreAnyVersion}
    250      * attribute of the &lt;application&gt; tag.
    251      */
    252     public static final int FLAG_RESTORE_ANY_VERSION = 1<<17;
    253 
    254     /**
    255      * Value for {@link #flags}: Set to true if the application is
    256      * currently installed on external/removable/unprotected storage.  Such
    257      * applications may not be available if their storage is not currently
    258      * mounted.  When the storage it is on is not available, it will look like
    259      * the application has been uninstalled (its .apk is no longer available)
    260      * but its persistent data is not removed.
    261      */
    262     public static final int FLAG_EXTERNAL_STORAGE = 1<<18;
    263 
    264     /**
    265      * Value for {@link #flags}: Set to true if the application has been
    266      * installed using the forward lock option.
    267      *
    268      * {@hide}
    269      */
    270     public static final int FLAG_FORWARD_LOCK = 1<<20;
    271 
    272     /**
    273      * Value for {@link #flags}: Set to true if the application is
    274      * native-debuggable, i.e. embeds a gdbserver binary in its .apk
    275      *
    276      * {@hide}
    277      */
    278     public static final int FLAG_NATIVE_DEBUGGABLE = 1<<21;
    279 
    280     /**
    281      * Flags associated with the application.  Any combination of
    282      * {@link #FLAG_SYSTEM}, {@link #FLAG_DEBUGGABLE}, {@link #FLAG_HAS_CODE},
    283      * {@link #FLAG_PERSISTENT}, {@link #FLAG_FACTORY_TEST}, and
    284      * {@link #FLAG_ALLOW_TASK_REPARENTING}
    285      * {@link #FLAG_ALLOW_CLEAR_USER_DATA}, {@link #FLAG_UPDATED_SYSTEM_APP},
    286      * {@link #FLAG_TEST_ONLY}, {@link #FLAG_SUPPORTS_SMALL_SCREENS},
    287      * {@link #FLAG_SUPPORTS_NORMAL_SCREENS},
    288      * {@link #FLAG_SUPPORTS_LARGE_SCREENS}, {@link #FLAG_RESIZEABLE_FOR_SCREENS},
    289      * {@link #FLAG_SUPPORTS_SCREEN_DENSITIES}, {@link #FLAG_VM_SAFE_MODE}
    290      */
    291     public int flags = 0;
    292 
    293     /**
    294      * Full path to the location of this package.
    295      */
    296     public String sourceDir;
    297 
    298     /**
    299      * Full path to the location of the publicly available parts of this
    300      * package (i.e. the primary resource package and manifest).  For
    301      * non-forward-locked apps this will be the same as {@link #sourceDir).
    302      */
    303     public String publicSourceDir;
    304 
    305     /**
    306      * Full paths to the locations of extra resource packages this application
    307      * uses. This field is only used if there are extra resource packages,
    308      * otherwise it is null.
    309      *
    310      * {@hide}
    311      */
    312     public String[] resourceDirs;
    313 
    314     /**
    315      * Paths to all shared libraries this application is linked against.  This
    316      * field is only set if the {@link PackageManager#GET_SHARED_LIBRARY_FILES
    317      * PackageManager.GET_SHARED_LIBRARY_FILES} flag was used when retrieving
    318      * the structure.
    319      */
    320     public String[] sharedLibraryFiles;
    321 
    322     /**
    323      * Full path to a directory assigned to the package for its persistent
    324      * data.
    325      */
    326     public String dataDir;
    327 
    328     /**
    329      * The kernel user-ID that has been assigned to this application;
    330      * currently this is not a unique ID (multiple applications can have
    331      * the same uid).
    332      */
    333     public int uid;
    334 
    335     /**
    336      * The minimum SDK version this application targets.  It may run on earlier
    337      * versions, but it knows how to work with any new behavior added at this
    338      * version.  Will be {@link android.os.Build.VERSION_CODES#CUR_DEVELOPMENT}
    339      * if this is a development build and the app is targeting that.  You should
    340      * compare that this number is >= the SDK version number at which your
    341      * behavior was introduced.
    342      */
    343     public int targetSdkVersion;
    344 
    345     /**
    346      * When false, indicates that all components within this application are
    347      * considered disabled, regardless of their individually set enabled status.
    348      */
    349     public boolean enabled = true;
    350 
    351     public void dump(Printer pw, String prefix) {
    352         super.dumpFront(pw, prefix);
    353         if (className != null) {
    354             pw.println(prefix + "className=" + className);
    355         }
    356         if (permission != null) {
    357             pw.println(prefix + "permission=" + permission);
    358         }
    359         pw.println(prefix + "uid=" + uid + " taskAffinity=" + taskAffinity);
    360         if (theme != 0) {
    361             pw.println(prefix + "theme=0x" + Integer.toHexString(theme));
    362         }
    363         pw.println(prefix + "flags=0x" + Integer.toHexString(flags)
    364                 + " processName=" + processName);
    365         pw.println(prefix + "sourceDir=" + sourceDir);
    366         pw.println(prefix + "publicSourceDir=" + publicSourceDir);
    367         pw.println(prefix + "resourceDirs=" + resourceDirs);
    368         pw.println(prefix + "dataDir=" + dataDir);
    369         if (sharedLibraryFiles != null) {
    370             pw.println(prefix + "sharedLibraryFiles=" + sharedLibraryFiles);
    371         }
    372         pw.println(prefix + "enabled=" + enabled + " targetSdkVersion=" + targetSdkVersion);
    373         if (manageSpaceActivityName != null) {
    374             pw.println(prefix + "manageSpaceActivityName="+manageSpaceActivityName);
    375         }
    376         if (descriptionRes != 0) {
    377             pw.println(prefix + "description=0x"+Integer.toHexString(descriptionRes));
    378         }
    379         super.dumpBack(pw, prefix);
    380     }
    381 
    382     public static class DisplayNameComparator
    383             implements Comparator<ApplicationInfo> {
    384         public DisplayNameComparator(PackageManager pm) {
    385             mPM = pm;
    386         }
    387 
    388         public final int compare(ApplicationInfo aa, ApplicationInfo ab) {
    389             CharSequence  sa = mPM.getApplicationLabel(aa);
    390             if (sa == null) {
    391                 sa = aa.packageName;
    392             }
    393             CharSequence  sb = mPM.getApplicationLabel(ab);
    394             if (sb == null) {
    395                 sb = ab.packageName;
    396             }
    397 
    398             return sCollator.compare(sa.toString(), sb.toString());
    399         }
    400 
    401         private final Collator   sCollator = Collator.getInstance();
    402         private PackageManager   mPM;
    403     }
    404 
    405     public ApplicationInfo() {
    406     }
    407 
    408     public ApplicationInfo(ApplicationInfo orig) {
    409         super(orig);
    410         taskAffinity = orig.taskAffinity;
    411         permission = orig.permission;
    412         processName = orig.processName;
    413         className = orig.className;
    414         theme = orig.theme;
    415         flags = orig.flags;
    416         sourceDir = orig.sourceDir;
    417         publicSourceDir = orig.publicSourceDir;
    418         resourceDirs = orig.resourceDirs;
    419         sharedLibraryFiles = orig.sharedLibraryFiles;
    420         dataDir = orig.dataDir;
    421         uid = orig.uid;
    422         targetSdkVersion = orig.targetSdkVersion;
    423         enabled = orig.enabled;
    424         manageSpaceActivityName = orig.manageSpaceActivityName;
    425         descriptionRes = orig.descriptionRes;
    426     }
    427 
    428 
    429     public String toString() {
    430         return "ApplicationInfo{"
    431             + Integer.toHexString(System.identityHashCode(this))
    432             + " " + packageName + "}";
    433     }
    434 
    435     public int describeContents() {
    436         return 0;
    437     }
    438 
    439     public void writeToParcel(Parcel dest, int parcelableFlags) {
    440         super.writeToParcel(dest, parcelableFlags);
    441         dest.writeString(taskAffinity);
    442         dest.writeString(permission);
    443         dest.writeString(processName);
    444         dest.writeString(className);
    445         dest.writeInt(theme);
    446         dest.writeInt(flags);
    447         dest.writeString(sourceDir);
    448         dest.writeString(publicSourceDir);
    449         dest.writeStringArray(resourceDirs);
    450         dest.writeStringArray(sharedLibraryFiles);
    451         dest.writeString(dataDir);
    452         dest.writeInt(uid);
    453         dest.writeInt(targetSdkVersion);
    454         dest.writeInt(enabled ? 1 : 0);
    455         dest.writeString(manageSpaceActivityName);
    456         dest.writeString(backupAgentName);
    457         dest.writeInt(descriptionRes);
    458     }
    459 
    460     public static final Parcelable.Creator<ApplicationInfo> CREATOR
    461             = new Parcelable.Creator<ApplicationInfo>() {
    462         public ApplicationInfo createFromParcel(Parcel source) {
    463             return new ApplicationInfo(source);
    464         }
    465         public ApplicationInfo[] newArray(int size) {
    466             return new ApplicationInfo[size];
    467         }
    468     };
    469 
    470     private ApplicationInfo(Parcel source) {
    471         super(source);
    472         taskAffinity = source.readString();
    473         permission = source.readString();
    474         processName = source.readString();
    475         className = source.readString();
    476         theme = source.readInt();
    477         flags = source.readInt();
    478         sourceDir = source.readString();
    479         publicSourceDir = source.readString();
    480         resourceDirs = source.readStringArray();
    481         sharedLibraryFiles = source.readStringArray();
    482         dataDir = source.readString();
    483         uid = source.readInt();
    484         targetSdkVersion = source.readInt();
    485         enabled = source.readInt() != 0;
    486         manageSpaceActivityName = source.readString();
    487         backupAgentName = source.readString();
    488         descriptionRes = source.readInt();
    489     }
    490 
    491     /**
    492      * Retrieve the textual description of the application.  This
    493      * will call back on the given PackageManager to load the description from
    494      * the application.
    495      *
    496      * @param pm A PackageManager from which the label can be loaded; usually
    497      * the PackageManager from which you originally retrieved this item.
    498      *
    499      * @return Returns a CharSequence containing the application's description.
    500      * If there is no description, null is returned.
    501      */
    502     public CharSequence loadDescription(PackageManager pm) {
    503         if (descriptionRes != 0) {
    504             CharSequence label = pm.getText(packageName, descriptionRes, this);
    505             if (label != null) {
    506                 return label;
    507             }
    508         }
    509         return null;
    510     }
    511 
    512     /**
    513      * Disable compatibility mode
    514      *
    515      * @hide
    516      */
    517     public void disableCompatibilityMode() {
    518         flags |= (FLAG_SUPPORTS_LARGE_SCREENS | FLAG_SUPPORTS_NORMAL_SCREENS |
    519                 FLAG_SUPPORTS_SMALL_SCREENS | FLAG_RESIZEABLE_FOR_SCREENS |
    520                 FLAG_SUPPORTS_SCREEN_DENSITIES);
    521     }
    522 
    523     /**
    524      * @hide
    525      */
    526     @Override protected Drawable loadDefaultIcon(PackageManager pm) {
    527         if ((flags & FLAG_EXTERNAL_STORAGE) != 0
    528                 && isPackageUnavailable(pm)) {
    529             return Resources.getSystem().getDrawable(
    530                     com.android.internal.R.drawable.sym_app_on_sd_unavailable_icon);
    531         }
    532         return pm.getDefaultActivityIcon();
    533     }
    534 
    535     private boolean isPackageUnavailable(PackageManager pm) {
    536         try {
    537             return pm.getPackageInfo(packageName, 0) == null;
    538         } catch (NameNotFoundException ex) {
    539             return true;
    540         }
    541     }
    542 
    543     /**
    544      * @hide
    545      */
    546     @Override protected ApplicationInfo getApplicationInfo() {
    547         return this;
    548     }
    549 }
    550