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.os; 18 19 import android.Manifest; 20 import android.annotation.NonNull; 21 import android.annotation.RequiresPermission; 22 import android.annotation.SuppressAutoDoc; 23 import android.annotation.SystemApi; 24 import android.annotation.TestApi; 25 import android.app.ActivityThread; 26 import android.app.Application; 27 import android.compat.annotation.UnsupportedAppUsage; 28 import android.content.Context; 29 import android.sysprop.TelephonyProperties; 30 import android.text.TextUtils; 31 import android.util.Slog; 32 import android.view.View; 33 34 import dalvik.system.VMRuntime; 35 36 import java.util.ArrayList; 37 import java.util.List; 38 import java.util.Objects; 39 import java.util.stream.Collectors; 40 41 /** 42 * Information about the current build, extracted from system properties. 43 */ 44 public class Build { 45 private static final String TAG = "Build"; 46 47 /** Value used for when a build property is unknown. */ 48 public static final String UNKNOWN = "unknown"; 49 50 /** Either a changelist number, or a label like "M4-rc20". */ 51 public static final String ID = getString("ro.build.id"); 52 53 /** A build ID string meant for displaying to the user */ 54 public static final String DISPLAY = getString("ro.build.display.id"); 55 56 /** The name of the overall product. */ 57 public static final String PRODUCT = getString("ro.product.name"); 58 59 /** The name of the industrial design. */ 60 public static final String DEVICE = getString("ro.product.device"); 61 62 /** The name of the underlying board, like "goldfish". */ 63 public static final String BOARD = getString("ro.product.board"); 64 65 /** 66 * The name of the instruction set (CPU type + ABI convention) of native code. 67 * 68 * @deprecated Use {@link #SUPPORTED_ABIS} instead. 69 */ 70 @Deprecated 71 public static final String CPU_ABI; 72 73 /** 74 * The name of the second instruction set (CPU type + ABI convention) of native code. 75 * 76 * @deprecated Use {@link #SUPPORTED_ABIS} instead. 77 */ 78 @Deprecated 79 public static final String CPU_ABI2; 80 81 /** The manufacturer of the product/hardware. */ 82 public static final String MANUFACTURER = getString("ro.product.manufacturer"); 83 84 /** The consumer-visible brand with which the product/hardware will be associated, if any. */ 85 public static final String BRAND = getString("ro.product.brand"); 86 87 /** The end-user-visible name for the end product. */ 88 public static final String MODEL = getString("ro.product.model"); 89 90 /** The system bootloader version number. */ 91 public static final String BOOTLOADER = getString("ro.bootloader"); 92 93 /** 94 * The radio firmware version number. 95 * 96 * @deprecated The radio firmware version is frequently not 97 * available when this class is initialized, leading to a blank or 98 * "unknown" value for this string. Use 99 * {@link #getRadioVersion} instead. 100 */ 101 @Deprecated 102 public static final String RADIO = joinListOrElse( 103 TelephonyProperties.baseband_version(), UNKNOWN); 104 105 /** The name of the hardware (from the kernel command line or /proc). */ 106 public static final String HARDWARE = getString("ro.hardware"); 107 108 /** 109 * Whether this build was for an emulator device. 110 * @hide 111 */ 112 @UnsupportedAppUsage 113 @TestApi 114 public static final boolean IS_EMULATOR = getString("ro.kernel.qemu").equals("1"); 115 116 /** 117 * A hardware serial number, if available. Alphanumeric only, case-insensitive. 118 * This field is always set to {@link Build#UNKNOWN}. 119 * 120 * @deprecated Use {@link #getSerial()} instead. 121 **/ 122 @Deprecated 123 // IMPORTANT: This field should be initialized via a function call to 124 // prevent its value being inlined in the app during compilation because 125 // we will later set it to the value based on the app's target SDK. 126 public static final String SERIAL = getString("no.such.thing"); 127 128 /** 129 * Gets the hardware serial number, if available. 130 * 131 * <p class="note"><b>Note:</b> Root access may allow you to modify device identifiers, such as 132 * the hardware serial number. If you change these identifiers, you can use 133 * <a href="/training/articles/security-key-attestation.html">key attestation</a> to obtain 134 * proof of the device's original identifiers. 135 * 136 * <p>Starting with API level 29, persistent device identifiers are guarded behind additional 137 * restrictions, and apps are recommended to use resettable identifiers (see <a 138 * href="c"> Best practices for unique identifiers</a>). This method can be invoked if one of 139 * the following requirements is met: 140 * <ul> 141 * <li>If the calling app has been granted the READ_PRIVILEGED_PHONE_STATE permission; this 142 * is a privileged permission that can only be granted to apps preloaded on the device. 143 * <li>If the calling app is the device or profile owner and has been granted the 144 * {@link Manifest.permission#READ_PHONE_STATE} permission. The profile owner is an app that 145 * owns a managed profile on the device; for more details see <a 146 * href="https://developer.android.com/work/managed-profiles">Work profiles</a>. 147 * Profile owner access is deprecated and will be removed in a future release. 148 * <li>If the calling app has carrier privileges (see {@link 149 * android.telephony.TelephonyManager#hasCarrierPrivileges}) on any active subscription. 150 * <li>If the calling app is the default SMS role holder (see {@link 151 * android.app.role.RoleManager#isRoleHeld(String)}). 152 * </ul> 153 * 154 * <p>If the calling app does not meet one of these requirements then this method will behave 155 * as follows: 156 * 157 * <ul> 158 * <li>If the calling app's target SDK is API level 28 or lower and the app has the 159 * READ_PHONE_STATE permission then {@link Build#UNKNOWN} is returned.</li> 160 * <li>If the calling app's target SDK is API level 28 or lower and the app does not have 161 * the READ_PHONE_STATE permission, or if the calling app is targeting API level 29 or 162 * higher, then a SecurityException is thrown.</li> 163 * </ul> 164 * 165 * @return The serial number if specified. 166 */ 167 @SuppressAutoDoc // No support for device / profile owner. 168 @RequiresPermission(Manifest.permission.READ_PRIVILEGED_PHONE_STATE) getSerial()169 public static String getSerial() { 170 IDeviceIdentifiersPolicyService service = IDeviceIdentifiersPolicyService.Stub 171 .asInterface(ServiceManager.getService(Context.DEVICE_IDENTIFIERS_SERVICE)); 172 try { 173 Application application = ActivityThread.currentApplication(); 174 String callingPackage = application != null ? application.getPackageName() : null; 175 return service.getSerialForPackage(callingPackage, null); 176 } catch (RemoteException e) { 177 e.rethrowFromSystemServer(); 178 } 179 return UNKNOWN; 180 } 181 182 /** 183 * An ordered list of ABIs supported by this device. The most preferred ABI is the first 184 * element in the list. 185 * 186 * See {@link #SUPPORTED_32_BIT_ABIS} and {@link #SUPPORTED_64_BIT_ABIS}. 187 */ 188 public static final String[] SUPPORTED_ABIS = getStringList("ro.product.cpu.abilist", ","); 189 190 /** 191 * An ordered list of <b>32 bit</b> ABIs supported by this device. The most preferred ABI 192 * is the first element in the list. 193 * 194 * See {@link #SUPPORTED_ABIS} and {@link #SUPPORTED_64_BIT_ABIS}. 195 */ 196 public static final String[] SUPPORTED_32_BIT_ABIS = 197 getStringList("ro.product.cpu.abilist32", ","); 198 199 /** 200 * An ordered list of <b>64 bit</b> ABIs supported by this device. The most preferred ABI 201 * is the first element in the list. 202 * 203 * See {@link #SUPPORTED_ABIS} and {@link #SUPPORTED_32_BIT_ABIS}. 204 */ 205 public static final String[] SUPPORTED_64_BIT_ABIS = 206 getStringList("ro.product.cpu.abilist64", ","); 207 208 /** {@hide} */ 209 @TestApi is64BitAbi(String abi)210 public static boolean is64BitAbi(String abi) { 211 return VMRuntime.is64BitAbi(abi); 212 } 213 214 static { 215 /* 216 * Adjusts CPU_ABI and CPU_ABI2 depending on whether or not a given process is 64 bit. 217 * 32 bit processes will always see 32 bit ABIs in these fields for backward 218 * compatibility. 219 */ 220 final String[] abiList; 221 if (VMRuntime.getRuntime().is64Bit()) { 222 abiList = SUPPORTED_64_BIT_ABIS; 223 } else { 224 abiList = SUPPORTED_32_BIT_ABIS; 225 } 226 227 CPU_ABI = abiList[0]; 228 if (abiList.length > 1) { 229 CPU_ABI2 = abiList[1]; 230 } else { 231 CPU_ABI2 = ""; 232 } 233 } 234 235 /** Various version strings. */ 236 public static class VERSION { 237 /** 238 * The internal value used by the underlying source control to 239 * represent this build. E.g., a perforce changelist number 240 * or a git hash. 241 */ 242 public static final String INCREMENTAL = getString("ro.build.version.incremental"); 243 244 /** 245 * The user-visible version string. E.g., "1.0" or "3.4b5" or "bananas". 246 * 247 * This field is an opaque string. Do not assume that its value 248 * has any particular structure or that values of RELEASE from 249 * different releases can be somehow ordered. 250 */ 251 public static final String RELEASE = getString("ro.build.version.release"); 252 253 /** 254 * The version string we show to the user; may be {@link #RELEASE} or 255 * {@link #CODENAME} if not a final release build. 256 */ 257 @NonNull public static final String RELEASE_OR_CODENAME = getString( 258 "ro.build.version.release_or_codename"); 259 260 /** 261 * The base OS build the product is based on. 262 */ 263 public static final String BASE_OS = SystemProperties.get("ro.build.version.base_os", ""); 264 265 /** 266 * The user-visible security patch level. This value represents the date when the device 267 * most recently applied a security patch. 268 */ 269 public static final String SECURITY_PATCH = SystemProperties.get( 270 "ro.build.version.security_patch", ""); 271 272 /** 273 * The user-visible SDK version of the framework in its raw String 274 * representation; use {@link #SDK_INT} instead. 275 * 276 * @deprecated Use {@link #SDK_INT} to easily get this as an integer. 277 */ 278 @Deprecated 279 public static final String SDK = getString("ro.build.version.sdk"); 280 281 /** 282 * The SDK version of the software currently running on this hardware 283 * device. This value never changes while a device is booted, but it may 284 * increase when the hardware manufacturer provides an OTA update. 285 * <p> 286 * Possible values are defined in {@link Build.VERSION_CODES}. 287 */ 288 public static final int SDK_INT = SystemProperties.getInt( 289 "ro.build.version.sdk", 0); 290 291 /** 292 * The SDK version of the software that <em>initially</em> shipped on 293 * this hardware device. It <em>never</em> changes during the lifetime 294 * of the device, even when {@link #SDK_INT} increases due to an OTA 295 * update. 296 * <p> 297 * Possible values are defined in {@link Build.VERSION_CODES}. 298 * 299 * @see #SDK_INT 300 * @hide 301 */ 302 @TestApi 303 public static final int FIRST_SDK_INT = SystemProperties 304 .getInt("ro.product.first_api_level", 0); 305 306 /** 307 * The developer preview revision of a prerelease SDK. This value will always 308 * be <code>0</code> on production platform builds/devices. 309 * 310 * <p>When this value is nonzero, any new API added since the last 311 * officially published {@link #SDK_INT API level} is only guaranteed to be present 312 * on that specific preview revision. For example, an API <code>Activity.fooBar()</code> 313 * might be present in preview revision 1 but renamed or removed entirely in 314 * preview revision 2, which may cause an app attempting to call it to crash 315 * at runtime.</p> 316 * 317 * <p>Experimental apps targeting preview APIs should check this value for 318 * equality (<code>==</code>) with the preview SDK revision they were built for 319 * before using any prerelease platform APIs. Apps that detect a preview SDK revision 320 * other than the specific one they expect should fall back to using APIs from 321 * the previously published API level only to avoid unwanted runtime exceptions. 322 * </p> 323 */ 324 public static final int PREVIEW_SDK_INT = SystemProperties.getInt( 325 "ro.build.version.preview_sdk", 0); 326 327 /** 328 * The SDK fingerprint for a given prerelease SDK. This value will always be 329 * {@code REL} on production platform builds/devices. 330 * 331 * <p>When this value is not {@code REL}, it contains a string fingerprint of the API 332 * surface exposed by the preview SDK. Preview platforms with different API surfaces 333 * will have different {@code PREVIEW_SDK_FINGERPRINT}. 334 * 335 * <p>This attribute is intended for use by installers for finer grained targeting of 336 * packages. Applications targeting preview APIs should not use this field and should 337 * instead use {@code PREVIEW_SDK_INT} or use reflection or other runtime checks to 338 * detect the presence of an API or guard themselves against unexpected runtime 339 * behavior. 340 * 341 * @hide 342 */ 343 @SystemApi 344 @NonNull public static final String PREVIEW_SDK_FINGERPRINT = SystemProperties.get( 345 "ro.build.version.preview_sdk_fingerprint", "REL"); 346 347 /** 348 * The current development codename, or the string "REL" if this is 349 * a release build. 350 */ 351 public static final String CODENAME = getString("ro.build.version.codename"); 352 353 private static final String[] ALL_CODENAMES 354 = getStringList("ro.build.version.all_codenames", ","); 355 356 /** 357 * @hide 358 */ 359 @UnsupportedAppUsage 360 @TestApi 361 public static final String[] ACTIVE_CODENAMES = "REL".equals(ALL_CODENAMES[0]) 362 ? new String[0] : ALL_CODENAMES; 363 364 /** 365 * The SDK version to use when accessing resources. 366 * Use the current SDK version code. For every active development codename 367 * we are operating under, we bump the assumed resource platform version by 1. 368 * @hide 369 */ 370 @TestApi 371 public static final int RESOURCES_SDK_INT = SDK_INT + ACTIVE_CODENAMES.length; 372 373 /** 374 * The current lowest supported value of app target SDK. Applications targeting 375 * lower values may not function on devices running this SDK version. Its possible 376 * values are defined in {@link Build.VERSION_CODES}. 377 * 378 * @hide 379 */ 380 public static final int MIN_SUPPORTED_TARGET_SDK_INT = SystemProperties.getInt( 381 "ro.build.version.min_supported_target_sdk", 0); 382 } 383 384 /** 385 * Enumeration of the currently known SDK version codes. These are the 386 * values that can be found in {@link VERSION#SDK}. Version numbers 387 * increment monotonically with each official platform release. 388 */ 389 public static class VERSION_CODES { 390 /** 391 * Magic version number for a current development build, which has 392 * not yet turned into an official release. 393 */ 394 public static final int CUR_DEVELOPMENT = VMRuntime.SDK_VERSION_CUR_DEVELOPMENT; 395 396 /** 397 * October 2008: The original, first, version of Android. Yay! 398 */ 399 public static final int BASE = 1; 400 401 /** 402 * February 2009: First Android update, officially called 1.1. 403 */ 404 public static final int BASE_1_1 = 2; 405 406 /** 407 * May 2009: Android 1.5. 408 */ 409 public static final int CUPCAKE = 3; 410 411 /** 412 * September 2009: Android 1.6. 413 * 414 * <p>Applications targeting this or a later release will get these 415 * new changes in behavior:</p> 416 * <ul> 417 * <li> They must explicitly request the 418 * {@link android.Manifest.permission#WRITE_EXTERNAL_STORAGE} permission to be 419 * able to modify the contents of the SD card. (Apps targeting 420 * earlier versions will always request the permission.) 421 * <li> They must explicitly request the 422 * {@link android.Manifest.permission#READ_PHONE_STATE} permission to be 423 * able to be able to retrieve phone state info. (Apps targeting 424 * earlier versions will always request the permission.) 425 * <li> They are assumed to support different screen densities and 426 * sizes. (Apps targeting earlier versions are assumed to only support 427 * medium density normal size screens unless otherwise indicated). 428 * They can still explicitly specify screen support either way with the 429 * supports-screens manifest tag. 430 * <li> {@link android.widget.TabHost} will use the new dark tab 431 * background design. 432 * </ul> 433 */ 434 public static final int DONUT = 4; 435 436 /** 437 * November 2009: Android 2.0 438 * 439 * <p>Applications targeting this or a later release will get these 440 * new changes in behavior:</p> 441 * <ul> 442 * <li> The {@link android.app.Service#onStartCommand 443 * Service.onStartCommand} function will return the new 444 * {@link android.app.Service#START_STICKY} behavior instead of the 445 * old compatibility {@link android.app.Service#START_STICKY_COMPATIBILITY}. 446 * <li> The {@link android.app.Activity} class will now execute back 447 * key presses on the key up instead of key down, to be able to detect 448 * canceled presses from virtual keys. 449 * <li> The {@link android.widget.TabWidget} class will use a new color scheme 450 * for tabs. In the new scheme, the foreground tab has a medium gray background 451 * the background tabs have a dark gray background. 452 * </ul> 453 */ 454 public static final int ECLAIR = 5; 455 456 /** 457 * December 2009: Android 2.0.1 458 */ 459 public static final int ECLAIR_0_1 = 6; 460 461 /** 462 * January 2010: Android 2.1 463 */ 464 public static final int ECLAIR_MR1 = 7; 465 466 /** 467 * June 2010: Android 2.2 468 */ 469 public static final int FROYO = 8; 470 471 /** 472 * November 2010: Android 2.3 473 * 474 * <p>Applications targeting this or a later release will get these 475 * new changes in behavior:</p> 476 * <ul> 477 * <li> The application's notification icons will be shown on the new 478 * dark status bar background, so must be visible in this situation. 479 * </ul> 480 */ 481 public static final int GINGERBREAD = 9; 482 483 /** 484 * February 2011: Android 2.3.3. 485 */ 486 public static final int GINGERBREAD_MR1 = 10; 487 488 /** 489 * February 2011: Android 3.0. 490 * 491 * <p>Applications targeting this or a later release will get these 492 * new changes in behavior:</p> 493 * <ul> 494 * <li> The default theme for applications is now dark holographic: 495 * {@link android.R.style#Theme_Holo}. 496 * <li> On large screen devices that do not have a physical menu 497 * button, the soft (compatibility) menu is disabled. 498 * <li> The activity lifecycle has changed slightly as per 499 * {@link android.app.Activity}. 500 * <li> An application will crash if it does not call through 501 * to the super implementation of its 502 * {@link android.app.Activity#onPause Activity.onPause()} method. 503 * <li> When an application requires a permission to access one of 504 * its components (activity, receiver, service, provider), this 505 * permission is no longer enforced when the application wants to 506 * access its own component. This means it can require a permission 507 * on a component that it does not itself hold and still access that 508 * component. 509 * <li> {@link android.content.Context#getSharedPreferences 510 * Context.getSharedPreferences()} will not automatically reload 511 * the preferences if they have changed on storage, unless 512 * {@link android.content.Context#MODE_MULTI_PROCESS} is used. 513 * <li> {@link android.view.ViewGroup#setMotionEventSplittingEnabled} 514 * will default to true. 515 * <li> {@link android.view.WindowManager.LayoutParams#FLAG_SPLIT_TOUCH} 516 * is enabled by default on windows. 517 * <li> {@link android.widget.PopupWindow#isSplitTouchEnabled() 518 * PopupWindow.isSplitTouchEnabled()} will return true by default. 519 * <li> {@link android.widget.GridView} and {@link android.widget.ListView} 520 * will use {@link android.view.View#setActivated View.setActivated} 521 * for selected items if they do not implement {@link android.widget.Checkable}. 522 * <li> {@link android.widget.Scroller} will be constructed with 523 * "flywheel" behavior enabled by default. 524 * </ul> 525 */ 526 public static final int HONEYCOMB = 11; 527 528 /** 529 * May 2011: Android 3.1. 530 */ 531 public static final int HONEYCOMB_MR1 = 12; 532 533 /** 534 * June 2011: Android 3.2. 535 * 536 * <p>Update to Honeycomb MR1 to support 7 inch tablets, improve 537 * screen compatibility mode, etc.</p> 538 * 539 * <p>As of this version, applications that don't say whether they 540 * support XLARGE screens will be assumed to do so only if they target 541 * {@link #HONEYCOMB} or later; it had been {@link #GINGERBREAD} or 542 * later. Applications that don't support a screen size at least as 543 * large as the current screen will provide the user with a UI to 544 * switch them in to screen size compatibility mode.</p> 545 * 546 * <p>This version introduces new screen size resource qualifiers 547 * based on the screen size in dp: see 548 * {@link android.content.res.Configuration#screenWidthDp}, 549 * {@link android.content.res.Configuration#screenHeightDp}, and 550 * {@link android.content.res.Configuration#smallestScreenWidthDp}. 551 * Supplying these in <supports-screens> as per 552 * {@link android.content.pm.ApplicationInfo#requiresSmallestWidthDp}, 553 * {@link android.content.pm.ApplicationInfo#compatibleWidthLimitDp}, and 554 * {@link android.content.pm.ApplicationInfo#largestWidthLimitDp} is 555 * preferred over the older screen size buckets and for older devices 556 * the appropriate buckets will be inferred from them.</p> 557 * 558 * <p>Applications targeting this or a later release will get these 559 * new changes in behavior:</p> 560 * <ul> 561 * <li><p>New {@link android.content.pm.PackageManager#FEATURE_SCREEN_PORTRAIT} 562 * and {@link android.content.pm.PackageManager#FEATURE_SCREEN_LANDSCAPE} 563 * features were introduced in this release. Applications that target 564 * previous platform versions are assumed to require both portrait and 565 * landscape support in the device; when targeting Honeycomb MR1 or 566 * greater the application is responsible for specifying any specific 567 * orientation it requires.</p> 568 * <li><p>{@link android.os.AsyncTask} will use the serial executor 569 * by default when calling {@link android.os.AsyncTask#execute}.</p> 570 * <li><p>{@link android.content.pm.ActivityInfo#configChanges 571 * ActivityInfo.configChanges} will have the 572 * {@link android.content.pm.ActivityInfo#CONFIG_SCREEN_SIZE} and 573 * {@link android.content.pm.ActivityInfo#CONFIG_SMALLEST_SCREEN_SIZE} 574 * bits set; these need to be cleared for older applications because 575 * some developers have done absolute comparisons against this value 576 * instead of correctly masking the bits they are interested in. 577 * </ul> 578 */ 579 public static final int HONEYCOMB_MR2 = 13; 580 581 /** 582 * October 2011: Android 4.0. 583 * 584 * <p>Applications targeting this or a later release will get these 585 * new changes in behavior:</p> 586 * <ul> 587 * <li> For devices without a dedicated menu key, the software compatibility 588 * menu key will not be shown even on phones. By targeting Ice Cream Sandwich 589 * or later, your UI must always have its own menu UI affordance if needed, 590 * on both tablets and phones. The ActionBar will take care of this for you. 591 * <li> 2d drawing hardware acceleration is now turned on by default. 592 * You can use 593 * {@link android.R.attr#hardwareAccelerated android:hardwareAccelerated} 594 * to turn it off if needed, although this is strongly discouraged since 595 * it will result in poor performance on larger screen devices. 596 * <li> The default theme for applications is now the "device default" theme: 597 * {@link android.R.style#Theme_DeviceDefault}. This may be the 598 * holo dark theme or a different dark theme defined by the specific device. 599 * The {@link android.R.style#Theme_Holo} family must not be modified 600 * for a device to be considered compatible. Applications that explicitly 601 * request a theme from the Holo family will be guaranteed that these themes 602 * will not change character within the same platform version. Applications 603 * that wish to blend in with the device should use a theme from the 604 * {@link android.R.style#Theme_DeviceDefault} family. 605 * <li> Managed cursors can now throw an exception if you directly close 606 * the cursor yourself without stopping the management of it; previously failures 607 * would be silently ignored. 608 * <li> The fadingEdge attribute on views will be ignored (fading edges is no 609 * longer a standard part of the UI). A new requiresFadingEdge attribute allows 610 * applications to still force fading edges on for special cases. 611 * <li> {@link android.content.Context#bindService Context.bindService()} 612 * will not automatically add in {@link android.content.Context#BIND_WAIVE_PRIORITY}. 613 * <li> App Widgets will have standard padding automatically added around 614 * them, rather than relying on the padding being baked into the widget itself. 615 * <li> An exception will be thrown if you try to change the type of a 616 * window after it has been added to the window manager. Previously this 617 * would result in random incorrect behavior. 618 * <li> {@link android.view.animation.AnimationSet} will parse out 619 * the duration, fillBefore, fillAfter, repeatMode, and startOffset 620 * XML attributes that are defined. 621 * <li> {@link android.app.ActionBar#setHomeButtonEnabled 622 * ActionBar.setHomeButtonEnabled()} is false by default. 623 * </ul> 624 */ 625 public static final int ICE_CREAM_SANDWICH = 14; 626 627 /** 628 * December 2011: Android 4.0.3. 629 */ 630 public static final int ICE_CREAM_SANDWICH_MR1 = 15; 631 632 /** 633 * June 2012: Android 4.1. 634 * 635 * <p>Applications targeting this or a later release will get these 636 * new changes in behavior:</p> 637 * <ul> 638 * <li> You must explicitly request the {@link android.Manifest.permission#READ_CALL_LOG} 639 * and/or {@link android.Manifest.permission#WRITE_CALL_LOG} permissions; 640 * access to the call log is no longer implicitly provided through 641 * {@link android.Manifest.permission#READ_CONTACTS} and 642 * {@link android.Manifest.permission#WRITE_CONTACTS}. 643 * <li> {@link android.widget.RemoteViews} will throw an exception if 644 * setting an onClick handler for views being generated by a 645 * {@link android.widget.RemoteViewsService} for a collection container; 646 * previously this just resulted in a warning log message. 647 * <li> New {@link android.app.ActionBar} policy for embedded tabs: 648 * embedded tabs are now always stacked in the action bar when in portrait 649 * mode, regardless of the size of the screen. 650 * <li> {@link android.webkit.WebSettings#setAllowFileAccessFromFileURLs(boolean) 651 * WebSettings.setAllowFileAccessFromFileURLs} and 652 * {@link android.webkit.WebSettings#setAllowUniversalAccessFromFileURLs(boolean) 653 * WebSettings.setAllowUniversalAccessFromFileURLs} default to false. 654 * <li> Calls to {@link android.content.pm.PackageManager#setComponentEnabledSetting 655 * PackageManager.setComponentEnabledSetting} will now throw an 656 * IllegalArgumentException if the given component class name does not 657 * exist in the application's manifest. 658 * <li> {@link android.nfc.NfcAdapter#setNdefPushMessage 659 * NfcAdapter.setNdefPushMessage}, 660 * {@link android.nfc.NfcAdapter#setNdefPushMessageCallback 661 * NfcAdapter.setNdefPushMessageCallback} and 662 * {@link android.nfc.NfcAdapter#setOnNdefPushCompleteCallback 663 * NfcAdapter.setOnNdefPushCompleteCallback} will throw 664 * IllegalStateException if called after the Activity has been destroyed. 665 * <li> Accessibility services must require the new 666 * {@link android.Manifest.permission#BIND_ACCESSIBILITY_SERVICE} permission or 667 * they will not be available for use. 668 * <li> {@link android.accessibilityservice.AccessibilityServiceInfo#FLAG_INCLUDE_NOT_IMPORTANT_VIEWS 669 * AccessibilityServiceInfo.FLAG_INCLUDE_NOT_IMPORTANT_VIEWS} must be set 670 * for unimportant views to be included in queries. 671 * </ul> 672 */ 673 public static final int JELLY_BEAN = 16; 674 675 /** 676 * November 2012: Android 4.2, Moar jelly beans! 677 * 678 * <p>Applications targeting this or a later release will get these 679 * new changes in behavior:</p> 680 * <ul> 681 * <li>Content Providers: The default value of {@code android:exported} is now 682 * {@code false}. See 683 * <a href="{@docRoot}guide/topics/manifest/provider-element.html#exported"> 684 * the android:exported section</a> in the provider documentation for more details.</li> 685 * <li>{@link android.view.View#getLayoutDirection() View.getLayoutDirection()} 686 * can return different values than {@link android.view.View#LAYOUT_DIRECTION_LTR} 687 * based on the locale etc. 688 * <li> {@link android.webkit.WebView#addJavascriptInterface(Object, String) 689 * WebView.addJavascriptInterface} requires explicit annotations on methods 690 * for them to be accessible from Javascript. 691 * </ul> 692 */ 693 public static final int JELLY_BEAN_MR1 = 17; 694 695 /** 696 * July 2013: Android 4.3, the revenge of the beans. 697 */ 698 public static final int JELLY_BEAN_MR2 = 18; 699 700 /** 701 * October 2013: Android 4.4, KitKat, another tasty treat. 702 * 703 * <p>Applications targeting this or a later release will get these 704 * new changes in behavior. For more information about this release, see the 705 * <a href="/about/versions/kitkat/">Android KitKat overview</a>.</p> 706 * <ul> 707 * <li> The default result of 708 * {@link android.preference.PreferenceActivity#isValidFragment(String) 709 * PreferenceActivity.isValueFragment} becomes false instead of true.</li> 710 * <li> In {@link android.webkit.WebView}, apps targeting earlier versions will have 711 * JS URLs evaluated directly and any result of the evaluation will not replace 712 * the current page content. Apps targetting KITKAT or later that load a JS URL will 713 * have the result of that URL replace the content of the current page</li> 714 * <li> {@link android.app.AlarmManager#set AlarmManager.set} becomes interpreted as 715 * an inexact value, to give the system more flexibility in scheduling alarms.</li> 716 * <li> {@link android.content.Context#getSharedPreferences(String, int) 717 * Context.getSharedPreferences} no longer allows a null name.</li> 718 * <li> {@link android.widget.RelativeLayout} changes to compute wrapped content 719 * margins correctly.</li> 720 * <li> {@link android.app.ActionBar}'s window content overlay is allowed to be 721 * drawn.</li> 722 * <li>The {@link android.Manifest.permission#READ_EXTERNAL_STORAGE} 723 * permission is now always enforced.</li> 724 * <li>Access to package-specific external storage directories belonging 725 * to the calling app no longer requires the 726 * {@link android.Manifest.permission#READ_EXTERNAL_STORAGE} or 727 * {@link android.Manifest.permission#WRITE_EXTERNAL_STORAGE} 728 * permissions.</li> 729 * </ul> 730 */ 731 public static final int KITKAT = 19; 732 733 /** 734 * June 2014: Android 4.4W. KitKat for watches, snacks on the run. 735 * 736 * <p>Applications targeting this or a later release will get these 737 * new changes in behavior:</p> 738 * <ul> 739 * <li>{@link android.app.AlertDialog} might not have a default background if the theme does 740 * not specify one.</li> 741 * </ul> 742 */ 743 public static final int KITKAT_WATCH = 20; 744 745 /** 746 * Temporary until we completely switch to {@link #LOLLIPOP}. 747 * @hide 748 */ 749 public static final int L = 21; 750 751 /** 752 * November 2014: Lollipop. A flat one with beautiful shadows. But still tasty. 753 * 754 * <p>Applications targeting this or a later release will get these 755 * new changes in behavior. For more information about this release, see the 756 * <a href="/about/versions/lollipop/">Android Lollipop overview</a>.</p> 757 * <ul> 758 * <li> {@link android.content.Context#bindService Context.bindService} now 759 * requires an explicit Intent, and will throw an exception if given an implicit 760 * Intent.</li> 761 * <li> {@link android.app.Notification.Builder Notification.Builder} will 762 * not have the colors of their various notification elements adjusted to better 763 * match the new material design look.</li> 764 * <li> {@link android.os.Message} will validate that a message is not currently 765 * in use when it is recycled.</li> 766 * <li> Hardware accelerated drawing in windows will be enabled automatically 767 * in most places.</li> 768 * <li> {@link android.widget.Spinner} throws an exception if attaching an 769 * adapter with more than one item type.</li> 770 * <li> If the app is a launcher, the launcher will be available to the user 771 * even when they are using corporate profiles (which requires that the app 772 * use {@link android.content.pm.LauncherApps} to correctly populate its 773 * apps UI).</li> 774 * <li> Calling {@link android.app.Service#stopForeground Service.stopForeground} 775 * with removeNotification false will modify the still posted notification so that 776 * it is no longer forced to be ongoing.</li> 777 * <li> A {@link android.service.dreams.DreamService} must require the 778 * {@link android.Manifest.permission#BIND_DREAM_SERVICE} permission to be usable.</li> 779 * </ul> 780 */ 781 public static final int LOLLIPOP = 21; 782 783 /** 784 * March 2015: Lollipop with an extra sugar coating on the outside! 785 * For more information about this release, see the 786 * <a href="/about/versions/android-5.1">Android 5.1 APIs</a>. 787 */ 788 public static final int LOLLIPOP_MR1 = 22; 789 790 /** 791 * M is for Marshmallow! 792 * 793 * <p>Applications targeting this or a later release will get these 794 * new changes in behavior. For more information about this release, see the 795 * <a href="/about/versions/marshmallow/">Android 6.0 Marshmallow overview</a>.</p> 796 * <ul> 797 * <li> Runtime permissions. Dangerous permissions are no longer granted at 798 * install time, but must be requested by the application at runtime through 799 * {@link android.app.Activity#requestPermissions}.</li> 800 * <li> Bluetooth and Wi-Fi scanning now requires holding the location permission.</li> 801 * <li> {@link android.app.AlarmManager#setTimeZone AlarmManager.setTimeZone} will fail if 802 * the given timezone is non-Olson.</li> 803 * <li> Activity transitions will only return shared 804 * elements mapped in the returned view hierarchy back to the calling activity.</li> 805 * <li> {@link android.view.View} allows a number of behaviors that may break 806 * existing apps: Canvas throws an exception if restore() is called too many times, 807 * widgets may return a hint size when returning UNSPECIFIED measure specs, and it 808 * will respect the attributes {@link android.R.attr#foreground}, 809 * {@link android.R.attr#foregroundGravity}, {@link android.R.attr#foregroundTint}, and 810 * {@link android.R.attr#foregroundTintMode}.</li> 811 * <li> {@link android.view.MotionEvent#getButtonState MotionEvent.getButtonState} 812 * will no longer report {@link android.view.MotionEvent#BUTTON_PRIMARY} 813 * and {@link android.view.MotionEvent#BUTTON_SECONDARY} as synonyms for 814 * {@link android.view.MotionEvent#BUTTON_STYLUS_PRIMARY} and 815 * {@link android.view.MotionEvent#BUTTON_STYLUS_SECONDARY}.</li> 816 * <li> {@link android.widget.ScrollView} now respects the layout param margins 817 * when measuring.</li> 818 * </ul> 819 */ 820 public static final int M = 23; 821 822 /** 823 * N is for Nougat. 824 * 825 * <p>Applications targeting this or a later release will get these 826 * new changes in behavior. For more information about this release, see 827 * the <a href="/about/versions/nougat/">Android Nougat overview</a>.</p> 828 * <ul> 829 * <li> {@link android.app.DownloadManager.Request#setAllowedNetworkTypes 830 * DownloadManager.Request.setAllowedNetworkTypes} 831 * will disable "allow over metered" when specifying only 832 * {@link android.app.DownloadManager.Request#NETWORK_WIFI}.</li> 833 * <li> {@link android.app.DownloadManager} no longer allows access to raw 834 * file paths.</li> 835 * <li> {@link android.app.Notification.Builder#setShowWhen 836 * Notification.Builder.setShowWhen} 837 * must be called explicitly to have the time shown, and various other changes in 838 * {@link android.app.Notification.Builder Notification.Builder} to how notifications 839 * are shown.</li> 840 * <li>{@link android.content.Context#MODE_WORLD_READABLE} and 841 * {@link android.content.Context#MODE_WORLD_WRITEABLE} are no longer supported.</li> 842 * <li>{@link android.os.FileUriExposedException} will be thrown to applications.</li> 843 * <li>Applications will see global drag and drops as per 844 * {@link android.view.View#DRAG_FLAG_GLOBAL}.</li> 845 * <li>{@link android.webkit.WebView#evaluateJavascript WebView.evaluateJavascript} 846 * will not persist state from an empty WebView.</li> 847 * <li>{@link android.animation.AnimatorSet} will not ignore calls to end() before 848 * start().</li> 849 * <li>{@link android.app.AlarmManager#cancel(android.app.PendingIntent) 850 * AlarmManager.cancel} will throw a NullPointerException if given a null operation.</li> 851 * <li>{@link android.app.FragmentManager} will ensure fragments have been created 852 * before being placed on the back stack.</li> 853 * <li>{@link android.app.FragmentManager} restores fragments in 854 * {@link android.app.Fragment#onCreate Fragment.onCreate} rather than after the 855 * method returns.</li> 856 * <li>{@link android.R.attr#resizeableActivity} defaults to true.</li> 857 * <li>{@link android.graphics.drawable.AnimatedVectorDrawable} throws exceptions when 858 * opening invalid VectorDrawable animations.</li> 859 * <li>{@link android.view.ViewGroup.MarginLayoutParams} will no longer be dropped 860 * when converting between some types of layout params (such as 861 * {@link android.widget.LinearLayout.LayoutParams LinearLayout.LayoutParams} to 862 * {@link android.widget.RelativeLayout.LayoutParams RelativeLayout.LayoutParams}).</li> 863 * <li>Your application processes will not be killed when the device density changes.</li> 864 * <li>Drag and drop. After a view receives the 865 * {@link android.view.DragEvent#ACTION_DRAG_ENTERED} event, when the drag shadow moves into 866 * a descendant view that can accept the data, the view receives the 867 * {@link android.view.DragEvent#ACTION_DRAG_EXITED} event and won’t receive 868 * {@link android.view.DragEvent#ACTION_DRAG_LOCATION} and 869 * {@link android.view.DragEvent#ACTION_DROP} events while the drag shadow is within that 870 * descendant view, even if the descendant view returns <code>false</code> from its handler 871 * for these events.</li> 872 * </ul> 873 */ 874 public static final int N = 24; 875 876 /** 877 * N MR1: Nougat++. For more information about this release, see 878 * <a href="/about/versions/nougat/android-7.1">Android 7.1 for 879 * Developers</a>. 880 */ 881 public static final int N_MR1 = 25; 882 883 /** 884 * O. 885 * 886 * <p>Applications targeting this or a later release will get these 887 * new changes in behavior. For more information about this release, see 888 * the <a href="/about/versions/oreo/">Android Oreo overview</a>.</p> 889 * <ul> 890 * <li><a href="{@docRoot}about/versions/oreo/background.html">Background execution limits</a> 891 * are applied to the application.</li> 892 * <li>The behavior of AccountManager's 893 * {@link android.accounts.AccountManager#getAccountsByType}, 894 * {@link android.accounts.AccountManager#getAccountsByTypeAndFeatures}, and 895 * {@link android.accounts.AccountManager#hasFeatures} has changed as documented there.</li> 896 * <li>{@link android.app.ActivityManager.RunningAppProcessInfo#IMPORTANCE_PERCEPTIBLE_PRE_26} 897 * is now returned as 898 * {@link android.app.ActivityManager.RunningAppProcessInfo#IMPORTANCE_PERCEPTIBLE}.</li> 899 * <li>The {@link android.app.NotificationManager} now requires the use of notification 900 * channels.</li> 901 * <li>Changes to the strict mode that are set in 902 * {@link Application#onCreate Application.onCreate} will no longer be clobbered after 903 * that function returns.</li> 904 * <li>A shared library apk with native code will have that native code included in 905 * the library path of its clients.</li> 906 * <li>{@link android.content.Context#getSharedPreferences Context.getSharedPreferences} 907 * in credential encrypted storage will throw an exception before the user is unlocked.</li> 908 * <li>Attempting to retrieve a {@link Context#FINGERPRINT_SERVICE} on a device that 909 * does not support that feature will now throw a runtime exception.</li> 910 * <li>{@link android.app.Fragment} will stop any active view animations when 911 * the fragment is stopped.</li> 912 * <li>Some compatibility code in Resources that attempts to use the default Theme 913 * the app may be using will be turned off, requiring the app to explicitly request 914 * resources with the right theme.</li> 915 * <li>{@link android.content.ContentResolver#notifyChange ContentResolver.notifyChange} and 916 * {@link android.content.ContentResolver#registerContentObserver 917 * ContentResolver.registerContentObserver} 918 * will throw a SecurityException if the caller does not have permission to access 919 * the provider (or the provider doesn't exit); otherwise the call will be silently 920 * ignored.</li> 921 * <li>{@link android.hardware.camera2.CameraDevice#createCaptureRequest 922 * CameraDevice.createCaptureRequest} will enable 923 * {@link android.hardware.camera2.CaptureRequest#CONTROL_ENABLE_ZSL} by default for 924 * still image capture.</li> 925 * <li>WallpaperManager's {@link android.app.WallpaperManager#getWallpaperFile}, 926 * {@link android.app.WallpaperManager#getDrawable}, 927 * {@link android.app.WallpaperManager#getFastDrawable}, 928 * {@link android.app.WallpaperManager#peekDrawable}, and 929 * {@link android.app.WallpaperManager#peekFastDrawable} will throw an exception 930 * if you can not access the wallpaper.</li> 931 * <li>The behavior of 932 * {@link android.hardware.usb.UsbDeviceConnection#requestWait UsbDeviceConnection.requestWait} 933 * is modified as per the documentation there.</li> 934 * <li>{@link StrictMode.VmPolicy.Builder#detectAll StrictMode.VmPolicy.Builder.detectAll} 935 * will also enable {@link StrictMode.VmPolicy.Builder#detectContentUriWithoutPermission} 936 * and {@link StrictMode.VmPolicy.Builder#detectUntaggedSockets}.</li> 937 * <li>{@link StrictMode.ThreadPolicy.Builder#detectAll StrictMode.ThreadPolicy.Builder.detectAll} 938 * will also enable {@link StrictMode.ThreadPolicy.Builder#detectUnbufferedIo}.</li> 939 * <li>{@link android.provider.DocumentsContract}'s various methods will throw failure 940 * exceptions back to the caller instead of returning null. 941 * <li>{@link View#hasFocusable View.hasFocusable} now includes auto-focusable views.</li> 942 * <li>{@link android.view.SurfaceView} will no longer always change the underlying 943 * Surface object when something about it changes; apps need to look at the current 944 * state of the object to determine which things they are interested in have changed.</li> 945 * <li>{@link android.view.WindowManager.LayoutParams#TYPE_APPLICATION_OVERLAY} must be 946 * used for overlay windows, other system overlay window types are not allowed.</li> 947 * <li>{@link android.view.ViewTreeObserver#addOnDrawListener 948 * ViewTreeObserver.addOnDrawListener} will throw an exception if called from within 949 * onDraw.</li> 950 * <li>{@link android.graphics.Canvas#setBitmap Canvas.setBitmap} will no longer preserve 951 * the current matrix and clip stack of the canvas.</li> 952 * <li>{@link android.widget.ListPopupWindow#setHeight ListPopupWindow.setHeight} 953 * will throw an exception if a negative height is supplied.</li> 954 * <li>{@link android.widget.TextView} will use internationalized input for numbers, 955 * dates, and times.</li> 956 * <li>{@link android.widget.Toast} must be used for showing toast windows; the toast 957 * window type can not be directly used.</li> 958 * <li>{@link android.net.wifi.WifiManager#getConnectionInfo WifiManager.getConnectionInfo} 959 * requires that the caller hold the location permission to return BSSID/SSID</li> 960 * <li>{@link android.net.wifi.p2p.WifiP2pManager#requestPeers WifiP2pManager.requestPeers} 961 * requires the caller hold the location permission.</li> 962 * <li>{@link android.R.attr#maxAspectRatio} defaults to 0, meaning there is no restriction 963 * on the app's maximum aspect ratio (so it can be stretched to fill larger screens).</li> 964 * <li>{@link android.R.attr#focusable} defaults to a new state ({@code auto}) where it will 965 * inherit the value of {@link android.R.attr#clickable} unless explicitly overridden.</li> 966 * <li>A default theme-appropriate focus-state highlight will be supplied to all Views 967 * which don't provide a focus-state drawable themselves. This can be disabled by setting 968 * {@link android.R.attr#defaultFocusHighlightEnabled} to false.</li> 969 * </ul> 970 */ 971 public static final int O = 26; 972 973 /** 974 * O MR1. 975 * 976 * <p>Applications targeting this or a later release will get these 977 * new changes in behavior. For more information about this release, see 978 * <a href="/about/versions/oreo/android-8.1">Android 8.1 features and 979 * APIs</a>.</p> 980 * <ul> 981 * <li>Apps exporting and linking to apk shared libraries must explicitly 982 * enumerate all signing certificates in a consistent order.</li> 983 * <li>{@link android.R.attr#screenOrientation} can not be used to request a fixed 984 * orientation if the associated activity is not fullscreen and opaque.</li> 985 * </ul> 986 * 987 */ 988 public static final int O_MR1 = 27; 989 990 /** 991 * P. 992 * 993 * <p>Applications targeting this or a later release will get these 994 * new changes in behavior. For more information about this release, see the 995 * <a href="/about/versions/pie/">Android 9 Pie overview</a>.</p> 996 * <ul> 997 * <li>{@link android.app.Service#startForeground Service.startForeground} requires 998 * that apps hold the permission 999 * {@link android.Manifest.permission#FOREGROUND_SERVICE}.</li> 1000 * <li>{@link android.widget.LinearLayout} will always remeasure weighted children, 1001 * even if there is no excess space.</li> 1002 * </ul> 1003 * 1004 */ 1005 public static final int P = 28; 1006 1007 /** 1008 * Q. 1009 * <p> 1010 * <em>Why? Why, to give you a taste of your future, a preview of things 1011 * to come. Con permiso, Capitan. The hall is rented, the orchestra 1012 * engaged. It's now time to see if you can dance.</em> 1013 */ 1014 public static final int Q = 29; 1015 1016 /** 1017 * R. 1018 */ 1019 public static final int R = 30; 1020 } 1021 1022 /** The type of build, like "user" or "eng". */ 1023 public static final String TYPE = getString("ro.build.type"); 1024 1025 /** Comma-separated tags describing the build, like "unsigned,debug". */ 1026 public static final String TAGS = getString("ro.build.tags"); 1027 1028 /** A string that uniquely identifies this build. Do not attempt to parse this value. */ 1029 public static final String FINGERPRINT = deriveFingerprint(); 1030 1031 /** 1032 * Some devices split the fingerprint components between multiple 1033 * partitions, so we might derive the fingerprint at runtime. 1034 */ deriveFingerprint()1035 private static String deriveFingerprint() { 1036 String finger = SystemProperties.get("ro.build.fingerprint"); 1037 if (TextUtils.isEmpty(finger)) { 1038 finger = getString("ro.product.brand") + '/' + 1039 getString("ro.product.name") + '/' + 1040 getString("ro.product.device") + ':' + 1041 getString("ro.build.version.release") + '/' + 1042 getString("ro.build.id") + '/' + 1043 getString("ro.build.version.incremental") + ':' + 1044 getString("ro.build.type") + '/' + 1045 getString("ro.build.tags"); 1046 } 1047 return finger; 1048 } 1049 1050 /** 1051 * Ensure that raw fingerprint system property is defined. If it was derived 1052 * dynamically by {@link #deriveFingerprint()} this is where we push the 1053 * derived value into the property service. 1054 * 1055 * @hide 1056 */ ensureFingerprintProperty()1057 public static void ensureFingerprintProperty() { 1058 if (TextUtils.isEmpty(SystemProperties.get("ro.build.fingerprint"))) { 1059 try { 1060 SystemProperties.set("ro.build.fingerprint", FINGERPRINT); 1061 } catch (IllegalArgumentException e) { 1062 Slog.e(TAG, "Failed to set fingerprint property", e); 1063 } 1064 } 1065 } 1066 1067 /** 1068 * True if Treble is enabled and required for this device. 1069 * 1070 * @hide 1071 */ 1072 public static final boolean IS_TREBLE_ENABLED = 1073 SystemProperties.getBoolean("ro.treble.enabled", false); 1074 1075 /** 1076 * Verifies the current flash of the device is consistent with what 1077 * was expected at build time. 1078 * 1079 * Treble devices will verify the Vendor Interface (VINTF). A device 1080 * launched without Treble: 1081 * 1082 * 1) Checks that device fingerprint is defined and that it matches across 1083 * various partitions. 1084 * 2) Verifies radio and bootloader partitions are those expected in the build. 1085 * 1086 * @hide 1087 */ isBuildConsistent()1088 public static boolean isBuildConsistent() { 1089 // Don't care on eng builds. Incremental build may trigger false negative. 1090 if (IS_ENG) return true; 1091 1092 if (IS_TREBLE_ENABLED) { 1093 // If we can run this code, the device should already pass AVB. 1094 // So, we don't need to check AVB here. 1095 int result = VintfObject.verifyWithoutAvb(); 1096 1097 if (result != 0) { 1098 Slog.e(TAG, "Vendor interface is incompatible, error=" 1099 + String.valueOf(result)); 1100 } 1101 1102 return result == 0; 1103 } 1104 1105 final String system = SystemProperties.get("ro.system.build.fingerprint"); 1106 final String vendor = SystemProperties.get("ro.vendor.build.fingerprint"); 1107 final String bootimage = SystemProperties.get("ro.bootimage.build.fingerprint"); 1108 final String requiredBootloader = SystemProperties.get("ro.build.expect.bootloader"); 1109 final String currentBootloader = SystemProperties.get("ro.bootloader"); 1110 final String requiredRadio = SystemProperties.get("ro.build.expect.baseband"); 1111 final String currentRadio = joinListOrElse( 1112 TelephonyProperties.baseband_version(), ""); 1113 1114 if (TextUtils.isEmpty(system)) { 1115 Slog.e(TAG, "Required ro.system.build.fingerprint is empty!"); 1116 return false; 1117 } 1118 1119 if (!TextUtils.isEmpty(vendor)) { 1120 if (!Objects.equals(system, vendor)) { 1121 Slog.e(TAG, "Mismatched fingerprints; system reported " + system 1122 + " but vendor reported " + vendor); 1123 return false; 1124 } 1125 } 1126 1127 /* TODO: Figure out issue with checks failing 1128 if (!TextUtils.isEmpty(bootimage)) { 1129 if (!Objects.equals(system, bootimage)) { 1130 Slog.e(TAG, "Mismatched fingerprints; system reported " + system 1131 + " but bootimage reported " + bootimage); 1132 return false; 1133 } 1134 } 1135 1136 if (!TextUtils.isEmpty(requiredBootloader)) { 1137 if (!Objects.equals(currentBootloader, requiredBootloader)) { 1138 Slog.e(TAG, "Mismatched bootloader version: build requires " + requiredBootloader 1139 + " but runtime reports " + currentBootloader); 1140 return false; 1141 } 1142 } 1143 1144 if (!TextUtils.isEmpty(requiredRadio)) { 1145 if (!Objects.equals(currentRadio, requiredRadio)) { 1146 Slog.e(TAG, "Mismatched radio version: build requires " + requiredRadio 1147 + " but runtime reports " + currentRadio); 1148 return false; 1149 } 1150 } 1151 */ 1152 1153 return true; 1154 } 1155 1156 /** Build information for a particular device partition. */ 1157 public static class Partition { 1158 /** The name identifying the system partition. */ 1159 public static final String PARTITION_NAME_SYSTEM = "system"; 1160 1161 private final String mName; 1162 private final String mFingerprint; 1163 private final long mTimeMs; 1164 Partition(String name, String fingerprint, long timeMs)1165 private Partition(String name, String fingerprint, long timeMs) { 1166 mName = name; 1167 mFingerprint = fingerprint; 1168 mTimeMs = timeMs; 1169 } 1170 1171 /** The name of this partition, e.g. "system", or "vendor" */ 1172 @NonNull getName()1173 public String getName() { 1174 return mName; 1175 } 1176 1177 /** The build fingerprint of this partition, see {@link Build#FINGERPRINT}. */ 1178 @NonNull getFingerprint()1179 public String getFingerprint() { 1180 return mFingerprint; 1181 } 1182 1183 /** The time (ms since epoch), at which this partition was built, see {@link Build#TIME}. */ getBuildTimeMillis()1184 public long getBuildTimeMillis() { 1185 return mTimeMs; 1186 } 1187 1188 @Override equals(Object o)1189 public boolean equals(Object o) { 1190 if (!(o instanceof Partition)) { 1191 return false; 1192 } 1193 Partition op = (Partition) o; 1194 return mName.equals(op.mName) 1195 && mFingerprint.equals(op.mFingerprint) 1196 && mTimeMs == op.mTimeMs; 1197 } 1198 1199 @Override hashCode()1200 public int hashCode() { 1201 return Objects.hash(mName, mFingerprint, mTimeMs); 1202 } 1203 } 1204 1205 /** 1206 * Get build information about partitions that have a separate fingerprint defined. 1207 * 1208 * The list includes partitions that are suitable candidates for over-the-air updates. This is 1209 * not an exhaustive list of partitions on the device. 1210 */ 1211 @NonNull getFingerprintedPartitions()1212 public static List<Partition> getFingerprintedPartitions() { 1213 ArrayList<Partition> partitions = new ArrayList(); 1214 1215 String[] names = new String[] { 1216 "bootimage", "odm", "product", "system_ext", Partition.PARTITION_NAME_SYSTEM, 1217 "vendor" 1218 }; 1219 for (String name : names) { 1220 String fingerprint = SystemProperties.get("ro." + name + ".build.fingerprint"); 1221 if (TextUtils.isEmpty(fingerprint)) { 1222 continue; 1223 } 1224 long time = getLong("ro." + name + ".build.date.utc") * 1000; 1225 partitions.add(new Partition(name, fingerprint, time)); 1226 } 1227 1228 return partitions; 1229 } 1230 1231 // The following properties only make sense for internal engineering builds. 1232 1233 /** The time at which the build was produced, given in milliseconds since the UNIX epoch. */ 1234 public static final long TIME = getLong("ro.build.date.utc") * 1000; 1235 public static final String USER = getString("ro.build.user"); 1236 public static final String HOST = getString("ro.build.host"); 1237 1238 /** 1239 * Returns true if we are running a debug build such as "user-debug" or "eng". 1240 * @hide 1241 */ 1242 @UnsupportedAppUsage 1243 public static final boolean IS_DEBUGGABLE = 1244 SystemProperties.getInt("ro.debuggable", 0) == 1; 1245 1246 /** {@hide} */ 1247 public static final boolean IS_ENG = "eng".equals(TYPE); 1248 /** {@hide} */ 1249 public static final boolean IS_USERDEBUG = "userdebug".equals(TYPE); 1250 /** {@hide} */ 1251 public static final boolean IS_USER = "user".equals(TYPE); 1252 1253 /** 1254 * Whether this build is running inside a container. 1255 * 1256 * We should try to avoid checking this flag if possible to minimize 1257 * unnecessarily diverging from non-container Android behavior. 1258 * Checking this flag is acceptable when low-level resources being 1259 * different, e.g. the availability of certain capabilities, access to 1260 * system resources being restricted, and the fact that the host OS might 1261 * handle some features for us. 1262 * For higher-level behavior differences, other checks should be preferred. 1263 * @hide 1264 */ 1265 public static final boolean IS_CONTAINER = 1266 SystemProperties.getBoolean("ro.boot.container", false); 1267 1268 /** 1269 * Specifies whether the permissions needed by a legacy app should be 1270 * reviewed before any of its components can run. A legacy app is one 1271 * with targetSdkVersion < 23, i.e apps using the old permission model. 1272 * If review is not required, permissions are reviewed before the app 1273 * is installed. 1274 * 1275 * @hide 1276 * @removed 1277 */ 1278 @SystemApi 1279 public static final boolean PERMISSIONS_REVIEW_REQUIRED = true; 1280 1281 /** 1282 * Returns the version string for the radio firmware. May return 1283 * null (if, for instance, the radio is not currently on). 1284 */ getRadioVersion()1285 public static String getRadioVersion() { 1286 return joinListOrElse(TelephonyProperties.baseband_version(), null); 1287 } 1288 1289 @UnsupportedAppUsage getString(String property)1290 private static String getString(String property) { 1291 return SystemProperties.get(property, UNKNOWN); 1292 } 1293 getStringList(String property, String separator)1294 private static String[] getStringList(String property, String separator) { 1295 String value = SystemProperties.get(property); 1296 if (value.isEmpty()) { 1297 return new String[0]; 1298 } else { 1299 return value.split(separator); 1300 } 1301 } 1302 1303 @UnsupportedAppUsage getLong(String property)1304 private static long getLong(String property) { 1305 try { 1306 return Long.parseLong(SystemProperties.get(property)); 1307 } catch (NumberFormatException e) { 1308 return -1; 1309 } 1310 } 1311 joinListOrElse(List<T> list, String defaultValue)1312 private static <T> String joinListOrElse(List<T> list, String defaultValue) { 1313 String ret = list.stream().map(elem -> elem == null ? "" : elem.toString()) 1314 .collect(Collectors.joining(",")); 1315 return ret.isEmpty() ? defaultValue : ret; 1316 } 1317 } 1318