AOT — what is Ahead-Of-Time compilation and how it works

Author: IT Sectr Published: 2026-04-16 Reading time: 9 min

AOT (Ahead-Of-Time) — a compilation technology where source code or bytecode is converted into machine instructions before program execution, at the build or installation stage. In Android, AOT compilation became a key innovation of the ART runtime environment, which replaced Dalvik in version 5.0 Lollipop. According to Google, 2024, AOT compilation in ART eliminates warm-up delays and reduces application power consumption by 10–15% compared to the JIT approach.

Key Takeaways

  • AOT — Ahead-Of-Time compilation: converting code to machine code before program execution.
  • In Android, AOT is performed by the dex2oat utility during APK installation or in the background.
  • The main advantage of AOT is instant app startup without a warm-up phase.
  • The disadvantage is increased installation time and additional disk space of 15–30%.
  • Modern systems use a hybrid approach: JIT for first launches, AOT for hot methods.

What is AOT Compilation?

Ahead-Of-Time (AOT) is a compilation method where a program is converted into machine code before it is run. The term “Ahead-Of-Time” contrasts with JIT (Just-In-Time): if JIT compiles “just in time,” then AOT compiles “ahead of time.” An AOT compiler takes source code or an intermediate representation (bytecode) as input and generates an executable file ready to run.

