summaryrefslogtreecommitdiff
path: root/src/arch
diff options
context:
space:
mode:
Diffstat (limited to 'src/arch')
-rw-r--r--src/arch/dalvik/Makefile.am8
-rw-r--r--src/arch/dalvik/instruction-def.h208
-rw-r--r--src/arch/dalvik/instruction-int.h52
-rw-r--r--src/arch/dalvik/instruction.c18
-rw-r--r--src/arch/dalvik/instruction.h171
-rw-r--r--src/arch/dalvik/processor.c83
-rw-r--r--src/arch/dalvik/pseudo/Makefile.am17
-rw-r--r--src/arch/dalvik/pseudo/fill.c214
-rw-r--r--src/arch/dalvik/pseudo/fill.h57
-rw-r--r--src/arch/dalvik/pseudo/switch.c217
-rw-r--r--src/arch/dalvik/pseudo/switch.h57
-rw-r--r--src/arch/dalvik/specins.c115
-rw-r--r--src/arch/dalvik/specins.h51
-rw-r--r--src/arch/instruction-int.h4
-rw-r--r--src/arch/instruction.c35
15 files changed, 937 insertions, 370 deletions
diff --git a/src/arch/dalvik/Makefile.am b/src/arch/dalvik/Makefile.am
index 6640180..18fb08d 100644
--- a/src/arch/dalvik/Makefile.am
+++ b/src/arch/dalvik/Makefile.am
@@ -3,6 +3,8 @@ noinst_LTLIBRARIES = libarchdalvik.la
libarchdalvik_la_SOURCES = \
context.h context.c \
+ instruction-def.h \
+ instruction-int.h \
instruction.h instruction.c \
dop_aget.c \
dop_aput.c \
@@ -43,11 +45,11 @@ libarchdalvik_la_SOURCES = \
operand.h operand.c \
processor.h processor.c \
register.h register.c \
- specins.h specins.c \
translate.h
libarchdalvik_la_LIBADD = \
- operands/libarchdalvikoperands.la
+ operands/libarchdalvikoperands.la \
+ pseudo/libarchdalvikpseudo.la
libarchdalvik_la_CFLAGS = $(AM_CFLAGS)
@@ -59,4 +61,4 @@ AM_CPPFLAGS =
AM_CFLAGS = $(DEBUG_CFLAGS) $(WARNING_FLAGS) $(COMPLIANCE_FLAGS)
-SUBDIRS = operands
+SUBDIRS = operands pseudo
diff --git a/src/arch/dalvik/instruction-def.h b/src/arch/dalvik/instruction-def.h
new file mode 100644
index 0000000..48d7e96
--- /dev/null
+++ b/src/arch/dalvik/instruction-def.h
@@ -0,0 +1,208 @@
+
+/* OpenIDA - Outil d'analyse de fichiers binaires
+ * instruction-def.h - définition interne des identifiants d'instructions Dalvik
+ *
+ * Copyright (C) 2011 Cyrille Bagard
+ *
+ * This file is part of OpenIDA.
+ *
+ * OpenIDA is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * OpenIDA is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Foobar. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+
+#ifndef _ARCH_DALVIK_INSTRUCTION_DEF_H
+#define _ARCH_DALVIK_INSTRUCTION_DEF_H
+
+
+
+/* Enumération de tous les opcodes */
+typedef enum _DalvikOpcodes
+{
+ DOP_NOP, /* nop (0x00) */
+ DOP_MOVE, /* move (0x01) */
+ DOP_MOVE_FROM_16, /* move/from16 (0x02) */
+
+ DOP_MOVE_OBJECT, /* move-object (0x07) */
+
+ DOP_MOVE_RESULT, /* move-result (0x0a) */
+ DOP_MOVE_RESULT_WIDE, /* move-result-wide (0x0b) */
+ DOP_MOVE_RESULT_OBJECT, /* move-result-object (0x0c) */
+ DOP_MOVE_EXCEPTION, /* move-exception (0x0d) */
+ DOP_RETURN_VOID, /* return-void (0x0e) */
+ DOP_RETURN, /* return (0x0f) */
+ DOP_RETURN_WIDE, /* return-wide (0x10) */
+ DOP_RETURN_OBJECT, /* return-object (0x11) */
+ DOP_CONST_4, /* const/4 (0x12) */
+ DOP_CONST_16, /* const/16 (0x13) */
+ DOP_CONST, /* const (0x14) */
+ DOP_CONST_HIGH16, /* const/high16 (0x15) */
+ DOP_CONST_WIDE_16, /* const-wide/16 (0x16) */
+
+ DOP_CONST_WIDE, /* const-wide (0x18) */
+
+ DOP_CONST_STRING, /* const-string (0x1a) */
+
+
+ DOP_CHECK_CAST, /* check-cast (0x1f) */
+
+ DOP_ARRAY_LENGTH, /* array-length (0x21) */
+ DOP_NEW_INSTANCE, /* new-instance (0x22) */
+ DOP_NEW_ARRAY, /* new-array (0x23) */
+
+ DOP_FILL_ARRAY_DATA, /* fill-array-data (0x26) */
+
+ DOP_GOTO, /* goto (0x28) */
+ DOP_GOTO_16, /* goto/16 (0x29) */
+ DOP_GOTO_32, /* goto/32 (0x2a) */
+
+
+ DOP_CMPL_FLOAT, /* cmp-long (0x2d) */
+ DOP_CMPG_FLOAT, /* cmpg-float (0x2e) */
+ DOP_CMPL_DOUBLE, /* cmpl-double (0x2f) */
+ DOP_CMPG_DOUBLE, /* cmpg-double (0x30) */
+ DOP_CMP_LONG, /* cmp-long (0x31) */
+ DOP_IF_EQ, /* if-eq (0x32) */
+ DOP_IF_NE, /* if-ne (0x33) */
+ DOP_IF_LT, /* if-lt (0x34) */
+ DOP_IF_GE, /* if-ge (0x35) */
+ DOP_IF_GT, /* if-gt (0x36) */
+ DOP_IF_LE, /* if-le (0x37) */
+ DOP_IF_EQZ, /* if-eqz (0x38) */
+ DOP_IF_NEZ, /* if-nez (0x39) */
+ DOP_IF_LTZ, /* if-ltz (0x3a) */
+ DOP_IF_GEZ, /* if-gez (0x3b) */
+ DOP_IF_GTZ, /* if-gtz (0x3c) */
+ DOP_IF_LEZ, /* if-lez (0x3d) */
+
+
+
+ DOP_AGET, /* aget (0x44) */
+ DOP_AGET_WIDE, /* aget-wide (0x45) */
+ DOP_AGET_OBJECT, /* aget-object (0x46) */
+ DOP_AGET_BOOLEAN, /* aget-boolean (0x47) */
+ DOP_AGET_BYTE, /* aget-byte (0x48) */
+ DOP_AGET_CHAR, /* aget-char (0x49) */
+ DOP_AGET_SHORT, /* aget-short (0x4a) */
+ DOP_APUT, /* aput (0x4b) */
+ DOP_APUT_WIDE, /* aput-wide (0x4c) */
+ DOP_APUT_OBJECT, /* aput-object (0x4d) */
+ DOP_APUT_BOOLEAN, /* aput-boolean (0x4e) */
+ DOP_APUT_BYTE, /* aput-byte (0x4f) */
+ DOP_APUT_CHAR, /* aput-char (0x50) */
+ DOP_APUT_SHORT, /* aput-short (0x51) */
+ DOP_IGET, /* iget (0x52) */
+ DOP_IGET_WIDE, /* iget-wide (0x53) */
+ DOP_IGET_OBJECT, /* iget-object (0x54) */
+ DOP_IGET_BOOLEAN, /* iget-boolean (0x55) */
+ DOP_IGET_BYTE, /* iget-byte (0x56) */
+ DOP_IGET_CHAR, /* iget-char (0x57) */
+ DOP_IGET_SHORT, /* iget-short (0x58) */
+ DOP_IPUT, /* iput (0x59) */
+ DOP_IPUT_WIDE, /* iput-wide (0x5a) */
+ DOP_IPUT_OBJECT, /* iput-object (0x5b) */
+ DOP_IPUT_BOOLEAN, /* iput-boolean (0x5c) */
+ DOP_IPUT_BYTE, /* iput-byte (0x5d) */
+ DOP_IPUT_CHAR, /* iput-char (0x5e) */
+ DOP_IPUT_SHORT, /* iput-short (0x5f) */
+ DOP_SGET, /* sget (0x60) */
+ DOP_SGET_WIDE, /* sget-wide (0x61) */
+ DOP_SGET_OBJECT, /* sget-object (0x62) */
+ DOP_SGET_BOOLEAN, /* sget-boolean (0x63) */
+ DOP_SGET_BYTE, /* sget-byte (0x64) */
+ DOP_SGET_CHAR, /* sget-char (0x65) */
+ DOP_SGET_SHORT, /* sget-short (0x66) */
+ DOP_SPUT, /* sput (0x67) */
+ DOP_SPUT_WIDE, /* sput-wide (0x68) */
+ DOP_SPUT_OBJECT, /* sput-object (0x69) */
+ DOP_SPUT_BOOLEAN, /* sput-boolean (0x6a) */
+ DOP_SPUT_BYTE, /* sput-byte (0x6b) */
+ DOP_SPUT_CHAR, /* sput-char (0x6c) */
+ DOP_SPUT_SHORT, /* sput-short (0x6d) */
+ DOP_INVOKE_VIRTUAL, /* invoke-virtual (0x6e) */
+ DOP_INVOKE_SUPER, /* invoke-super (0x6f) */
+ DOP_INVOKE_DIRECT, /* invoke-direct (0x70) */
+ DOP_INVOKE_STATIC, /* invoke-static (0x71) */
+ DOP_INVOKE_INTERFACE, /* invoke-interface (0x72) */
+
+
+
+ DOP_TO_INT_LONG, /* int-to-long (0x81) */
+ DOP_TO_INT_FLOAT, /* int-to-float (0x82) */
+ DOP_TO_INT_DOUBLE, /* int-to-double (0x83) */
+ DOP_TO_LONG_INT, /* long-to-int (0x84) */
+ DOP_TO_LONG_FLOAT, /* long-to-float (0x85) */
+ DOP_TO_LONG_DOUBLE, /* long-to-double (0x86) */
+ DOP_TO_FLOAT_INT, /* float-to-int (0x87) */
+ DOP_TO_FLOAT_LONG, /* float-to-long (0x88) */
+ DOP_TO_FLOAT_DOUBLE, /* float-to-double (0x89) */
+ DOP_TO_DOUBLE_INT, /* double-to-int (0x8a) */
+ DOP_TO_DOUBLE_LONG, /* double-to-long (0x8b) */
+ DOP_TO_DOUBLE_FLOAT, /* double-to-float (0x8c) */
+ DOP_TO_INT_BYTE, /* int-to-byte (0x8d) */
+ DOP_TO_INT_CHAR, /* int-to-char (0x8e) */
+ DOP_TO_INT_SHORT, /* int-to-short (0x8f) */
+ DOP_ADD_INT, /* add-int (0x90) */
+ DOP_SUB_INT, /* sub-int (0x91) */
+ DOP_MUL_INT, /* mul-int (0x92) */
+ DOP_DIV_INT, /* div-int (0x93) */
+ DOP_REM_INT, /* rem-int (0x94) */
+ DOP_AND_INT, /* and-int (0x95) */
+ DOP_OR_INT, /* or-int (0x96) */
+ DOP_XOR_INT, /* xor-int (0x97) */
+
+ DOP_ADD_INT_2ADDR, /* add-int/2addr (0xb0) */
+
+ DOP_MUL_INT_2ADDR, /* mul-int/2addr (0xb2) */
+ DOP_DIV_INT_2ADDR, /* div-int/2addr (0xb3) */
+ DOP_REM_INT_2ADDR, /* rem-int/2addr (0xb4) */
+ DOP_AND_INT_2ADDR, /* and-int/2addr (0xb5) */
+ DOP_OR_INT_2ADDR, /* or-int/2addr (0xb6) */
+ DOP_XOR_INT_2ADDR, /* xor-int/2addr (0xb7) */
+
+ DOP_MUL_DOUBLE_2ADDR, /* mul-double/2addr (0xcd) */
+
+ DOP_ADD_INT_LIT16, /* add-int/lit16 (0xd0) */
+ DOP_RSUB_INT, /* rsub-int (0xd1) */
+ DOP_MUL_INT_LIT16, /* mul-int/lit16 (0xd2) */
+ DOP_DIV_INT_LIT16, /* div-int/lit16 (0xd3) */
+ DOP_REM_INT_LIT16, /* rem-int/lit16 (0xd4) */
+ DOP_AND_INT_LIT16, /* and-int/lit16 (0xd5) */
+ DOP_OR_INT_LIT16, /* or-int/lit16 (0xd6) */
+ DOP_XOR_INT_LIT16, /* xor-int/lit16 (0xd7) */
+ DOP_ADD_INT_LIT8, /* add-int/lit8 (0xd8) */
+ DOP_RSUB_INT_LIT8, /* rsub-int/lit8 (0xd9) */
+ DOP_MUL_INT_LIT8, /* mul-int/lit8 (0xda) */
+ DOP_DIV_INT_LIT8, /* div-int/lit8 (0xdb) */
+ DOP_REM_INT_LIT8, /* rem-int/lit8 (0xdc) */
+ DOP_AND_INT_LIT8, /* and-int/lit8 (0xdd) */
+ DOP_OR_INT_LIT8, /* or-int/lit8 (0xde) */
+ DOP_XOR_INT_LIT8, /* xor-int/lit8 (0xdf) */
+
+ DOP_COUNT
+
+} DalvikOpcodes;
+
+
+/* Enumération de tous les pseudo-opcodes */
+typedef enum _DalvikPseudoOpcodes
+{
+ DPO_PACKED_SWITCH = 0x0100, /* Switch aux clefs compactes */
+ DPO_SPARSE_SWITCH = 0x0200, /* Switch aux clefs éclatées */
+ DPO_FILL_ARRAY_DATA = 0x0300 /* Contenu de tableau */
+
+} DalvikPseudoOpcodes;
+
+
+
+#endif /* _ARCH_DALVIK_INSTRUCTION_DEF_H */
diff --git a/src/arch/dalvik/instruction-int.h b/src/arch/dalvik/instruction-int.h
new file mode 100644
index 0000000..9166c0c
--- /dev/null
+++ b/src/arch/dalvik/instruction-int.h
@@ -0,0 +1,52 @@
+
+/* OpenIDA - Outil d'analyse de fichiers binaires
+ * instruction-int.h - prototypes pour la définition générique interne des instructions Dalvik
+ *
+ * Copyright (C) 2011 Cyrille Bagard
+ *
+ * This file is part of OpenIDA.
+ *
+ * OpenIDA is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * OpenIDA is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Foobar. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+
+#ifndef _ARCH_DALVIK_INSTRUCTION_INT_H
+#define _ARCH_DALVIK_INSTRUCTION_INT_H
+
+
+#include "instruction-def.h"
+#include "../instruction-int.h"
+
+
+
+/* Définition générique d'une instruction d'architecture Dalvik (instance) */
+struct _GDalvikInstruction
+{
+ GArchInstruction parent; /* A laisser en premier */
+
+ DalvikOpcodes type; /* Position dans la liste */
+ DalvikPseudoOpcodes ptype; /* Position dans la liste #2 */
+
+};
+
+/* Définition générique d'une instruction d'architecture Dalvik (classe) */
+struct _GDalvikInstructionClass
+{
+ GArchInstructionClass parent; /* A laisser en premier */
+
+};
+
+
+
+#endif /* _ARCH_DALVIK_INSTRUCTION_INT_H */
diff --git a/src/arch/dalvik/instruction.c b/src/arch/dalvik/instruction.c
index 4595193..0d68a83 100644
--- a/src/arch/dalvik/instruction.c
+++ b/src/arch/dalvik/instruction.c
@@ -24,28 +24,12 @@
#include "instruction.h"
+#include "instruction-int.h"
#include "translate.h"
#include "../instruction-int.h"
-/* Définition générique d'une instruction d'architecture Dalvik (instance) */
-struct _GDalvikInstruction
-{
- GArchInstruction parent; /* A laisser en premier */
-
- DalvikOpcodes type; /* Position dans la liste */
-
-};
-
-/* Définition générique d'une instruction d'architecture Dalvik (classe) */
-struct _GDalvikInstructionClass
-{
- GArchInstructionClass parent; /* A laisser en premier */
-
-};
-
-
/* Initialise la classe des instructions pour Dalvik. */
static void g_dalvik_instruction_class_init(GDalvikInstructionClass *);
diff --git a/src/arch/dalvik/instruction.h b/src/arch/dalvik/instruction.h
index c359c66..0caee00 100644
--- a/src/arch/dalvik/instruction.h
+++ b/src/arch/dalvik/instruction.h
@@ -25,178 +25,11 @@
#define _ARCH_DALVIK_INSTRUCTION_H
+#include "instruction-def.h"
#include "../instruction.h"
-/* Enumération de tous les opcodes */
-typedef enum _DalvikOpcodes
-{
- DOP_NOP, /* nop (0x00) */
- DOP_MOVE, /* move (0x01) */
- DOP_MOVE_FROM_16, /* move/from16 (0x02) */
-
- DOP_MOVE_OBJECT, /* move-object (0x07) */
-
- DOP_MOVE_RESULT, /* move-result (0x0a) */
- DOP_MOVE_RESULT_WIDE, /* move-result-wide (0x0b) */
- DOP_MOVE_RESULT_OBJECT, /* move-result-object (0x0c) */
- DOP_MOVE_EXCEPTION, /* move-exception (0x0d) */
- DOP_RETURN_VOID, /* return-void (0x0e) */
- DOP_RETURN, /* return (0x0f) */
- DOP_RETURN_WIDE, /* return-wide (0x10) */
- DOP_RETURN_OBJECT, /* return-object (0x11) */
- DOP_CONST_4, /* const/4 (0x12) */
- DOP_CONST_16, /* const/16 (0x13) */
- DOP_CONST, /* const (0x14) */
- DOP_CONST_HIGH16, /* const/high16 (0x15) */
- DOP_CONST_WIDE_16, /* const-wide/16 (0x16) */
-
- DOP_CONST_WIDE, /* const-wide (0x18) */
-
- DOP_CONST_STRING, /* const-string (0x1a) */
-
-
- DOP_CHECK_CAST, /* check-cast (0x1f) */
-
- DOP_ARRAY_LENGTH, /* array-length (0x21) */
- DOP_NEW_INSTANCE, /* new-instance (0x22) */
- DOP_NEW_ARRAY, /* new-array (0x23) */
-
- DOP_FILL_ARRAY_DATA, /* fill-array-data (0x26) */
-
- DOP_GOTO, /* goto (0x28) */
- DOP_GOTO_16, /* goto/16 (0x29) */
- DOP_GOTO_32, /* goto/32 (0x2a) */
-
-
- DOP_CMPL_FLOAT, /* cmp-long (0x2d) */
- DOP_CMPG_FLOAT, /* cmpg-float (0x2e) */
- DOP_CMPL_DOUBLE, /* cmpl-double (0x2f) */
- DOP_CMPG_DOUBLE, /* cmpg-double (0x30) */
- DOP_CMP_LONG, /* cmp-long (0x31) */
- DOP_IF_EQ, /* if-eq (0x32) */
- DOP_IF_NE, /* if-ne (0x33) */
- DOP_IF_LT, /* if-lt (0x34) */
- DOP_IF_GE, /* if-ge (0x35) */
- DOP_IF_GT, /* if-gt (0x36) */
- DOP_IF_LE, /* if-le (0x37) */
- DOP_IF_EQZ, /* if-eqz (0x38) */
- DOP_IF_NEZ, /* if-nez (0x39) */
- DOP_IF_LTZ, /* if-ltz (0x3a) */
- DOP_IF_GEZ, /* if-gez (0x3b) */
- DOP_IF_GTZ, /* if-gtz (0x3c) */
- DOP_IF_LEZ, /* if-lez (0x3d) */
-
-
-
- DOP_AGET, /* aget (0x44) */
- DOP_AGET_WIDE, /* aget-wide (0x45) */
- DOP_AGET_OBJECT, /* aget-object (0x46) */
- DOP_AGET_BOOLEAN, /* aget-boolean (0x47) */
- DOP_AGET_BYTE, /* aget-byte (0x48) */
- DOP_AGET_CHAR, /* aget-char (0x49) */
- DOP_AGET_SHORT, /* aget-short (0x4a) */
- DOP_APUT, /* aput (0x4b) */
- DOP_APUT_WIDE, /* aput-wide (0x4c) */
- DOP_APUT_OBJECT, /* aput-object (0x4d) */
- DOP_APUT_BOOLEAN, /* aput-boolean (0x4e) */
- DOP_APUT_BYTE, /* aput-byte (0x4f) */
- DOP_APUT_CHAR, /* aput-char (0x50) */
- DOP_APUT_SHORT, /* aput-short (0x51) */
- DOP_IGET, /* iget (0x52) */
- DOP_IGET_WIDE, /* iget-wide (0x53) */
- DOP_IGET_OBJECT, /* iget-object (0x54) */
- DOP_IGET_BOOLEAN, /* iget-boolean (0x55) */
- DOP_IGET_BYTE, /* iget-byte (0x56) */
- DOP_IGET_CHAR, /* iget-char (0x57) */
- DOP_IGET_SHORT, /* iget-short (0x58) */
- DOP_IPUT, /* iput (0x59) */
- DOP_IPUT_WIDE, /* iput-wide (0x5a) */
- DOP_IPUT_OBJECT, /* iput-object (0x5b) */
- DOP_IPUT_BOOLEAN, /* iput-boolean (0x5c) */
- DOP_IPUT_BYTE, /* iput-byte (0x5d) */
- DOP_IPUT_CHAR, /* iput-char (0x5e) */
- DOP_IPUT_SHORT, /* iput-short (0x5f) */
- DOP_SGET, /* sget (0x60) */
- DOP_SGET_WIDE, /* sget-wide (0x61) */
- DOP_SGET_OBJECT, /* sget-object (0x62) */
- DOP_SGET_BOOLEAN, /* sget-boolean (0x63) */
- DOP_SGET_BYTE, /* sget-byte (0x64) */
- DOP_SGET_CHAR, /* sget-char (0x65) */
- DOP_SGET_SHORT, /* sget-short (0x66) */
- DOP_SPUT, /* sput (0x67) */
- DOP_SPUT_WIDE, /* sput-wide (0x68) */
- DOP_SPUT_OBJECT, /* sput-object (0x69) */
- DOP_SPUT_BOOLEAN, /* sput-boolean (0x6a) */
- DOP_SPUT_BYTE, /* sput-byte (0x6b) */
- DOP_SPUT_CHAR, /* sput-char (0x6c) */
- DOP_SPUT_SHORT, /* sput-short (0x6d) */
- DOP_INVOKE_VIRTUAL, /* invoke-virtual (0x6e) */
- DOP_INVOKE_SUPER, /* invoke-super (0x6f) */
- DOP_INVOKE_DIRECT, /* invoke-direct (0x70) */
- DOP_INVOKE_STATIC, /* invoke-static (0x71) */
- DOP_INVOKE_INTERFACE, /* invoke-interface (0x72) */
-
-
-
- DOP_TO_INT_LONG, /* int-to-long (0x81) */
- DOP_TO_INT_FLOAT, /* int-to-float (0x82) */
- DOP_TO_INT_DOUBLE, /* int-to-double (0x83) */
- DOP_TO_LONG_INT, /* long-to-int (0x84) */
- DOP_TO_LONG_FLOAT, /* long-to-float (0x85) */
- DOP_TO_LONG_DOUBLE, /* long-to-double (0x86) */
- DOP_TO_FLOAT_INT, /* float-to-int (0x87) */
- DOP_TO_FLOAT_LONG, /* float-to-long (0x88) */
- DOP_TO_FLOAT_DOUBLE, /* float-to-double (0x89) */
- DOP_TO_DOUBLE_INT, /* double-to-int (0x8a) */
- DOP_TO_DOUBLE_LONG, /* double-to-long (0x8b) */
- DOP_TO_DOUBLE_FLOAT, /* double-to-float (0x8c) */
- DOP_TO_INT_BYTE, /* int-to-byte (0x8d) */
- DOP_TO_INT_CHAR, /* int-to-char (0x8e) */
- DOP_TO_INT_SHORT, /* int-to-short (0x8f) */
- DOP_ADD_INT, /* add-int (0x90) */
- DOP_SUB_INT, /* sub-int (0x91) */
- DOP_MUL_INT, /* mul-int (0x92) */
- DOP_DIV_INT, /* div-int (0x93) */
- DOP_REM_INT, /* rem-int (0x94) */
- DOP_AND_INT, /* and-int (0x95) */
- DOP_OR_INT, /* or-int (0x96) */
- DOP_XOR_INT, /* xor-int (0x97) */
-
- DOP_ADD_INT_2ADDR, /* add-int/2addr (0xb0) */
-
- DOP_MUL_INT_2ADDR, /* mul-int/2addr (0xb2) */
- DOP_DIV_INT_2ADDR, /* div-int/2addr (0xb3) */
- DOP_REM_INT_2ADDR, /* rem-int/2addr (0xb4) */
- DOP_AND_INT_2ADDR, /* and-int/2addr (0xb5) */
- DOP_OR_INT_2ADDR, /* or-int/2addr (0xb6) */
- DOP_XOR_INT_2ADDR, /* xor-int/2addr (0xb7) */
-
- DOP_MUL_DOUBLE_2ADDR, /* mul-double/2addr (0xcd) */
-
- DOP_ADD_INT_LIT16, /* add-int/lit16 (0xd0) */
- DOP_RSUB_INT, /* rsub-int (0xd1) */
- DOP_MUL_INT_LIT16, /* mul-int/lit16 (0xd2) */
- DOP_DIV_INT_LIT16, /* div-int/lit16 (0xd3) */
- DOP_REM_INT_LIT16, /* rem-int/lit16 (0xd4) */
- DOP_AND_INT_LIT16, /* and-int/lit16 (0xd5) */
- DOP_OR_INT_LIT16, /* or-int/lit16 (0xd6) */
- DOP_XOR_INT_LIT16, /* xor-int/lit16 (0xd7) */
- DOP_ADD_INT_LIT8, /* add-int/lit8 (0xd8) */
- DOP_RSUB_INT_LIT8, /* rsub-int/lit8 (0xd9) */
- DOP_MUL_INT_LIT8, /* mul-int/lit8 (0xda) */
- DOP_DIV_INT_LIT8, /* div-int/lit8 (0xdb) */
- DOP_REM_INT_LIT8, /* rem-int/lit8 (0xdc) */
- DOP_AND_INT_LIT8, /* and-int/lit8 (0xdd) */
- DOP_OR_INT_LIT8, /* or-int/lit8 (0xde) */
- DOP_XOR_INT_LIT8, /* xor-int/lit8 (0xdf) */
-
- DOP_COUNT
-
-} DalvikOpcodes;
-
-
#define G_TYPE_DALVIK_INSTRUCTION g_dalvik_instruction_get_type()
#define G_DALVIK_INSTRUCTION(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), g_dalvik_instruction_get_type(), GDalvikInstruction))
#define G_IS_DALVIK_INSTRUCTION(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), g_dalvik_instruction_get_type()))
@@ -217,7 +50,7 @@ GType g_dalvik_instruction_get_type(void);
GArchInstruction *g_dalvik_instruction_new(DalvikOpcodes);
/* Indique l'opcode associé à une instruction Dalvik. */
-DalvikOpcodes g_dalvik_instruction_get_opcode(const GDalvikInstruction *);
+DalvikOpcodes g_dalvik_instruction_get_opcode(const struct _GDalvikInstruction *);
diff --git a/src/arch/dalvik/processor.c b/src/arch/dalvik/processor.c
index 2f56f87..7925c55 100644
--- a/src/arch/dalvik/processor.c
+++ b/src/arch/dalvik/processor.c
@@ -27,7 +27,8 @@
#include "context.h"
#include "instruction.h"
#include "opcodes.h"
-#include "specins.h"
+#include "pseudo/fill.h"
+#include "pseudo/switch.h"
#include "../processor-int.h"
@@ -57,6 +58,9 @@ static void g_dalvik_processor_init(GDalvikProcessor *);
/* Fournit un contexte pour l'exécution du processeur Dalvik. */
static GDalvikContext *g_dalvik_processor_get_context(const GDalvikProcessor *);
+/* Décode une pseudo-instruction dans un flux de données. */
+static GArchInstruction *g_dalvik_guess_pseudo_instruction(const GDalvikProcessor *, const bin_t *, off_t *, off_t, vmpa_t);
+
/* Décode une instruction dans un flux de données. */
static GArchInstruction *g_dalvik_processor_decode_instruction(const GDalvikProcessor *, GDalvikContext *, const bin_t *, off_t *, off_t, vmpa_t);
@@ -157,6 +161,58 @@ static GDalvikContext *g_dalvik_processor_get_context(const GDalvikProcessor *pr
/******************************************************************************
* *
* Paramètres : proc = architecture visée par la procédure. *
+* data = flux de données à analyser. *
+* pos = position courante dans ce flux. [OUT] *
+* len = taille totale des données à analyser. *
+* addr = adresse virtuelle de l'instruction. *
+* *
+* Description : Décode une pseudo-instruction dans un flux de données. *
+* *
+* Retour : Instruction mise en place ou NULL si aucune trouvée. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static GArchInstruction *g_dalvik_guess_pseudo_instruction(const GDalvikProcessor *proc, const bin_t *data, off_t *pos, off_t len, vmpa_t addr)
+{
+ GArchInstruction *result; /* Instruction à renvoyer */
+ off_t tmp; /* Position modifiable */
+ uint16_t ident; /* Valeur lue dans le code */
+
+ /* Vérification astucieuse et rapide...*/
+ if (data[*pos] != 0x00 /* DOP_NOP */) return NULL;
+
+ tmp = *pos;
+
+ if (!read_u16(&ident, data, &tmp, len, SRE_LITTLE))
+ return NULL;
+
+ switch (ident)
+ {
+ case DPO_PACKED_SWITCH:
+ case DPO_SPARSE_SWITCH:
+ result = g_dalvik_switch_instr_new(data, pos, len, addr, proc);
+ break;
+
+ case DPO_FILL_ARRAY_DATA:
+ result = g_dalvik_fill_instr_new(data, pos, len, addr, proc);
+ break;
+
+ default:
+ result = NULL;
+ break;
+
+ }
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : proc = architecture visée par la procédure. *
* ctx = contexte lié à l'exécution du processeur. *
* data = flux de données à analyser. *
* pos = position courante dans ce flux. [OUT] *
@@ -341,22 +397,21 @@ static GArchInstruction *g_dalvik_processor_decode_instruction(const GDalvikProc
};
- /* Continuité d'une zone spéciale... */
- if (g_dalvik_context_have_to_skip(ctx, addr))
- return SKIPPED_INSTR;
-
- /* Début d'une nouvelle zone spéciale... */
- if (g_dalvik_guess_special_instruction(ctx, data, *pos, len, addr))
- return SKIPPED_INSTR;
-
- /* Ou instruction classique */
+ /* Pseudo-instruction... */
+ result = g_dalvik_guess_pseudo_instruction(proc, data, pos, len, addr);
- id = dalvik_guess_next_instruction(data, *pos, len);
+ /* ... ou instruction classique */
+ if (result == NULL)
+ {
+ id = dalvik_guess_next_instruction(data, *pos, len);
- if (id != DOP_COUNT) (*pos)++;
+ if (id != DOP_COUNT)
+ {
+ (*pos)++;
+ result = decodings[id](data, pos, len, addr, proc);
+ }
- if (id == DOP_COUNT) result = NULL;
- else result = decodings[id](data, pos, len, addr, proc);
+ }
return result;
diff --git a/src/arch/dalvik/pseudo/Makefile.am b/src/arch/dalvik/pseudo/Makefile.am
new file mode 100644
index 0000000..05e361f
--- /dev/null
+++ b/src/arch/dalvik/pseudo/Makefile.am
@@ -0,0 +1,17 @@
+
+noinst_LTLIBRARIES = libarchdalvikpseudo.la
+
+libarchdalvikpseudo_la_SOURCES = \
+ fill.h fill.c \
+ switch.h switch.c
+
+libarchdalvikpseudo_la_LIBADD =
+
+libarchdalvikpseudo_la_CFLAGS = $(AM_CFLAGS)
+
+
+INCLUDES = $(LIBGTK_CFLAGS) $(LIBXML_CFLAGS)
+
+AM_CPPFLAGS =
+
+AM_CFLAGS = $(DEBUG_CFLAGS) $(WARNING_FLAGS) $(COMPLIANCE_FLAGS)
diff --git a/src/arch/dalvik/pseudo/fill.c b/src/arch/dalvik/pseudo/fill.c
new file mode 100644
index 0000000..9573000
--- /dev/null
+++ b/src/arch/dalvik/pseudo/fill.c
@@ -0,0 +1,214 @@
+
+/* OpenIDA - Outil d'analyse de fichiers binaires
+ * fill.c - prise en charge de l'instruction spéciale fill-array-data
+ *
+ * Copyright (C) 2011 Cyrille Bagard
+ *
+ * This file is part of OpenIDA.
+ *
+ * OpenIDA is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * OpenIDA is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Foobar. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+
+#include "fill.h"
+
+
+#include <string.h>
+
+
+#include "../instruction-int.h"
+
+
+
+/* Définition générique d'une instruction d'architecture Dalvik (instance) */
+struct _GDalvikFillInstr
+{
+ GDalvikInstruction parent; /* A laisser en premier */
+
+ uint16_t array_width; /* Taille des éléments */
+ uint32_t array_size; /* Taille du tableau */
+
+};
+
+/* Définition générique d'une instruction d'architecture Dalvik (classe) */
+struct _GDalvikFillInstrClass
+{
+ GDalvikInstructionClass parent; /* A laisser en premier */
+
+};
+
+
+
+/* Initialise la classe générique des instructions. */
+static void g_dalvik_fill_instr_class_init(GDalvikFillInstrClass *);
+
+/* Initialise une instance d'opérande d'architecture. */
+static void g_dalvik_fill_instr_init(GDalvikFillInstr *);
+
+/* Ajoute à un tampon GLib le contenu de l'instance spécifiée. */
+static void g_dalvik_fill_instr_print(const GDalvikFillInstr *, GCodeBuffer *, MemoryDataSize, const bin_t *, AsmSyntax);
+
+
+
+/* Indique le type défini pour une pseudo-instruction Dalvik de remplissage. */
+G_DEFINE_TYPE(GDalvikFillInstr, g_dalvik_fill_instr, G_TYPE_DALVIK_INSTRUCTION);
+
+
+/******************************************************************************
+* *
+* Paramètres : klass = classe à initialiser. *
+* *
+* Description : Initialise la classe générique des instructions. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void g_dalvik_fill_instr_class_init(GDalvikFillInstrClass *klass)
+{
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : instr = instance à initialiser. *
+* *
+* Description : Initialise une instance d'instruction d'architecture. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void g_dalvik_fill_instr_init(GDalvikFillInstr *instr)
+{
+ GArchInstruction *parent; /* Instance parente */
+
+ parent = G_ARCH_INSTRUCTION(instr);
+
+ parent->print = (print_instruction_fc)g_dalvik_fill_instr_print;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : data = flux de données à analyser. *
+* pos = position courante dans ce flux. [OUT] *
+* len = taille totale des données à analyser. *
+* addr = adresse virtuelle de l'instruction. *
+* proc = architecture ciblée par le désassemblage. *
+* *
+* Description : Crée une pesudo-instruction Dalvik de remplissage. *
+* *
+* Retour : Instruction mise en place. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+GArchInstruction *g_dalvik_fill_instr_new(const bin_t *data, off_t *pos, off_t len, vmpa_t addr, const GDalvikProcessor *proc)
+{
+ GDalvikFillInstr *result; /* Structure à retourner */
+ uint16_t ident; /* Valeur lue dans le code */
+
+ result = g_object_new(G_TYPE_DALVIK_FILL_INSTR, NULL);
+
+ if (!read_u16(&ident, data, pos, len, SRE_LITTLE))
+ goto gdfin_bad;
+
+ G_DALVIK_INSTRUCTION(result)->ptype = DPO_FILL_ARRAY_DATA;
+
+ if (!read_u16(&result->array_width, data, pos, len, SRE_LITTLE))
+ goto gdfin_bad;
+ if (!read_u32(&result->array_size, data, pos, len, SRE_LITTLE))
+ goto gdfin_bad;
+
+ *pos += result->array_width * result->array_size;
+
+ return G_ARCH_INSTRUCTION(result);
+
+ gdfin_bad:
+
+ g_object_unref(result);
+
+ return NULL;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : instr = instruction d'assemblage à représenter. *
+* buffer = espace où placer ledit contenu. *
+* syntax = type de représentation demandée. *
+* *
+* Description : Ajoute à un tampon GLib le contenu de l'instance spécifiée. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void g_dalvik_fill_instr_print(const GDalvikFillInstr *instr, GCodeBuffer *buffer, MemoryDataSize msize, const bin_t *content, AsmSyntax syntax)
+{
+ GArchInstruction *base; /* Version basique de l'objet */
+ GBufferLine *line; /* Ligne de destination */
+ char address[VMPA_MAX_SIZE]; /* Adresse au format texte */
+ size_t len; /* Taille de l'élément inséré */
+ char *bin_code; /* Tampon du code binaire */
+ off_t i; /* Boucle de parcours */
+ const char *key; /* Mot clef principal */
+ size_t klen; /* Taille de ce mot clef */
+
+ base = G_ARCH_INSTRUCTION(instr);
+
+ line = g_code_buffer_append_new_line(buffer);
+
+ /* Adresse virtuelle ou physique */
+
+ len = vmpa_to_string(base->address, msize, address);
+
+ g_buffer_line_insert_text(line, BLC_ADDRESS, address, len, RTT_RAW);
+
+ /* Code brut */
+
+ bin_code = (char *)calloc(3 * 3 + 3, sizeof(char));
+
+ for (i = 0; i < 3; i++)
+ {
+ if ((i + 1) < 3)
+ snprintf(&bin_code[i * (2 + 1)], 4, "%02hhx ", content[base->offset + i]);
+ else
+ snprintf(&bin_code[i * (2 + 1)], 6, "%02hhx...", content[base->offset + i]);
+ }
+
+ g_buffer_line_insert_text(line, BLC_BINARY,
+ bin_code, 3 * 3 + 2, RTT_RAW_CODE);
+
+ free(bin_code);
+
+ /* Instruction proprement dite */
+
+ key = "<fill-array>";
+ klen = strlen(key);
+
+ g_buffer_line_insert_text(line, BLC_ASSEMBLY_HEAD, key, klen, RTT_INSTRUCTION);
+
+}
diff --git a/src/arch/dalvik/pseudo/fill.h b/src/arch/dalvik/pseudo/fill.h
new file mode 100644
index 0000000..058e67b
--- /dev/null
+++ b/src/arch/dalvik/pseudo/fill.h
@@ -0,0 +1,57 @@
+
+/* OpenIDA - Outil d'analyse de fichiers binaires
+ * fill.h - prototypes pour la prise en charge de l'instruction spéciale fill-array-data
+ *
+ * Copyright (C) 2011 Cyrille Bagard
+ *
+ * This file is part of OpenIDA.
+ *
+ * OpenIDA is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * OpenIDA is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Foobar. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+
+#ifndef _ARCH_DALVIK_PSEUDO_FILL_H
+#define _ARCH_DALVIK_PSEUDO_FILL_H
+
+
+#include "../instruction.h"
+#include "../processor.h"
+
+
+#include <glib-object.h>
+
+
+
+#define G_TYPE_DALVIK_FILL_INSTR g_dalvik_fill_instr_get_type()
+#define G_DALVIK_FILL_INSTR(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), g_dalvik_fill_instr_get_type(), GDalvikFillInstr))
+#define G_IS_DALVIK_FILL_INSTR(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), g_dalvik_fill_instr_get_type()))
+#define G_DALVIK_FILL_INSTR_GET_IFACE(inst) (G_TYPE_INSTANCE_GET_INTERFACE((inst), g_dalvik_fill_instr_get_type(), GDalvikFillInstrIface))
+
+
+/* Définition générique d'une instruction d'architecture (instance) */
+typedef struct _GDalvikFillInstr GDalvikFillInstr;
+
+/* Définition générique d'une instruction d'architecture (classe) */
+typedef struct _GDalvikFillInstrClass GDalvikFillInstrClass;
+
+
+/* Indique le type défini pour une pseudo-instruction Dalvik de remplissage. */
+GType g_dalvik_fill_instr_get_type(void);
+
+/* Crée une pesudo-instruction Dalvik de remplissage. */
+GArchInstruction *g_dalvik_fill_instr_new(const bin_t *, off_t *, off_t, vmpa_t, const GDalvikProcessor *);
+
+
+
+#endif /* _ARCH_DALVIK_PSEUDO_FILL_H */
diff --git a/src/arch/dalvik/pseudo/switch.c b/src/arch/dalvik/pseudo/switch.c
new file mode 100644
index 0000000..30511ac
--- /dev/null
+++ b/src/arch/dalvik/pseudo/switch.c
@@ -0,0 +1,217 @@
+
+/* OpenIDA - Outil d'analyse de fichiers binaires
+ * switch.c - prise en charge des instructions spéciales (packed|sparse)switch
+ *
+ * Copyright (C) 2011 Cyrille Bagard
+ *
+ * This file is part of OpenIDA.
+ *
+ * OpenIDA is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * OpenIDA is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Foobar. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+
+#include "switch.h"
+
+
+#include <string.h>
+
+
+#include "../instruction-int.h"
+
+
+
+/* Définition générique d'une instruction d'architecture Dalvik (instance) */
+struct _GDalvikSwitchInstr
+{
+ GDalvikInstruction parent; /* A laisser en premier */
+
+ uint16_t switch_size; /* Taille du switch considéré */
+
+};
+
+/* Définition générique d'une instruction d'architecture Dalvik (classe) */
+struct _GDalvikSwitchInstrClass
+{
+ GDalvikInstructionClass parent; /* A laisser en premier */
+
+};
+
+
+
+/* Initialise la classe générique des instructions. */
+static void g_dalvik_switch_instr_class_init(GDalvikSwitchInstrClass *);
+
+/* Initialise une instance d'opérande d'architecture. */
+static void g_dalvik_switch_instr_init(GDalvikSwitchInstr *);
+
+/* Ajoute à un tampon GLib le contenu de l'instance spécifiée. */
+static void g_dalvik_switch_instr_print(const GDalvikSwitchInstr *, GCodeBuffer *, MemoryDataSize, const bin_t *, AsmSyntax);
+
+
+
+/* Indique le type défini pour une pseudo-instruction Dalvik de remplissage. */
+G_DEFINE_TYPE(GDalvikSwitchInstr, g_dalvik_switch_instr, G_TYPE_DALVIK_INSTRUCTION);
+
+
+/******************************************************************************
+* *
+* Paramètres : klass = classe à initialiser. *
+* *
+* Description : Initialise la classe générique des instructions. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void g_dalvik_switch_instr_class_init(GDalvikSwitchInstrClass *klass)
+{
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : instr = instance à initialiser. *
+* *
+* Description : Initialise une instance d'instruction d'architecture. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void g_dalvik_switch_instr_init(GDalvikSwitchInstr *instr)
+{
+ GArchInstruction *parent; /* Instance parente */
+
+ parent = G_ARCH_INSTRUCTION(instr);
+
+ parent->print = (print_instruction_fc)g_dalvik_switch_instr_print;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : data = flux de données à analyser. *
+* pos = position courante dans ce flux. [OUT] *
+* len = taille totale des données à analyser. *
+* addr = adresse virtuelle de l'instruction. *
+* proc = architecture ciblée par le désassemblage. *
+* *
+* Description : Crée une pesudo-instruction Dalvik de branchement. *
+* *
+* Retour : Instruction mise en place. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+GArchInstruction *g_dalvik_switch_instr_new(const bin_t *data, off_t *pos, off_t len, vmpa_t addr, const GDalvikProcessor *proc)
+{
+ GDalvikSwitchInstr *result; /* Structure à retourner */
+ uint16_t ident; /* Valeur lue dans le code */
+
+ result = g_object_new(G_TYPE_DALVIK_SWITCH_INSTR, NULL);
+
+ if (!read_u16(&ident, data, pos, len, SRE_LITTLE))
+ goto gdsin_bad;
+
+ if (ident != DPO_PACKED_SWITCH && ident != DPO_SPARSE_SWITCH)
+ goto gdsin_bad;
+
+ G_DALVIK_INSTRUCTION(result)->ptype = ident;
+
+ if (!read_u16(&result->switch_size, data, pos, len, SRE_LITTLE))
+ goto gdsin_bad;
+
+ if (ident != DPO_PACKED_SWITCH)
+ *pos += (1 + result->switch_size) * sizeof(uint32_t);
+ else
+ *pos += (2 * result->switch_size) * sizeof(uint32_t);
+
+ return G_ARCH_INSTRUCTION(result);
+
+ gdsin_bad:
+
+ g_object_unref(result);
+
+ return NULL;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : instr = instruction d'assemblage à représenter. *
+* buffer = espace où placer ledit contenu. *
+* syntax = type de représentation demandée. *
+* *
+* Description : Ajoute à un tampon GLib le contenu de l'instance spécifiée. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void g_dalvik_switch_instr_print(const GDalvikSwitchInstr *instr, GCodeBuffer *buffer, MemoryDataSize msize, const bin_t *content, AsmSyntax syntax)
+{
+ GArchInstruction *base; /* Version basique de l'objet */
+ GBufferLine *line; /* Ligne de destination */
+ char address[VMPA_MAX_SIZE]; /* Adresse au format texte */
+ size_t len; /* Taille de l'élément inséré */
+ char *bin_code; /* Tampon du code binaire */
+ off_t i; /* Boucle de parcours */
+ const char *key; /* Mot clef principal */
+ size_t klen; /* Taille de ce mot clef */
+
+ base = G_ARCH_INSTRUCTION(instr);
+
+ line = g_code_buffer_append_new_line(buffer);
+
+ /* Adresse virtuelle ou physique */
+
+ len = vmpa_to_string(base->address, msize, address);
+
+ g_buffer_line_insert_text(line, BLC_ADDRESS, address, len, RTT_RAW);
+
+ /* Code brut */
+
+ bin_code = (char *)calloc(3 * 3 + 3, sizeof(char));
+
+ for (i = 0; i < 3; i++)
+ {
+ if ((i + 1) < 3)
+ snprintf(&bin_code[i * (2 + 1)], 4, "%02hhx ", content[base->offset + i]);
+ else
+ snprintf(&bin_code[i * (2 + 1)], 6, "%02hhx...", content[base->offset + i]);
+ }
+
+ g_buffer_line_insert_text(line, BLC_BINARY,
+ bin_code, 3 * 3 + 2, RTT_RAW_CODE);
+
+ free(bin_code);
+
+ /* Instruction proprement dite */
+
+ key = "<fill-array>";
+ klen = strlen(key);
+
+ g_buffer_line_insert_text(line, BLC_ASSEMBLY_HEAD, key, klen, RTT_INSTRUCTION);
+
+}
diff --git a/src/arch/dalvik/pseudo/switch.h b/src/arch/dalvik/pseudo/switch.h
new file mode 100644
index 0000000..602af48
--- /dev/null
+++ b/src/arch/dalvik/pseudo/switch.h
@@ -0,0 +1,57 @@
+
+/* OpenIDA - Outil d'analyse de fichiers binaires
+ * switch.h - prototypes pour la prise en charge des instructions spéciales (packed|sparse)switch
+ *
+ * Copyright (C) 2011 Cyrille Bagard
+ *
+ * This file is part of OpenIDA.
+ *
+ * OpenIDA is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * OpenIDA is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Foobar. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+
+#ifndef _ARCH_DALVIK_PSEUDO_SWITCH_H
+#define _ARCH_DALVIK_PSEUDO_SWITCH_H
+
+
+#include "../instruction.h"
+#include "../processor.h"
+
+
+#include <glib-object.h>
+
+
+
+#define G_TYPE_DALVIK_SWITCH_INSTR g_dalvik_switch_instr_get_type()
+#define G_DALVIK_SWITCH_INSTR(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), g_dalvik_switch_instr_get_type(), GDalvikSwitchInstr))
+#define G_IS_DALVIK_SWITCH_INSTR(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), g_dalvik_switch_instr_get_type()))
+#define G_DALVIK_SWITCH_INSTR_GET_IFACE(inst) (G_TYPE_INSTANCE_GET_INTERFACE((inst), g_dalvik_switch_instr_get_type(), GDalvikSwitchInstrIface))
+
+
+/* Définition générique d'une instruction d'architecture (instance) */
+typedef struct _GDalvikSwitchInstr GDalvikSwitchInstr;
+
+/* Définition générique d'une instruction d'architecture (classe) */
+typedef struct _GDalvikSwitchInstrClass GDalvikSwitchInstrClass;
+
+
+/* Indique le type défini pour une pseudo-instruction Dalvik de remplissage. */
+GType g_dalvik_switch_instr_get_type(void);
+
+/* Crée une pesudo-instruction Dalvik de branchement. */
+GArchInstruction *g_dalvik_switch_instr_new(const bin_t *, off_t *, off_t, vmpa_t, const GDalvikProcessor *);
+
+
+
+#endif /* _ARCH_DALVIK_PSEUDO_SWITCH_H */
diff --git a/src/arch/dalvik/specins.c b/src/arch/dalvik/specins.c
deleted file mode 100644
index b6a7c4e..0000000
--- a/src/arch/dalvik/specins.c
+++ /dev/null
@@ -1,115 +0,0 @@
-
-/* OpenIDA - Outil d'analyse de fichiers binaires
- * specins.c - gestion des instructions spéciales de la VM Dalvik
- *
- * Copyright (C) 2011 Cyrille Bagard
- *
- * This file is part of OpenIDA.
- *
- * OpenIDA is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 3 of the License, or
- * (at your option) any later version.
- *
- * OpenIDA is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Foobar. If not, see <http://www.gnu.org/licenses/>.
- */
-
-
-#include "specins.h"
-
-
-#include "../../common/endianness.h"
-
-
-
-/******************************************************************************
-* *
-* Paramètres : ctx = contexte lié à l'exécution du processeur. *
-* data = flux de données à analyser. *
-* pos = position courante dans ce flux. *
-* len = taille totale des données à analyser. *
-* addr = adresse virtuelle de l'instruction. *
-* *
-* Description : Détermine si du code doit être écarté du traitement. *
-* *
-* Retour : true si une nouvelle zone de données est à écarter. *
-* *
-* Remarques : - *
-* *
-******************************************************************************/
-
-bool g_dalvik_guess_special_instruction(GDalvikContext *ctx, const bin_t *data, off_t pos, off_t len, vmpa_t addr)
-{
- bool result; /* Bilan à retourner */
- uint16_t ident; /* Valeur lue dans le code */
- vmpa_t start; /* Début d'une zone de données */
- vmpa_t end; /* Fin d'une zone de données */
- uint16_t switch_size; /* Taille du switch considéré */
- uint16_t array_width; /* Taille des éléments */
- uint32_t array_size; /* Taille du tableau */
-
- /* Vérification astucieuse et rapide...*/
- if (data[pos] != 0x00 /* DOP_NOP */) return false;
-
- if (!read_u16(&ident, data, &pos, len, SRE_LITTLE))
- return false;
-
- start = addr + sizeof(ident);
- end = start;
-
- switch (ident)
- {
- case DID_PACKED_SWITCH:
-
- if (!read_u16(&switch_size, data, &pos, len, SRE_LITTLE))
- return false;
-
- end += sizeof(switch_size) + (1 + switch_size) * sizeof(uint32_t);
-
- g_dalvik_context_skip_new_area(ctx, start, end);
- result = true;
-
- break;
-
- case DID_SPARSE_SWITCH:
-
- if (!read_u16(&switch_size, data, &pos, len, SRE_LITTLE))
- return false;
-
- end += sizeof(switch_size) + (2 * switch_size) * sizeof(uint32_t);
-
- g_dalvik_context_skip_new_area(ctx, start, end);
- result = true;
-
- break;
-
- case DID_FILL_ARRAY_DATA:
-
- if (!read_u16(&array_width, data, &pos, len, SRE_LITTLE))
- return false;
- if (!read_u32(&array_size, data, &pos, len, SRE_LITTLE))
- return false;
-
- end += sizeof(array_width) + sizeof(array_size)
- + array_width * array_size;
-
- g_dalvik_context_skip_new_area(ctx, start, end);
- result = true;
-
- break;
-
- default:
- result = false;
- break;
-
- }
-
- return result;
-
-}
diff --git a/src/arch/dalvik/specins.h b/src/arch/dalvik/specins.h
deleted file mode 100644
index 51cf6e9..0000000
--- a/src/arch/dalvik/specins.h
+++ /dev/null
@@ -1,51 +0,0 @@
-
-/* OpenIDA - Outil d'analyse de fichiers binaires
- * specins.h - prototypes pour la gestion des instructions spéciales de la VM Dalvik
- *
- * Copyright (C) 2011 Cyrille Bagard
- *
- * This file is part of OpenIDA.
- *
- * OpenIDA is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 3 of the License, or
- * (at your option) any later version.
- *
- * OpenIDA is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Foobar. If not, see <http://www.gnu.org/licenses/>.
- */
-
-
-#ifndef _ARCH_DALVIK_SPECINS_H
-#define _ARCH_DALVIK_SPECINS_H
-
-
-#include <stdbool.h>
-
-
-#include "../archbase.h"
-#include "context.h"
-
-
-
-/* Speinss spéciales */
-typedef enum _DalvikIdents
-{
- DID_PACKED_SWITCH = 0x0100, /* Switch aux clefs compactes */
- DID_SPARSE_SWITCH = 0x0200, /* Switch aux clefs éclatées */
- DID_FILL_ARRAY_DATA = 0x0300 /* Contenu de tableau */
-
-} DalvikIdents;
-
-
-/* Détermine si du code doit être écarté du traitement. */
-bool g_dalvik_guess_special_instruction(GDalvikContext *, const bin_t *, off_t, off_t, vmpa_t);
-
-
-
-#endif /* _ARCH_DALVIK_SPECINS_H */
diff --git a/src/arch/instruction-int.h b/src/arch/instruction-int.h
index 4eca0a5..4ffb5b0 100644
--- a/src/arch/instruction-int.h
+++ b/src/arch/instruction-int.h
@@ -33,6 +33,9 @@
+/* Ajoute à un tampon GLib le contenu de l'instance spécifiée. */
+typedef void (* print_instruction_fc) (const GArchInstruction *, GCodeBuffer *, MemoryDataSize, const bin_t *, AsmSyntax);
+
/* Traduit une instruction en version humainement lisible. */
typedef const char * (* get_instruction_text_fc) (const GArchInstruction *, const GExeFormat *, AsmSyntax);
@@ -64,6 +67,7 @@ struct _GArchInstruction
InstructionLinkType *links_type; /* Type des liens de dest. */
size_t to_count; /* Nombre de ces destinations */
+ print_instruction_fc print; /* Imprime l'ensemble */
get_instruction_text_fc get_text; /* Texte humain équivalent */
get_instruction_link_fc get_link; /* Référence à une instruction */
is_instruction_return_fc is_return; /* Retour de fonction ou pas ? */
diff --git a/src/arch/instruction.c b/src/arch/instruction.c
index 677a1a3..047ed86 100644
--- a/src/arch/instruction.c
+++ b/src/arch/instruction.c
@@ -46,6 +46,14 @@ static void g_arch_instruction_to_buffer(const GArchInstruction *, GBufferLine *
+/* --------------------- CONVERSIONS DU FORMAT DES INSTRUCTIONS --------------------- */
+
+
+/* Ajoute à un tampon GLib le contenu de l'instance spécifiée. */
+static void _g_arch_instruction_print(const GArchInstruction *, GCodeBuffer *, MemoryDataSize, const bin_t *, AsmSyntax);
+
+
+
/* Indique le type défini pour une instruction d'architecture. */
G_DEFINE_TYPE(GArchInstruction, g_arch_instruction, G_TYPE_CONTENT_EXPORTER);
@@ -590,7 +598,7 @@ size_t g_arch_instruction_get_destinations(const GArchInstruction *instr, GArchI
* *
******************************************************************************/
-void g_arch_instruction_print(const GArchInstruction *instr, GCodeBuffer *buffer, MemoryDataSize msize, const bin_t *content, AsmSyntax syntax)
+static void _g_arch_instruction_print(const GArchInstruction *instr, GCodeBuffer *buffer, MemoryDataSize msize, const bin_t *content, AsmSyntax syntax)
{
GBufferLine *line; /* Ligne de destination */
char address[VMPA_MAX_SIZE]; /* Adresse au format texte */
@@ -653,6 +661,31 @@ void g_arch_instruction_print(const GArchInstruction *instr, GCodeBuffer *buffer
/******************************************************************************
* *
+* Paramètres : instr = instruction d'assemblage à représenter. *
+* buffer = espace où placer ledit contenu. *
+* syntax = type de représentation demandée. *
+* *
+* Description : Ajoute à un tampon GLib le contenu de l'instance spécifiée. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+void g_arch_instruction_print(const GArchInstruction *instr, GCodeBuffer *buffer, MemoryDataSize msize, const bin_t *content, AsmSyntax syntax)
+{
+ if (instr->print != NULL)
+ instr->print(instr, buffer, msize, content, syntax);
+
+ else
+ _g_arch_instruction_print(instr, buffer, msize, content, syntax);
+
+}
+
+
+/******************************************************************************
+* *
* Paramètres : instr = instruction d'origine à convertir. *
* ctx = contexte de la phase de décompilation. *
* *