Introduction to Android Verified Boot 2.0 (AVB 2.0)
Android Verified Boot (AVB) 2.0 is a critical security feature in modern Android devices, designed to ensure the integrity and authenticity of the operating system from the moment the device powers on. It establishes a chain of trust from a hardware root of trust, verifying each stage of the boot process before execution. For device integrators, custom ROM developers, and security researchers, understanding how to interact with AVB 2.0, particularly through the use of test keys, is essential. This lab provides a detailed guide on generating custom AVB 2.0 test keys, signing boot images, and flashing them onto an Android device for development and testing purposes.
By generating and flashing your own test keys, you can simulate different boot states, test custom firmware, and understand the verification process without compromising the device’s production security posture. This process is invaluable for debugging boot issues, validating custom kernels or system images, and developing secure update mechanisms.
Why Use Test Keys?
- Development & Debugging: Sign custom builds (kernels, bootloaders, system images) to allow them to boot on devices where AVB is enforced.
- Security Research: Experiment with different verification scenarios and understand AVB’s behavior under various conditions.
- OEM Customization: For device manufacturers, testing new firmware versions before moving to production keys.
Prerequisites for Your AVB 2.0 Lab
Before proceeding, ensure you have the following tools and environment set up:
- Android Open Source Project (AOSP) Source Tree: Access to a full AOSP build environment is highly recommended, as it contains the necessary
avbtooland other utilities. Alternatively, you can buildavbtoolfrom its source. avbtool: The Android Verified Boot tool, usually found in/out/host/linux-x86/bin/or similar paths after an AOSP build.openssl: A standard cryptographic toolkit, used for generating RSA key pairs.- Android SDK Platform Tools: Specifically,
adbandfastbootfor interacting with your Android device. - An Android Device: A test device with an unlocked bootloader, compatible with AVB 2.0 and supporting custom key flashing. Pixel devices are often good candidates for such experiments.
Understanding AVB 2.0 Key Hierarchies
AVB 2.0 relies on a hierarchical key structure to establish its chain of trust:
- Root of Trust (RoT): This is the hardware-fused public key on the device, immutable and non-modifiable. It’s the ultimate authority, used to verify the primary bootloader and the
vbmeta.img. vbmeta.imgSigning Key: This is the key pair used to sign thevbmeta.img. The public part of this key is embedded within thevbmeta.imgitself. During boot, the device’s RoT verifies thevbmeta.imgagainst the trusted public key. If verified, thevbmeta.img‘s public key (or a hash of it) becomes the new root of trust for subsequent partitions.- Partition Signing Keys: These keys sign individual partitions like
boot.img,system.img,vendor.img. Their public key hashes or full public keys are typically embedded as descriptors within thevbmeta.img.
For our lab, we’ll focus on generating keys for signing vbmeta.img and subsequent partitions, and then demonstrating how to instruct the device’s bootloader to trust our custom vbmeta.img.
Step 1: Generating AVB 2.0 Test Keys
We’ll generate an RSA 4096-bit key pair using openssl. This key pair will be used to sign our vbmeta.img.
1. Generate RSA Private Key (PEM format)
openssl genrsa -out rsa4096_vbmeta.pem 4096
This command creates a 4096-bit RSA private key named rsa4096_vbmeta.pem.
2. Convert Private Key to PK8 format
AVB tools typically require the private key in PKCS#8 (PK8) format.
openssl pkcs8 -in rsa4096_vbmeta.pem -topk8 -nocrypt -out rsa4096_vbmeta.pk8
The -nocrypt flag ensures the key is not encrypted, which is suitable for test environments. For production, you’d typically encrypt it.
3. Extract Public Key in AVB-specific formats
We need the public key in two formats: one for flashing to the device’s custom key partition (if applicable) and another for verifying vbmeta.img itself.
a. For Flashing (e.g., avb_custom_key partition)
This generates a blob (`.bin`) that some bootloaders can flash as a custom AVB key. This is how the device learns to trust your `vbmeta.img` signed by your test key.
avbtool extract_public_key --input rsa4096_vbmeta.pk8 --output rsa4096_vbmeta.bin --header_only
b. For `avbtool` internal use (e.g., `–key_path`)
This simply extracts the public key data to a file, which `avbtool` can use to inspect signed images.
avbtool extract_public_key --input rsa4096_vbmeta.pk8 --output rsa4096_vbmeta.avbpubkey
Step 2: Signing Android Partitions with Test Keys
Now that we have our test keys, we’ll use them to sign our Android partitions. This involves adding AVB footers to images like boot.img and system.img, and then creating a vbmeta.img that contains the hashes or descriptors for these signed partitions.
For this example, assume you have a boot.img and system.img that you wish to sign. You’ll need to know their approximate partition sizes on the device.
1. Add AVB Footer to boot.img
This command adds a hash footer to your boot.img. The size specified should match the actual partition size on the device.
avbtool add_hash_footer --image boot.img --partition_name boot --partition_size 134217728 --key rsa4096_vbmeta.pk8 --algorithm SHA256_RSA4096 --output boot_signed.img
Note: 134217728 bytes is 128MB, a common size for boot partitions. Adjust as necessary.
2. Add AVB Footer to system.img
Similarly, sign your system.img. Assume a larger size for the system partition.
avbtool add_hash_footer --image system.img --partition_name system --partition_size 3221225472 --key rsa4096_vbmeta.pk8 --algorithm SHA256_RSA4096 --output system_signed.img
Note: 3221225472 bytes is 3GB. Adjust as necessary.
3. Create and Sign vbmeta.img
The vbmeta.img is the central piece. It’s signed with our private key and includes descriptors for the boot_signed.img and system_signed.img.
avbtool make_vbmeta_image --output vbmeta.img --key rsa4096_vbmeta.pk8 --algorithm SHA256_RSA4096 --include_descriptors_from_image boot_signed.img --include_descriptors_from_image system_signed.img --padding_size 4096
The --padding_size 4096 ensures the vbmeta.img is padded to a block size, which is often required for flashing. If you have other partitions (e.g., vendor.img, dtbo.img), you would add footers to them and include them in the vbmeta.img similarly.
Step 3: Flashing Test Keys and Signed Images to Device
Now, we’ll flash our generated public key and the signed images to an Android device. Ensure your device is in fastboot mode.
1. Unlock Critical Partitions (if necessary)
Some devices require unlocking critical partitions to flash custom AVB keys. This typically wipes the device.
fastboot flashing unlock_critical
2. Flash the Custom AVB Public Key
This step enrolls your custom public key (from `rsa4096_vbmeta.bin`) with the device’s bootloader. This tells the bootloader to trust vbmeta.img signed by your `rsa4096_vbmeta.pk8` private key. This command might vary based on your device’s bootloader. For many devices, avb_custom_key is a known partition or a command alias.
fastboot flash avb_custom_key rsa4096_vbmeta.bin
If your device does not support avb_custom_key directly via fastboot, you might need a device-specific OEM tool or a different method to enroll the public key into the bootloader’s trusted store. Refer to your device’s documentation or community resources for alternatives.
3. Flash the Signed Partitions
Flash your newly signed `vbmeta.img` and other images.
fastboot flash vbmeta vbmeta.imgfastboot flash boot boot_signed.imgfastboot flash system system_signed.img
After flashing, reboot your device.
fastboot reboot
Step 4: Verifying AVB State on Device
Once your device reboots, you can verify the AVB state using `adb`.
1. Check Device Information
While in `fastboot` mode, you can check general device information:
fastboot oem device-info
Look for `Device unlocked` (should be true if you unlocked it) and `Device critical unlocked` (should be true if you unlocked critical partitions). You might also see information about AVB state, like `verified boot state`.
2. Check AVB State with avbctl
Once the device boots up (even if it’s in a warning state), you can use `adb shell avbctl` to inspect the AVB configuration.
adb shell avbctl get-verity-mode
This should return `eio` (enforcing I/O) or `logging`.
adb shell avbctl get-state
This command can provide details on the current AVB state. Possible states include:
- GREEN: Verified boot is enforcing, and everything is trusted.
- YELLOW: Verified boot is enforcing, but some images are non-stock. This usually means a custom key is trusted.
- ORANGE: Verified boot is off, or the device is unlocked and not enforcing verification.
If your `vbmeta.img` was correctly signed by your custom key, and the key was successfully enrolled, you should typically see a YELLOW state, indicating that custom software is running but is still being verified by a trusted, albeit custom, key.
Conclusion
Generating and flashing custom AVB 2.0 test keys is a fundamental skill for anyone involved in Android device integration, custom firmware development, or security analysis. This lab has provided a comprehensive, step-by-step guide to navigate the intricacies of AVB 2.0, from key generation to image signing and on-device verification. By mastering these techniques, you gain significant control over the boot process, enabling robust testing and development of custom Android solutions while maintaining the principles of verified boot security.
Android Mobile Specs & Compare Directory
Are you researching mobile hardware properties, processor SoCs, GPU chipsets, or RAM configurations? Access our complete specs catalog to compare up to 5 devices side-by-side!
Compare Devices Specs →