summaryrefslogtreecommitdiff
path: root/src/arch/dalvik/context.c
diff options
context:
space:
mode:
authorCyrille Bagard <nocbos@gmail.com>2013-01-20 13:10:06 (GMT)
committerCyrille Bagard <nocbos@gmail.com>2013-01-20 13:10:06 (GMT)
commit37fd2f1329c56078bc8a8b2fc955aa001c109c01 (patch)
tree71bcce9a3eaf6b7569d1f1d3e057752ae517ebde /src/arch/dalvik/context.c
parenta9bbd894bd25f7c2bb72fb7d4064b19377d90c6d (diff)
Took care of shared allocations between blocks when converting registers.
git-svn-id: svn://svn.gna.org/svn/chrysalide/trunk@326 abbe820e-26c8-41b2-8c08-b7b2b41f8b0a
Diffstat (limited to 'src/arch/dalvik/context.c')
-rw-r--r--src/arch/dalvik/context.c73
1 files changed, 67 insertions, 6 deletions
diff --git a/src/arch/dalvik/context.c b/src/arch/dalvik/context.c
index e80ead3..7918467 100644
--- a/src/arch/dalvik/context.c
+++ b/src/arch/dalvik/context.c
@@ -123,8 +123,11 @@ static void g_dalvik_dcontext_finalize(GDalvikDContext *);
/* Duplique un contexte de compilation. */
static GDalvikDContext *g_dalvik_dcontext_dup(GDalvikDContext *);
+/* Propage un registre alloué et attendu par la suite. */
+static void g_dalvik_context_spread_allocated_shared_reg(GDalvikDContext *, GDalvikRegister *, GDecInstruction *);
+
/* Convertit un registre machine en un pseudo-registre. */
-static GDecInstruction *g_dalvik_dcontext_convert_register(GDalvikDContext *, GDalvikRegisterOperand *, bool);
+static GDecInstruction *g_dalvik_dcontext_convert_register(GDalvikDContext *, GDalvikRegisterOperand *, bool, vmpa_t);
@@ -335,6 +338,7 @@ static void g_dalvik_dcontext_init(GDalvikDContext *ctx)
parent = G_DEC_CONTEXT(ctx);
parent->dup = (dup_dec_context_fc)g_dalvik_dcontext_dup;
+ parent->spread = (spread_reg_fc)g_dalvik_context_spread_allocated_shared_reg;
parent->convert_reg = (convert_register_fc)g_dalvik_dcontext_convert_register;
}
@@ -443,9 +447,46 @@ static GDalvikDContext *g_dalvik_dcontext_dup(GDalvikDContext *orig)
/******************************************************************************
* *
+* Paramètres : parent = instance à éventuellement compléter. *
+* child = instance à venir consulter. *
+* *
+* Description : Propage un registre alloué et attendu par la suite. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void g_dalvik_context_spread_allocated_shared_reg(GDalvikDContext *ctx, GDalvikRegister *reg, GDecInstruction *dinstr)
+{
+ GDexFormat *format; /* Recherche de méthode */
+ GBinRoutine *routine; /* Objet des recherches */
+ GDexMethod *method; /* Méthode décompilée */
+ uint16_t index; /* Identifiant du registre */
+ DexVariableIndex info; /* Nature du registre */
+
+ format = G_DEX_FORMAT(G_DEC_CONTEXT(ctx)->format);
+ routine = G_DEC_CONTEXT(ctx)->routine;
+
+ method = g_dex_format_find_method_by_address(format, g_binary_routine_get_address(routine));
+
+ index = g_dalvik_register_get_index(reg);
+ info = g_dex_method_get_variable(method, index);
+
+ g_object_ref(G_OBJECT(dinstr));
+ g_hash_table_insert(ctx->locals, GUINT_TO_POINTER(DVI_INDEX(info)), dinstr);
+ ctx->locals_count++;
+
+}
+
+
+/******************************************************************************
+* *
* Paramètres : ctx = instance à consulter, voire mettre à jour. *
* operand = opérande représentant un registre quelconque. *
* assign = précise le sort prochain du registre. *
+* addr = adresse de l'instruction décompilée. *
* *
* Description : Convertit un registre machine en un pseudo-registre. *
* *
@@ -455,7 +496,7 @@ static GDalvikDContext *g_dalvik_dcontext_dup(GDalvikDContext *orig)
* *
******************************************************************************/
-static GDecInstruction *g_dalvik_dcontext_convert_register(GDalvikDContext *ctx, GDalvikRegisterOperand *operand, bool assign)
+static GDecInstruction *g_dalvik_dcontext_convert_register(GDalvikDContext *ctx, GDalvikRegisterOperand *operand, bool assign, vmpa_t addr)
{
GDecInstruction *result; /* Instance à retourner */
GDexFormat *format; /* Recherche de méthode */
@@ -522,17 +563,37 @@ static GDecInstruction *g_dalvik_dcontext_convert_register(GDalvikDContext *ctx,
{
found = g_hash_table_lookup(ctx->locals, GUINT_TO_POINTER(DVI_INDEX(info)));
- if (/*!assign && */found != NULL)
+ if (!assign && found != NULL)
{
g_object_ref(G_OBJECT(found));
result = G_DEC_INSTRUCTION(found);
}
else
{
- result = g_pseudo_register_new();
- g_pseudo_register_set_basename(G_PSEUDO_REGISTER(result), "var");
- g_pseudo_register_set_index(G_PSEUDO_REGISTER(result), ctx->locals_count);
+ /*
+ if (!assign)
+ {
+ printf("bug");
+ exit(0);
+ }
+ */
+
+ result = g_dec_context_get_awaited_alloc(G_DEC_CONTEXT(ctx), G_ARCH_REGISTER(reg), addr);
+
+ if (result == NULL)
+ {
+ result = g_pseudo_register_new();
+ g_pseudo_register_set_basename(G_PSEUDO_REGISTER(result), "var");
+ g_pseudo_register_set_index(G_PSEUDO_REGISTER(result), ctx->locals_count);
+
+ g_dec_context_notify_reg_alloc(G_DEC_CONTEXT(ctx), G_ARCH_REGISTER(reg),
+ result, addr);
+
+ }
+ else
+ g_object_ref(G_OBJECT(result));
+ g_object_ref(G_OBJECT(result));
g_hash_table_insert(ctx->locals, GUINT_TO_POINTER(DVI_INDEX(info)), result);
ctx->locals_count++;