DEX: mi ez, a bájtkód szerkezete és működési elve

Szerző: IT Sectr Megjelenés: 2026-04-15 Olvasási idő: 8 perc

A DEX (Dalvik Executable) az a bájtkód formátum, amelybe az Android-alkalmazások Java és Kotlin forráskódja lefordításra kerül. A DEX fájlokat a Dalvik virtuális gép (Android 4.4-ig) vagy az Android Runtime (ART, Android 5.0-tól) hajtja végre. A Android Open Source Project, 2026 adatai szerint a DEX formátum átlagosan 30%-kal tömörebb kódábrázolást biztosít a szabványos JVM bájtkódhoz képest.

Főbb pontok

  • DEX — bájtkód formátum Androidhoz, Dalvikon vagy ART-on fut.
  • Tömörség — a DEX 30%-kal kevesebb helyet foglal, mint a szabványos Java bájtkód.
  • Multidex — mechanizmus a 65536 metódus határának megkerülésére egy DEX fájlban.
  • ART — Android Runtime, amely felváltotta a Dalvikot, telepítéskor natív kódba fordítja a DEX-et.
  • D8 — modern Java/Kotlin fordító DEX-be, amely 2018 óta felváltotta a DX-et.

Mi az a DEX és miért van rá szükség

A DEX (Dalvik Executable) egy kifejezetten Android mobileszközökhöz tervezett bájtkód formátum. A szabványos Java bájtkóddal (.class fájlok) ellentétben a DEX korlátozott erőforrásokra van optimalizálva: kevesebb memória, kisebb méret és gyorsabb osztálybetöltés.

Javától a DEX-ig

A Java vagy Kotlin forráskódot a javac/kotlinc szabványos .class fájlokba (Java bájtkód) fordítja. Ezután a d8 (vagy korábban dx) eszköz a .class fájlokat egy vagy több DEX fájllá alakítja. Ez az átalakítás nem egyszerű átcsomagolás — a d8 optimalizálásokat végez: egyesíti a konstans poolokat, átírja az utasításokat regiszter architektúrába, és eltávolítja a duplikált adatokat.

Architekturális jellemzők

A DEX regiszter architektúrát használ (ellentétben a JVM veremalapú architektúrájával). Minden metódusnak fix számú regisztere van (legfeljebb 65536). A DEX utasítások rövidebbek — átlagosan 2 bájt a JVM 1–4 bájtjával szemben. Ez tömörebb kódot eredményez: egy tipikus alkalmazás 10–15 MB .class-ról 4–6 MB .dex-re csökken.

A DEX fájl szerkezete: szekciók és fejléc

A DEX fájl szigorúan meghatározott bináris szerkezettel rendelkezik. Minden fájl fejléccel kezdődik, és több szekciót tartalmaz, amelyek egymásra offset-eken keresztül hivatkoznak.

SzekcióCél
headerFejléc: magic, ellenőrző összeg, aláírás, szekciók méretei és offset-jei
string_idsKarakterlánc tábla: osztályok, metódusok, mezők nevei
type_idsTípusok: hivatkozások a típusok karakterlánc-azonosítóira
proto_idsMetódus prototípusok: visszatérési típus és paraméterek
field_idsOsztálymezők: osztály, típus, név
method_idsMetódusok: osztály, prototípus, név
class_defsOsztálydefiníciók: jelzők, superclass, interfészek, adat offset-ek
dataTényleges adatok: metóduskód, annotációk, debug információ

DEX fejléc

A DEX varázsszáma — `dex\n035\0` (035-ös verzió). Egyéb verziók: 036, 037, 038 (Android 8.0+ esetén). A 0x70 bájt méretű fejléc SHA-1 ellenőrző összeget és az összes szekció offset-jeit tartalmazza. A fejléc érvényesítése — az első lépés a DEX virtuális gép általi betöltésekor.

Konstans poolok

A string_ids, type_ids, proto_ids, field_ids, method_ids — indexelt táblák. A teljes nevek metóduskódban való tárolása helyett 4 bájtos indexet használunk. Ez a kulcsfontosságú optimalizálás: ha egy osztály 100-szor szerepel, a neve egyszer kerül tárolásra a string_ids-ben. A dex2oat az ART fordítás során tovább optimalizálja ezeket a táblákat.

A Java és Kotlin DEX-be fordításának folyamata

A forráskód DEX-be alakításának folyamata több szakaszból áll. A modern lánc a D8 fordítót használja, amely 2018-ban az Android Gradle Plugin 3.2-vel váltotta fel a DX-et.

1. szakasz: Fordítás .class-ba

A javac (Java esetén) vagy kotlinc (Kotlin esetén) a forráskódot .class fájlokba fordítja. Minden osztály — egy külön .class fájl Java bájtkódban. Ebben a szakaszban típusellenőrzés, hídmetódusok generálása és konstansok beágyazása történik.

