1# SdkExtensions module 2 3SdkExtensions module is responsible for: 4- deciding the extension SDK level of the device; 5- providing APIs for applications to query the extension SDK level; 6- determining the values for the BOOTCLASSPATH, DEX2OATBOOTCLASSPATH, and 7 SYSTEMSERVERCLASSPATH environment variables. 8 9## General information 10 11### Structure 12 13The module is packaged in an apex, `com.android.sdkext`, and has several 14components: 15- `bin/derive_classpath`: a native binary that runs early in the device boot 16 process. It reads individual classpath configs files from the system and 17 other modules, merges them, and defines the definition of *CLASSPATH environ 18 variables. 19- `bin/derive_sdk`: native binary that runs early in the device boot process and 20 reads metadata of other modules, to set system properties relating to the 21 extension SDK (for instance `build.version.extensions.r`). 22- `javalib/framework-sdkextension.jar`: this is a jar on the bootclasspath that 23 exposes APIs to applications to query the extension SDK level. 24 25### Deriving extension SDK level 26`derive_sdk` is a program that reads metadata stored in other apex modules, in 27the form of binary protobuf files in subpath `etc/sdkinfo.pb` inside each 28apex. The structure of this protobuf can be seen [here][sdkinfo-proto]. The 29exact steps for converting a set of metadata files to actual extension versions 30is likely to change over time, and should not be depended upon. 31 32### Reading extension SDK level 33The module exposes a java class [`SdkExtensions`][sdkextensions-java] in the 34package `android.os.ext`. The method `getExtensionVersion(int)` can be used to 35read the version of a particular sdk extension, e.g. 36`getExtensionVersion(Build.VERSION_CODES.R)`. 37 38### Deriving classpaths 39`derive_classpath` service reads and merges individual config files in the 40`/system/etc/classpaths/` and `/apex/*/etc/classpaths`. Each config stores 41protobuf message from [`classpaths.proto`] in a proto binary format. Exact 42merging algorithm that determines the order of the classpath entries is 43described in [`derive_classpath.cpp`] and may change over time. 44 45[`classpaths.proto`]: https://android.googlesource.com/platform/packages/modules/common/+/refs/heads/master/proto/classpaths.proto 46[`derive_classpath.cpp`]: derive_classpath/derive_classpath.cpp 47[sdkinfo-proto]: https://android.googlesource.com/platform/packages/modules/common/+/refs/heads/master/proto/sdk.proto 48[sdkextensions-java]: java/android/os/ext/SdkExtensions.java 49 50## Developer information 51 52### Defining a new extension version 53 54In order to bump the extension version, the following steps must be taken. 55 56#### Gather information 57 581) Identify the set of modules that are part of this extension version release. 59These are the set of modules that are releasing new APIs in this train. 60 612) Decide the integer value of this extension version. Usually this is the 62`previous_version + 1`. 63 64#### Code changes 65 663) **build/make:** Update the extension version of the module development 67branch. This is defined by the `PLATFORM_SDK_EXTENSION_VERSION` variable in 68`core/version_defaults.mk`. Subsequent module builds in the branch will embed 69the new version code into the proto in the modules. 70 71 [Example CL][bump] 72 734) **packages/modules/SdkExtensions:** Define the new SDK extension version. 74We have a utility script that automates this. Run: 75 ```sh 76 $ packages/modules/SdkExtensions/gen_sdk/bump_sdk.sh <NEW_VERSION> <MODULES> <BUG> 77 ``` 78 79 ...where `<MODULES>` is a comma-separated list of modules included in the 80 bump, with identifiers listed in the [sdkinfo proto][sdkinfo-proto]). To 81 include all modules, this argument can be omitted. 82 83 [Example CL][def] 84 855) Upload these two CLs in a topic and submit them. It is imperative that 86 87 * the cl generated in step #3 is included in the builds of all the relevant 88 modules in the train 89 * the cl generated in step #4 is included in the SdkExtensions build of the 90 train 91 92#### Update continuous test configuration 93 946) The continuous test configuration has a list of module builds to include when 95running the SdkExtensions tests. They need to be updated to use module builds 96that contain the CLs generated above. See http://shortn/_aKhLxsQLZd 97 98#### Finalize SDK artifacts 99 1007) **prebuilts/sdk & module sdk repos:** Once the train is finalized, the API 101artifacts need to be recorded for doc generation to work correctly. Do this by 102running the finalize_sdk script: 103 104 ``` 105 $ packages/modules/common/tools/finalize_sdk.py \ 106 -f <VERSION> \ 107 -b <BUG> \ 108 -r <README_ENTRY> \ 109 -m <MODULE1> \ 110 -m <MODULE2> [..] 111 ``` 112 113 [Example CL][finalize] 114 115[bump]: https://android.googlesource.com/platform//build/+/f5dfe3ff7b59b44556510ba89d15161c87312069 116[def]: https://android.googlesource.com/platform/packages/modules/SdkExtensions/+/5663ebb842412b0235a140656db17025280f9f08 117[derive_sdk_test]: derive_sdk/derive_sdk_test.cpp 118[current_version]: java/com/android/os/ext/testing/CurrentVersion.java 119[finalize]: https://android.googlesource.com/platform/prebuilts/sdk/+/d77e77b6746acba806c263344711eb0c4df2b108 120 121### Adding a new extension 122 123An extension is a way to group a set of modules so that they are versioned 124together. We currently define a new extension for every Android SDK level that 125introduces new modules. Every module shipped in previous versions are also part 126of the new extension. For example, all the R modules are part of both the R 127extensions and the S extensions. 128 129The steps to define a new extension are: 130 131- Add any new modules to the SdkModule enum in sdk.proto. e.g. 132 [for new required, updatable modules in U](http://ag/21148706) 133 134- Add the binary "current sdk version" proto to the apexes of the new modules. 135 e.g. [for health fitness](http://ag/21158651) and 136 [config infrastructure](http://ag/21158650). 137 138- Update `derive_sdk.cpp` by: 139 140 * mapping the modules' package names to the new enum values 141 142 * creating a new set with the new enum values of the modules relevant for 143 this extension. 144 145 * set a new sysprop to the value of `GetSdkLevel` with the new enum set 146 147 * add a unit test to `derive_sdk_test.cpp` verifying the new extensions 148 work 149 150 * update the hard-coded list of extensions in `ReadSystemProperties` 151 152 * e.g. [for U extension](http://ag/21481214) 153 154- Make the `SdkExtensions.getExtensionVersion` API support the new extensions. 155 156 * Extend `CtsSdkExtentensionsTestCase` to verify the above two behaviors. 157 158 * e.g. [for U extensions](http://ag/21507939) 159 160- Add a new sdk tag in sdk-extensions-info.xml 161