The history of AOT dates back to traditional C and C++ compilers, where compilation always happens before execution. In the context of managed languages (Java, C#, Dart), AOT is a more recent innovation: for a long time, it was believed that dynamic capabilities (reflection, dynamic class loading) made AOT difficult to implement. Google solved this problem for Android by creating dex2oat — an AOT compiler of DEX bytecode into native code.

How AOT Works

An AOT compiler performs a full translation cycle. The first stage is parsing and building an abstract syntax tree (AST). The second is analysis and optimization: dead code elimination, inlining, loop optimization. The third is generating machine code for the target architecture (ARM, ARM64, x86). The result is an executable file that requires no additional processing at runtime.

bash
# Manual launch of AOT compiler dex2oat
dex2oat --dex-file=classes.dex \
        --oat-file=classes.oat \
        --arch=arm64 \
        --instruction-set-variant=generic

# Check compiled OAT file
oatdump --oat-file=classes.oat --output=oat_dump.txt

AOT in Android: dex2oat and OAT Files

In Android, AOT compilation is implemented through the dex2oat utility (dalvik executable to optimized android translator). When a user installs an application, the system runs dex2oat, which reads DEX files from the APK, optimizes the bytecode, and creates an OAT file — an ELF binary with native code. This file is saved in the /data/dalvik-cache/ partition.

The compilation process includes several levels of optimization. The basic level — bytecode verification and basic optimizations (dead code elimination, constant folding). The intermediate level — method inlining, loop unrolling, escape analysis. The maximum level — global optimizations of the entire application, including devirtualization and stack size optimization. The optimization level depends on the compilation mode (speed, speed-profile, space).

OAT File Structure

An OAT file uses the ELF (Executable and Linkable Format) format — the same format used by native Linux binaries. Inside the OAT file is the compiled code for each application method, along with metadata: information about classes, fields, methods, and their relationships. ART uses this metadata for fast class loading and resolving symbolic references without full DEX parsing.

OAT ComponentPurpose
ELF headerELF format header
Code sectionMachine code of compiled methods
OAT headerART metadata: version, section sizes
DEX sectionsOriginal DEX data for reflection
Link tableLink table for JNI and native libraries

AOT vs JIT: Comparative Analysis

AOT and JIT represent different points in the trade-off space between performance and flexibility. AOT provides maximum execution speed from the first second but requires more disk space and installation time. JIT saves space and installation time but pays with warm-up delays and peak power consumption.

The key selection factor is the use case. For applications that are launched once and run for a long time (games, editors, navigation), AOT is preferable — the compilation costs are offset by stable performance. For small utilities that are rarely launched and run for short periods, JIT may be more advantageous — fast installation and small footprint are more important than peak performance.

CriterionAOTJIT
StartupInstantWith warm-up
InstallationSlower (compilation)Fast
Disk space+15–30%Minimal
Power consumptionStablePeaks during compilation
AdaptabilityLowHigh

Code Performance

An interesting nuance: AOT code is not always faster than JIT. JIT has access to runtime profiling information — precise object types, call frequencies, real branching patterns. This allows applying optimizations unavailable to AOT (e.g., profile-guided inlining). In practice, the performance difference of compiled code between AOT and JIT is ±5–10% depending on the scenario.

Advantages of AOT Compilation

AOT provides three key advantages for mobile applications. First — predictable performance. The user doesn’t see “stuttering” in the first seconds: the application runs at maximum speed from the first frame. This is critical for games, animations, and interfaces with smooth transitions.

Second — energy efficiency. AOT doesn’t create peak CPU loads typical of JIT compilation. The processor operates in a stable mode, reducing power consumption by 10–15% during the first 30–60 seconds of application usage. For a typical user launching 20–30 apps per day, this provides a noticeable increase in battery life.

Runtime Simplification

AOT compilation simplifies the runtime environment. When all code is already compiled, there is no need for a JIT compiler, interpreter, or profiler at runtime. This reduces the size of the runtime itself and lowers the chance of errors. ART in full AOT mode uses approximately 15% less RAM than a similar environment with active JIT.

Disadvantages of AOT Compilation

The main disadvantage of AOT is installation time. On early devices with Android 5.0, installing large applications (100–200 MB) could take 2–5 minutes due to AOT compilation. This created a negative user experience: after downloading the APK, users had to wait before opening the application. Google partially solved this problem in Android 7.0 by switching to a hybrid scheme.

The second disadvantage is disk space. OAT files are 15–30% larger than the original DEX files. On devices with 8–16 GB of internal storage, each application “eats” additional space on the system partition. For users with a large number of installed applications (50–100), this can lead to insufficient space for system updates.

Lack of Adaptability

AOT code is fixed at compile time. If the application uses different execution patterns depending on the Android version, device model, or user settings, AOT cannot adapt. Optimizations chosen for one scenario may be suboptimal for another. JIT is more flexible in this regard: it recompiles hot methods when execution conditions change.

AOT Beyond Android: Flutter, .NET, Go

AOT compilation is used not only in Android. Flutter uses AOT to compile Dart code into native code for iOS and Android. This ensures UI performance at 60 fps even on low-end devices. During development, Flutter uses JIT (hot reload), and for release builds — AOT, combining the advantages of both approaches.

In the .NET ecosystem, the ReadyToRun (R2R) technology allows compiling assemblies into native code ahead of time. This reduces .NET application startup time by 30–50%. The Go compiler is inherently an AOT compiler: Go programs are compiled into a single static binary with no external dependencies, making them ideal for container environments.

dart
// Flutter: AOT compilation of Dart into native code
// Release build uses AOT
flutter build apk --release

// Result: libapp.so with AOT-compiled Dart code
// Development uses JIT (hot reload)
flutter run

AOT and Security

An additional advantage of AOT is making reverse engineering harder. Compiled native code is more difficult to decompile than bytecode. Tools like JADX and APKTool work with the DEX format but cannot recover source code from OAT files at the same level of detail. This doesn’t replace obfuscation (ProGuard, R8), but creates an additional barrier for analyzers.

Hybrid Strategy: Profiled Compilation

The modern standard in Android is profiled AOT compilation, implemented in ART starting with Android 7.0. When installing, the application is not fully compiled — instead, fast bytecode verification and JIT are used for the first launches. This solves the long installation problem characteristic of pure AOT in Android 5.0–6.0.

After 2–3 application launches, the ART profiler collects data about real usage and determines which methods are most critical for performance. Then, in the background (usually at night when the device is charging), dex2oat compiles these hot methods into native code. After background compilation, the application achieves performance equivalent to full AOT, without negatively impacting the user experience during installation.

kotlin
// Programmatic control of compilation mode (Android 9+)
fun requestProfileCompilation(context: Context) {
    val pm = context.packageManager
    // It is recommended to use profiled compilation
    pm.setComponentEnabledSetting(
        ComponentName(context, javaClass()),
        PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
        PackageManager.DONT_KILL_APP
    )
}

Optimizing for Hybrid Mode

To maximize the benefits of hybrid compilation, developers should follow a few rules. Use baseline profiles — pre-collected profiles that ship with the APK and allow ART to start AOT compilation of hot methods immediately after installation. Baseline profiles reduce the time to reach full performance from 2–3 launches to the very first launch.

Frequently Asked Questions

What is AOT compilation in simple terms?

AOT is converting a program into machine code in advance, before the user runs it. Imagine that a book is translated entirely into your language before you open it — you read it immediately, without delays for page translation.

How is AOT different from JIT?

AOT compiles code during installation (slower installation, but faster startup). JIT compiles code at runtime (fast installation, but the first seconds are slower). Modern systems combine both approaches.

Why did Android switch from Dalvik to ART with AOT?

Google wanted to eliminate the JIT warm-up problem — delays in the first seconds of application execution. AOT compilation in ART provided instant startup and reduced power consumption, which was critically important for mobile devices.

How does AOT affect application size?

The APK size doesn’t change — AOT compilation creates OAT files on the system partition that are 15–30% larger than the original DEX files. The user sees this as a reduction in free internal storage space, not as an increase in the download file size.

What is profiled AOT?

This is a hybrid approach where the first launches of the application use JIT, and then the system compiles only frequently used methods into native code in the background. This combines the fast installation of JIT with the high performance of AOT.

Summary

  • AOT (Ahead-Of-Time) — compilation of bytecode into machine code before program execution, at the installation stage.
  • In Android, AOT is implemented through the dex2oat utility, creating ELF binaries (OAT files).
  • Main advantages of AOT: instant startup, stable performance, and low power consumption.
  • Main disadvantages: increased installation time and additional disk space of 15–30%.
  • AOT is used not only in Android, but also in Flutter (Dart), .NET (R2R) and Go.
  • Modern ART uses profiled AOT: JIT for first launches, background compilation of hot methods.
  • Baseline profiles allow AOT compilation of key methods to start immediately after installation of the application.

We will develop a mobile application turnkey

IT Sectr creates iOS and Android applications for startups and businesses since 2017. We will advise you and propose the best solution.

Discuss the project

Read also