Permalink
Browse files

Add rules to detect Jack compiler

Reference: http://tools.android.com/tech-docs/jackandjill

Also, split out dex manipulators such as dexmerge and compilers such as dx.
  • Loading branch information...
CalebFenton committed Dec 1, 2016
1 parent 377cb73 commit ccca5ed519b7b2551a3205686be364c26020f1cd
Showing with 117 additions and 23 deletions.
  1. +117 −23 apkid/rules/dex/compilers.yara
@@ -28,11 +28,8 @@
import "dex"
include "common.yara"
rule dexlib1 : compiler
private rule unsorted_string_table
{
meta:
description = "dexlib 1.x"
condition:
/*
* DEX format requires string IDs to be sorted according to the data at their offsets but the actual
@@ -42,60 +39,157 @@ rule dexlib1 : compiler
for any i in (0..dex.header.string_ids_size - 1) : (dex.string_ids[i].offset + dex.string_ids[i].item_size + 1 != dex.string_ids[i + 1].offset)
}
rule dexlib2 : compiler
private rule dexlib2_map_type_order
{
meta:
description = "dexlib 2.x"
condition:
/*
* The map_list types are in different orders for DX, dexmerge, and dexlib (1 and 2 are the same)
*/
not dexlib1 and
dex.map_list.map_items[7].type == 0x2002 // TYPE_STRING_DATA_ITEM
}
rule dexlib2beta : compiler
private rule null_interfaces
{
meta:
description = "dexlib 2.x beta"
condition:
/*
* Dexlib2 adds a non-zero interfaces_offset to every class_def_item, even if the class doesn't implement an
* interface. It points to 4 null bytes right after string pool. DEX documentation says the value for
* interfaces_offset should be 0 if there is no interface, which is what DX does. It's enough to check
* if a single class has an interface which points to null bytes since no one else does this.
*/
not dexlib1 and not dexlib2 and
for any i in (0..dex.header.class_defs_size) : (dex.class_defs[i].interfaces_offset > 0 and uint32(dex.class_defs[i].interfaces_offset) == 0)
}
rule dx : compiler
private rule dx_map_type_order
{
meta:
description = "Android SDK (dx)"
condition:
/*
* The map_list types are in different orders for DX, dexmerge, and dexlib (1 and 2 are the same)
* DX order derrived from: http://osxr.org/android/source/dalvik/dx/src/com/android/dx/dex/file/DexFile.java#0111
*/
not dexlib1 and not dexlib2 and not dexlib2beta and
(dex.map_list.map_items[7].type == 0x1002 or // TYPE_ANNOTATION_SET_REF_LIST
dex.map_list.map_items[7].type == 0x1003 or // TYPE_ANNOTATION_SET_ITEM
dex.map_list.map_items[7].type == 0x2001) // TYPE_CODE_ITEM
}
rule dexmerge : compiler
private rule dexmerge_map_type_order
{
meta:
description = "Android SDK (dexmerge)"
condition:
/*
* The map_list types are in different orders for DX, dexmerge, and dexlib (1 and 2 are the same)
* DexMerge order derrived from: http://osxr.org/android/source/dalvik/dx/src/com/android/dx/merge/DexMerger.java#0111
*/
dex.map_list.map_items[7].type == 0x1000 // TYPE_MAP_LIST
}
rule dexlib1 : compiler
{
meta:
description = "dexlib 1.x"
condition:
unsorted_string_table
}
rule dexlib2 : compiler
{
meta:
description = "dexlib 2.x"
condition:
not dexlib1 and dexlib2_map_type_order
}
rule dexlib2beta : compiler
{
meta:
description = "dexlib 2.x beta"
condition:
not dexlib1 and not dexlib2 and null_interfaces
}
rule dx : compiler
{
meta:
description = "Android SDK (dx)"
condition:
not dexlib1 and not dexlib2 and not dexlib2beta and dx_map_type_order
}
rule dexmerge : manipulator
{
meta:
description = "Android SDK (dexmerge)"
condition:
dexmerge_map_type_order
}
rule jack_4_12 : compiler
{
meta:
description = "Jack 4.12"
strings:
$jack_emitter = {00 12 65 6D 69 74 74 65 72 3A 20 6A 61 63 6B 2D 34 2E 31 32 00}
condition:
is_dex and $jack_emitter
}
rule jack_3x : compiler
{
meta:
description = "Jack 3.x"
strings:
//\0<len>emitter: jack-3.??\0
$jack_emitter = {00 1? 65 6D 69 74 74 65 72 3A 20 6A 61 63 6B 2D 33 2E [1-3] 00}
condition:
is_dex and $jack_emitter
}
rule jack_4x : compiler
{
meta:
description = "Jack 4.x"
strings:
//\0<len>emitter: jack-4.??\0
$jack_emitter = {00 1? 65 6D 69 74 74 65 72 3A 20 6A 61 63 6B 2D 34 2E [1-3] 00}
condition:
is_dex and not jack_4_12 and $jack_emitter
}
rule jack_5x : compiler
{
meta:
description = "Jack 5.x"
strings:
//\0<len>emitter: jack-5.??\0
$jack_emitter = {00 1? 65 6D 69 74 74 65 72 3A 20 6A 61 63 6B 2D 35 2E [1-3] 00}
condition:
is_dex and $jack_emitter
}
rule jack_generic : compiler
{
// http://tools.android.com/tech-docs/jackandjill
meta:
description = "Jack (unknown version)"
strings:
$jack_emitter = "emitter: jack-"
condition:
is_dex and not jack_3x and not jack_4x and not jack_5x
and not jack_4_12
and $jack_emitter
}

0 comments on commit ccca5ed

Please sign in to comment.