|
| 1 | + |
| 2 | +# Android Application Info Flags |
| 3 | + |
| 4 | +This documentation covers Android Application Info flags, which provide detailed information about installed applications on Android devices. These flags are part of the `ApplicationInfo` class and can be accessed through the Package Manager. |
| 5 | + |
| 6 | +## Overview |
| 7 | + |
| 8 | +Application Info flags are bitwise flags that describe various properties and capabilities of an Android application. They are stored as integer values where each bit position represents a specific application characteristic. |
| 9 | + |
| 10 | +## Getting Application Info |
| 11 | + |
| 12 | +To retrieve application information and flags, use the Package Manager: |
| 13 | + |
| 14 | +```javascript |
| 15 | +// To use the `global` variable you require the WXU Plugin |
| 16 | +const pm = global.require("pm") |
| 17 | +const info = JSON.parse(pm.getApplicationInfo("com.goolag.pif")) |
| 18 | + |
| 19 | +let number = info.flags; |
| 20 | +// flag for system apps |
| 21 | +let flag = 1<<0; |
| 22 | + |
| 23 | +if ((number & flag) != 0) { |
| 24 | + console.log("This app is a system app"); |
| 25 | +} else { |
| 26 | + console.log("This app is not a system app"); |
| 27 | +} |
| 28 | +``` |
| 29 | + |
| 30 | +## Understanding Bit Shifting |
| 31 | + |
| 32 | +Before diving into the flags, it's important to understand bit shifting operations: |
| 33 | + |
| 34 | +### What is Bit Shifting? |
| 35 | + |
| 36 | +Bit shifting is a bitwise operation that moves bits to the left or right. In the context of Android flags: |
| 37 | + |
| 38 | +- `1<<0` means shift the bit 1 zero positions to the left, resulting in: `00000001` (decimal 1) |
| 39 | +- `1<<1` means shift the bit 1 one position to the left, resulting in: `00000010` (decimal 2) |
| 40 | +- `1<<2` means shift the bit 1 two positions to the left, resulting in: `00000100` (decimal 4) |
| 41 | + |
| 42 | +### Why Use Bit Shifting for Flags? |
| 43 | + |
| 44 | +1. **Memory Efficiency**: Multiple boolean values can be stored in a single integer |
| 45 | +2. **Performance**: Bitwise operations are very fast |
| 46 | +3. **Compatibility**: Allows for easy addition of new flags without breaking existing code |
| 47 | + |
| 48 | +### Checking if a Flag is Set |
| 49 | + |
| 50 | +To check if a specific flag is set, use the bitwise AND operator (`&`): |
| 51 | + |
| 52 | +```javascript |
| 53 | +const FLAG_SYSTEM = 1<<0; // Value: 1 |
| 54 | +const FLAG_DEBUGGABLE = 1<<1; // Value: 2 |
| 55 | + |
| 56 | +// Check if app is a system app |
| 57 | +if ((info.flags & FLAG_SYSTEM) != 0) { |
| 58 | + console.log("System app"); |
| 59 | +} |
| 60 | + |
| 61 | +// Check if app is debuggable |
| 62 | +if ((info.flags & FLAG_DEBUGGABLE) != 0) { |
| 63 | + console.log("Debuggable app"); |
| 64 | +} |
| 65 | +``` |
| 66 | + |
| 67 | +## Complete Application Info Flags Reference |
| 68 | + |
| 69 | +Here are all the available Application Info flags with their descriptions: |
| 70 | + |
| 71 | +### Core Application Flags |
| 72 | + |
| 73 | +| Flag | Value | Description | |
| 74 | +|------|-------|-------------| |
| 75 | +| `FLAG_SYSTEM` | `1<<0` (1) | Application is installed in the device's system image | |
| 76 | +| `FLAG_DEBUGGABLE` | `1<<1` (2) | Application allows debugging of its code | |
| 77 | +| `FLAG_HAS_CODE` | `1<<2` (4) | Application has code associated with it | |
| 78 | +| `FLAG_PERSISTENT` | `1<<3` (8) | Application is persistent | |
| 79 | +| `FLAG_FACTORY_TEST` | `1<<4` (16) | Application holds FACTORY_TEST permission | |
| 80 | +| `FLAG_ALLOW_TASK_REPARENTING` | `1<<5` (32) | Allows task reparenting | |
| 81 | +| `FLAG_ALLOW_CLEAR_USER_DATA` | `1<<6` (64) | Allows clearing user data | |
| 82 | +| `FLAG_UPDATED_SYSTEM_APP` | `1<<7` (128) | System app that has been updated | |
| 83 | +| `FLAG_TEST_ONLY` | `1<<8` (256) | Application is for testing only | |
| 84 | + |
| 85 | +### Screen Support Flags |
| 86 | + |
| 87 | +| Flag | Value | Description | |
| 88 | +|------|-------|-------------| |
| 89 | +| `FLAG_SUPPORTS_SMALL_SCREENS` | `1<<9` (512) | Supports small screens | |
| 90 | +| `FLAG_SUPPORTS_NORMAL_SCREENS` | `1<<10` (1024) | Supports normal screens | |
| 91 | +| `FLAG_SUPPORTS_LARGE_SCREENS` | `1<<11` (2048) | Supports large screens | |
| 92 | +| `FLAG_RESIZEABLE_FOR_SCREENS` | `1<<12` (4096) | UI can adjust for different screen sizes | |
| 93 | +| `FLAG_SUPPORTS_SCREEN_DENSITIES` | `1<<13` (8192) | Supports different screen densities (deprecated) | |
| 94 | +| `FLAG_SUPPORTS_XLARGE_SCREENS` | `1<<19` (524288) | Supports extra large screens | |
| 95 | + |
| 96 | +### System and Security Flags |
| 97 | + |
| 98 | +| Flag | Value | Description | |
| 99 | +|------|-------|-------------| |
| 100 | +| `FLAG_VM_SAFE_MODE` | `1<<14` (16384) | VM operates in safe mode | |
| 101 | +| `FLAG_ALLOW_BACKUP` | `1<<15` (32768) | Allows OS-driven backups | |
| 102 | +| `FLAG_KILL_AFTER_RESTORE` | `1<<16` (65536) | Killed after restore operation | |
| 103 | +| `FLAG_RESTORE_ANY_VERSION` | `1<<17` (131072) | Can restore from future versions | |
| 104 | +| `FLAG_EXTERNAL_STORAGE` | `1<<18` (262144) | Installed on external storage | |
| 105 | +| `FLAG_LARGE_HEAP` | `1<<20` (1048576) | Requests large heap | |
| 106 | +| `FLAG_STOPPED` | `1<<21` (2097152) | Package is in stopped state | |
| 107 | +| `FLAG_SUPPORTS_RTL` | `1<<22` (4194304) | Supports right-to-left layouts | |
| 108 | +| `FLAG_INSTALLED` | `1<<23` (8388608) | Currently installed for calling user | |
| 109 | +| `FLAG_IS_DATA_ONLY` | `1<<24` (16777216) | Only data is installed | |
| 110 | +| `FLAG_FULL_BACKUP_ONLY` | `1<<26` (67108864) | Uses full-data streaming backups | |
| 111 | +| `FLAG_USES_CLEARTEXT_TRAFFIC` | `1<<27` (134217728) | May use cleartext network traffic | |
| 112 | +| `FLAG_EXTRACT_NATIVE_LIBS` | `1<<28` (268435456) | Extracts native libraries | |
| 113 | +| `FLAG_HARDWARE_ACCELERATED` | `1<<29` (536870912) | Hardware accelerated rendering | |
| 114 | +| `FLAG_SUSPENDED` | `1<<30` (1073741824) | Package is suspended | |
| 115 | +| `FLAG_MULTIARCH` | `1<<31` (2147483648) | Code may be loaded into other processes | |
| 116 | + |
| 117 | +### Deprecated Flags |
| 118 | + |
| 119 | +| Flag | Value | Description | |
| 120 | +|------|-------|-------------| |
| 121 | +| `FLAG_IS_GAME` | `1<<25` (33554432) | Application is a game (deprecated, use CATEGORY_GAME instead) | |
| 122 | + |
| 123 | +## Practical Examples |
| 124 | + |
| 125 | +### Example 1: Checking Multiple Flags |
| 126 | + |
| 127 | +```javascript |
| 128 | +const info = JSON.parse(pm.getApplicationInfo("com.example.app")); |
| 129 | +const flags = info.flags; |
| 130 | + |
| 131 | +// Define flag constants |
| 132 | +const FLAG_SYSTEM = 1<<0; |
| 133 | +const FLAG_DEBUGGABLE = 1<<1; |
| 134 | +const FLAG_ALLOW_BACKUP = 1<<15; |
| 135 | + |
| 136 | +// Check multiple flags |
| 137 | +const isSystem = (flags & FLAG_SYSTEM) != 0; |
| 138 | +const isDebuggable = (flags & FLAG_DEBUGGABLE) != 0; |
| 139 | +const allowsBackup = (flags & FLAG_ALLOW_BACKUP) != 0; |
| 140 | + |
| 141 | +console.log(`System app: ${isSystem}`); |
| 142 | +console.log(`Debuggable: ${isDebuggable}`); |
| 143 | +console.log(`Allows backup: ${allowsBackup}`); |
| 144 | +``` |
| 145 | + |
| 146 | +### Example 2: Creating a Flag Checker Function |
| 147 | + |
| 148 | +```javascript |
| 149 | +function checkAppFlags(packageName) { |
| 150 | + const info = JSON.parse(pm.getApplicationInfo(packageName)); |
| 151 | + const flags = info.flags; |
| 152 | + |
| 153 | + const flagChecks = { |
| 154 | + 'System App': (flags & (1<<0)) != 0, |
| 155 | + 'Debuggable': (flags & (1<<1)) != 0, |
| 156 | + 'Has Code': (flags & (1<<2)) != 0, |
| 157 | + 'Persistent': (flags & (1<<3)) != 0, |
| 158 | + 'Updated System App': (flags & (1<<7)) != 0, |
| 159 | + 'Test Only': (flags & (1<<8)) != 0, |
| 160 | + 'External Storage': (flags & (1<<18)) != 0, |
| 161 | + 'Large Heap': (flags & (1<<20)) != 0, |
| 162 | + 'Stopped': (flags & (1<<21)) != 0, |
| 163 | + 'Suspended': (flags & (1<<30)) != 0 |
| 164 | + }; |
| 165 | + |
| 166 | + console.log(`Flags for ${packageName}:`); |
| 167 | + for (const [flagName, isSet] of Object.entries(flagChecks)) { |
| 168 | + console.log(` ${flagName}: ${isSet}`); |
| 169 | + } |
| 170 | +} |
| 171 | + |
| 172 | +// Usage |
| 173 | +checkAppFlags("com.android.settings"); |
| 174 | +``` |
| 175 | + |
| 176 | +## Important Notes |
| 177 | + |
| 178 | +1. **Security Warning**: Don't use `FLAG_SYSTEM` for security decisions. Use signature checks or permissions instead. |
| 179 | + |
| 180 | +2. **API Level Considerations**: Some flags may behave differently or be ignored on certain Android API levels. |
| 181 | + |
| 182 | +3. **Performance**: Bitwise operations are very efficient, making flag checking fast even for multiple flags. |
| 183 | + |
| 184 | +4. **Future Compatibility**: New flags may be added in future Android versions, so always check documentation for the target API level. |
| 185 | + |
| 186 | +## See Also |
| 187 | + |
| 188 | +- [Android Developer Documentation - ApplicationInfo](https://developer.android.com/reference/android/content/pm/ApplicationInfo) |
| 189 | +- [Bitwise Operations in Programming](https://en.wikipedia.org/wiki/Bitwise_operation) |
| 190 | +- [Package Manager API Reference](https://developer.android.com/reference/android/content/pm/PackageManager) |
0 commit comments