2. szakasz: D8 fordítás

A D8 az összes .class fájlt átveszi, és DEX bájtkóddá alakítja. A D8 több optimalizálást is végez: eltávolítja a nem használt metódus argumentumokat, egyesíti a konstans poolokat különböző .class fájlokból egy globális DEX poolba, átalakítja a JVM veremutasításokat Dalvik regiszterutasításokká.

kotlin
// Kotlin forráskód
data class User(
    val name: String,
    val email: String
)

fun greet(user: User): String {
    return "Hello, ${user.name}!"
}

A D8 fordítás után ez a kód kompakt DEX utasításokká alakul: const-string egy karakterlánc betöltéséhez, iget-object egy objektum mező eléréséhez, invoke-virtual a StringBuilder.append meghívásához.

D8 vs DX

A D8 2–3-szor gyorsabb, mint a DX, tömörebb DEX-et generál (5–10%-kal), és jobban optimalizálja a Kotlin-specifikus szerkezeteket (inline függvények, lambda). A DX 2018 óta elavultnak (deprecated) minősül, és eltávolításra került az Android Gradle Plugin 8.0-ból.

Dalvik vs ART: hogyan változott a DEX végrehajtása

A DEX kód végrehajtása Androidban két szakaszon ment keresztül: az eredeti Dalvik virtuális gép (Android 2.2–4.4) és az Android Runtime ART (Android 5.0+). A fordítási megközelítés különbsége alapvető.

Dalvik VM: JIT fordítás

A Dalvik Just-In-Time (JIT) fordítást használt: a DEX bájtkód értelmezésre került, a gyakran hívott metódusok pedig menet közben natív kódba lettek fordítva. Előny — gyors telepítés. Hátrány — lassabb indítás és állandó CPU terhelés a JIT miatt.

ART: AOT fordítás

Az ART (Android Runtime) az alkalmazás telepítésekor a dex2oat segítségével natív kódba fordítja a DEX-et. Ez az Ahead-Of-Time (AOT) megközelítés: a telepítés tovább tart, de az indítás gyorsabb és az energiafogyasztás kisebb. Android 7.0 óta az ART hibrid megközelítést használ — AOT + JIT + Profile Guided Optimization.

dex2oat: konverzió telepítéskor

A dex2oat eszköz az alkalmazás telepítésekor vagy frissítésekor fut. A DEX-et ELF fájllá fordítja natív kóddal az eszköz architektúrájához. Eredmény — .oat és .art fájlok a /data/dalvik-cache/ könyvtárban. A Google folyamatosan fejleszti a dex2oat-ot: Android 14-ben optimalizálás került hozzáadásra a hajlítható eszközökhöz.

Multidex: a 64K metódus korlát áthidalása

A 65536 metódus korlátozása egy DEX fájlban — a Dalvik architektúra öröksége. A method_ids mező a DEX fejlécben 4 bájtot foglal, ami maximum 2^16 = 65536 egyedi hivatkozást tesz lehetővé. A modern alkalmazások Google Play Services-szel, Firebase-zel és más SDK-kkal könnyen túllépik ezt a korlátot.

Multidex mechanizmus

A Multidex egy mechanizmus a kód több DEX fájlra osztására. A fő classes.dex tartalmazza a belépési pontokat (Application osztály, fő Activity), a többi — classes2.dex, classes3.dex és így tovább. Indításkor a kiegészítő DEX-ekből származó osztályok a DexClassLoader segítségével töltődnek be.

kotlin
// build.gradle.kts — multidex engedélyezése
android {
    defaultConfig {
        multiDexEnabled = true
    }
}

// Application osztály multidex támogatással
class MyApp : Application() {
    override fun attachBaseContext(base: Context) {
        super.attachBaseContext(base)
        MultiDex.install(this)
    }
}

Multidex problémák

A kiegészítő DEX-ek betöltése az alkalmazás indítási szakaszában ANR-t (Application Not Responding) okozhat Android 5.0-ig terjedő eszközökön. Javaslat — csak szükség esetén használjon multidex-et, és minimalizálja a függőségeket, hogy ne lépje túl a korlátot.

DEX optimalizálás: ProGuard, R8 és obfuszkáció

A DEX optimalizálás — a release Android alkalmazás készítésének szabványos szakasza. Az R8 és ProGuard eszközök csökkentik a DEX méretét, obfuszkálják a kódot, és eltávolítják a nem használt osztályokat.

R8 vs ProGuard

Az R8 — a ProGuard utódja, 2019 óta beépítve az Android Gradle Plugin-be. Az R8 egy menetben végzi el a minifikációt, obfuszkációt és optimalizálást, míg a ProGuard két szakaszt igényelt: ProGuard → D8. A ProGuard továbbra is támogatott, de a Google az R8-at ajánlja új projektekhez.

