summaryrefslogtreecommitdiff
path: root/src/analysis/decomp/il.c
diff options
context:
space:
mode:
authorCyrille Bagard <nocbos@gmail.com>2013-01-17 22:21:03 (GMT)
committerCyrille Bagard <nocbos@gmail.com>2013-01-17 22:21:03 (GMT)
commita9bbd894bd25f7c2bb72fb7d4064b19377d90c6d (patch)
treed430c135864caa960c71ed86c5713507de66f708 /src/analysis/decomp/il.c
parent2ab78407e9f73b6508afc281400a7c3fc018217f (diff)
Forked the decompilation context when needed.
git-svn-id: svn://svn.gna.org/svn/chrysalide/trunk@325 abbe820e-26c8-41b2-8c08-b7b2b41f8b0a
Diffstat (limited to 'src/analysis/decomp/il.c')
-rw-r--r--src/analysis/decomp/il.c79
1 files changed, 51 insertions, 28 deletions
diff --git a/src/analysis/decomp/il.c b/src/analysis/decomp/il.c
index 60e86b6..642c921 100644
--- a/src/analysis/decomp/il.c
+++ b/src/analysis/decomp/il.c
@@ -40,7 +40,8 @@ static bool track_used_registers(GFlowBlock *, BlockFollowPosition, GRAccessList
/* Etablit le relévé des allocations de registre. */
static void setup_awaited_regs_allocation(const GInstrBlock *, vmpa_t);
-
+/* Met en place un contexte adapté aux sous-blocs d'un bloc. */
+static GDecContext *create_new_context_for_sub_block(GDecContext *, GInstrBlock *);
@@ -185,12 +186,9 @@ static bool track_used_registers(GFlowBlock *block, BlockFollowPosition pos, GRA
static void setup_awaited_regs_allocation(const GInstrBlock *list, vmpa_t start)
{
- GDecContext *result; /* Contexte pour la décompil. */
GInstrBlock *first; /* Bloc de départ du flot */
GRAccessList *needed; /* Registres inter-blocs */
- result = NULL;
-
first = g_instr_block_find_by_addr(list, start, true);
needed = g_raccess_list_new();
@@ -200,11 +198,31 @@ static void setup_awaited_regs_allocation(const GInstrBlock *list, vmpa_t start)
g_object_unref(G_OBJECT(needed));
+}
- return result;
-}
+/******************************************************************************
+* *
+* Paramètres : ctx = contexte de décompilation courant. *
+* block = block regroupant les branches de division. *
+* *
+* Description : Met en place un contexte adapté aux sous-blocs d'un bloc. *
+* *
+* Retour : Nouveau contexte près à emploi. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static GDecContext *create_new_context_for_sub_block(GDecContext *ctx, GInstrBlock *block)
+{
+
+ return g_dec_context_dup(ctx);
+
+
+
+}
/* ---------------------------------------------------------------------------------- */
@@ -272,11 +290,13 @@ static GDecInstruction *decompiled_instructions_block(GFlowBlock *block, GDecCon
vmpa_t max; /* Adresse de fin du bloc */
GArchInstruction *iter; /* Boucle de parcours */
GDecInstruction *decomp; /* Dernier résultat de décomp. */
+ GInstrBlock *sub_parent; /* Groupe des sous-branches */
+ GDecContext *sub_ctx; /* Sous-contexte pour branche */
GDecInstruction *true_dinstr; /* Décompilation 'cond vraie' */
GDecInstruction *false_dinstr; /* Décompilation 'cond fausse' */
GArchInstruction *next; /* Instruction de branchement */
vmpa_t next_addr; /* Adresse de cette instruct° */
- GInstrBlock *next_parent; /* Bloc basique correspondant */
+ //GInstrBlock *next_parent; /* Bloc basique correspondant */
GInstrBlock *next_block; /* Sous-bloc basique direct */
instrs = g_flow_block_get_all_instructions_list(block);
@@ -297,43 +317,47 @@ static GDecInstruction *decompiled_instructions_block(GFlowBlock *block, GDecCon
/* Post-traitement selon les types de lien */
- res = g_dec_context_get_decomp_instrs(ctx);
+ //res = g_dec_context_get_decomp_instrs(ctx);
/* if ... then ... else ... */
if (G_IS_ITE_INSTRUCTION(decomp))
{
- next = g_arch_instruction_get_given_destination(last, ILT_JUMP_IF_TRUE);
-
- printf("@ 0x%08llx : true : %p\n", max, next);
+ sub_parent = g_instr_block_get_links_block(G_INSTR_BLOCK(block));
true_dinstr = NULL;
+ next = g_arch_instruction_get_given_destination(last, ILT_JUMP_IF_TRUE);
if (next != NULL)
{
g_arch_instruction_get_location(next, NULL, NULL, &next_addr);
- next_parent = g_instr_block_get_links_block(G_INSTR_BLOCK(block));
- next_block = g_instr_block_find_by_addr(next_parent, next_addr, false);
+ next_block = g_instr_block_find_by_addr(sub_parent, next_addr, false);
if (next_block != NULL)
- true_dinstr = decompiled_basic_block(next_block, ctx);
+ {
+ sub_ctx = create_new_context_for_sub_block(ctx, sub_parent);
+ true_dinstr = decompiled_basic_block(next_block, sub_ctx);
+ /* TODO : merge awaited */
+ g_object_unref(G_OBJECT(sub_ctx));
+ }
}
- next = g_arch_instruction_get_given_destination(last, ILT_JUMP_IF_FALSE);
-
- printf("@ 0x%08llx : false : %p\n", max, next);
-
false_dinstr = NULL;
+ next = g_arch_instruction_get_given_destination(last, ILT_JUMP_IF_FALSE);
if (next != NULL)
{
g_arch_instruction_get_location(next, NULL, NULL, &next_addr);
- next_parent = g_instr_block_get_links_block(G_INSTR_BLOCK(block));
- next_block = g_instr_block_find_by_addr(next_parent, next_addr, false);
+ next_block = g_instr_block_find_by_addr(sub_parent, next_addr, false);
if (next_block != NULL)
- false_dinstr = decompiled_basic_block(next_block, ctx);
+ {
+ sub_ctx = create_new_context_for_sub_block(ctx, sub_parent);
+ false_dinstr = decompiled_basic_block(next_block, sub_ctx);
+ /* TODO : merge awaited */
+ g_object_unref(G_OBJECT(sub_ctx));
+ }
}
@@ -350,9 +374,9 @@ static GDecInstruction *decompiled_instructions_block(GFlowBlock *block, GDecCon
/* Renvoi des instructions mises en place */
- return res;
+ //return res;
- //return g_dec_context_get_decomp_instrs(ctx);
+ return g_dec_context_get_decomp_instrs(ctx);
}
@@ -393,13 +417,15 @@ static GDecInstruction *decompiled_instructions_blocks(GVirtualBlock *block, GDe
if (!G_IS_FLOW_BLOCK(sub_block)) continue;
/* FIXME */
- g_dec_context_set_decomp_instrs(ctx, NULL);
+ //g_dec_context_set_decomp_instrs(ctx, NULL);
dinstrs = decompiled_instructions_block(G_FLOW_BLOCK(sub_block), ctx);
- result = merge_decompiled_instructions(result, dinstrs);
+ //result = merge_decompiled_instructions(result, dinstrs);
}
+ result = merge_decompiled_instructions(result, dinstrs);
+
return result;
}
@@ -422,9 +448,6 @@ static GDecInstruction *decompiled_basic_block(GInstrBlock *block, GDecContext *
{
GDecInstruction *result; /* Instructions à retourner */
- /* FIXME */
- g_dec_context_set_decomp_instrs(ctx, NULL);
-
if (G_IS_VIRTUAL_BLOCK(block))
result = decompiled_instructions_blocks(G_VIRTUAL_BLOCK(block), ctx);