diff options
author | Cyrille Bagard <nocbos@gmail.com> | 2010-11-12 22:13:21 (GMT) |
---|---|---|
committer | Cyrille Bagard <nocbos@gmail.com> | 2010-11-12 22:13:21 (GMT) |
commit | ae8cf6257c8d929de1b7ee86e29fcb45ab4af91c (patch) | |
tree | 59fa356b2f83020e23df4cf6975ca5d97567df4d /src/decomp | |
parent | abaf85fdc0edb2bfe67d07d52ae734d50c6fbf61 (diff) |
Changed the display of the pseudo registers by using an index.
git-svn-id: svn://svn.gna.org/svn/chrysalide/trunk@192 abbe820e-26c8-41b2-8c08-b7b2b41f8b0a
Diffstat (limited to 'src/decomp')
-rw-r--r-- | src/decomp/context.c | 55 | ||||
-rw-r--r-- | src/decomp/context.h | 5 | ||||
-rw-r--r-- | src/decomp/expr/pseudo.c | 30 | ||||
-rw-r--r-- | src/decomp/expr/pseudo.h | 3 |
4 files changed, 91 insertions, 2 deletions
diff --git a/src/decomp/context.c b/src/decomp/context.c index 7fe6937..6440c56 100644 --- a/src/decomp/context.c +++ b/src/decomp/context.c @@ -24,6 +24,14 @@ #include "context.h" +#include <malloc.h> + + +#include "expr/pseudo.h" +#include "../arch/operand.h" +#include "../glibext/gnhash.h" + + /* Définition d'une context décompilée (instance) */ struct _GDecContext @@ -32,6 +40,12 @@ struct _GDecContext vmpa_t max; /* Première adresse à écarter */ + GHashTable *machine; /* Correspondance reg./pseudo */ + GHashTable *ssa; /* Remplacement des pseudos */ + + GDecInstruction **pseudos; /* Liste des pseudos-registre */ + size_t count; /* Taille de cette liste */ + }; @@ -87,6 +101,8 @@ static void g_dec_context_class_init(GDecContextClass *klass) static void g_dec_context_init(GDecContext *ctx) { + ctx->machine = g_hash_table_new(g_constant_hash, (GEqualFunc)g_arch_operand_compare); + ctx->ssa = g_hash_table_new(NULL, NULL); } @@ -151,3 +167,42 @@ void g_dec_context_set_max_address(GDecContext *ctx, vmpa_t max) ctx->max = max; } + + +/****************************************************************************** +* * +* Paramètres : ctx = instance à consulter, voire mettre à jour. * +* operand = opérande représentant un registre quelconque. * +* * +* Description : Convertit un registre machine en un pseudo-registre. * +* * +* Retour : Pseudo-registre, existant ou non, prêt à emploi. * +* * +* Remarques : - * +* * +******************************************************************************/ + +GDecInstruction *g_dec_context_convert_register(GDecContext *ctx, gpointer operand) +{ + GDecInstruction *result; /* Instance à retourner */ + gpointer *found; /* Pseudo-registre trouvé */ + + found = g_hash_table_lookup(ctx->machine, operand); + + if (found != NULL) result = G_DEC_INSTRUCTION(found); + else + { + result = g_pseudo_register_new(); + g_pseudo_register_set_index(G_PSEUDO_REGISTER(result), ctx->count); + + g_hash_table_insert(ctx->machine, operand, result); + + ctx->pseudos = (GDecInstruction **)realloc(ctx->pseudos, + ++ctx->count * sizeof(GDecInstruction *)); + ctx->pseudos[ctx->count - 1] = result; + + } + + return result; + +} diff --git a/src/decomp/context.h b/src/decomp/context.h index 76105e6..926a372 100644 --- a/src/decomp/context.h +++ b/src/decomp/context.h @@ -28,7 +28,7 @@ #include <glib-object.h> -#include "expr/pseudo.h" +#include "instruction.h" #include "../arch/archbase.h" @@ -61,6 +61,9 @@ vmpa_t g_dec_context_get_max_address(const GDecContext *); /* Définit l'adresse où la décompilation n'est plus souhaitée. */ void g_dec_context_set_max_address(GDecContext *, vmpa_t); +/* Convertit un registre machine en un pseudo-registre. */ +GDecInstruction *g_dec_context_convert_register(GDecContext *, gpointer); + #endif /* _DECOMP_CONTEXT_H */ diff --git a/src/decomp/expr/pseudo.c b/src/decomp/expr/pseudo.c index 393f32c..abfcd4d 100644 --- a/src/decomp/expr/pseudo.c +++ b/src/decomp/expr/pseudo.c @@ -24,6 +24,10 @@ #include "pseudo.h" +#include <stdio.h> +#include <string.h> + + #include "../expression-int.h" @@ -33,6 +37,8 @@ struct _GPseudoRegister { GDecExpression parent; /* A laisser en premier */ + size_t index; /* Position dans l'ensemble */ + }; @@ -141,8 +147,30 @@ GDecInstruction *g_pseudo_register_new(void) static void g_pseudo_register_print(const GPseudoRegister *reg, GCodeBuffer *buffer, GBufferLine *line, GLangOutput *output) { + char label[32]; + + snprintf(label, 32, "var%d", reg->index); + + g_buffer_line_insert_text(line, BLC_ASSEMBLY, label, strlen(label), RTT_RAW); - g_buffer_line_insert_text(line, BLC_ASSEMBLY, "varX", 4, RTT_RAW); +} + + +/****************************************************************************** +* * +* Paramètres : reg = expression représentant un pseudo-registre à traiter.* +* index = indice à associer au pseudo-registre. * +* * +* Description : Définit un indice unique pour un pseudo-registre donné. * +* * +* Retour : - * +* * +* Remarques : - * +* * +******************************************************************************/ +void g_pseudo_register_set_index(GPseudoRegister *reg, size_t index) +{ + reg->index = index; } diff --git a/src/decomp/expr/pseudo.h b/src/decomp/expr/pseudo.h index 9734625..95612a9 100644 --- a/src/decomp/expr/pseudo.h +++ b/src/decomp/expr/pseudo.h @@ -54,6 +54,9 @@ GType g_pseudo_register_get_type(void); /* Assigne le contenu d'une expression dans une autre. */ GDecInstruction *g_pseudo_register_new(void); +/* Définit un indice unique pour un pseudo-registre donné. */ +void g_pseudo_register_set_index(GPseudoRegister *, size_t); + #endif /* _DECOMP_EXPR_PSEUDO_H */ |