Az R8 eltávolítja a nem használt osztályokat, metódusokat és mezőket, rövid nevekre (a, b, c) nevezi át őket, beágyazza az inline függvényeket, és kidobja a halott kódot. Eredmény — a DEX 20–40%-kal csökken a funkcionalitás elvesztése nélkül.

R8 szabályok

Az R8 konfigurációja a proguard-rules.pro fájlban van megadva. A fejlesztő megadhatja, mely osztályok nem nevezhetők át (például reflexió vagy Gson szerializáció esetén). A Firebase és más SDK-k saját szabályokat szállítanak a függőségeikben.

DEX dekompiláció: eszközök és védelem

A DEX visszafordítható Java kóddá. Ez az Android alkalmazások biztonságának kulcskérdése: obfuszkáció nélkül a kód az eredetihez közeli szinten állítható helyre.

Dekompilációs eszközök

A JADX — a legnépszerűbb DEX dekompilátor Java-ba. Visszaállítja az osztályneveket, metódusokat, mezőket és a logika nagy részét. Az apktool DEX-et smali kóddá (Dalvik assembler) dekompilálja — alacsony szintű reprezentáció, közel az eredeti utasításokhoz. A Bytecode Viewer több dekompilátort egyesít egy felületen.

Védelmi módszerek

Az R8/ProGuard obfuszkáció — az első védelmi vonal: az osztály- és metódusnevek olvashatatlanná válnak. A DexGuard — kereskedelmi eszköz további módszerekkel: karakterlánc-titkosítás, integritás-ellenőrzés, anti-tamper. Az obfuszkáció Control Flow szinten (O-LLVM) megváltoztatja a kód szerkezetét, megtartva funkcionalitását, de az elemzést sokkal nehezebbé téve.

Gyakran ismételt kérdések

Miben különbözik a DEX a Java bájtkódtól?

A DEX regiszter architektúrát használ a JVM veremalapú helyett, tömörebb formátummal rendelkezik (30%-kal kisebb), egyesíti az összes .class fájlt egy fájlba egységes konstans pool-lal, és 16 bites indexeket használ 8 bites helyett.

Mi az a smali?

A smali — a DEX bájtkód assemblerje. Minden DEX utasításnak van szöveges megjelenítése smali formátumban. A baksmali eszköz DEX-et smali-vé alakít (visszafejtés), a smali pedig smali-ból DEX-et készít.

Hogyan ellenőrizhető a metódusok száma a DEX-ben?

A Gradle countMethods task vagy a dex-method-counts plugin mutatja a metódusok számát minden DEX fájlban. Az adb shell parancs a dumpsys-szel szintén megjeleníti a betöltött DEX-ek statisztikáját a telepített alkalmazásokhoz.

Befolyásolja-e a DEX-ek száma a teljesítményt?

Igen, Android 8.0-ig terjedő eszközökön a több DEX lassítja az alkalmazás indítását, mivel minden további fájl külön töltődik be. ART-on Android 8.0+ esetén a különbség minimális a dex2oat egyetlen .oat fájlba történő fordításának köszönhetően.

Futtatható a DEX Android nélkül?

Igen, léteznek olyan projektek, mint a dexplorer és Android-kompatibilis JVM implementációk, amelyek képesek DEX bájtkódot futtatni Androidon kívül. Azonban a legtöbb DEX fájl az Android API-t használja, ami alkalmatlanná teszi őket szokványos JVM-en való futtatásra.

Összefoglalás

  • DEX — Android bájtkód formátum regiszter architektúrával és tömör kódábrázolással.
  • Szerkezet fejlécet, azonosító táblákat és adat szekciót tartalmaz utasításokkal.
  • Fordítás DEX-be a D8-on keresztül: .class → DEX optimalizálással és konstans poolok egyesítésével.
  • ART a DEX-et natív kódba fordítja telepítéskor (AOT), gyorsítva az alkalmazás indítását.
  • Multidex — megoldás a 65536 metódus korlát problémájára több DEX fájlra osztással.
  • Optimalizálás — az R8 20–40%-kal csökkenti a DEX-et, obfuszkálja a neveket és eltávolítja a halott kódot.
  • Védelem — R8/ProGuard, DexGuard és O-LLVM obfuszkáció akadályozza meg a DEX dekompilálását.

Kulcsrakész mobilalkalmazást fejlesztünk

Az IT Sectr 2017 óta készít iOS és Android alkalmazásokat induló vállalkozásoknak és vállalkozásoknak. Tanácsot adunk, és a legjobb megoldást javasoljuk.

Projekt megbeszélése

Olvassa el is